Merge pull request #3199 from lambdageek/dev/proxy-setter
authorAleksey Kliger (λgeek) <akliger@gmail.com>
Tue, 26 Jul 2016 16:47:45 +0000 (12:47 -0400)
committerGitHub <noreply@github.com>
Tue, 26 Jul 2016 16:47:45 +0000 (12:47 -0400)
[remoting] Convert mono_store_remote_field_new_checked to managed code

1  2 
mono/metadata/remoting.c
mono/mini/aot-compiler.c
mono/mini/aot-runtime.c
mono/mini/mini-runtime.c
mono/mini/mini-trampolines.c

diff --combined mono/metadata/remoting.c
index 62379f245e97f296a16b4a72a252c86bf7d79a84,a4ca540bd30c4cf8646d0b3f5a181883b00c2b21..30595ee5410e1a43cf886966b5e7175899ccf2ff
@@@ -198,7 -198,6 +198,6 @@@ mono_remoting_marshal_init (void
                register_icall (mono_remoting_wrapper, "mono_remoting_wrapper", "object ptr ptr", FALSE);
                register_icall (mono_upgrade_remote_class_wrapper, "mono_upgrade_remote_class_wrapper", "void object object", FALSE);
                register_icall (mono_compile_method_icall, "mono_compile_method_icall", "ptr ptr", FALSE);
-               /* mono_store_remote_field_new_icall registered  by mini-runtime.c */
  
        }
  
@@@ -1521,7 -1520,8 +1520,7 @@@ mono_marshal_get_ldflda_wrapper (MonoTy
                        klass = mono_defaults.array_class;
                } else if (type->type == MONO_TYPE_VALUETYPE) {
                        klass = type->data.klass;
 -              } else if (t == MONO_TYPE_OBJECT || t == MONO_TYPE_CLASS || t == MONO_TYPE_STRING ||
 -                         t == MONO_TYPE_CLASS) { 
 +              } else if (t == MONO_TYPE_OBJECT || t == MONO_TYPE_CLASS || t == MONO_TYPE_STRING) { 
                        klass = mono_defaults.object_class;
                } else if (t == MONO_TYPE_PTR || t == MONO_TYPE_FNPTR) {
                        klass = mono_defaults.int_class;
        return res;
  }
  
- /*
-  * mono_marshal_get_stfld_remote_wrapper:
-  * klass: The type of the field
-  *
-  *  This function generates a wrapper for calling mono_store_remote_field_new
-  * with the appropriate signature.
-  * Similarly to mono_marshal_get_ldfld_remote_wrapper () this doesn't depend on the
-  * klass argument anymore.
-  */
- MonoMethod *
- mono_marshal_get_stfld_remote_wrapper (MonoClass *klass)
- {
-       MonoMethodSignature *sig;
-       MonoMethodBuilder *mb;
-       MonoMethod *res;
-       static MonoMethod *cached = NULL;
-       mono_marshal_lock_internal ();
-       if (cached) {
-               mono_marshal_unlock_internal ();
-               return cached;
-       }
-       mono_marshal_unlock_internal ();
-       mb = mono_mb_new_no_dup_name (mono_defaults.object_class, "__mono_store_remote_field_new_wrapper", MONO_WRAPPER_STFLD_REMOTE);
-       mb->method->save_lmf = 1;
-       sig = mono_metadata_signature_alloc (mono_defaults.corlib, 4);
-       sig->params [0] = &mono_defaults.object_class->byval_arg;
-       sig->params [1] = &mono_defaults.int_class->byval_arg;
-       sig->params [2] = &mono_defaults.int_class->byval_arg;
-       sig->params [3] = &mono_defaults.object_class->byval_arg;
-       sig->ret = &mono_defaults.void_class->byval_arg;
- #ifndef DISABLE_JIT
-       mono_mb_emit_ldarg (mb, 0);
-       mono_mb_emit_ldarg (mb, 1);
-       mono_mb_emit_ldarg (mb, 2);
-       mono_mb_emit_ldarg (mb, 3);
-       mono_mb_emit_icall (mb, mono_store_remote_field_new_icall);
-       mono_mb_emit_byte (mb, CEE_RET);
- #endif
-       mono_marshal_lock_internal ();
-       res = cached;
-       mono_marshal_unlock_internal ();
-       if (!res) {
-               MonoMethod *newm;
-               newm = mono_mb_create (mb, sig, 6, NULL);
-               mono_marshal_lock_internal ();
-               res = cached;
-               if (!res) {
-                       res = newm;
-                       cached = res;
-                       mono_marshal_unlock_internal ();
-               } else {
-                       mono_marshal_unlock_internal ();
-                       mono_free_method (newm);
-               }
-       }
-       mono_mb_free (mb);
-       
-       return res;
- }
  
  /*
   * mono_marshal_get_stfld_wrapper:
@@@ -1706,6 -1639,7 +1638,7 @@@ mono_marshal_get_stfld_wrapper (MonoTyp
        WrapperInfo *info;
        char *name;
        int t, pos;
+       static MonoMethod *tp_store = NULL;
  
        type = mono_type_get_underlying_type (type);
        t = type->type;
        if ((res = mono_marshal_find_in_cache (cache, klass)))
                return res;
  
+ #ifndef DISABLE_REMOTING
+       if (!tp_store) {
+               tp_store = mono_class_get_method_from_name (mono_defaults.transparent_proxy_class, "StoreRemoteField", -1);
+               g_assert (tp_store != NULL);
+       }
+ #endif
        /* we add the %p pointer value of klass because class names are not unique */
        name = g_strdup_printf ("__stfld_wrapper_%p_%s.%s", klass, klass->name_space, klass->name); 
        mb = mono_mb_new (mono_defaults.object_class, name, MONO_WRAPPER_STFLD);
        mono_mb_emit_ldarg (mb, 0);
        pos = mono_mb_emit_proxy_check (mb, CEE_BNE_UN);
  
