[aot] Add support for references to GENERIC_ARRAY_HELPER wrappers. (#42580)
authormonojenkins <jo.shields+jenkins@xamarin.com>
Fri, 25 Sep 2020 00:42:13 +0000 (20:42 -0400)
committerGitHub <noreply@github.com>
Fri, 25 Sep 2020 00:42:13 +0000 (20:42 -0400)
The testcase only fails when AOTed using --aot=soft-debug.

Fixes https://github.com/mono/mono/issues/20421.

Co-authored-by: vargaz <vargaz@users.noreply.github.com>
src/mono/mono/metadata/marshal.c
src/mono/mono/metadata/marshal.h
src/mono/mono/mini/aot-compiler.c
src/mono/mono/mini/aot-runtime.c
src/mono/mono/mini/aot-tests.cs

index 69f2db6..71f59b7 100644 (file)
@@ -6559,6 +6559,9 @@ mono_marshal_get_generic_array_helper (MonoClass *klass, const gchar *name, Mono
        get_marshal_cb ()->mb_skip_visibility (mb);
 
        info = mono_wrapper_info_create (mb, WRAPPER_SUBTYPE_GENERIC_ARRAY_HELPER);
+       /* Assume name is constant/not freed */
+       info->d.generic_array_helper.name = name;
+       info->d.generic_array_helper.klass = klass;
        info->d.generic_array_helper.method = method;
        res = mono_mb_create (mb, csig, csig->param_count + 16, info);
 
index 18e2373..13b3ec9 100644 (file)
@@ -171,6 +171,8 @@ typedef struct {
 } SynchronizedInnerWrapperInfo;
 
 typedef struct {
+       MonoClass *klass;
+       const char *name;
        MonoMethod *method;
 } GenericArrayHelperWrapperInfo;
 
index 5ca434f..98fd573 100644 (file)
@@ -3723,6 +3723,12 @@ encode_method_ref (MonoAotCompile *acfg, MonoMethod *method, guint8 *buf, guint8
                                encode_value (info->d.element_addr.elem_size, p, &p);
                        } else if (info->subtype == WRAPPER_SUBTYPE_STRING_CTOR) {
                                encode_method_ref (acfg, info->d.string_ctor.method, p, &p);
+                       } else if (info->subtype == WRAPPER_SUBTYPE_GENERIC_ARRAY_HELPER) {
+                               encode_klass_ref (acfg, info->d.generic_array_helper.klass, p, &p);
+                               encode_method_ref (acfg, info->d.generic_array_helper.method, p, &p);
+                               int len = strlen (info->d.generic_array_helper.name);
+                               guint32 idx = add_to_blob (acfg, (guint8*)info->d.generic_array_helper.name, len + 1);
+                               encode_value (idx, p, &p);
                        } else {
                                g_assert_not_reached ();
                        }
index 27d27ad..ad43071 100644 (file)
@@ -1156,6 +1156,16 @@ decode_method_ref_with_target (MonoAotModule *module, MethodRef *ref, MonoMethod
                                        ref->method = target;
                                else
                                        return FALSE;
+                       } else if (subtype == WRAPPER_SUBTYPE_GENERIC_ARRAY_HELPER) {
+                               MonoClass *klass = decode_klass_ref (module, p, &p, error);
+                               if (!klass)
+                                       return FALSE;
+                               MonoMethod *m = decode_resolve_method_ref (module, p, &p, error);
+                               if (!m)
+                                       return FALSE;
+                               int name_idx = decode_value (p, &p);
+                               const char *name = (const char*)module->blob + name_idx;
+                               ref->method = mono_marshal_get_generic_array_helper (klass, name, m);
                        }
                        break;
                }
index e3ee879..a468d00 100644 (file)
@@ -709,4 +709,17 @@ class Tests
                return 0;
        }
 #endif
+
+       struct DummyStruct {
+       }
+
+       [MethodImplAttribute (MethodImplOptions.NoInlining)]
+       static void array_ienumerable<T1, T> (T t) where T: IEnumerable<T1> {
+               var e = t.GetEnumerator ();
+       }
+
+       public static int test_0_array_ienumerable_constrained () {
+               array_ienumerable<DummyStruct, DummyStruct[]> (new DummyStruct [0]);
+               return 0;
+       }
 }