Fix the generation of stelemref wrappers in full-aot mode. Some wrappers were not...
authorZoltan Varga <vargaz@gmail.com>
Sat, 2 Mar 2013 00:27:37 +0000 (01:27 +0100)
committerZoltan Varga <vargaz@gmail.com>
Sat, 2 Mar 2013 00:27:46 +0000 (01:27 +0100)
mono/metadata/marshal.c
mono/metadata/marshal.h
mono/mini/aot-compiler.c

index 865aa9270cb6a5767ba3b38120b51b5cc6d3c4fb..103759cfd827f7f5c87de198f1754e06385b8619 100644 (file)
@@ -10300,14 +10300,13 @@ record_slot_vstore (MonoObject *array, size_t index, MonoObject *value)
  *     - Maybe mve some MonoClass field into the vtable to reduce the number of loads
  *     - Add a case for arrays of arrays.
  */
-MonoMethod*
-mono_marshal_get_virtual_stelemref (MonoClass *array_class)
+static MonoMethod*
+get_virtual_stelemref_wrapper (int kind)
 {
        static MonoMethod *cached_methods [STELEMREF_KIND_COUNT] = { NULL }; /*object iface sealed regular*/
        static MonoMethodSignature *signature;
        MonoMethodBuilder *mb;
        MonoMethod *res;
-       int kind;
        char *name;
        const char *param_names [16];
        guint32 b1, b2, b3;
@@ -10315,9 +10314,6 @@ mono_marshal_get_virtual_stelemref (MonoClass *array_class)
        int array_slot_addr;
        WrapperInfo *info;
 
-       g_assert (array_class->rank == 1);
-       kind = get_virtual_stelemref_kind (array_class->element_class);
-
        if (cached_methods [kind])
                return cached_methods [kind];
 
@@ -10685,6 +10681,30 @@ mono_marshal_get_virtual_stelemref (MonoClass *array_class)
        return cached_methods [kind];
 }
 
+MonoMethod*
+mono_marshal_get_virtual_stelemref (MonoClass *array_class)
+{
+       int kind;
+
+       g_assert (array_class->rank == 1);
+       kind = get_virtual_stelemref_kind (array_class->element_class);
+
+       return get_virtual_stelemref_wrapper (kind);
+}
+
+MonoMethod**
+mono_marshal_get_virtual_stelemref_wrappers (int *nwrappers)
+{
+       MonoMethod **res;
+       int i;
+
+       *nwrappers = STELEMREF_KIND_COUNT;
+       res = g_malloc0 (STELEMREF_KIND_COUNT * sizeof (MonoMethod*));
+       for (i = 0; i < STELEMREF_KIND_COUNT; ++i)
+               res [i] = get_virtual_stelemref_wrapper (i);
+       return res;
+}
+
 /*
  * The wrapper info for the wrapper is a WrapperInfo structure.
  */
index 60cdf599184474959582910a161751fa5f1c3b1e..a01de88ce95fe3eab25776b8705c975d5aa72342 100644 (file)
@@ -335,6 +335,9 @@ mono_marshal_get_stelemref (void) MONO_INTERNAL;
 MonoMethod*
 mono_marshal_get_virtual_stelemref (MonoClass *array_class) MONO_INTERNAL;
 
+MonoMethod**
+mono_marshal_get_virtual_stelemref_wrappers (int *nwrappers) MONO_INTERNAL;
+
 MonoMethod*
 mono_marshal_get_array_address (int rank, int elem_size) MONO_INTERNAL;
 
index 61af478f6f248087fb9b12205e35aebd7bbd3508..d5ce6cfb80bf286c18bac9454a05552013909cb7 100644 (file)
@@ -3281,16 +3281,14 @@ add_wrappers (MonoAotCompile *acfg)
 #endif
 
                /* Stelemref wrappers */
-               /* There is only a constant number of these, iterating over all types should handle them all */
-               for (i = 0; i < acfg->image->tables [MONO_TABLE_TYPEDEF].rows; ++i) {
-                       MonoClass *klass;
-               
-                       token = MONO_TOKEN_TYPE_DEF | (i + 1);
-                       klass = mono_class_get (acfg->image, token);
-                       if (klass)
-                               add_method (acfg, mono_marshal_get_virtual_stelemref (mono_array_class_get (klass, 1)));
-                       else
-                               mono_loader_clear_error ();
+               {
+                       MonoMethod **wrappers;
+                       int nwrappers;
+
+                       wrappers = mono_marshal_get_virtual_stelemref_wrappers (&nwrappers);
+                       for (i = 0; i < nwrappers; ++i)
+                               add_method (acfg, wrappers [i]);
+                       g_free (wrappers);
                }
 
                /* castclass_with_check wrapper */