#include <mono/utils/mono-compiler.h>
#include <mono/utils/mono-counters.h>
#include <mono/utils/mono-digest.h>
+#include <mono/utils/mono-threads-coop.h>
#include "mini.h"
#include "seq-points.h"
}
break;
}
- case MONO_WRAPPER_LDFLD_REMOTE:
- ref->method = mono_marshal_get_ldfld_remote_wrapper (NULL);
- break;
- case MONO_WRAPPER_STFLD_REMOTE:
- ref->method = mono_marshal_get_stfld_remote_wrapper (NULL);
- break;
#endif
case MONO_WRAPPER_ALLOC: {
int atype = decode_value (p, &p);
-
- ref->method = mono_gc_get_managed_allocator_by_type (atype, !!(mono_profiler_get_events () & MONO_PROFILE_ALLOCATIONS));
+ ManagedAllocatorVariant variant =
+ mono_profiler_get_events () & MONO_PROFILE_ALLOCATIONS ?
+ MANAGED_ALLOCATOR_SLOW_PATH : MANAGED_ALLOCATOR_REGULAR;
+
+ ref->method = mono_gc_get_managed_allocator_by_type (atype, variant);
+ /* Try to fallback to the slow path version */
+ if (!ref->method && variant == MANAGED_ALLOCATOR_REGULAR)
+ ref->method = mono_gc_get_managed_allocator_by_type (atype, MANAGED_ALLOCATOR_SLOW_PATH);
if (!ref->method) {
mono_error_set_bad_image_name (error, module->aot_name, "Error: No managed allocator, but we need one for AOT.\nAre you using non-standard GC options?\n");
return FALSE;
msg = g_strdup_printf ("not compiled with --aot=llvmonly");
usable = FALSE;
}
-#ifdef TARGET_ARM
- /* mono_arch_find_imt_method () requires this */
- if ((info->flags & MONO_AOT_FILE_FLAG_WITH_LLVM) && !mono_use_llvm) {
- msg = g_strdup_printf ("compiled against LLVM");
- usable = FALSE;
- }
- if (!(info->flags & MONO_AOT_FILE_FLAG_WITH_LLVM) && mono_use_llvm) {
- msg = g_strdup_printf ("not compiled against LLVM");
- usable = FALSE;
- }
-#endif
if (mini_get_debug_options ()->mdb_optimizations && !(info->flags & MONO_AOT_FILE_FLAG_DEBUG) && !full_aot) {
msg = g_strdup_printf ("not compiled for debugging");
usable = FALSE;
find_symbol (sofile, globals, "mono_aot_file_info", (gpointer*)&info);
}
+ // Copy aotid to MonoImage
+ memcpy(&assembly->image->aotid, info->aotid, 16);
+
if (version_symbol) {
/* Old file format */
version = atoi (version_symbol);
amodule->mono_eh_frame = (guint8 *)info->mono_eh_frame;
amodule->trampolines [MONO_AOT_TRAMP_SPECIFIC] = (guint8 *)info->specific_trampolines;
amodule->trampolines [MONO_AOT_TRAMP_STATIC_RGCTX] = (guint8 *)info->static_rgctx_trampolines;
- amodule->trampolines [MONO_AOT_TRAMP_IMT_THUNK] = (guint8 *)info->imt_thunks;
+ amodule->trampolines [MONO_AOT_TRAMP_IMT] = (guint8 *)info->imt_trampolines;
amodule->trampolines [MONO_AOT_TRAMP_GSHAREDVT_ARG] = (guint8 *)info->gsharedvt_arg_trampolines;
if (!strcmp (assembly->aname.name, "mscorlib"))
}
}
- if (!(is_llvm_code (amodule, code) && (amodule->info.flags & MONO_AOT_FILE_FLAG_LLVM_ONLY))) {
+ if (!(is_llvm_code (amodule, code) && (amodule->info.flags & MONO_AOT_FILE_FLAG_LLVM_ONLY)) ||
+ (mono_llvm_only && method && method->wrapper_type == MONO_WRAPPER_NATIVE_TO_MANAGED)) {
res = init_method (amodule, method_index, method, NULL, NULL, error);
if (!res)
goto cleanup;
break;
}
- /*
- * Special case: wrappers of shared generic methods.
- * This is needed because of the way mini_get_shared_method () works,
- * we could end up with multiple copies of the same wrapper.
- */
- if (m && method->wrapper_type && method->wrapper_type == m->wrapper_type &&
- method->wrapper_type == MONO_WRAPPER_SYNCHRONIZED) {
- MonoMethod *w1 = mono_marshal_method_from_wrapper (method);
- MonoMethod *w2 = mono_marshal_method_from_wrapper (m);
-
- if ((w1 == w2) || (w1->is_inflated && ((MonoMethodInflated *)w1)->declaring == w2)) {
- index = value;
- break;
- }
- }
- if (m && method->wrapper_type && method->wrapper_type == m->wrapper_type &&
- method->wrapper_type == MONO_WRAPPER_DELEGATE_INVOKE) {
- WrapperInfo *info1 = mono_marshal_get_wrapper_info (method);
- WrapperInfo *info2 = mono_marshal_get_wrapper_info (m);
-
- if (info1 && info2 && info1->subtype == info2->subtype && method->klass == m->klass) {
- index = value;
- break;
- }
- }
-
/* Methods decoded needlessly */
if (m) {
//printf ("%d %s %s %p\n", n_extra_decodes, mono_method_full_name (method, TRUE), mono_method_full_name (m, TRUE), orig_p);
if (info->subtype == WRAPPER_SUBTYPE_ARRAY_ACCESSOR) {
MonoMethod *array_method = info->d.array_accessor.method;
if (MONO_TYPE_IS_REFERENCE (&array_method->klass->element_class->byval_arg)) {
- MonoClass *obj_array_class = mono_array_class_get (mono_defaults.object_class, 1);
+ int rank;
+
+ if (!strcmp (array_method->name, "Set"))
+ rank = mono_method_signature (array_method)->param_count - 1;
+ else if (!strcmp (array_method->name, "Get") || !strcmp (array_method->name, "Address"))
+ rank = mono_method_signature (array_method)->param_count;
+ else
+ g_assert_not_reached ();
+ MonoClass *obj_array_class = mono_array_class_get (mono_defaults.object_class, rank);
MonoMethod *m = mono_class_get_method_from_name (obj_array_class, array_method->name, mono_method_signature (array_method)->param_count);
g_assert (m);
gpointer res = mono_aot_get_method_checked (domain, method, &error);
/* This is external only, so its ok to raise here */
- mono_error_raise_exception (&error);
+ mono_error_raise_exception (&error); /* OK to throw, external only without a good alternative */
return res;
}
sprintf (symbol_name, "specific_trampolines_page_%s_p", is_generic ? "gen" : "sp");
else if (tramp_type == MONO_AOT_TRAMP_STATIC_RGCTX)
sprintf (symbol_name, "rgctx_trampolines_page_%s_p", is_generic ? "gen" : "sp");
- else if (tramp_type == MONO_AOT_TRAMP_IMT_THUNK)
+ else if (tramp_type == MONO_AOT_TRAMP_IMT)
sprintf (symbol_name, "imt_trampolines_page_%s_p", is_generic ? "gen" : "sp");
else if (tramp_type == MONO_AOT_TRAMP_GSHAREDVT_ARG)
sprintf (symbol_name, "gsharedvt_trampolines_page_%s_p", is_generic ? "gen" : "sp");
tpage = load_function (amodule, "specific_trampolines_page");
else if (tramp_type == MONO_AOT_TRAMP_STATIC_RGCTX)
tpage = load_function (amodule, "rgctx_trampolines_page");
- else if (tramp_type == MONO_AOT_TRAMP_IMT_THUNK)
+ else if (tramp_type == MONO_AOT_TRAMP_IMT)
tpage = load_function (amodule, "imt_trampolines_page");
else if (tramp_type == MONO_AOT_TRAMP_GSHAREDVT_ARG)
tpage = load_function (amodule, "gsharedvt_arg_trampolines_page");
void *code;
gpointer *data;
- code = get_new_trampoline_from_page (MONO_AOT_TRAMP_IMT_THUNK);
+ code = get_new_trampoline_from_page (MONO_AOT_TRAMP_IMT);
data = (gpointer*)((char*)code - MONO_AOT_TRAMP_PAGE_SIZE);
data [0] = arg;
}
static void
-no_imt_thunk (void)
+no_imt_trampoline (void)
{
- g_assert_not_reached ();
+ g_assert_not_reached ();
}
gpointer
-mono_aot_get_imt_thunk (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckItem **imt_entries, int count, gpointer fail_tramp)
+mono_aot_get_imt_trampoline (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckItem **imt_entries, int count, gpointer fail_tramp)
{
guint32 got_offset;
gpointer code;
MonoAotModule *amodule;
if (mono_llvm_only)
- return no_imt_thunk;
+ return no_imt_trampoline;
real_count = 0;
for (i = 0; i < count; ++i) {
if (USE_PAGE_TRAMPOLINES) {
code = get_new_imt_trampoline_from_page (buf);
} else {
- code = get_numerous_trampoline (MONO_AOT_TRAMP_IMT_THUNK, 1, &amodule, &got_offset, NULL);
+ code = get_numerous_trampoline (MONO_AOT_TRAMP_IMT, 1, &amodule, &got_offset, NULL);
amodule->got [got_offset] = buf;
}
gpointer
mono_aot_get_method_checked (MonoDomain *domain,
- MonoMethod *method, MonoError *error);
+ MonoMethod *method, MonoError *error)
{
mono_error_init (error);
return NULL;
}
gpointer
-mono_aot_get_imt_thunk (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckItem **imt_entries, int count, gpointer fail_tramp)
+mono_aot_get_imt_trampoline (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckItem **imt_entries, int count, gpointer fail_tramp)
{
g_assert_not_reached ();
return NULL;