From 82b5d81363c72097b8afa13433d6fdef5e3ad7a8 Mon Sep 17 00:00:00 2001 From: Zoltan Varga Date: Wed, 27 Jan 2016 19:55:48 -0500 Subject: [jit] Use MonoError in mono_jit_compile_method () and the trampoline code. --- mono/mini/aot-runtime.c | 5 +++- mono/mini/mini-runtime.c | 53 +++++++++++++++++++++++++++++++-------- mono/mini/mini-trampolines.c | 59 +++++++++++++++++++++++++++++++++----------- mono/mini/mini.h | 2 +- 4 files changed, 92 insertions(+), 27 deletions(-) diff --git a/mono/mini/aot-runtime.c b/mono/mini/aot-runtime.c index 437d82f05f8..98c346de4cd 100644 --- a/mono/mini/aot-runtime.c +++ b/mono/mini/aot-runtime.c @@ -4607,6 +4607,7 @@ mono_aot_plt_resolve (gpointer aot_module, guint32 plt_info_offset, guint8 *code MonoAotModule *module = (MonoAotModule*)aot_module; gboolean res, no_ftnptr = FALSE; MonoMemPool *mp; + MonoError error; gboolean using_gsharedvt = FALSE; //printf ("DYN: %p %d\n", aot_module, plt_info_offset); @@ -4635,7 +4636,9 @@ mono_aot_plt_resolve (gpointer aot_module, guint32 plt_info_offset, guint8 *code */ if (mono_aot_only && ji.type == MONO_PATCH_INFO_METHOD && !ji.data.method->is_generic && !mono_method_check_context_used (ji.data.method) && !(ji.data.method->iflags & METHOD_IMPL_ATTRIBUTE_SYNCHRONIZED) && !mono_method_needs_static_rgctx_invoke (ji.data.method, FALSE) && !using_gsharedvt) { - target = (guint8 *)mono_jit_compile_method (ji.data.method); + target = (guint8 *)mono_jit_compile_method (ji.data.method, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); no_ftnptr = TRUE; } else { target = (guint8 *)mono_resolve_patch_target (NULL, mono_domain_get (), NULL, &ji, TRUE); diff --git a/mono/mini/mini-runtime.c b/mono/mini/mini-runtime.c index edd3669a82d..95678d89fd7 100644 --- a/mono/mini/mini-runtime.c +++ b/mono/mini/mini-runtime.c @@ -1991,13 +1991,22 @@ mono_jit_compile_method_with_opt (MonoMethod *method, guint32 opt, MonoError *er } gpointer -mono_jit_compile_method (MonoMethod *method) +mono_jit_compile_method (MonoMethod *method, MonoError *error) +{ + gpointer code; + + code = mono_jit_compile_method_with_opt (method, mono_get_optimizations_for_method (method, default_opt), error); + return code; +} + +static gpointer +mono_jit_compile_method_raise (MonoMethod *method) { MonoError error; gpointer code; mono_error_init (&error); - code = mono_jit_compile_method_with_opt (method, mono_get_optimizations_for_method (method, default_opt), &error); + code = mono_jit_compile_method (method, &error); if (!code) { g_assert (!mono_error_ok (&error)); mono_error_raise_exception (&error); @@ -2203,7 +2212,7 @@ typedef struct { } RuntimeInvokeInfo; static RuntimeInvokeInfo* -create_runtime_invoke_info (MonoDomain *domain, MonoMethod *method, gpointer compiled_method, gboolean callee_gsharedvt) +create_runtime_invoke_info (MonoDomain *domain, MonoMethod *method, gpointer compiled_method, gboolean callee_gsharedvt, MonoError *error) { MonoMethod *invoke; RuntimeInvokeInfo *info; @@ -2306,7 +2315,11 @@ create_runtime_invoke_info (MonoDomain *domain, MonoMethod *method, gpointer com invoke = mono_marshal_get_runtime_invoke_for_sig (wrapper_sig); g_free (wrapper_sig); - info->compiled_method = mono_jit_compile_method (wrapper); + info->compiled_method = mono_jit_compile_method (wrapper, error); + if (!mono_error_ok (error)) { + g_free (info); + return NULL; + } } else { /* Gsharedvt methods can be invoked the same way */ /* The out wrapper has the same signature as the compiled gsharedvt method */ @@ -2318,7 +2331,11 @@ create_runtime_invoke_info (MonoDomain *domain, MonoMethod *method, gpointer com g_free (wrapper_sig); } } - info->runtime_invoke = mono_jit_compile_method (invoke); + info->runtime_invoke = mono_jit_compile_method (invoke, error); + if (!mono_error_ok (error)) { + g_free (info); + return NULL; + } } return info; @@ -2412,6 +2429,7 @@ mono_jit_runtime_invoke (MonoMethod *method, void *obj, void **params, MonoObjec RuntimeInvokeInfo *info, *info2; MonoJitInfo *ji = NULL; gboolean callee_gsharedvt = FALSE; + MonoError error; if (obj == NULL && !(method->flags & METHOD_ATTRIBUTE_STATIC) && !method->string_ctor && (method->wrapper_type == 0)) { g_warning ("Ignoring invocation of an instance method on a NULL instance.\n"); @@ -2462,8 +2480,6 @@ mono_jit_runtime_invoke (MonoMethod *method, void *obj, void **params, MonoObjec } if (callee) { - MonoError error; - compiled_method = mono_jit_compile_method_with_opt (callee, mono_get_optimizations_for_method (callee, default_opt), &error); if (!compiled_method) { g_assert (!mono_error_ok (&error)); @@ -2489,7 +2505,15 @@ mono_jit_runtime_invoke (MonoMethod *method, void *obj, void **params, MonoObjec compiled_method = NULL; } - info = create_runtime_invoke_info (domain, method, compiled_method, callee_gsharedvt); + info = create_runtime_invoke_info (domain, method, compiled_method, callee_gsharedvt, &error); + if (!mono_error_ok (&error)) { + if (exc) { + *exc = (MonoObject*)mono_error_convert_to_exception (&error); + return NULL; + } else { + mono_error_raise_exception (&error); + } + } mono_domain_lock (domain); info2 = (RuntimeInvokeInfo *)mono_conc_hashtable_insert (domain_info->runtime_invoke_hash, method, info); @@ -2527,7 +2551,16 @@ mono_jit_runtime_invoke (MonoMethod *method, void *obj, void **params, MonoObjec if (!dyn_runtime_invoke) { invoke = mono_marshal_get_runtime_invoke_dynamic (); - dyn_runtime_invoke = (RuntimeInvokeDynamicFunction)mono_jit_compile_method (invoke); + dyn_runtime_invoke = (RuntimeInvokeDynamicFunction)mono_jit_compile_method (invoke, &error); + if (!mono_error_ok (&error)) { + if (exc) { + *exc = (MonoObject*)mono_error_convert_to_exception (&error); + return NULL; + } else { + mono_error_raise_exception (&error); + /* coverity[unreachable] */ + } + } } /* Convert the arguments to the format expected by start_dyn_call () */ @@ -3566,7 +3599,7 @@ mini_init (const char *filename, const char *runtime_version) #define JIT_TRAMPOLINES_WORK #ifdef JIT_TRAMPOLINES_WORK - mono_install_compile_method (mono_jit_compile_method); + mono_install_compile_method (mono_jit_compile_method_raise); mono_install_free_method (mono_jit_free_method); mono_install_trampoline (mono_create_jit_trampoline); mono_install_jump_trampoline (mono_create_jump_trampoline); diff --git a/mono/mini/mini-trampolines.c b/mono/mini/mini-trampolines.c index 6e1ca5a66dc..23c300b7fc5 100644 --- a/mono/mini/mini-trampolines.c +++ b/mono/mini/mini-trampolines.c @@ -501,13 +501,13 @@ mini_add_method_wrappers_llvmonly (MonoMethod *m, gpointer compiled_method, gboo } /** - * common_call_trampoline: + * common_call_trampoline_inner: * * The code to handle normal, virtual, and interface method calls and jumps, both * from JITted and LLVM compiled code. */ static gpointer -common_call_trampoline_inner (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVTable *vt, gpointer *vtable_slot) +common_call_trampoline_inner (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVTable *vt, gpointer *vtable_slot, MonoError *error) { gpointer addr, compiled_method; gboolean generic_shared = FALSE; @@ -520,6 +520,8 @@ common_call_trampoline_inner (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVT gpointer *orig_vtable_slot, *vtable_slot_to_patch = NULL; MonoJitInfo *ji = NULL; + mono_error_init (error); + virtual_ = vt && (gpointer)vtable_slot > (gpointer)vt; imt_call = vt && (gpointer)vtable_slot < (gpointer)vt; @@ -691,8 +693,9 @@ common_call_trampoline_inner (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVT if (!code && mono_method_needs_static_rgctx_invoke (m, FALSE)) need_rgctx_tramp = TRUE; - addr = compiled_method = mono_compile_method (m); - g_assert (addr); + addr = compiled_method = mono_jit_compile_method (m, error); + if (!addr) + return NULL; if (generic_virtual || variant_iface) { if (vt->klass->valuetype) /*FIXME is this required variant iface?*/ @@ -801,11 +804,11 @@ common_call_trampoline_inner (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVT } static gpointer -common_call_trampoline (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVTable *vt, gpointer *vtable_slot) +common_call_trampoline (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVTable *vt, gpointer *vtable_slot, MonoError *error) { gpointer res; MONO_PREPARE_RESET_BLOCKING; - res = common_call_trampoline_inner (regs, code, m, vt, vtable_slot); + res = common_call_trampoline_inner (regs, code, m, vt, vtable_slot, error); MONO_FINISH_RESET_BLOCKING; return res; } @@ -818,9 +821,15 @@ common_call_trampoline (mgreg_t *regs, guint8 *code, MonoMethod *m, MonoVTable * gpointer mono_magic_trampoline (mgreg_t *regs, guint8 *code, gpointer arg, guint8* tramp) { + MonoError error; + gpointer res; + trampoline_calls ++; - return common_call_trampoline (regs, code, (MonoMethod *)arg, NULL, NULL); + res = common_call_trampoline (regs, code, (MonoMethod *)arg, NULL, NULL, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); + return res; } /** @@ -835,7 +844,8 @@ mono_vcall_trampoline (mgreg_t *regs, guint8 *code, int slot, guint8 *tramp) MonoVTable *vt; gpointer *vtable_slot; MonoMethod *m; - gpointer addr; + MonoError error; + gpointer addr, res; trampoline_calls ++; @@ -889,7 +899,10 @@ mono_vcall_trampoline (mgreg_t *regs, guint8 *code, int slot, guint8 *tramp) m = NULL; } - return common_call_trampoline (regs, code, m, vt, vtable_slot); + res = common_call_trampoline (regs, code, m, vt, vtable_slot, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); + return res; } #ifndef DISABLE_REMOTING @@ -922,7 +935,9 @@ mono_generic_virtual_remoting_trampoline (mgreg_t *regs, guint8 *code, MonoMetho g_assert (mono_error_ok (&error)); /* FIXME don't swallow the error */; m = mono_marshal_get_remoting_invoke_with_check (m); - addr = mono_compile_method (m); + addr = mono_jit_compile_method (m, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); g_assert (addr); return addr; @@ -1075,6 +1090,7 @@ mono_delegate_trampoline (mgreg_t *regs, guint8 *code, gpointer *arg, guint8* tr MonoJitInfo *ji; MonoMethod *m; MonoMethod *method = NULL; + MonoError error; gboolean multicast, callvirt = FALSE, closed_over_null = FALSE; gboolean need_rgctx_tramp = FALSE; gboolean need_unbox_tramp = FALSE; @@ -1201,7 +1217,9 @@ mono_delegate_trampoline (mgreg_t *regs, guint8 *code, gpointer *arg, guint8* tr if (enable_caching && delegate->method_code && *delegate->method_code) { delegate->method_ptr = *delegate->method_code; } else { - compiled_method = addr = mono_compile_method (method); + compiled_method = addr = mono_jit_compile_method (method, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); addr = mini_add_method_trampoline (method, compiled_method, need_rgctx_tramp, need_unbox_tramp); delegate->method_ptr = addr; if (enable_caching && delegate->method_code) @@ -1227,7 +1245,9 @@ mono_delegate_trampoline (mgreg_t *regs, guint8 *code, gpointer *arg, guint8* tr if (!code) { /* The general, unoptimized case */ m = mono_marshal_get_delegate_invoke (invoke, delegate); - code = (guint8 *)mono_compile_method (m); + code = (guint8 *)mono_jit_compile_method (m, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); code = (guint8 *)mini_add_method_trampoline (m, code, mono_method_needs_static_rgctx_invoke (m, FALSE), FALSE); } @@ -1412,6 +1432,7 @@ mono_create_specific_trampoline (gpointer arg1, MonoTrampolineType tramp_type, M gpointer mono_create_jump_trampoline (MonoDomain *domain, MonoMethod *method, gboolean add_sync_wrapper) { + MonoError error; MonoJitInfo *ji; gpointer code; guint32 code_size = 0; @@ -1426,8 +1447,12 @@ mono_create_jump_trampoline (MonoDomain *domain, MonoMethod *method, gboolean ad if (code && !ji->has_generic_jit_info && !(method->iflags & METHOD_IMPL_ATTRIBUTE_SYNCHRONIZED)) return code; - if (mono_llvm_only) - return mono_jit_compile_method (method); + if (mono_llvm_only) { + code = mono_jit_compile_method (method, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); + return code; + } mono_domain_lock (domain); code = g_hash_table_lookup (domain_jit_info (domain)->jump_trampoline_hash, method); @@ -1466,6 +1491,7 @@ method_not_found (void) gpointer mono_create_jit_trampoline_in_domain (MonoDomain *domain, MonoMethod *method) { + MonoError error; gpointer tramp; if (mono_aot_only) { @@ -1480,7 +1506,10 @@ mono_create_jit_trampoline_in_domain (MonoDomain *domain, MonoMethod *method) /* These wrappers are not generated */ return method_not_found; /* Methods are lazily initialized on first call, so this can't lead recursion */ - return mono_compile_method (method); + code = mono_jit_compile_method (method, &error); + if (!mono_error_ok (&error)) + mono_error_raise_exception (&error); + return code; } } diff --git a/mono/mini/mini.h b/mono/mini/mini.h index 38a78fa802c..277a3906f85 100644 --- a/mono/mini/mini.h +++ b/mono/mini/mini.h @@ -2325,7 +2325,7 @@ MonoJumpInfo *mono_patch_info_list_prepend (MonoJumpInfo *list, int ip, MonoJum gpointer mono_resolve_patch_target (MonoMethod *method, MonoDomain *domain, guint8 *code, MonoJumpInfo *patch_info, gboolean run_cctors) MONO_LLVM_INTERNAL; gpointer mono_jit_find_compiled_method_with_jit_info (MonoDomain *domain, MonoMethod *method, MonoJitInfo **ji); gpointer mono_jit_find_compiled_method (MonoDomain *domain, MonoMethod *method); -gpointer mono_jit_compile_method (MonoMethod *method); +gpointer mono_jit_compile_method (MonoMethod *method, MonoError *error); gpointer mono_jit_compile_method_inner (MonoMethod *method, MonoDomain *target_domain, int opt, MonoError *error); MonoLMF * mono_get_lmf (void); MonoLMF** mono_get_lmf_addr (void); -- cgit v1.2.3