+ #ifndef DISABLE_REMOTING
        mono_mb_emit_ldarg (mb, 0);
        mono_mb_emit_ldarg (mb, 1);
        mono_mb_emit_ldarg (mb, 2);
        if (klass->valuetype)
                mono_mb_emit_op (mb, CEE_BOX, klass);
  
-       mono_mb_emit_managed_call (mb, mono_marshal_get_stfld_remote_wrapper (klass), NULL);
+       mono_mb_emit_managed_call (mb, tp_store, NULL);
  
        mono_mb_emit_byte (mb, CEE_RET);
+ #endif
  
        mono_mb_patch_branch (mb, pos);
  
diff --combined mono/mini/aot-compiler.c
index 7791ec26d0b55fbff726f895120fea3eb16e118b,157054bbbb164f69580070684d81ed73913028b4..5719f5f1207d158d57f30b258e1595631142d73d
@@@ -51,7 -51,6 +51,7 @@@
  #include <mono/utils/mono-compiler.h>
  #include <mono/utils/mono-time.h>
  #include <mono/utils/mono-mmap.h>
 +#include <mono/utils/mono-rand.h>
  #include <mono/utils/json.h>
  #include <mono/utils/mono-threads-coop.h>
  
@@@ -114,8 -113,8 +114,8 @@@ typedef struct MonoAotOptions 
        gboolean soft_debug;
        gboolean log_generics;
        gboolean log_instances;
 -      gboolean gen_seq_points_file;
 -      char *gen_seq_points_file_path;
 +      gboolean gen_msym_dir;
 +      char *gen_msym_dir_path;
        gboolean direct_pinvoke;
        gboolean direct_icalls;
        gboolean no_direct_calls;
