diff options
author | Massimiliano Mantione <massi@mono-cvs.ximian.com> | 2009-05-15 18:16:37 +0400 |
---|---|---|
committer | Massimiliano Mantione <massi@mono-cvs.ximian.com> | 2009-05-15 18:16:37 +0400 |
commit | af1e5f95cccab9e880d32aeaa7e316f1195df580 (patch) | |
tree | 7a45d2f30a8925f358f86face8e8f907e26682d9 | |
parent | 81d9b184ebfa8fa677bd4b413ff751687c977e47 (diff) |
Made it possible for mono_arch_instrument_epilog to preserve argument registers.
svn path=/trunk/mono/; revision=134207
-rw-r--r-- | mono/mini/ChangeLog | 22 | ||||
-rw-r--r-- | mono/mini/mini-alpha.c | 3 | ||||
-rw-r--r-- | mono/mini/mini-amd64.c | 14 | ||||
-rw-r--r-- | mono/mini/mini-arm.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-hppa.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-ia64.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-mips.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-ppc.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-s390.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-s390x.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-sparc.c | 2 | ||||
-rw-r--r-- | mono/mini/mini-x86.c | 2 | ||||
-rw-r--r-- | mono/mini/mini.c | 5 | ||||
-rw-r--r-- | mono/mini/mini.h | 1 |
14 files changed, 50 insertions, 13 deletions
diff --git a/mono/mini/ChangeLog b/mono/mini/ChangeLog index 75913463341..68c942743d2 100644 --- a/mono/mini/ChangeLog +++ b/mono/mini/ChangeLog @@ -1,3 +1,25 @@ +2009-05-15 Massimiliano Mantione <massi@ximian.com> + + Made it possible for mono_arch_instrument_epilog to preserve + argument registers, otherwise instrumenting the "epilogue" before + a tail call would clobber them. + * mini.h: Added "mono_arch_instrument_epilog_full" prototype, which + if like mono_arch_instrument_epilog but with an additional parameter + that states if argument registers must be preserved. + * mini.c: implemented mono_arch_instrument_epilog as a call to + mono_arch_instrument_epilog_full without asking to preserve argument + registers (this makes the existing code work as usual). + * mini-amd64.c: + - mono_arch_instrument_epilog: add parameter to transform it into + mono_arch_instrument_epilog_full, and preserve argument registers + when required. + - mono_arch_output_basic_block, OP_TAILCALL case: call + mono_arch_instrument_epilog_full. + * mini-alpha.c, mini-arm.c, mini-hppa.c, mini-ia64.c, mini-mips.c, + mini-ppc.c, mini-s390.c, mini-s390x.c, mini-sparc.c, mini-x86.c: + only transformed mono_arch_instrument_epilog into + mono_arch_instrument_epilog_full. + 2009-05-15 Geoff Norton <gnorton@novell.com> * mini-darwin.c: This works on arm now. diff --git a/mono/mini/mini-alpha.c b/mono/mini/mini-alpha.c index 7708ca6d182..2d5507660d2 100644 --- a/mono/mini/mini-alpha.c +++ b/mono/mini/mini-alpha.c @@ -5315,8 +5315,7 @@ enum { /*------------------------------------------------------------------*/ void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, - gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { unsigned int *code = p; int save_mode = SAVE_NONE; diff --git a/mono/mini/mini-amd64.c b/mono/mini/mini-amd64.c index 36678a4aef6..c69e2a3a512 100644 --- a/mono/mini/mini-amd64.c +++ b/mono/mini/mini-amd64.c @@ -3540,7 +3540,7 @@ mono_arch_output_basic_block (MonoCompile *cfg, MonoBasicBlock *bb) /* FIXME: no tracing support... */ if (cfg->prof_options & MONO_PROFILE_ENTER_LEAVE) - code = mono_arch_instrument_epilog (cfg, mono_profiler_method_leave, code, FALSE); + code = mono_arch_instrument_epilog_full (cfg, mono_profiler_method_leave, code, FALSE, FALSE); g_assert (!cfg->method->save_lmf); @@ -5491,7 +5491,7 @@ enum { }; void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guchar *code = p; int save_mode = SAVE_NONE; @@ -5564,10 +5564,20 @@ mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean ena else amd64_mov_reg_imm (code, AMD64_RAX, 0); + if (preserve_argument_registers) { + amd64_push_reg (code, MONO_AMD64_ARG_REG1); + amd64_push_reg (code, MONO_AMD64_ARG_REG2); + } + mono_add_patch_info (cfg, code-cfg->native_code, MONO_PATCH_INFO_METHODCONST, method); amd64_set_reg_template (code, AMD64_ARG_REG1); code = emit_call (cfg, code, MONO_PATCH_INFO_ABS, (gpointer)func, TRUE); + if (preserve_argument_registers) { + amd64_pop_reg (code, MONO_AMD64_ARG_REG2); + amd64_pop_reg (code, MONO_AMD64_ARG_REG1); + } + /* Restore result */ switch (save_mode) { case SAVE_EAX: diff --git a/mono/mini/mini-arm.c b/mono/mini/mini-arm.c index 533925480cc..c5470c8733e 100644 --- a/mono/mini/mini-arm.c +++ b/mono/mini/mini-arm.c @@ -1423,7 +1423,7 @@ enum { }; void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guchar *code = p; int save_mode = SAVE_NONE; diff --git a/mono/mini/mini-hppa.c b/mono/mini/mini-hppa.c index eb3e1f2f801..f5f1afecc1f 100644 --- a/mono/mini/mini-hppa.c +++ b/mono/mini/mini-hppa.c @@ -2116,7 +2116,7 @@ enum { }; void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guint32 *code = (guint32*)p; DEBUG_FUNC_ENTER(); diff --git a/mono/mini/mini-ia64.c b/mono/mini/mini-ia64.c index 322c48ce987..8b29baa2d60 100644 --- a/mono/mini/mini-ia64.c +++ b/mono/mini/mini-ia64.c @@ -4352,7 +4352,7 @@ mono_arch_instrument_prolog (MonoCompile *cfg, void *func, void *p, gboolean ena } void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { Ia64CodegenState code; CallInfo *cinfo = NULL; diff --git a/mono/mini/mini-mips.c b/mono/mini/mini-mips.c index 5d0267eedd3..372f500597b 100644 --- a/mono/mini/mini-mips.c +++ b/mono/mini/mini-mips.c @@ -4881,7 +4881,7 @@ enum { }; void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guchar *code = p; int save_mode = SAVE_NONE; diff --git a/mono/mini/mini-ppc.c b/mono/mini/mini-ppc.c index 46dc1d8b24b..cb1ce2cf5d8 100644 --- a/mono/mini/mini-ppc.c +++ b/mono/mini/mini-ppc.c @@ -1641,7 +1641,7 @@ enum { }; void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guchar *code = p; int save_mode = SAVE_NONE; diff --git a/mono/mini/mini-s390.c b/mono/mini/mini-s390.c index 750c53e296e..19d0f7ef981 100644 --- a/mono/mini/mini-s390.c +++ b/mono/mini/mini-s390.c @@ -2381,7 +2381,7 @@ mono_arch_instrument_prolog (MonoCompile *cfg, void *func, void *p, /*------------------------------------------------------------------*/ void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guchar *code = p; int save_mode = SAVE_NONE, diff --git a/mono/mini/mini-s390x.c b/mono/mini/mini-s390x.c index 3059c8ba2ef..e7a03079955 100644 --- a/mono/mini/mini-s390x.c +++ b/mono/mini/mini-s390x.c @@ -2408,7 +2408,7 @@ mono_arch_instrument_prolog (MonoCompile *cfg, void *func, void *p, /*------------------------------------------------------------------*/ void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guchar *code = p; int save_mode = SAVE_NONE, diff --git a/mono/mini/mini-sparc.c b/mono/mini/mini-sparc.c index d788fdd8916..3cdd7d48258 100644 --- a/mono/mini/mini-sparc.c +++ b/mono/mini/mini-sparc.c @@ -3808,7 +3808,7 @@ enum { }; void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guint32 *code = (guint32*)p; int save_mode = SAVE_NONE; diff --git a/mono/mini/mini-x86.c b/mono/mini/mini-x86.c index a0b99f55701..e226cf4b731 100644 --- a/mono/mini/mini-x86.c +++ b/mono/mini/mini-x86.c @@ -1460,7 +1460,7 @@ enum { }; void* -mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) +mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) { guchar *code = p; int arg_size = 0, save_mode = SAVE_NONE; diff --git a/mono/mini/mini.c b/mono/mini/mini.c index 4c09cb24614..831acf15ffa 100644 --- a/mono/mini/mini.c +++ b/mono/mini/mini.c @@ -5268,3 +5268,8 @@ void mono_precompile_assemblies () g_hash_table_destroy (assemblies); } + +void* +mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) { + return mono_arch_instrument_epilog_full (cfg, func, p, enable_arguments, FALSE); +} diff --git a/mono/mini/mini.h b/mono/mini/mini.h index 5b9c317c677..6ed1afdd755 100644 --- a/mono/mini/mini.h +++ b/mono/mini/mini.h @@ -1517,6 +1517,7 @@ guint32 mono_arch_cpu_optimizazions (guint32 *exclude_mask) MONO_INT void mono_arch_instrument_mem_needs (MonoMethod *method, int *stack, int *code) MONO_INTERNAL; void *mono_arch_instrument_prolog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) MONO_INTERNAL; void *mono_arch_instrument_epilog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments) MONO_INTERNAL; +void *mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers) MONO_INTERNAL; void mono_codegen (MonoCompile *cfg) MONO_INTERNAL; void mono_call_inst_add_outarg_reg (MonoCompile *cfg, MonoCallInst *call, int vreg, int hreg, gboolean fp) MONO_INTERNAL; const char *mono_arch_regname (int reg) MONO_INTERNAL; |