From: Zoltan Varga Date: Fri, 1 Mar 2013 04:01:19 +0000 (+0100) Subject: Implement a fast version of mono_get_lmf_addr () on ARM by inlining the call to pthre... X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=commitdiff_plain;h=8575b06a0ecb83643f0a63e71a26b633cc5d62a3;p=mono.git Implement a fast version of mono_get_lmf_addr () on ARM by inlining the call to pthread_getspecific () into the managed to native wrappers. --- diff --git a/mono/mini/aot-compiler.c b/mono/mini/aot-compiler.c index 1c03981310d..61af478f6f2 100644 --- a/mono/mini/aot-compiler.c +++ b/mono/mini/aot-compiler.c @@ -4437,6 +4437,7 @@ encode_patch (MonoAotCompile *acfg, MonoJumpInfo *patch_info, guint8 *buf, guint encode_value (get_image_index (acfg, patch_info->data.image), p, &p); break; case MONO_PATCH_INFO_MSCORLIB_GOT_ADDR: + case MONO_PATCH_INFO_JIT_TLS_ID: case MONO_PATCH_INFO_GC_CARD_TABLE_ADDR: case MONO_PATCH_INFO_CASTCLASS_CACHE: break; @@ -8179,6 +8180,10 @@ mono_compile_assembly (MonoAssembly *ass, guint32 opts, const char *aot_options) ji = mono_mempool_alloc0 (acfg->mempool, sizeof (MonoAotCompile)); ji->type = MONO_PATCH_INFO_GC_CARD_TABLE_ADDR; get_got_offset (acfg, ji); + + ji = mono_mempool_alloc0 (acfg->mempool, sizeof (MonoAotCompile)); + ji->type = MONO_PATCH_INFO_JIT_TLS_ID; + get_got_offset (acfg, ji); } TV_GETTIME (atv); diff --git a/mono/mini/aot-runtime.c b/mono/mini/aot-runtime.c index cd164ebd71d..e08d90fbde5 100644 --- a/mono/mini/aot-runtime.c +++ b/mono/mini/aot-runtime.c @@ -2885,6 +2885,7 @@ decode_patch (MonoAotModule *aot_module, MonoMemPool *mp, MonoJumpInfo *ji, guin case MONO_PATCH_INFO_MONITOR_EXIT: case MONO_PATCH_INFO_GC_CARD_TABLE_ADDR: case MONO_PATCH_INFO_CASTCLASS_CACHE: + case MONO_PATCH_INFO_JIT_TLS_ID: break; case MONO_PATCH_INFO_RGCTX_FETCH: { gboolean res; diff --git a/mono/mini/mini-arm.c b/mono/mini/mini-arm.c index ec1d943550d..eabff5c1c5c 100644 --- a/mono/mini/mini-arm.c +++ b/mono/mini/mini-arm.c @@ -385,7 +385,7 @@ emit_save_lmf (MonoCompile *cfg, guint8 *code, gint32 lmf_offset) if (lmf_addr_tls_offset != -1) { get_lmf_fast = TRUE; - mono_add_patch_info (cfg, code - cfg->native_code, MONO_PATCH_INFO_INTERNAL_METHOD, + mono_add_patch_info (cfg, code - cfg->native_code, MONO_PATCH_INFO_INTERNAL_METHOD, (gpointer)"__aeabi_read_tp"); code = emit_call_seq (cfg, code); @@ -393,9 +393,38 @@ emit_save_lmf (MonoCompile *cfg, guint8 *code, gint32 lmf_offset) get_lmf_fast = TRUE; } #endif + +#ifdef TARGET_IOS + if (cfg->method->wrapper_type == MONO_WRAPPER_MANAGED_TO_NATIVE) { + int lmf_offset; + + /* Inline mono_get_lmf_addr () */ + /* jit_tls = pthread_getspecific (mono_jit_tls_id); lmf_addr = &jit_tls->lmf; */ + + /* Load mono_jit_tls_id */ + /* OP_AOTCONST */ + mono_add_patch_info (cfg, code - cfg->native_code, MONO_PATCH_INFO_JIT_TLS_ID, NULL); + ARM_LDR_IMM (code, ARMREG_R0, ARMREG_PC, 0); + ARM_B (code, 0); + *(gpointer*)code = NULL; + code += 4; + ARM_LDR_REG_REG (code, ARMREG_R0, ARMREG_PC, ARMREG_R0); + /* call pthread_getspecific () */ + mono_add_patch_info (cfg, code - cfg->native_code, MONO_PATCH_INFO_INTERNAL_METHOD, + (gpointer)"pthread_getspecific"); + code = emit_call_seq (cfg, code); + /* lmf_addr = &jit_tls->lmf */ + lmf_offset = G_STRUCT_OFFSET (MonoJitTlsData, lmf); + g_assert (arm_is_imm8 (lmf_offset)); + ARM_ADD_REG_IMM (code, ARMREG_R0, ARMREG_R0, lmf_offset, 0); + + get_lmf_fast = TRUE; + } +#endif + if (!get_lmf_fast) { mono_add_patch_info (cfg, code - cfg->native_code, MONO_PATCH_INFO_INTERNAL_METHOD, - (gpointer)"mono_get_lmf_addr"); + (gpointer)"mono_get_lmf_addr"); code = emit_call_seq (cfg, code); } /* we build the MonoLMF structure on the stack - see mini-arm.h */ diff --git a/mono/mini/mini.c b/mono/mini/mini.c index dfdbc8b9400..214a5c28551 100644 --- a/mono/mini/mini.c +++ b/mono/mini/mini.c @@ -3362,6 +3362,10 @@ mono_resolve_patch_target (MonoMethod *method, MonoDomain *domain, guint8 *code, target = mono_domain_alloc0 (domain, sizeof (gpointer)); break; } + case MONO_PATCH_INFO_JIT_TLS_ID: { + target = (gpointer)mono_jit_tls_id; + break; + } default: g_assert_not_reached (); } @@ -7099,7 +7103,10 @@ mini_init (const char *filename, const char *runtime_version) register_icall (mono_object_isinst_with_cache, "mono_object_isinst_with_cache", "object object ptr ptr", FALSE); register_icall (mono_debugger_agent_user_break, "mono_debugger_agent_user_break", "void", FALSE); +#endif +#ifdef TARGET_IOS + register_icall (pthread_getspecific, "pthread_getspecific", NULL, TRUE); #endif mono_generic_sharing_init (); diff --git a/mono/mini/patch-info.h b/mono/mini/patch-info.h index 53800be31bb..b7fd39d8081 100644 --- a/mono/mini/patch-info.h +++ b/mono/mini/patch-info.h @@ -44,4 +44,6 @@ PATCH_INFO(GC_CARD_TABLE_ADDR, "gc_card_table_addr") PATCH_INFO(CASTCLASS_CACHE, "castclass_cache") PATCH_INFO(SIGNATURE, "signature") PATCH_INFO(GSHAREDVT_CALL, "gsharedvt_call") +PATCH_INFO(JIT_TLS_ID, "jit_tls_id") PATCH_INFO(NONE, "none") +