Hide some more methods
[mono.git] / mono / metadata / icall.c
index 298c11cab730228610ac5370e4b3e83025ef1e02..41b3ee3f809a72dc95fffb3679a063b0a74d96d7 100644 (file)
@@ -578,10 +578,6 @@ ves_icall_System_Array_FastCopy (MonoArray *source, int source_idx, MonoArray* d
                (source_idx + length > mono_array_length (source)))
                return FALSE;
 
-       element_size = mono_array_element_size (source->obj.vtable->klass);
-       dest_addr = mono_array_addr_with_size (dest, element_size, dest_idx);
-       source_addr = mono_array_addr_with_size (source, element_size, source_idx);
-
        src_class = source->obj.vtable->klass->element_class;
        dest_class = dest->obj.vtable->klass->element_class;
 
@@ -591,6 +587,7 @@ ves_icall_System_Array_FastCopy (MonoArray *source, int source_idx, MonoArray* d
 
        /* Case1: object[] -> valuetype[] (ArrayList::ToArray) */
        if (src_class == mono_defaults.object_class && dest_class->valuetype) {
+               int has_refs = dest_class->has_references;
                for (i = source_idx; i < source_idx + length; ++i) {
                        MonoObject *elem = mono_array_get (source, MonoObject*, i);
                        if (elem && !mono_object_isinst (elem, dest_class))
@@ -598,11 +595,14 @@ ves_icall_System_Array_FastCopy (MonoArray *source, int source_idx, MonoArray* d
                }
 
                element_size = mono_array_element_size (dest->obj.vtable->klass);
+               memset (mono_array_addr_with_size (dest, element_size, dest_idx), 0, element_size * length);
                for (i = 0; i < length; ++i) {
                        MonoObject *elem = mono_array_get (source, MonoObject*, source_idx + i);
                        void *addr = mono_array_addr_with_size (dest, element_size, dest_idx + i);
                        if (!elem)
-                               memset (addr, 0, element_size);
+                               continue;
+                       if (has_refs)
+                               mono_value_copy (addr, (char *)elem + sizeof (MonoObject), dest_class);
                        else
                                memcpy (addr, (char *)elem + sizeof (MonoObject), element_size);
                }
@@ -627,7 +627,18 @@ ves_icall_System_Array_FastCopy (MonoArray *source, int source_idx, MonoArray* d
                        return FALSE;
        }
 
-       memmove (dest_addr, source_addr, element_size * length);
+       if (dest_class->valuetype) {
+               element_size = mono_array_element_size (source->obj.vtable->klass);
+               source_addr = mono_array_addr_with_size (source, element_size, source_idx);
+               if (dest_class->has_references) {
+                       mono_value_copy_array (dest, dest_idx, source_addr, length);
+               } else {
+                       dest_addr = mono_array_addr_with_size (dest, element_size, dest_idx);
+                       memmove (dest_addr, source_addr, element_size * length);
+               }
+       } else {
+               mono_array_memcpy_refs (dest, dest_idx, source, source_idx, length);
+       }
 
        return TRUE;
 }
@@ -780,7 +791,7 @@ ves_icall_System_ValueType_InternalGetHashCode (MonoObject *this, MonoArray **fi
        klass = mono_object_class (this);
 
        if (mono_class_num_fields (klass) == 0)
-               return ves_icall_System_Object_GetHashCode (this);
+               return mono_object_hash (this);
 
        /*
         * Compute the starting value of the hashcode for fields of primitive
@@ -814,11 +825,13 @@ ves_icall_System_ValueType_InternalGetHashCode (MonoObject *this, MonoArray **fi
        }
 
        if (values) {
+               int i;
                *fields = mono_array_new (mono_domain_get (), mono_defaults.object_class, count);
-               memcpy (mono_array_addr (*fields, MonoObject*, 0), values, count * sizeof (MonoObject*));
-       }
-       else
+               for (i = 0; i < count; ++i)
+                       mono_array_setref (*fields, i, values [i]);
+       } else {
                *fields = NULL;
+       }
        return result;
 }
 
@@ -889,13 +902,14 @@ ves_icall_System_ValueType_Equals (MonoObject *this, MonoObject *that, MonoArray
        }
 
        if (values) {
+               int i;
                *fields = mono_array_new (mono_domain_get (), mono_defaults.object_class, count);
-               memcpy (mono_array_addr (*fields, MonoObject*, 0), values, count * sizeof (MonoObject*));
-
+               for (i = 0; i < count; ++i)
+                       mono_array_setref (*fields, i, values [i]);
                return FALSE;
-       }
-       else
+       } else {
                return TRUE;
+       }
 }
 
 static MonoReflectionType *
@@ -1460,9 +1474,9 @@ ves_icall_MonoField_GetValueInternal (MonoReflectionField *field, MonoObject *ob
 
                /* Convert the Nullable structure into a boxed vtype */
                if (is_static)
-                       buf = (char*)vtable->data + cf->offset;
+                       buf = (guint8*)vtable->data + cf->offset;
                else
-                       buf = (char*)obj + cf->offset;
+                       buf = (guint8*)obj + cf->offset;
 
                return mono_nullable_box (buf, nklass);
        }
@@ -1538,7 +1552,7 @@ ves_icall_FieldInfo_SetValueInternal (MonoReflectionField *field, MonoObject *ob
 
                                mono_nullable_init (buf, value, nklass);
 
-                               v = buf;
+                               v = (gchar*)buf;
                        }
                        else 
                                if (gclass->container_class->valuetype && (v != NULL))
@@ -1648,9 +1662,16 @@ ves_icall_Type_GetInterfaces (MonoReflectionType* type)
        MonoClass *class = mono_class_from_mono_type (type->type);
        MonoClass *parent;
        MonoBitSet *slots;
+       MonoGenericContext *context = NULL;
 
        MONO_ARCH_SAVE_REGS;
 
+       /* open generic-instance classes can share their interface_id */
+       if (class->generic_class && class->generic_class->inst->is_open) {
+               context = class->generic_class->context;
+               class = class->generic_class->container_class;
+       }
+
        mono_class_setup_vtable (class);
 
        slots = mono_bitset_new (class->max_interface_id + 1, 0);
@@ -1686,8 +1707,11 @@ ves_icall_Type_GetInterfaces (MonoReflectionType* type)
        intf = mono_array_new (domain, mono_defaults.monotype_class, ifaces->len);
        for (i = 0; i < ifaces->len; ++i) {
                MonoClass *ic = g_ptr_array_index (ifaces, i);
+               MonoType *ret = &ic->byval_arg;
+               if (context && ic->generic_class && ic->generic_class->inst->is_open)
+                       ret = mono_class_inflate_generic_type (ret, context);
                
-               mono_array_setref (intf, i, mono_type_get_object (domain, &ic->byval_arg));
+               mono_array_setref (intf, i, mono_type_get_object (domain, ret));
        }
        g_ptr_array_free (ifaces, TRUE);
 
@@ -2488,8 +2512,8 @@ ves_icall_MonoMethod_GetDllImportAttribute (MonoMethod *method)
        
        attr = (MonoReflectionDllImportAttribute*)mono_object_new (domain, DllImportAttributeClass);
 
-       attr->dll = mono_string_new (domain, scope);
-       attr->entry_point = mono_string_new (domain, import);
+       MONO_OBJECT_SETREF (attr, dll, mono_string_new (domain, scope));
+       MONO_OBJECT_SETREF (attr, entry_point, mono_string_new (domain, import));
        attr->call_conv = (flags & 0x700) >> 8;
        attr->charset = ((flags & 0x6) >> 1) + 1;
        if (attr->charset == 1)
@@ -2799,7 +2823,7 @@ write_enum_value (char *mem, int type, guint64 value)
        switch (type) {
        case MONO_TYPE_U1:
        case MONO_TYPE_I1: {
-               guint8 *p = mem;
+               guint8 *p = (guint8*)mem;
                *p = value;
                break;
        }
@@ -2844,9 +2868,10 @@ ves_icall_System_Enum_ToObject (MonoReflectionType *type, MonoObject *obj)
        enumc = mono_class_from_mono_type (type->type);
        objc = obj->vtable->klass;
 
-       MONO_CHECK_ARG (obj, enumc->enumtype == TRUE);
-       MONO_CHECK_ARG (obj, (objc->enumtype) || (objc->byval_arg.type >= MONO_TYPE_I1 &&
-                                                 objc->byval_arg.type <= MONO_TYPE_U8));
+       if (!enumc->enumtype)
+               mono_raise_exception (mono_get_exception_argument ("enumType", "Type provided must be an Enum."));
+       if (!((objc->enumtype) || (objc->byval_arg.type >= MONO_TYPE_I1 && objc->byval_arg.type <= MONO_TYPE_U8)))
+               mono_raise_exception (mono_get_exception_argument ("value", "The value passed in must be an enum base or an underlying type for an enum, such as an Int32."));
 
        res = mono_object_new (domain, enumc);
        val = read_enum_value ((char *)obj + sizeof (MonoObject), objc->enumtype? objc->enum_basetype->type: objc->byval_arg.type);
@@ -3101,7 +3126,7 @@ ves_icall_Type_GetMethodsByName (MonoReflectionType *type, MonoString *name, gui
        MonoMethod *method;
        gpointer iter;
        MonoObject *member;
-       int i, len, match;
+       int i, len, match, nslots;
        guint32 method_slots_default [8];
        guint32 *method_slots;
        gchar *mname = NULL;
@@ -3122,8 +3147,9 @@ ves_icall_Type_GetMethodsByName (MonoReflectionType *type, MonoString *name, gui
 
        mono_class_setup_vtable (klass);
 
-       if (klass->vtable_size >= sizeof (method_slots_default) * 8) {
-               method_slots = g_new0 (guint32, klass->vtable_size / 32 + 1);
+       nslots = MONO_CLASS_IS_INTERFACE (klass) ? mono_class_num_methods (klass) : klass->vtable_size;
+       if (nslots >= sizeof (method_slots_default) * 8) {
+               method_slots = g_new0 (guint32, nslots / 32 + 1);
        } else {
                method_slots = method_slots_default;
                memset (method_slots, 0, sizeof (method_slots_default));
@@ -3164,6 +3190,7 @@ handle_parent:
                
                match = 0;
                if (method->slot != -1) {
+                       g_assert (method->slot < nslots);
                        if (method_slots [method->slot >> 5] & (1 << (method->slot & 0x1f)))
                                continue;
                        method_slots [method->slot >> 5] |= 1 << (method->slot & 0x1f);
@@ -3265,7 +3292,7 @@ ves_icall_Type_GetPropertiesByName (MonoReflectionType *type, MonoString *name,
        MonoArray *res;
        MonoMethod *method;
        MonoProperty *prop;
-       int i, match;
+       int i, match, nslots;
        int len = 0;
        guint32 flags;
        guint32 method_slots_default [8];
@@ -3289,8 +3316,11 @@ ves_icall_Type_GetPropertiesByName (MonoReflectionType *type, MonoString *name,
                compare_func = (ignore_case) ? g_strcasecmp : strcmp;
        }
 
-       if (klass->vtable_size >= sizeof (method_slots_default) * 8) {
-               method_slots = g_new0 (guint32, klass->vtable_size / 32 + 1);
+       mono_class_setup_vtable (klass);
+
+       nslots = MONO_CLASS_IS_INTERFACE (klass) ? mono_class_num_methods (klass) : klass->vtable_size;
+       if (nslots >= sizeof (method_slots_default) * 8) {
+               method_slots = g_new0 (guint32, nslots / 32 + 1);
        } else {
                method_slots = method_slots_default;
                memset (method_slots, 0, sizeof (method_slots_default));
@@ -3680,6 +3710,14 @@ ves_icall_System_Reflection_Assembly_get_code_base (MonoReflectionAssembly *asse
        MONO_ARCH_SAVE_REGS;
 
        absolute = g_build_filename (mass->basedir, mass->image->module_name, NULL);
+#if PLATFORM_WIN32
+       {
+               gint i;
+               for (i = strlen (absolute) - 1; i >= 0; i--)
+                       if (absolute [i] == '\\')
+                               absolute [i] = '/';
+       }
+#endif
        if (escaped) {
                uri = g_filename_to_uri (absolute, NULL, NULL);
        } else {
@@ -3858,7 +3896,7 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
                aname = (MonoReflectionAssemblyName *) mono_object_new (
                        domain, System_Reflection_AssemblyName);
 
-               aname->name = mono_string_new (domain, mono_metadata_string_heap (image, cols [MONO_ASSEMBLYREF_NAME]));
+               MONO_OBJECT_SETREF (aname, name, mono_string_new (domain, mono_metadata_string_heap (image, cols [MONO_ASSEMBLYREF_NAME])));
 
                aname->major = cols [MONO_ASSEMBLYREF_MAJOR_VERSION];
                aname->minor = cols [MONO_ASSEMBLYREF_MINOR_VERSION];
@@ -3867,12 +3905,12 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
                aname->flags = cols [MONO_ASSEMBLYREF_FLAGS];
                aname->versioncompat = 1; /* SameMachine (default) */
                aname->hashalg = ASSEMBLY_HASH_SHA1; /* SHA1 (default) */
-               aname->version = create_version (domain, aname->major, aname->minor, aname->build, aname->revision);
+               MONO_OBJECT_SETREF (aname, version, create_version (domain, aname->major, aname->minor, aname->build, aname->revision));
 
                if (create_culture) {
                        gpointer args [1];
                        args [0] = mono_string_new (domain, mono_metadata_string_heap (image, cols [MONO_ASSEMBLYREF_CULTURE]));
-                       aname->cultureInfo = mono_runtime_invoke (create_culture, NULL, args, NULL);
+                       MONO_OBJECT_SETREF (aname, cultureInfo, mono_runtime_invoke (create_culture, NULL, args, NULL));
                }
                
                if (cols [MONO_ASSEMBLYREF_PUBLIC_KEY]) {
@@ -3882,10 +3920,10 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
                        if ((cols [MONO_ASSEMBLYREF_FLAGS] & ASSEMBLYREF_FULL_PUBLIC_KEY_FLAG)) {
                                /* public key token isn't copied - the class library will 
                                automatically generate it from the public key if required */
-                               aname->publicKey = mono_array_new (domain, mono_defaults.byte_class, pkey_len);
+                               MONO_OBJECT_SETREF (aname, publicKey, mono_array_new (domain, mono_defaults.byte_class, pkey_len));
                                memcpy (mono_array_addr (aname->publicKey, guint8, 0), pkey_ptr, pkey_len);
                        } else {
-                               aname->keyToken = mono_array_new (domain, mono_defaults.byte_class, pkey_len);
+                               MONO_OBJECT_SETREF (aname, keyToken, mono_array_new (domain, mono_defaults.byte_class, pkey_len));
                                memcpy (mono_array_addr (aname->keyToken, guint8, 0), pkey_ptr, pkey_len);
                        }
                }
@@ -4023,7 +4061,7 @@ ves_icall_System_Reflection_Assembly_GetManifestResourceInfoInternal (MonoReflec
                        table = &assembly->assembly->image->tables [MONO_TABLE_FILE];
                        mono_metadata_decode_row (table, i - 1, file_cols, MONO_FILE_SIZE);
                        val = mono_metadata_string_heap (assembly->assembly->image, file_cols [MONO_FILE_NAME]);
-                       info->filename = mono_string_new (mono_object_domain (assembly), val);
+                       MONO_OBJECT_SETREF (info, filename, mono_string_new (mono_object_domain (assembly), val));
                        if (file_cols [MONO_FILE_FLAGS] && FILE_CONTAINS_NO_METADATA)
                                info->location = 0;
                        else
@@ -4039,7 +4077,7 @@ ves_icall_System_Reflection_Assembly_GetManifestResourceInfoInternal (MonoReflec
                                g_free (msg);
                                mono_raise_exception (ex);
                        }
-                       info->assembly = mono_assembly_get_object (mono_domain_get (), assembly->assembly->image->references [i - 1]);
+                       MONO_OBJECT_SETREF (info, assembly, mono_assembly_get_object (mono_domain_get (), assembly->assembly->image->references [i - 1]));
 
                        /* Obtain info recursively */
                        ves_icall_System_Reflection_Assembly_GetManifestResourceInfoInternal (info->assembly, name, info);
@@ -4269,18 +4307,18 @@ fill_reflection_assembly_name (MonoDomain *domain, MonoReflectionAssemblyName *a
 
        MONO_ARCH_SAVE_REGS;
 
-       aname->name = mono_string_new (domain, name->name);
+       MONO_OBJECT_SETREF (aname, name, mono_string_new (domain, name->name));
        aname->major = name->major;
        aname->minor = name->minor;
        aname->build = name->build;
        aname->revision = name->revision;
        aname->hashalg = name->hash_alg;
        if (by_default_version)
-               aname->version = create_version (domain, name->major, name->minor, name->build, name->revision);
+               MONO_OBJECT_SETREF (aname, version, create_version (domain, name->major, name->minor, name->build, name->revision));
        
        codebase = g_filename_to_uri (absolute, NULL, NULL);
        if (codebase) {
-               aname->codebase = mono_string_new (domain, codebase);
+               MONO_OBJECT_SETREF (aname, codebase, mono_string_new (domain, codebase));
                g_free (codebase);
        }
 
@@ -4293,14 +4331,14 @@ fill_reflection_assembly_name (MonoDomain *domain, MonoReflectionAssemblyName *a
 
        if (name->culture) {
                args [0] = mono_string_new (domain, name->culture);
-               aname->cultureInfo = mono_runtime_invoke (create_culture, NULL, args, NULL);
+               MONO_OBJECT_SETREF (aname, cultureInfo, mono_runtime_invoke (create_culture, NULL, args, NULL));
        }
 
        if (name->public_key) {
                pkey_ptr = (char*)name->public_key;
                pkey_len = mono_metadata_decode_blob_size (pkey_ptr, &pkey_ptr);
 
-               aname->publicKey = mono_array_new (domain, mono_defaults.byte_class, pkey_len);
+               MONO_OBJECT_SETREF (aname, publicKey, mono_array_new (domain, mono_defaults.byte_class, pkey_len));
                memcpy (mono_array_addr (aname->publicKey, guint8, 0), pkey_ptr, pkey_len);
        }
 
@@ -4309,7 +4347,7 @@ fill_reflection_assembly_name (MonoDomain *domain, MonoReflectionAssemblyName *a
                int i, j;
                char *p;
 
-               aname->keyToken = mono_array_new (domain, mono_defaults.byte_class, 8);
+               MONO_OBJECT_SETREF (aname, keyToken, mono_array_new (domain, mono_defaults.byte_class, 8));
                p = mono_array_addr (aname->keyToken, char, 0);
 
                for (i = 0, j = 0; i < 8; i++) {
@@ -4349,7 +4387,7 @@ ves_icall_System_Reflection_Assembly_InternalGetAssemblyName (MonoString *fname,
        filename = mono_string_to_utf8 (fname);
 
        image = mono_image_open (filename, &status);
-       
+
        if (!image){
                MonoException *exc;
 
@@ -4358,6 +4396,8 @@ ves_icall_System_Reflection_Assembly_InternalGetAssemblyName (MonoString *fname,
                mono_raise_exception (exc);
        }
 
+       /* So we can call mono_image_close () later */
+       mono_image_addref (image);
        res = mono_assembly_fill_assembly_name (image, &name);
        if (!res) {
                mono_image_close (image);
@@ -4455,28 +4495,21 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
                if (abuilder->modules) {
                        for (i = 0; i < mono_array_length(abuilder->modules); i++) {
                                MonoReflectionModuleBuilder *mb = mono_array_get (abuilder->modules, MonoReflectionModuleBuilder*, i);
-                               if (res == NULL)
-                                       res = mb->types;
-                               else {
-                                       MonoArray *append = mb->types;
-                                       if (mono_array_length (append) > 0) {
-                                               guint32 len1, len2;
-                                               MonoArray *new;
-                                               len1 = mono_array_length (res);
-                                               len2 = mono_array_length (append);
-                                               new = mono_array_new (domain, mono_defaults.monotype_class, len1 + len2);
-                                               memcpy (mono_array_addr (new, MonoReflectionType*, 0),
-                                                       mono_array_addr (res, MonoReflectionType*, 0),
-                                                       len1 * sizeof (MonoReflectionType*));
-                                               memcpy (mono_array_addr (new, MonoReflectionType*, len1),
-                                                       mono_array_addr (append, MonoReflectionType*, 0),
-                                                       len2 * sizeof (MonoReflectionType*));
-                                               res = new;
-                                       }
+                               MonoArray *append = mb->types;
+                               if (append && mono_array_length (append) > 0) {
+                                       guint32 len1, len2;
+                                       MonoArray *new;
+                                       len1 = res ? mono_array_length (res) : 0;
+                                       len2 = mono_array_length (append);
+                                       new = mono_array_new (domain, mono_defaults.monotype_class, len1 + len2);
+                                       if (res)
+                                               mono_array_memcpy_refs (new, 0, res, 0, len1);
+                                       mono_array_memcpy_refs (new, len1, append, 0, len2);
+                                       res = new;
                                }
                        }
 
-                       /* 
+                       /*
                         * Replace TypeBuilders with the created types to be compatible
                         * with MS.NET.
                         */
@@ -4492,27 +4525,23 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
                if (abuilder->loaded_modules)
                        for (i = 0; i < mono_array_length(abuilder->loaded_modules); i++) {
                                MonoReflectionModule *rm = mono_array_get (abuilder->loaded_modules, MonoReflectionModule*, i);
-                               if (res == NULL)
-                                       res = mono_module_get_types (domain, rm->image, exportedOnly);
-                               else {
-                                       MonoArray *append = mono_module_get_types (domain, rm->image, exportedOnly);
-                                       if (mono_array_length (append) > 0) {
-                                               guint32 len1, len2;
-                                               MonoArray *new;
-                                               len1 = mono_array_length (res);
-                                               len2 = mono_array_length (append);
-                                               new = mono_array_new (domain, mono_defaults.monotype_class, len1 + len2);
-                                               memcpy (mono_array_addr (new, MonoReflectionType*, 0),
-                                                       mono_array_addr (res, MonoReflectionType*, 0),
-                                                       len1 * sizeof (MonoReflectionType*));
-                                               memcpy (mono_array_addr (new, MonoReflectionType*, len1),
-                                                       mono_array_addr (append, MonoReflectionType*, 0),
-                                                       len2 * sizeof (MonoReflectionType*));
-                                               res = new;
-                                       }
+                               MonoArray *append = mono_module_get_types (domain, rm->image, exportedOnly);
+                               if (append && mono_array_length (append) > 0) {
+                                       guint32 len1, len2;
+                                       MonoArray *new;
+                                       len1 = res ? mono_array_length (res) : 0;
+                                       len2 = mono_array_length (append);
+                                       new = mono_array_new (domain, mono_defaults.monotype_class, len1 + len2);
+                                       if (res)
+                                               mono_array_memcpy_refs (new, 0, res, 0, len1);
+                                       mono_array_memcpy_refs (new, len1, append, 0, len2);
+                                       res = new;
                                }
                        }
-               return res;
+               if (res)
+                       return res;
+               else
+                       return mono_array_new (domain, mono_defaults.monotype_class, 0);
        }
        image = assembly->assembly->image;
        table = &image->tables [MONO_TABLE_FILE];
@@ -4532,12 +4561,8 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
                                        len1 = mono_array_length (res);
                                        len2 = mono_array_length (res2);
                                        res3 = mono_array_new (domain, mono_defaults.monotype_class, len1 + len2);
-                                       memcpy (mono_array_addr (res3, MonoReflectionType*, 0),
-                                                       mono_array_addr (res, MonoReflectionType*, 0),
-                                                       len1 * sizeof (MonoReflectionType*));
-                                       memcpy (mono_array_addr (res3, MonoReflectionType*, len1),
-                                                       mono_array_addr (res2, MonoReflectionType*, 0),
-                                                       len2 * sizeof (MonoReflectionType*));
+                                       mono_array_memcpy_refs (res3, 0, res, 0, len1);
+                                       mono_array_memcpy_refs (res3, len1, res2, 0, len2);
                                        res = res3;
                                }
                        }
@@ -5381,7 +5406,7 @@ ves_icall_Remoting_RealProxy_GetTransparentProxy (MonoObject *this, MonoString *
        res = mono_object_new (domain, mono_defaults.transparent_proxy_class);
        tp = (MonoTransparentProxy*) res;
        
-       tp->rp = rp;
+       MONO_OBJECT_SETREF (tp, rp, rp);
        type = ((MonoReflectionType *)rp->class_to_proxy)->type;
        klass = mono_class_from_mono_type (type);
 
@@ -5520,6 +5545,36 @@ ves_icall_System_Environment_GetEnvironmentVariableNames (void)
        return names;
 }
 
+/*
+ * If your platform lacks setenv/unsetenv, you must upgrade your glib.
+ */
+#if !GLIB_CHECK_VERSION(2,4,0)
+#define g_setenv(a,b,c)   setenv(a,b,c)
+#define g_unsetenv(a) unsetenv(a)
+#endif
+
+static void
+ves_icall_System_Environment_InternalSetEnvironmentVariable (MonoString *name, MonoString *value)
+{
+       gchar *utf8_name, *utf8_value;
+
+       MONO_ARCH_SAVE_REGS;
+
+       utf8_name = mono_string_to_utf8 (name); /* FIXME: this should be ascii */
+
+       if ((value == NULL) || (mono_string_length (value) == 0) || (mono_string_chars (value)[0] == 0)) {
+               g_unsetenv (utf8_name);
+               return;
+       }
+
+       utf8_value = mono_string_to_utf8 (value);
+
+       g_setenv (utf8_name, utf8_value, TRUE);
+
+       g_free (utf8_name);
+       g_free (utf8_value);
+}
+
 /*
  * Returns: the number of milliseconds elapsed since the system started.
  */
@@ -6454,6 +6509,7 @@ static const IcallEntry environment_icalls [] = {
        {"GetMachineConfigPath", ves_icall_System_Configuration_DefaultConfig_get_machine_config_path},
        {"GetOSVersionString", ves_icall_System_Environment_GetOSVersionString},
        {"GetWindowsFolderPath", ves_icall_System_Environment_GetWindowsFolderPath},
+       {"InternalSetEnvironmentVariable", ves_icall_System_Environment_InternalSetEnvironmentVariable},
        {"get_ExitCode", mono_environment_exitcode_get},
        {"get_HasShutdownStarted", ves_icall_System_Environment_get_HasShutdownStarted},
        {"get_MachineName", ves_icall_System_Environment_get_MachineName},
@@ -6534,7 +6590,7 @@ static const IcallEntry monoio_icalls [] = {
        {"GetTempPath(string&)", ves_icall_System_IO_MonoIO_GetTempPath},
        {"Lock(intptr,long,long,System.IO.MonoIOError&)", ves_icall_System_IO_MonoIO_Lock},
        {"MoveFile(string,string,System.IO.MonoIOError&)", ves_icall_System_IO_MonoIO_MoveFile},
-       {"Open(string,System.IO.FileMode,System.IO.FileAccess,System.IO.FileShare,bool,System.IO.MonoIOError&)", ves_icall_System_IO_MonoIO_Open},
+       {"Open(string,System.IO.FileMode,System.IO.FileAccess,System.IO.FileShare,System.IO.FileOptions,System.IO.MonoIOError&)", ves_icall_System_IO_MonoIO_Open},
        {"Read(intptr,byte[],int,int,System.IO.MonoIOError&)", ves_icall_System_IO_MonoIO_Read},
        {"RemoveDirectory(string,System.IO.MonoIOError&)", ves_icall_System_IO_MonoIO_RemoveDirectory},
        {"Seek(intptr,long,System.IO.SeekOrigin,System.IO.MonoIOError&)", ves_icall_System_IO_MonoIO_Seek},
@@ -6785,7 +6841,7 @@ static const IcallEntry socketex_icalls [] = {
 
 static const IcallEntry object_icalls [] = {
        {"GetType", ves_icall_System_Object_GetType},
-       {"InternalGetHashCode", ves_icall_System_Object_GetHashCode},
+       {"InternalGetHashCode", mono_object_hash},
        {"MemberwiseClone", ves_icall_System_Object_MemberwiseClone},
        {"obj_address", ves_icall_System_Object_obj_address}
 };
@@ -7018,6 +7074,7 @@ static const IcallEntry thread_icalls [] = {
        {"Abort_internal(object)", ves_icall_System_Threading_Thread_Abort},
        {"ClrState", ves_icall_System_Threading_Thread_ClrState},
        {"CurrentThread_internal", mono_thread_current},
+       {"FreeLocalSlotValues", mono_thread_free_local_slot_values},
        {"GetCachedCurrentCulture", ves_icall_System_Threading_Thread_GetCachedCurrentCulture},
        {"GetCachedCurrentUICulture", ves_icall_System_Threading_Thread_GetCachedCurrentUICulture},
        {"GetDomainID", ves_icall_System_Threading_Thread_GetDomainID},