@@@ -903,10 -902,7 +903,10 @@@ arch_init (MonoAotCompile *acfg
        if (acfg->aot_opts.mtriple && strstr (acfg->aot_opts.mtriple, "darwin")) {
                g_string_append (acfg->llc_args, "-mattr=+v6");
        } else {
 -#ifdef ARM_FPU_VFP
 +#if defined(ARM_FPU_VFP_HARD)
 +              g_string_append (acfg->llc_args, " -mattr=+vfp2,-neon,+d16 -float-abi=hard");
 +              g_string_append (acfg->as_args, " -mfpu=vfp3");
 +#elif defined(ARM_FPU_VFP)
                g_string_append (acfg->llc_args, " -mattr=+vfp2,-neon,+d16");
                g_string_append (acfg->as_args, " -mfpu=vfp3");
  #else
@@@ -3104,8 -3100,6 +3104,6 @@@ encode_method_ref (MonoAotCompile *acfg
                        encode_klass_ref (acfg, info->d.proxy.klass, p, &p);
                        break;
                }
-               case MONO_WRAPPER_STFLD_REMOTE:
-                       break;
                case MONO_WRAPPER_ALLOC: {
                        /* The GC name is saved once in MonoAotFileInfo */
                        g_assert (info->d.alloc.alloc_type != -1);
@@@ -3589,9 -3583,7 +3587,9 @@@ get_runtime_invoke_sig (MonoMethodSigna
  
        mb = mono_mb_new (mono_defaults.object_class, "FOO", MONO_WRAPPER_NONE);
        m = mono_mb_create_method (mb, sig, 16);
 -      return mono_marshal_get_runtime_invoke (m, FALSE);
 +      MonoMethod *invoke = mono_marshal_get_runtime_invoke (m, FALSE);
 +      mono_mb_free (mb);
 +      return invoke;
  }
  
  static MonoMethod*
@@@ -4239,7 -4231,6 +4237,7 @@@ add_wrappers (MonoAotCompile *acfg
                                if (export_name)
                                        g_hash_table_insert (acfg->export_names, wrapper, export_name);
                        }
 +                      g_free (cattr);
                }
  
                if ((method->flags & METHOD_ATTRIBUTE_PINVOKE_IMPL) ||
@@@ -4664,11 -4655,9 +4662,11 @@@ add_types_from_method_header (MonoAotCo
                for (j = 0; j < header->num_locals; ++j)
                        if (header->locals [j]->type == MONO_TYPE_GENERICINST)
                                add_generic_class_with_depth (acfg, mono_class_from_mono_type (header->locals [j]), depth + 1, "local");
 +              mono_metadata_free_mh (header);
        } else {
                mono_error_cleanup (&error); /* FIXME report the error */
        }
 +
  }
  
  /*
@@@ -5404,7 -5393,6 +5402,7 @@@ emit_and_reloc_code (MonoAotCompile *ac
                }
        }
  
 +      g_ptr_array_free (patches, TRUE);
        g_free (locs);
  }
  
@@@ -5900,8 -5888,6 +5898,8 @@@ emit_method_info (MonoAotCompile *acfg
  
        encode_patch_list (acfg, patches, n_patches, cfg->compile_llvm, first_got_offset, p, &p);
  
 +      g_ptr_array_free (patches, TRUE);
 +
        acfg->stats.info_size += p - buf;
  
        g_assert (p - buf < buf_size);
@@@ -5988,8 -5974,6 +5986,8 @@@ emit_exception_debug_info (MonoAotCompi
  
                unwind_desc = get_unwind_info_offset (acfg, encoded, encoded_len);
                encode_value (unwind_desc, p, &p);
 +
 +              g_free (encoded);
        } else {
                encode_value (jinfo->unwind_info, p, &p);
        }
@@@ -6528,7 -6512,6 +6526,7 @@@ emit_trampoline_full (MonoAotCompile *a
  
        encode_patch_list (acfg, patches, patches->len, FALSE, got_offset, p, &p);
        g_assert (p - buf < buf_size);
 +      g_ptr_array_free (patches, TRUE);
  
        sprintf (symbol, "%s%s_p", acfg->user_symbol_prefix, name);
  
                if (acfg->dwarf)
                        mono_dwarf_writer_emit_trampoline (acfg->dwarf, symbol, symbol2, NULL, NULL, code_size, unwind_ops);
        }
 +
 +      g_free (buf);
  }
  
  static G_GNUC_UNUSED void
@@@ -6667,12 -6648,10 +6665,12 @@@ emit_trampolines (MonoAotCompile *acfg
                        offset = MONO_RGCTX_SLOT_MAKE_RGCTX (i);
                        mono_arch_create_rgctx_lazy_fetch_trampoline (offset, &info, TRUE);
                        emit_trampoline (acfg, acfg->got_offset, info);
 +                      g_free (info);
  
                        offset = MONO_RGCTX_SLOT_MAKE_MRGCTX (i);
                        mono_arch_create_rgctx_lazy_fetch_trampoline (offset, &info, TRUE);
                        emit_trampoline (acfg, acfg->got_offset, info);
 +                      g_free (info);
                }
  
  #ifdef MONO_ARCH_HAVE_GENERAL_RGCTX_LAZY_FETCH_TRAMPOLINE
                        }
                }
  
 +#ifdef MONO_ARCH_HAVE_HANDLER_BLOCK_GUARD_AOT
 +              mono_arch_create_handler_block_trampoline (&info, TRUE);
 +              emit_trampoline (acfg, acfg->got_offset, info);
 +#endif
 +
  #endif /* #ifdef MONO_ARCH_HAVE_FULL_AOT_TRAMPOLINES */
  
                /* Emit trampolines which are numerous */
@@@ -7071,13 -7045,12 +7069,13 @@@ mono_aot_parse_options (const char *aot
                } else if (str_begins_with (arg, "soft-debug")) {
                        opts->soft_debug = TRUE;
                } else if (str_begins_with (arg, "gen-seq-points-file=")) {
 -                      debug_options.gen_seq_points_compact_data = TRUE;
 -                      opts->gen_seq_points_file = TRUE;
 -                      opts->gen_seq_points_file_path = g_strdup (arg + strlen ("gen-seq-points-file="));;
 +                      fprintf (stderr, "Mono Warning: aot option gen-seq-points-file= is deprecated.\n");
                } else if (str_begins_with (arg, "gen-seq-points-file")) {
 -                      debug_options.gen_seq_points_compact_data = TRUE;
 -                      opts->gen_seq_points_file = TRUE;
 +                      fprintf (stderr, "Mono Warning: aot option gen-seq-points-file is deprecated.\n");
 +              } else if (str_begins_with (arg, "msym-dir=")) {
 +                      debug_options.no_seq_points_compact_data = FALSE;
 +                      opts->gen_msym_dir = TRUE;
 +                      opts->gen_msym_dir_path = g_strdup (arg + strlen ("msym_dir="));;
                } else if (str_begins_with (arg, "direct-pinvoke")) {
                        opts->direct_pinvoke = TRUE;
                } else if (str_begins_with (arg, "direct-icalls")) {
                        printf ("    tool-prefix=\n");
                        printf ("    readonly-value=\n");
                        printf ("    soft-debug\n");
 -                      printf ("    gen-seq-points-file\n");
 +                      printf ("    msym-dir=\n");
                        printf ("    gc-maps\n");
                        printf ("    print-skipped\n");
                        printf ("    no-instances\n");
@@@ -7209,7 -7182,6 +7207,6 @@@ can_encode_method (MonoAotCompile *acfg
                        case MONO_WRAPPER_STFLD:
                        case MONO_WRAPPER_LDFLD:
                        case MONO_WRAPPER_LDFLDA:
-                       case MONO_WRAPPER_STFLD_REMOTE:
                        case MONO_WRAPPER_STELEMREF:
                        case MONO_WRAPPER_ISINST:
                        case MONO_WRAPPER_PROXY_ISINST:
@@@ -7491,6 -7463,7 +7488,6 @@@ compile_method (MonoAotCompile *acfg, M
                if (acfg->aot_opts.print_skipped_methods)
                        printf ("Skip (disabled): %s\n", mono_method_get_full_name (method));
                InterlockedIncrement (&acfg->stats.ocount);
 -              mono_destroy_compile (cfg);
                return;
        }
        cfg->method_index = index;
                if (acfg->aot_opts.print_skipped_methods)
                        printf ("Skip (abs call): %s\n", mono_method_get_full_name (method));
                InterlockedIncrement (&acfg->stats.abscount);
 -              mono_destroy_compile (cfg);
                return;
        }
  
                if (acfg->aot_opts.print_skipped_methods)
                        printf ("Skip (patches): %s\n", mono_method_get_full_name (method));
                acfg->stats.ocount++;
 -              mono_destroy_compile (cfg);
                mono_acfg_unlock (acfg);
                return;
        }
                        locals [i] = (MonoInst *)mono_mempool_alloc (acfg->mempool, sizeof (MonoInst));
                        memcpy (locals [i], cfg->locals [i], sizeof (MonoInst));
                }
 +              mono_metadata_free_mh (header);
                cfg->locals = locals;
        }
  
        /* Free some fields used by cfg to conserve memory */
 -      mono_mempool_destroy (cfg->mempool);
 -      cfg->mempool = NULL;
 -      g_free (cfg->varinfo);
 -      cfg->varinfo = NULL;
 -      g_free (cfg->vars);
 -      cfg->vars = NULL;
 -      if (cfg->rs) {
 -              mono_regstate_free (cfg->rs);
 -              cfg->rs = NULL;
 -      }
 +      mono_empty_compile (cfg);
  
        //printf ("Compile:           %s\n", mono_method_full_name (method, TRUE));
  
