klass->this_arg.type = (MonoTypeEnum)t;
}
- if (MONO_CLASS_IS_INTERFACE (klass))
+ if (MONO_CLASS_IS_INTERFACE (klass)) {
klass->interface_id = mono_get_unique_iid (klass);
+
+ if (is_corlib && !strcmp (nspace, "System.Collections.Generic")) {
+ //FIXME IEnumerator needs to be special because GetEnumerator uses magic under the hood
+ /* FIXME: System.Array/InternalEnumerator don't need all this interface fabrication machinery.
+ * MS returns diferrent types based on which instance is called. For example:
+ * object obj = new byte[10][];
+ * Type a = ((IEnumerable<byte[]>)obj).GetEnumerator ().GetType ();
+ * Type b = ((IEnumerable<IList<byte>>)obj).GetEnumerator ().GetType ();
+ * a != b ==> true
+ */
+ if (!strcmp (name, "IList`1") || !strcmp (name, "ICollection`1") || !strcmp (name, "IEnumerable`1") || !strcmp (name, "IEnumerator`1"))
+ klass->is_array_special_interface = 1;
+ }
+ }
}
#ifndef DISABLE_COM
#endif
klass->cast_class = klass->element_class = klass;
+ if (mono_is_corlib_image (klass->image)) {
+ switch (klass->byval_arg.type) {
+ case MONO_TYPE_I1:
+ if (mono_defaults.byte_class)
+ klass->cast_class = mono_defaults.byte_class;
+ break;
+ case MONO_TYPE_U1:
+ if (mono_defaults.sbyte_class)
+ mono_defaults.sbyte_class = klass;
+ break;
+ case MONO_TYPE_I2:
+ if (mono_defaults.uint16_class)
+ mono_defaults.uint16_class = klass;
+ break;
+ case MONO_TYPE_U2:
+ if (mono_defaults.int16_class)
+ klass->cast_class = mono_defaults.int16_class;
+ break;
+ case MONO_TYPE_I4:
+ if (mono_defaults.uint32_class)
+ mono_defaults.uint32_class = klass;
+ break;
+ case MONO_TYPE_U4:
+ if (mono_defaults.int32_class)
+ klass->cast_class = mono_defaults.int32_class;
+ break;
+ case MONO_TYPE_I8:
+ if (mono_defaults.uint64_class)
+ mono_defaults.uint64_class = klass;
+ break;
+ case MONO_TYPE_U8:
+ if (mono_defaults.int64_class)
+ klass->cast_class = mono_defaults.int64_class;
+ break;
+ }
+ }
if (!klass->enumtype) {
if (!mono_metadata_interfaces_from_typedef_full (
mono_defaults.uint64_class = mono_class_load_from_name (
mono_defaults.corlib, "System", "UInt64");
- //XXX find a better place, which kinda doesn't exists as those types depend on each other.
- mono_defaults.uint32_class->cast_class = mono_defaults.int32_class;
- mono_defaults.uint16_class->cast_class = mono_defaults.int16_class;
- mono_defaults.sbyte_class->cast_class = mono_defaults.byte_class;
- mono_defaults.uint64_class->cast_class = mono_defaults.int64_class;
-
-
mono_defaults.single_class = mono_class_load_from_name (
mono_defaults.corlib, "System", "Single");
mono_class_init (mono_defaults.array_class);
mono_defaults.generic_nullable_class = mono_class_load_from_name (
mono_defaults.corlib, "System", "Nullable`1");
- mono_defaults.generic_ireadonlylist_class = mono_class_load_from_name (
- mono_defaults.corlib, "System.Collections.Generic", "IReadOnlyList`1");
-
- //IList, ICollection, IEnumerable
mono_defaults.generic_ilist_class = mono_class_load_from_name (
mono_defaults.corlib, "System.Collections.Generic", "IList`1");
- mono_defaults.generic_icollection_class = mono_class_load_from_name (
- mono_defaults.corlib, "System.Collections.Generic", "ICollection`1");
- mono_defaults.generic_ienumerable_class = mono_class_load_from_name (
- mono_defaults.corlib, "System.Collections.Generic", "IEnumerable`1");
-
- //XXX This is a hack, there's probably a better place to do this. Probably in mono_class_create_from_typedef
- mono_defaults.generic_ilist_class->is_array_special_interface = 1;
- mono_defaults.generic_icollection_class->is_array_special_interface = 1;
- mono_defaults.generic_ienumerable_class->is_array_special_interface = 1;
-
- //FIXME IEnumerator needs to be special because GetEnumerator uses magic under the hood
- MonoClass *tmp = mono_class_load_from_name (
- mono_defaults.corlib, "System.Collections.Generic", "IEnumerator`1");
- tmp->is_array_special_interface = 1;
-
+ mono_defaults.generic_ireadonlylist_class = mono_class_load_from_name (
+ mono_defaults.corlib, "System.Collections.Generic", "IReadOnlyList`1");
mono_defaults.threadpool_wait_callback_class = mono_class_load_from_name (
mono_defaults.corlib, "System.Threading", "_ThreadPoolWaitCallback");