2004-05-11 Zoltan Varga <vargaz@freemail.hu>
[mono.git] / mono / metadata / reflection.c
index 93936aee3c61ede8fbfbe6a0eab49379db5b0f1c..d7c958f1bd2442d782558548316f59bfe94b7882 100644 (file)
@@ -738,6 +738,10 @@ encode_locals (MonoDynamicImage *assembly, MonoReflectionILGen *ilgen)
        mono_metadata_encode_value (nl, p, &p);
        for (i = 0; i < nl; ++i) {
                MonoReflectionLocalBuilder *lb = mono_array_get (ilgen->locals, MonoReflectionLocalBuilder*, i);
+               
+               if (lb->is_pinned)
+                       mono_metadata_encode_value (MONO_TYPE_PINNED, p, &p);
+               
                encode_reflection_type (assembly, lb->type, p, &p);
        }
        g_assert (p - buf < size);
@@ -1378,11 +1382,11 @@ type_get_fully_qualified_name (MonoType *type) {
        klass = my_mono_class_from_mono_type (type);
        ta = klass->image->assembly;
 
-       /* missing public key */
-       result = g_strdup_printf ("%s, %s, Version=%d.%d.%d.%d, Culture=%s",
+       result = g_strdup_printf ("%s, %s, Version=%d.%d.%d.%d, Culture=%s, PublicKeyToken=%s",
                name, ta->aname.name,
                ta->aname.major, ta->aname.minor, ta->aname.build, ta->aname.revision,
-               ta->aname.culture && *ta->aname.culture? ta->aname.culture: "neutral");
+               ta->aname.culture && *ta->aname.culture? ta->aname.culture: "neutral",
+               ta->aname.public_tok_value ? ta->aname.public_tok_value : "null");
        g_free (name);
        return result;
 }