@@@ -8247,7 -8230,7 +8244,7 @@@ emit_llvm_file (MonoAotCompile *acfg
                opts = g_strdup ("");
        else
  #if LLVM_API_VERSION > 100
 -              opts = g_strdup ("-O2");
 +              opts = g_strdup ("-O2 -disable-tail-calls");
  #else
                opts = g_strdup ("-targetlibinfo -no-aa -basicaa -notti -instcombine -simplifycfg -inline-cost -inline -sroa -domtree -early-cse -lazy-value-info -correlated-propagation -simplifycfg -instcombine -simplifycfg -reassociate -domtree -loops -loop-simplify -lcssa -loop-rotate -licm -lcssa -loop-unswitch -instcombine -scalar-evolution -loop-simplify -lcssa -indvars -loop-idiom -loop-deletion -loop-unroll -memdep -gvn -memdep -memcpyopt -sccp -instcombine -lazy-value-info -correlated-propagation -domtree -memdep -adce -simplifycfg -instcombine -strip-dead-prototypes -domtree -verify");
  #endif
        if (acfg->aot_opts.llvm_only) {
                /* Use the stock clang from xcode */
                // FIXME: arch
 -              command = g_strdup_printf ("clang -march=x86-64 -fpic -msse -msse2 -msse3 -msse4 -O2 -fno-optimize-sibling-calls -Wno-override-module -c -o \"%s\" \"%s.opt.bc\"", acfg->llvm_ofile, acfg->tmpbasename);
 +              command = g_strdup_printf ("clang++ -fexceptions -march=x86-64 -fpic -msse -msse2 -msse3 -msse4 -O2 -fno-optimize-sibling-calls -Wno-override-module -c -o \"%s\" \"%s.opt.bc\"", acfg->llvm_ofile, acfg->tmpbasename);
  
                aot_printf (acfg, "Executing clang: %s\n", command);
                if (execute_system (command) != 0)
@@@ -8833,7 -8816,6 +8830,7 @@@ emit_extra_methods (MonoAotCompile *acf
                        g_ptr_array_add (table, new_entry);
                }
        }
 +      g_free (chain_lengths);
  
        //printf ("MAX: %d\n", max_chain_length);
  
        /* Emit the table */
        emit_aot_data (acfg, MONO_AOT_TABLE_EXTRA_METHOD_TABLE, "extra_method_table", buf, p - buf);
  
 +      g_free (buf);
 +
        /* 
         * Emit a table reverse mapping method indexes to their index in extra_method_info.
         * This is used by mono_aot_find_jit_info ().
                encode_int (info_offsets [i], p, &p);
        }
        emit_aot_data (acfg, MONO_AOT_TABLE_EXTRA_METHOD_INFO_OFFSETS, "extra_method_info_offsets", buf, p - buf);
 +
 +      g_free (buf);
 +      g_free (info_offsets);
 +      g_ptr_array_free (table, TRUE);
  }     
  
 +static void
 +generate_aotid (guint8* aotid)
 +{
 +      gpointer *rand_handle;
 +      MonoError error;
 +
 +      mono_rand_open ();
 +      rand_handle = mono_rand_init (NULL, 0);
 +
 +      mono_rand_try_get_bytes (rand_handle, aotid, 16, &error);
 +      mono_error_assert_ok (&error);
 +
 +      mono_rand_close (rand_handle);
 +}
 +
  static void
  emit_exception_info (MonoAotCompile *acfg)
  {
  
                        // By design aot-runtime decode_exception_debug_info is not able to load sequence point debug data from a file.
                        // As it is not possible to load debug data from a file its is also not possible to store it in a file.
 -                      gboolean method_seq_points_to_file = acfg->aot_opts.gen_seq_points_file &&
 +                      gboolean method_seq_points_to_file = acfg->aot_opts.gen_msym_dir &&
                                cfg->gen_seq_points && !cfg->gen_sdb_seq_points;
                        gboolean method_seq_points_to_binary = cfg->gen_seq_points && !method_seq_points_to_file;
                        
        }
  
        if (seq_points_to_file) {
 -              char *seq_points_aot_file = acfg->aot_opts.gen_seq_points_file_path ? acfg->aot_opts.gen_seq_points_file_path
 -                      : g_strdup_printf("%s%s", acfg->image->name, SEQ_POINT_AOT_EXT);
 -              mono_seq_point_data_write (&sp_data, seq_points_aot_file);
 +              char *aotid = mono_guid_to_string_minimal (acfg->image->aotid);
 +              char *dir = g_build_filename (acfg->aot_opts.gen_msym_dir_path, aotid, NULL);
 +              char *image_basename = g_path_get_basename (acfg->image->name);
 +              char *aot_file = g_strdup_printf("%s%s", image_basename, SEQ_POINT_AOT_EXT);
 +              char *aot_file_path = g_build_filename (dir, aot_file, NULL);
 +
 +              if (g_ensure_directory_exists (aot_file_path) == FALSE) {
 +                      fprintf (stderr, "AOT : failed to create msym directory: %s\n", aot_file_path);
 +                      exit (1);
 +              }
 +
 +              mono_seq_point_data_write (&sp_data, aot_file_path);
                mono_seq_point_data_free (&sp_data);
 -              g_free (seq_points_aot_file);
 +
 +              g_free (aotid);
 +              g_free (dir);
 +              g_free (image_basename);
 +              g_free (aot_file);
 +              g_free (aot_file_path);
        }
  
        acfg->stats.offsets_size += emit_offset_table (acfg, "ex_info_offsets", MONO_AOT_TABLE_EX_INFO_OFFSETS, acfg->nmethods, 10, offsets);
@@@ -9088,14 -9035,10 +9085,14 @@@ emit_class_name_table (MonoAotCompile *
                        else
                                encode_int16 (0, p, &p);
                }
 +              g_free (entry);
        }
        g_assert (p - buf <= buf_size);
 +      g_ptr_array_free (table, TRUE);
  
        emit_aot_data (acfg, MONO_AOT_TABLE_CLASS_NAME, "class_name_table", buf, p - buf);
 +
 +      g_free (buf);
  }
  
  static void
@@@ -9411,8 -9354,6 +9408,8 @@@ init_aot_file_info (MonoAotCompile *acf
        info->nshared_got_entries = acfg->nshared_got_entries;
        for (i = 0; i < MONO_AOT_TRAMP_NUM; ++i)
                info->tramp_page_code_offsets [i] = acfg->tramp_page_code_offsets [i];
 +
 +      memcpy(&info->aotid, acfg->image->aotid, 16);
  }
  
  static void
@@@ -9545,8 -9486,6 +9542,8 @@@ emit_aot_file_info (MonoAotCompile *acf
        for (i = 0; i < MONO_AOT_TRAMP_NUM; ++i)
                emit_int32 (acfg, info->tramp_page_code_offsets [i]);
  
 +      emit_bytes (acfg, info->aotid, 16);
 +
        if (acfg->aot_opts.static_link) {
                emit_global_inner (acfg, acfg->static_linking_symbol, FALSE);
                emit_alignment (acfg, sizeof (gpointer));
@@@ -9965,17 -9904,9 +9962,17 @@@ compile_asm (MonoAotCompile *acfg
                wrap_path (g_strdup_printf ("%s.o", acfg->tmpfname)), ld_flags);
  #else
        // Default (linux)
 -      command = g_strdup_printf ("\"%sld\" %s -shared -o %s %s %s %s", tool_prefix, LD_OPTIONS,
 +      char *args = g_strdup_printf ("%s %s -shared -o %s %s %s %s", tool_prefix, LD_OPTIONS,
                wrap_path (tmp_outfile_name), wrap_path (llvm_ofile),
                wrap_path (g_strdup_printf ("%s.o", acfg->tmpfname)), ld_flags);
 +
 +      if (acfg->llvm) {
 +              command = g_strdup_printf ("clang++ %s", args);
 +      } else {
 +              command = g_strdup_printf ("\"%sld\" %s", tool_prefix, args);
 +      }
 +      g_free (args);
 +
  #endif
        aot_printf (acfg, "Executing the native linker: %s\n", command);
        if (execute_system (command) != 0) {
         * gas generates 'mapping symbols' each time code and data is mixed, which 
         * happens a lot in emit_and_reloc_code (), so we need to get rid of them.
         */
 -      command = g_strdup_printf ("\"%sstrip\" --strip-symbol=\\$a --strip-symbol=\\$d %s", tool_prefix, tmp_outfile_name);
 +      command = g_strdup_printf ("\"%sstrip\" --strip-symbol=\\$a --strip-symbol=\\$d %s", wrap_path(tool_prefix), wrap_path(tmp_outfile_name));
        aot_printf (acfg, "Stripping the binary: %s\n", command);
        if (execute_system (command) != 0) {
                g_free (tmp_outfile_name);
@@@ -10114,10 -10045,8 +10111,10 @@@ acfg_free (MonoAotCompile *acfg
        mono_img_writer_destroy (acfg->w);
        for (i = 0; i < acfg->nmethods; ++i)
                if (acfg->cfgs [i])
 -                      g_free (acfg->cfgs [i]);
 +                      mono_destroy_compile (acfg->cfgs [i]);
 +
        g_free (acfg->cfgs);
 +
        g_free (acfg->static_linking_symbol);
        g_free (acfg->got_symbol);
        g_free (acfg->plt_symbol);
@@@ -10447,12 -10376,6 +10444,12 @@@ mono_compile_assembly (MonoAssembly *as
                mono_set_generic_sharing_vt_supported (TRUE);
  
        aot_printf (acfg, "Mono Ahead of Time compiler - compiling assembly %s\n", image->name);
 +
 +      generate_aotid ((guint8*) &acfg->image->aotid);
 +
 +      char *aotid = mono_guid_to_string (acfg->image->aotid);
 +      aot_printf (acfg, "AOTID %s\n", aotid);
 +      g_free (aotid);
  
  #ifndef MONO_ARCH_HAVE_FULL_AOT_TRAMPOLINES
        if (mono_aot_mode_is_full (&acfg->aot_opts)) {
diff --combined mono/mini/aot-runtime.c
index 14fcfbabc056fbde074805348a4d92c75fdb1133,58234e6440b718e3454deab26b2cbcaa5a6573fd..2f818c6821cef511e12f349739f013f8de8e7116
@@@ -922,9 -922,6 +922,6 @@@ decode_method_ref_with_target (MonoAotM
                        }
                        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);
@@@ -1782,6 -1779,17 +1779,6 @@@ check_usable (MonoAssembly *assembly, M
                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;
@@@ -2002,9 -2010,6 +1999,9 @@@ load_aot_module (MonoAssembly *assembly
                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);
@@@ -5834,7 -5839,7 +5831,7 @@@ mono_aot_get_method (MonoDomain *domain
  
  gpointer
  mono_aot_get_method_checked (MonoDomain *domain,
 -                                                       MonoMethod *method, MonoError *error);
 +                                                       MonoMethod *method, MonoError *error)
  {
        mono_error_init (error);
        return NULL;
diff --combined mono/mini/mini-runtime.c
index dfce66481ea8db4cef11787384c1f03ad25ac634,c087b6d6f246e28ef880a11c6f1ca5dffc0b855f..e1918076a8a97099a952d461b43b0d7e6f9fdfad
@@@ -1514,7 -1514,7 +1514,7 @@@ mono_resolve_patch_target (MonoMethod *
                handle = mono_ldtoken_checked (patch_info->data.token->image,
                                                           patch_info->data.token->token, &handle_class, patch_info->data.token->has_context ? &patch_info->data.token->context : NULL, error);
                if (!mono_error_ok (error))
 -                      g_error ("Could not patch ldtoken due to %s", mono_error_get_message (error));
 +                      return NULL;
                mono_class_init (handle_class);
                mono_class_init (mono_class_from_mono_type ((MonoType *)handle));
  
@@@ -1810,10 -1810,6 +1810,10 @@@ mono_jit_compile_method_with_opt (MonoM
  
        mono_error_init (error);
  
 +      if (mono_llvm_only)
 +              /* Should be handled by the caller */
 +              g_assert (!(method->iflags & METHOD_IMPL_ATTRIBUTE_SYNCHRONIZED));
 +
        /*
         * ICALL wrappers are handled specially, since there is only one copy of them
         * shared by all appdomains.
@@@ -2779,9 -2775,6 +2779,9 @@@ MONO_SIG_HANDLER_FUNC (, mono_sigill_si
        MonoException *exc;
        MONO_SIG_HANDLER_GET_CONTEXT;
  
 +      if (mono_runtime_get_no_exec ())
 +              exit (1);
 +
        MONO_ENTER_GC_UNSAFE_UNBALANCED;
  
        exc = mono_get_exception_execution_engine ("SIGILL");
@@@ -3056,17 -3049,6 +3056,17 @@@ mini_init_delegate (MonoDelegate *del
                del->extra_arg = mini_get_delegate_arg (del->method, del->method_ptr);
  }
  
 +char*
 +mono_get_delegate_virtual_invoke_impl_name (gboolean load_imt_reg, int offset)
 +{
 +      int abs_offset;
 +
 +      abs_offset = offset;
 +      if (abs_offset < 0)
 +              abs_offset = - abs_offset;
 +      return g_strdup_printf ("delegate_virtual_invoke%s_%s%d", load_imt_reg ? "_imt" : "", offset < 0 ? "m_" : "", abs_offset / SIZEOF_VOID_P);
 +}
 +
  gpointer
  mono_get_delegate_virtual_invoke_impl (MonoMethodSignature *sig, MonoMethod *method)
  {
  
        /* FIXME Support more cases */
        if (mono_aot_only) {
 -              char tramp_name [256];
 -              const char *imt = load_imt_reg ? "_imt" : "";
 -              int ind = (load_imt_reg ? (-offset) : offset) / SIZEOF_VOID_P;
 -
 -              sprintf (tramp_name, "delegate_virtual_invoke%s_%d", imt, ind);
 -              cache [idx] = (guint8 *)mono_aot_get_trampoline (tramp_name);
 +              cache [idx] = (guint8 *)mono_aot_get_trampoline (mono_get_delegate_virtual_invoke_impl_name (load_imt_reg, offset));
                g_assert (cache [idx]);
        } else {
                cache [idx] = (guint8 *)mono_arch_get_delegate_virtual_invoke_impl (sig, method, offset, load_imt_reg);
@@@ -3166,9 -3153,7 +3166,9 @@@ mini_parse_debug_option (const char *op
        else if (!strcmp (option, "gen-seq-points"))
                debug_options.gen_sdb_seq_points = TRUE;
        else if (!strcmp (option, "gen-compact-seq-points"))
 -              debug_options.gen_seq_points_compact_data = TRUE;
 +              fprintf (stderr, "Mono Warning: option gen-compact-seq-points is deprecated.\n");
 +      else if (!strcmp (option, "no-compact-seq-points"))
 +              debug_options.no_seq_points_compact_data = TRUE;
        else if (!strcmp (option, "single-imm-size"))
                debug_options.single_imm_size = TRUE;
        else if (!strcmp (option, "init-stacks"))
@@@ -3213,7 -3198,7 +3213,7 @@@ mini_parse_debug_options (void
  
                if (!mini_parse_debug_option (arg)) {
                        fprintf (stderr, "Invalid option for the MONO_DEBUG env variable: %s\n", arg);
 -                      fprintf (stderr, "Available options: 'handle-sigint', 'keep-delegates', 'reverse-pinvoke-exceptions', 'collect-pagefault-stats', 'break-on-unverified', 'no-gdb-backtrace', 'suspend-on-sigsegv', 'suspend-on-exception', 'suspend-on-unhandled', 'dont-free-domains', 'dyn-runtime-invoke', 'gdb', 'explicit-null-checks', 'gen-seq-points', 'gen-compact-seq-points', 'single-imm-size', 'init-stacks', 'casts', 'soft-breakpoints', 'check-pinvoke-callconv', 'arm-use-fallback-tls', 'debug-domain-unload', 'partial-sharing', 'align-small-structs', 'native-debugger-break'\n");
 +                      fprintf (stderr, "Available options: 'handle-sigint', 'keep-delegates', 'reverse-pinvoke-exceptions', 'collect-pagefault-stats', 'break-on-unverified', 'no-gdb-backtrace', 'suspend-on-sigsegv', 'suspend-on-exception', 'suspend-on-unhandled', 'dont-free-domains', 'dyn-runtime-invoke', 'gdb', 'explicit-null-checks', 'gen-seq-points', 'no-compact-seq-points', 'single-imm-size', 'init-stacks', 'casts', 'soft-breakpoints', 'check-pinvoke-callconv', 'arm-use-fallback-tls', 'debug-domain-unload', 'partial-sharing', 'align-small-structs', 'native-debugger-break'\n");
                        exit (1);
                }
        }
@@@ -3695,7 -3680,9 +3695,7 @@@ mini_init (const char *filename, const 
        mono_simd_intrinsics_init ();
  #endif
  
 -#if MONO_SUPPORT_TASKLETS
        mono_tasklets_init ();
 -#endif
  
        register_trampolines (domain);
  
@@@ -3776,9 -3763,6 +3776,6 @@@ register_icalls (void
        register_icall (mono_thread_get_undeniable_exception, "mono_thread_get_undeniable_exception", "object", FALSE);
        register_icall (mono_thread_interruption_checkpoint, "mono_thread_interruption_checkpoint", "object", FALSE);
        register_icall (mono_thread_force_interruption_checkpoint_noraise, "mono_thread_force_interruption_checkpoint_noraise", "object", FALSE);
- #ifndef DISABLE_REMOTING
-       register_icall (mono_store_remote_field_new_icall, "mono_store_remote_field_new_icall", "void object ptr ptr object", FALSE);
- #endif
  
  #if defined(__native_client__) || defined(__native_client_codegen__)
        register_icall (mono_nacl_gc, "mono_nacl_gc", "void", FALSE);
index 12be87a1fab52deee3d143b7202cbf665e572f47,c10102b1ef780acde5cd5abc9dbf49b4c6dd6d22..8c1fe23297bffd8ba8b6ce8c9a6f43e62fff2b78
@@@ -1304,19 -1304,15 +1304,19 @@@ gpointe
  mono_create_handler_block_trampoline (void)
  {
        static gpointer code;
 -      if (code) {
 +
 +      if (code)
 +              return code;
 +
 +      if (mono_aot_only) {
 +              gpointer tmp = mono_aot_get_trampoline ("handler_block_trampoline");
 +              g_assert (tmp);
                mono_memory_barrier ();
 +              code = tmp;
                return code;
        }
  
 -      g_assert (!mono_aot_only);
 -
        mono_trampolines_lock ();
 -
        if (!code) {
                MonoTrampInfo *info;
                gpointer tmp;
@@@ -1513,17 -1509,13 +1513,16 @@@ mono_create_jit_trampoline (MonoDomain 
        mono_error_init (error);
  
        if (mono_aot_only) {
 +              if (mono_llvm_only && method->iflags & METHOD_IMPL_ATTRIBUTE_SYNCHRONIZED)
 +                      method = mono_marshal_get_synchronized_wrapper (method);
 +
                /* Avoid creating trampolines if possible */
                gpointer code = mono_jit_find_compiled_method (domain, method);
                
                if (code)
                        return code;
                if (mono_llvm_only) {
-                       if (method->wrapper_type == MONO_WRAPPER_PROXY_ISINST ||
-                               method->wrapper_type == MONO_WRAPPER_STFLD_REMOTE)
+                       if (method->wrapper_type == MONO_WRAPPER_PROXY_ISINST)
                                /* These wrappers are not generated */
                                return method_not_found;
                        /* Methods are lazily initialized on first call, so this can't lead recursion */