@@ -1547,7 +1551,16 @@ encode_marshal_blob (MonoDynamicImage *assembly, MonoReflectionMarshal *minfo) {
                mono_metadata_encode_value (minfo->type, p, &p);
                mono_metadata_encode_value (minfo->count, p, &p);
                break;
-               /* FIXME: handle ARRAY and other unmanaged types that need extra info */
+       case MONO_NATIVE_LPARRAY:
+               mono_metadata_encode_value (minfo->type, p, &p);
+               if (minfo->eltype || (minfo->count > 0)) {
+                       mono_metadata_encode_value (minfo->eltype, p, &p);
+                       if (minfo->count > 0) {
+                               mono_metadata_encode_value (0, p, &p);
+                               mono_metadata_encode_value (minfo->count, p, &p);
+                       }
+               }
+               break;
        case MONO_NATIVE_CUSTOM:
                mono_metadata_encode_value (minfo->type, p, &p);
                if (minfo->guid) {
@@ -1835,6 +1848,75 @@ mono_image_get_event_info (MonoReflectionEventBuilder *eb, MonoDynamicImage *ass
        }
 }
 
+static void
+encode_new_constraint (MonoDynamicImage *assembly, guint32 owner)
+{
+       static MonoClass *NewConstraintAttr;
+       static MonoMethod *NewConstraintAttr_ctor;
+       MonoDynamicTable *table;
+       guint32 *values;
+       guint32 token, type;
+       char blob_size [4] = { 0x01, 0x00, 0x00, 0x00 };
+       char *buf, *p;
+
+       if (!NewConstraintAttr)
+               NewConstraintAttr = mono_class_from_name (
+                       mono_defaults.corlib, "System.Runtime.CompilerServices",
+                       "NewConstraintAttribute");
+       g_assert (NewConstraintAttr);
+
+       if (!NewConstraintAttr_ctor) {
+               int i;
+
+               for (i = 0; i < NewConstraintAttr->method.count; i++) {
+                       MonoMethod *m = NewConstraintAttr->methods [i];
+
+                       if (strcmp (m->name, ".ctor"))
+                               continue;
+
+                       NewConstraintAttr_ctor = m;
+                       break;
+               }
+
+               g_assert (NewConstraintAttr_ctor);
+       }
+
+       table = &assembly->tables [MONO_TABLE_CUSTOMATTRIBUTE];
+       table->rows += 1;
+       alloc_table (table, table->rows);
+
+       values = table->values + table->next_idx * MONO_CUSTOM_ATTR_SIZE;
+       owner <<= CUSTOM_ATTR_BITS;
+       owner |= CUSTOM_ATTR_GENERICPAR;
+       values [MONO_CUSTOM_ATTR_PARENT] = owner;
+
+       token = mono_image_get_methodref_token (assembly, NewConstraintAttr_ctor);
+
+       type = mono_metadata_token_index (token);
+       type <<= CUSTOM_ATTR_TYPE_BITS;
+       switch (mono_metadata_token_table (token)) {
+       case MONO_TABLE_METHOD:
+               type |= CUSTOM_ATTR_TYPE_METHODDEF;
+               break;
+       case MONO_TABLE_MEMBERREF:
+               type |= CUSTOM_ATTR_TYPE_MEMBERREF;
+               break;
+       default:
+               g_warning ("got wrong token in custom attr");
+               return;
+       }
+       values [MONO_CUSTOM_ATTR_TYPE] = type;
+
+       buf = p = g_malloc (1);
+       mono_metadata_encode_value (4, p, &p);
+       g_assert (p-buf == 1);
+
+       values [MONO_CUSTOM_ATTR_VALUE] = add_to_blob_cached (assembly, buf, 1, blob_size, 4);
+
+       values += MONO_CUSTOM_ATTR_SIZE;
+       ++table->next_idx;
+}
+
 static void
 encode_constraints (MonoReflectionGenericParam *gparam, guint32 owner, MonoDynamicImage *assembly)
 {
@@ -1844,19 +1926,36 @@ encode_constraints (MonoReflectionGenericParam *gparam, guint32 owner, MonoDynam
        guint32 table_idx;
 
        table = &assembly->tables [MONO_TABLE_GENERICPARAMCONSTRAINT];
-       num_constraints = gparam ? mono_array_length (gparam->constraints) : 0;
+       num_constraints = gparam->iface_constraints ?
+               mono_array_length (gparam->iface_constraints) : 0;
        table->rows += num_constraints;
+       if (gparam->base_type)
+               table->rows++;
        alloc_table (table, table->rows);
 
+       if (gparam->base_type) {
+               table_idx = table->next_idx ++;
+               values = table->values + table_idx * MONO_GENPARCONSTRAINT_SIZE;
+
+               values [MONO_GENPARCONSTRAINT_GENERICPAR] = owner;
+               values [MONO_GENPARCONSTRAINT_CONSTRAINT] = mono_image_typedef_or_ref (
+                       assembly, gparam->base_type->type);
+       }
+
        for (i = 0; i < num_constraints; i++) {
-               MonoReflectionType *constraint = mono_array_get (gparam->constraints, gpointer, i);
+               MonoReflectionType *constraint = mono_array_get (
+                       gparam->iface_constraints, gpointer, i);
 
                table_idx = table->next_idx ++;
                values = table->values + table_idx * MONO_GENPARCONSTRAINT_SIZE;
 
                values [MONO_GENPARCONSTRAINT_GENERICPAR] = owner;
-               values [MONO_GENPARCONSTRAINT_CONSTRAINT] = mono_image_typedef_or_ref (assembly, constraint->type);
+               values [MONO_GENPARCONSTRAINT_CONSTRAINT] = mono_image_typedef_or_ref (
+                       assembly, constraint->type);
        }
+
+       if (gparam->has_ctor_constraint)
+               encode_new_constraint (assembly, owner);
 }
 
 static void
@@ -1874,14 +1973,17 @@ mono_image_get_generic_param_info (MonoReflectionGenericParam *gparam, guint32 o
        param = gparam->type.type->data.generic_param;
 
        values [MONO_GENERICPARAM_OWNER] = owner;
-       values [MONO_GENERICPARAM_FLAGS] = param->flags;
+       if (gparam->has_value_type)
+               values [MONO_GENERICPARAM_FLAGS] = 0x18;
+       else if (gparam->has_reference_type)
+               values [MONO_GENERICPARAM_FLAGS] = 0x04;
+       else
+               values [MONO_GENERICPARAM_FLAGS] = 0x00;
        values [MONO_GENERICPARAM_NUMBER] = param->num;
        values [MONO_GENERICPARAM_NAME] = string_heap_insert (&assembly->sheap, param->name);
        values [MONO_GENERICPARAM_KIND] = 0;
-       values [MONO_GENERICPARAM_DEPRECATED_CONSTRAINT] = 0;
 
-       if (gparam->constraints)
-               encode_constraints (gparam, table_idx, assembly);
+       encode_constraints (gparam, table_idx, assembly);
 }
 
 static guint32
@@ -1926,10 +2028,7 @@ resolution_scope_from_image (MonoDynamicImage *assembly, MonoImage *image)
        table->rows ++;
        alloc_table (table, table->rows);
        values = table->values + token * MONO_ASSEMBLYREF_SIZE;
-       if (strcmp ("corlib", image->assembly_name) == 0)
-               values [MONO_ASSEMBLYREF_NAME] = string_heap_insert (&assembly->sheap, "mscorlib");
-       else
-               values [MONO_ASSEMBLYREF_NAME] = string_heap_insert (&assembly->sheap, image->assembly_name);
+       values [MONO_ASSEMBLYREF_NAME] = string_heap_insert (&assembly->sheap, image->assembly_name);
        values [MONO_ASSEMBLYREF_MAJOR_VERSION] = cols [MONO_ASSEMBLY_MAJOR_VERSION];
        values [MONO_ASSEMBLYREF_MINOR_VERSION] = cols [MONO_ASSEMBLY_MINOR_VERSION];
        values [MONO_ASSEMBLYREF_BUILD_NUMBER] = cols [MONO_ASSEMBLY_BUILD_NUMBER];
@@ -1938,6 +2037,11 @@ resolution_scope_from_image (MonoDynamicImage *assembly, MonoImage *image)
        values [MONO_ASSEMBLYREF_CULTURE] = 0;
        values [MONO_ASSEMBLYREF_HASH_VALUE] = 0;
 
+       if (strcmp ("", image->assembly->aname.culture)) {
+               values [MONO_ASSEMBLYREF_CULTURE] = string_heap_insert (&assembly->sheap,
+                               image->assembly->aname.culture);
+       }
+
        if ((pubkey = mono_image_get_public_key (image, &publen))) {
                guchar pubtoken [9];
                pubtoken [0] = 8;
@@ -1952,8 +2056,7 @@ resolution_scope_from_image (MonoDynamicImage *assembly, MonoImage *image)
                 * recognized by ms, yuck!
                 * FIXME: need to add more assembly names, as needed.
                 */
-               if (strcmp (image->assembly_name, "corlib") == 0 ||
-                               strcmp (image->assembly_name, "mscorlib") == 0 ||
+               if (strcmp (image->assembly_name, "mscorlib") == 0 ||
                                strcmp (image->assembly_name, "System") == 0 ||
                                strcmp (image->assembly_name, "System.Runtime.Remoting") == 0 ||
                                strcmp (image->assembly_name, "System.Xml") == 0 ||
@@ -2340,6 +2443,16 @@ create_generic_typespec (MonoDynamicImage *assembly, MonoReflectionTypeBuilder *
        char *b = blob_size;
        int count, i;
 
+       /*
+        * We're creating a TypeSpec for the TypeBuilder of a generic type declaration,
+        * ie. what we'd normally use as the generic type in a TypeSpec signature.
+        * Because of this, we must not insert it into the `typeref' hash table.
+        */
+
+       token = GPOINTER_TO_UINT (g_hash_table_lookup (assembly->typespec, tb->type.type));
+       if (token)
+               return token;
+
        g_assert (tb->generic_params);
        klass = mono_class_from_mono_type (tb->type.type);
 
@@ -2367,7 +2480,7 @@ create_generic_typespec (MonoDynamicImage *assembly, MonoReflectionTypeBuilder *
        }
 
        token = TYPEDEFORREF_TYPESPEC | (table->next_idx << TYPEDEFORREF_BITS);
-       g_hash_table_insert (assembly->typeref, tb->type.type, GUINT_TO_POINTER(token));
+       g_hash_table_insert (assembly->typespec, tb->type.type, GUINT_TO_POINTER(token));
        table->next_idx ++;
        return token;
 }
@@ -2381,6 +2494,10 @@ mono_image_get_generic_field_token (MonoDynamicImage *assembly, MonoReflectionFi
        guint32 token, pclass, parent, sig;
        gchar *name;
 
+       token = GPOINTER_TO_UINT (g_hash_table_lookup (assembly->handleref, fb));
+       if (token)
+               return token;
+
        klass = mono_class_from_mono_type (fb->typeb->type);
        name = mono_string_to_utf8 (fb->name);
 
@@ -2404,7 +2521,7 @@ mono_image_get_generic_field_token (MonoDynamicImage *assembly, MonoReflectionFi
 
        token = MONO_TOKEN_MEMBER_REF | table->next_idx;
        table->next_idx ++;
-
+       g_hash_table_insert (assembly->handleref, fb, GUINT_TO_POINTER(token));
        return token;
 }
 
@@ -3123,8 +3240,17 @@ build_compressed_metadata (MonoDynamicImage *assembly)
        int32val = (guint32*)p;
        *int32val = GUINT32_TO_LE (0); /* reserved */
        p += 4;
-       *p++ = 1; /* version */
-       *p++ = 0;
+
+       if ((assembly->tables [MONO_TABLE_GENERICPARAM].rows > 0) ||
+           (assembly->tables [MONO_TABLE_METHODSPEC].rows > 0) ||
+           (assembly->tables [MONO_TABLE_GENERICPARAMCONSTRAINT].rows > 0)) {
+               *p++ = 1; /* version */
+               *p++ = 1;
+       } else {
+               *p++ = 1; /* version */
+               *p++ = 0;
+       }
+
        if (meta->idx_string_wide)
                *p |= 0x01;
        if (meta->idx_guid_wide)
@@ -3747,7 +3873,7 @@ mono_image_create_token (MonoDynamicImage *assembly, MonoObject *obj)
                token = tb->table_idx | MONO_TOKEN_TYPE_DEF;
        }
        else if (strcmp (klass->name, "MonoType") == 0 ||
-                strcmp (klass->name, "MonoGenericParam") == 0) {
+                strcmp (klass->name, "GenericTypeParameterBuilder") == 0) {
                MonoReflectionType *tb = (MonoReflectionType *)obj;
                token = mono_metadata_token_from_dor (
                        mono_image_typedef_or_ref (assembly, tb->type));
@@ -3859,6 +3985,7 @@ create_dynamic_mono_image (MonoDynamicAssembly *assembly,
        image->method_aux_hash = mono_g_hash_table_new (NULL, NULL);
        image->handleref = g_hash_table_new (NULL, NULL);
        image->tokens = mono_g_hash_table_new (NULL, NULL);
+       image->typespec = g_hash_table_new ((GHashFunc)mono_metadata_type_hash, (GCompareFunc)mono_metadata_type_equal);
        image->typeref = g_hash_table_new ((GHashFunc)mono_metadata_type_hash, (GCompareFunc)mono_metadata_type_equal);
        image->blob_cache = mono_g_hash_table_new ((GHashFunc)mono_blob_entry_hash, (GCompareFunc)mono_blob_entry_equal);
 
@@ -4828,6 +4955,8 @@ mono_generic_inst_get_object (MonoDomain *domain, MonoType *geninst)
        ginst = geninst->data.generic_inst;
        gklass = mono_class_from_mono_type (ginst->generic_type);
 
+       mono_class_init (ginst->klass);
+
        res = (MonoReflectionGenericInst *) mono_object_new (domain, System_Reflection_MonoGenericInst);
 
        res->type.type = geninst;
@@ -4860,7 +4989,7 @@ mono_type_get_object (MonoDomain *domain, MonoType *type)
                mono_domain_unlock (domain);
                return res;
        }
-       if (type->type == MONO_TYPE_GENERICINST) {
+       if ((type->type == MONO_TYPE_GENERICINST) && type->data.generic_inst->is_dynamic) {
                res = (MonoReflectionType *)mono_generic_inst_get_object (domain, type);
                mono_g_hash_table_insert (domain->type_hash, type, res);
                mono_domain_unlock (domain);
@@ -5053,7 +5182,8 @@ assembly_name_to_aname (MonoAssemblyName *assembly, char *p) {
        memset (assembly, 0, sizeof (MonoAssemblyName));
        assembly->name = p;
        assembly->culture = "";
-       
+       assembly->public_tok_value = NULL;
+
        while (*p && (isalnum (*p) || *p == '.' || *p == '-' || *p == '_' || *p == '$' || *p == '@'))
                p++;
        found_sep = 0;
@@ -5066,7 +5196,7 @@ assembly_name_to_aname (MonoAssemblyName *assembly, char *p) {
        if (!found_sep)
                return 1;
        while (*p) {
-               if (*p == 'V' && strncmp (p, "Version=", 8) == 0) {
+               if (*p == 'V' && g_ascii_strncasecmp (p, "Version=", 8) == 0) {
                        p += 8;
                        assembly->major = strtoul (p, &s, 10);
                        if (s == p || *s != '.')
@@ -5083,10 +5213,11 @@ assembly_name_to_aname (MonoAssemblyName *assembly, char *p) {
                        assembly->revision = strtoul (p, &s, 10);
                        if (s == p)
                                return 1;
-               } else if (*p == 'C' && strncmp (p, "Culture=", 8) == 0) {
+                       p = s;
+               } else if (*p == 'C' && g_ascii_strncasecmp (p, "Culture=", 8) == 0) {
                        p += 8;
-                       if (strncmp (p, "neutral", 7) == 0) {
-                               assembly->culture = "";
+                       if (g_ascii_strncasecmp (p, "neutral", 7) == 0) {
+                               assembly->culture = g_strdup ("");
                                p += 7;
                        } else {
                                assembly->culture = p;
@@ -5094,26 +5225,16 @@ assembly_name_to_aname (MonoAssemblyName *assembly, char *p) {
                                        p++;
                                }
                        }
-               } else if (*p == 'P' && strncmp (p, "PublicKeyToken=", 15) == 0) {
+               } else if (*p == 'P' && g_ascii_strncasecmp (p, "PublicKeyToken=", 15) == 0) {
                        p += 15;
-                       s = p;
-                       while (*s && isxdigit (*s)) {
-                               *s = tolower (*s);
-                               s++;
-                       }
-                       assembly->hash_len = s - p;
-                       if (!(s-p) || ((s-p) & 1))
-                               return 1;
-                       assembly->hash_value = s = p;
-                       while (*s && isxdigit (*s)) {
-                               int val;
-                               val = *s >= '0' && *s <= '9'? *s - '0': *s - 'a' + 10;
-                               s++;
-                               *p = val << 4;
-                               *p |= *s >= '0' && *s <= '9'? *s - '0': *s - 'a' + 10;
-                               p++;
+                       if (strncmp (p, "null", 4) == 0) {
+                               p += 4;
+                       } else {
+                               assembly->public_tok_value = p;
+                               while (*p && *p != ',') {
+                                       p++;
+                               }
                        }
-                       p = s;
                } else {
                        while (*p && *p != ',')
                                p++;
@@ -5356,9 +5477,36 @@ mono_reflection_get_type (MonoImage* image, MonoTypeNameParse *info, gboolean ig
        assembly = 
                mono_domain_try_type_resolve (
                        mono_domain_get (), fullName->str, NULL);
-       if (assembly && (!image || (assembly->assembly->image == image)))
-               type = mono_reflection_get_type_internal (assembly->assembly->image, 
-                                                                                info, ignorecase);
+       if (assembly && (!image || (assembly->assembly->image == image))) {
+
+               if (assembly->assembly->dynamic) {
+                       /* Enumerate all modules */
+                       MonoReflectionAssemblyBuilder *abuilder = (MonoReflectionAssemblyBuilder*)assembly;
+                       int i;
+
+                       type = NULL;
+                       if (abuilder->modules) {
+                               for (i = 0; i < mono_array_length (abuilder->modules); ++i) {
+                                       MonoReflectionModuleBuilder *mb = mono_array_get (abuilder->modules, MonoReflectionModuleBuilder*, i);
+                                       type = mono_reflection_get_type_internal (&mb->dynamic_image->image, info, ignorecase);
+                                       if (type)
+                                               break;
+                               }
+                       }
+
+                       if (!type && abuilder->loaded_modules) {
+                               for (i = 0; i < mono_array_length (abuilder->loaded_modules); ++i) {
+                                       MonoReflectionModule *mod = mono_array_get (abuilder->loaded_modules, MonoReflectionModule*, i);
+                                       type = mono_reflection_get_type_internal (mod->image, info, ignorecase);
+                                       if (type)
+                                               break;
+                               }
+                       }
+               }
+               else
+                       type = mono_reflection_get_type_internal (assembly->assembly->image, 
+                                                                                                         info, ignorecase);
+       }
        g_string_free (fullName, TRUE);
        return type;
 }
@@ -6901,7 +7049,7 @@ fieldbuilder_to_mono_class_field (MonoClass *klass, MonoReflectionFieldBuilder*
 
 static MonoType*
 do_mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc,
-                                           MonoType **types, MonoType *nested_in)
+                                           MonoType **types)
 {
        MonoClass *klass;
        MonoReflectionTypeBuilder *tb = NULL;
@@ -6920,7 +7068,6 @@ do_mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_a
        domain = mono_object_domain (type);
 
        ginst = g_new0 (MonoGenericInst, 1);
-       ginst->is_dynamic = 1;
 
        if (!klass->generic_inst) {
                ginst->type_argc = type_argc;
@@ -6971,6 +7118,16 @@ do_mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_a
                tb = (MonoReflectionTypeBuilder *) type;
 
                icount = tb->interfaces ? mono_array_length (tb->interfaces) : 0;
+               ginst->is_dynamic = TRUE;
+       } else if (!strcmp (((MonoObject *) type)->vtable->klass->name, "MonoGenericInst")) {
+               MonoReflectionGenericInst *rgi = (MonoReflectionGenericInst *) type;
+               MonoReflectionType *rgt = rgi->generic_type;
+
+               g_assert (!strcmp (((MonoObject *) rgt)->vtable->klass->name, "TypeBuilder"));
+               tb = (MonoReflectionTypeBuilder *) rgt;
+
+               icount = tb->interfaces ? mono_array_length (tb->interfaces) : 0;
+               ginst->is_dynamic = TRUE;
        } else
                icount = klass->interface_count;
 
@@ -6989,8 +7146,6 @@ do_mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_a
                        ginst->ifaces [i] = itype->type;
        }
 
-       ginst->nested_in = nested_in;
-
        mono_class_create_generic (ginst);
 
        g_hash_table_insert (klass->image->generic_inst_cache, ginst, geninst);
@@ -7003,9 +7158,9 @@ do_mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_a
 MonoType*
 mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc, MonoType **types)
 {
-       MonoClass *klass, *pklass = NULL, *oklass = NULL;
-       MonoReflectionType *parent = NULL, *outer = NULL;
-       MonoType *geninst, *nested_in = NULL;
+       MonoClass *klass, *pklass = NULL;
+       MonoReflectionType *parent = NULL;
+       MonoType *geninst;
        MonoReflectionTypeBuilder *tb = NULL;
        MonoGenericInst *ginst;
        MonoDomain *domain;
@@ -7020,23 +7175,13 @@ mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc
                        parent = tb->parent;
                        pklass = mono_class_from_mono_type (parent->type);
                }
-               if (tb->nesting_type) {
-                       outer = tb->nesting_type;
-                       oklass = mono_class_from_mono_type (outer->type);
-               }
        } else {
                pklass = klass->parent;
                if (pklass)
                        parent = mono_type_get_object (domain, &pklass->byval_arg);
-               oklass = klass->nested_in;
-               if (oklass)
-                       outer = mono_type_get_object (domain, &oklass->byval_arg);
        }
 
-       if (oklass)
-               nested_in = mono_reflection_bind_generic_parameters (outer, oklass->num_gen_params, types);
-
-       geninst = do_mono_reflection_bind_generic_parameters (type, type_argc, types, nested_in);
+       geninst = do_mono_reflection_bind_generic_parameters (type, type_argc, types);
        if (!geninst)
                return NULL;
 
@@ -7048,57 +7193,6 @@ mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc
        return geninst;
 }
 
-void
-mono_reflection_generic_inst_get_nested_types (MonoReflectionGenericInst *type)
-{
-       MonoReflectionTypeBuilder *tb;
-       MonoGenericInst *ginst;
-       int i;
-
-       ginst = type->type.type->data.generic_inst;
-       if (ginst->nested)
-               return;
-
-       if (strcmp (((MonoObject *) type->generic_type)->vtable->klass->name, "TypeBuilder"))
-               return;
-
-       tb = (MonoReflectionTypeBuilder *) type->generic_type;
-
-       ginst->count_nested = tb->subtypes ? mono_array_length (tb->subtypes) : 0;
-       ginst->nested = g_new0 (MonoType *, ginst->count_nested);
-
-       for (i = 0; i < ginst->count_nested; i++) {
-               MonoReflectionTypeBuilder *ntype;
-               MonoType **ntypes;
-               int ntype_argc, j;
-
-               ntype = mono_array_get (tb->subtypes, gpointer, i);
-               ntype_argc = ntype->generic_params ? mono_array_length (ntype->generic_params) : 0;
-
-               if (ntype_argc > ginst->type_argc) {
-                       ntypes = g_new0 (MonoType *, ntype_argc);
-
-                       for (j = 0; j < ginst->type_argc; j++)
-                               ntypes [j] = ginst->type_argv [j];
-
-                       for (j = ginst->type_argc; j < ntype_argc; j++) {
-                               MonoReflectionGenericParam *ngparam;
-                               MonoType *pt = g_new0 (MonoType, 1);
-
-                               ngparam = mono_array_get (ntype->generic_params, gpointer, j);
-
-                               pt->type = MONO_TYPE_VAR;
-                               pt->data.generic_param = ngparam->type.type->data.generic_param;
-
-                               ntypes [j] = pt;
-                       }
-               } else
-                       ntypes = ginst->type_argv;
-
-               ginst->nested [i] = mono_reflection_bind_generic_parameters ((MonoReflectionType *) ntype, ntype_argc, ntypes);
-       }
-}
-
 MonoReflectionMethod*
 mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, MonoArray *types)
 {
@@ -7149,12 +7243,24 @@ inflate_mono_method (MonoReflectionGenericInst *type, MonoMethod *method, MonoOb
        MonoGenericMethod *gmethod;
        MonoGenericInst *ginst;
        MonoGenericContext *context;
+       int i;
 
        ginst = type->type.type->data.generic_inst;
 
        gmethod = g_new0 (MonoGenericMethod, 1);
        gmethod->reflection_info = obj;
 
+       gmethod->mtype_argc = method->signature->generic_param_count;
+       gmethod->mtype_argv = g_new0 (MonoType *, gmethod->mtype_argc);
+
+       for (i = 0; i < gmethod->mtype_argc; i++) {
+               MonoMethodNormal *mn = (MonoMethodNormal *) method;
+               MonoGenericParam *gparam = &mn->header->gen_params [i];
+
+               g_assert (gparam->pklass);
+               gmethod->mtype_argv [i] = &gparam->pklass->byval_arg;
+       }
+
        context = g_new0 (MonoGenericContext, 1);
        context->ginst = ginst;
        context->gmethod = gmethod;
@@ -7583,74 +7689,29 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
        return res;
 }
 
-MonoReflectionGenericParam *
-mono_reflection_define_generic_parameter (MonoReflectionTypeBuilder *tb, MonoReflectionMethodBuilder *mb, MonoString *name, guint32 index)
-{
-       static MonoClass *System_Reflection_MonoGenericParam;
-       MonoImage *image;
-       MonoGenericParam *param;
-       MonoReflectionGenericParam *res;
-       MonoDomain *domain;
-
-       if (!System_Reflection_MonoGenericParam) {
-               System_Reflection_MonoGenericParam = mono_class_from_name (
-                       mono_defaults.corlib, "System.Reflection", "MonoGenericParam");
-               g_assert (System_Reflection_MonoGenericParam);
-       }
-
-       param = g_new0 (MonoGenericParam, 1);
-
-       if (mb)
-               tb = (MonoReflectionTypeBuilder *) mb->type;
-
-       domain = mono_object_domain (tb);
-       image = (MonoImage*)tb->module->dynamic_image;
-
-       param->method = NULL;
-       param->name = mono_string_to_utf8 (name);
-       param->num = index;
-
-       res = (MonoReflectionGenericParam *)mono_object_new (domain, System_Reflection_MonoGenericParam);
-       res->type.type = g_new0 (MonoType, 1);
-       res->type.type->type = mb ? MONO_TYPE_MVAR : MONO_TYPE_VAR;
-       res->type.type->data.generic_param = param;
-
-       res->refobj = mb ? (MonoObject *) mb : (MonoObject *) tb;
-       res->index = index;
-       res->name = name;
-
-       return res;
-}
-
 void
 mono_reflection_initialize_generic_parameter (MonoReflectionGenericParam *gparam)
 {
        MonoGenericParam *param;
-       MonoReflectionMethodBuilder *mb = NULL;
-       MonoReflectionTypeBuilder *tb;
        MonoImage *image;
-       int count, i;
 
-       param = gparam->type.type->data.generic_param;
-       count = gparam->constraints ? mono_array_length (gparam->constraints) : 0;
-       param->constraints = g_new0 (MonoClass *, count + 1);
-       for (i = 0; i < count; i++) {
-               MonoReflectionType *constraint = mono_array_get (gparam->constraints, MonoReflectionType *, i);
+       MONO_ARCH_SAVE_REGS;
 
-               param->constraints [i] = mono_class_from_mono_type (constraint->type);
-       }
+       param = g_new0 (MonoGenericParam, 1);
 
-       if (!strcmp (gparam->refobj->vtable->klass->name, "MethodBuilder")) {
-               mb = (MonoReflectionMethodBuilder *) gparam->refobj;
-               tb = (MonoReflectionTypeBuilder *) mb->type;
-       } else
-               tb = (MonoReflectionTypeBuilder *) gparam->refobj;
+       param->method = NULL;
+       param->name = mono_string_to_utf8 (gparam->name);
+       param->num = gparam->index;
 
-       image = (MonoImage*)tb->module->dynamic_image;
+       image = &gparam->tbuilder->module->dynamic_image->image;
+       mono_class_from_generic_parameter (param, image, gparam->mbuilder != NULL);
 
-       param->pklass = mono_class_from_generic_parameter (param, image, mb != NULL);
+       param->pklass->reflection_info = gparam;
 
-       gparam->initialized = TRUE;
+       gparam->type.type = g_new0 (MonoType, 1);
+       gparam->type.type->type = gparam->mbuilder ? MONO_TYPE_MVAR : MONO_TYPE_VAR;
+       gparam->type.type->attrs = TYPE_ATTRIBUTE_PUBLIC;
+       gparam->type.type->data.generic_param = param;
 }
 
 MonoArray *