[jit] Use MONO_INS_IS_PCONST_NULL () macro in more places.
[mono.git] / mcs / class / corlib / System.Reflection.Emit / TypeBuilder.cs
1 //
2 // System.Reflection.Emit.TypeBuilder.cs
3 //
4 // Author:
5 //   Paolo Molaro (lupus@ximian.com)
6 //   Marek Safar (marek.safar@gmail.com)
7 //
8 // (C) 2001 Ximian, Inc.  http://www.ximian.com
9 //
10
11 //
12 // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
13 //
14 // Permission is hereby granted, free of charge, to any person obtaining
15 // a copy of this software and associated documentation files (the
16 // "Software"), to deal in the Software without restriction, including
17 // without limitation the rights to use, copy, modify, merge, publish,
18 // distribute, sublicense, and/or sell copies of the Software, and to
19 // permit persons to whom the Software is furnished to do so, subject to
20 // the following conditions:
21 // 
22 // The above copyright notice and this permission notice shall be
23 // included in all copies or substantial portions of the Software.
24 // 
25 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
26 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
27 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
28 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
29 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
30 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
31 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
32 //
33
34 #if !FULL_AOT_RUNTIME
35 using System;
36 using System.Text;
37 using System.Reflection;
38 using System.Reflection.Emit;
39 using System.Runtime.CompilerServices;
40 using System.Runtime.InteropServices;
41 using System.Globalization;
42 using System.Collections;
43 using System.Collections.Generic;
44 using System.Security;
45 using System.Security.Permissions;
46 using System.Diagnostics.SymbolStore;
47
48
49 namespace System.Reflection.Emit
50 {
51         [ComVisible (true)]
52         [ComDefaultInterface (typeof (_TypeBuilder))]
53         [ClassInterface (ClassInterfaceType.None)]
54         [StructLayout (LayoutKind.Sequential)]
55         public sealed class TypeBuilder : TypeInfo, _TypeBuilder
56         {
57 #pragma warning disable 169             
58                 #region Sync with reflection.h
59                 private string tname; // name in internal form
60                 private string nspace; // namespace in internal form
61                 private Type parent;
62                 private Type nesting_type;
63                 internal Type[] interfaces;
64                 internal int num_methods;
65                 internal MethodBuilder[] methods;
66                 internal ConstructorBuilder[] ctors;
67                 internal PropertyBuilder[] properties;
68                 internal int num_fields;
69                 internal FieldBuilder[] fields;
70                 internal EventBuilder[] events;
71                 private CustomAttributeBuilder[] cattrs;
72                 internal TypeBuilder[] subtypes;
73                 internal TypeAttributes attrs;
74                 private int table_idx;
75                 private ModuleBuilder pmodule;
76                 private int class_size;
77                 private PackingSize packing_size;
78                 private IntPtr generic_container;
79                 private GenericTypeParameterBuilder[] generic_params;
80                 private RefEmitPermissionSet[] permissions;
81                 private TypeInfo created;
82                 #endregion
83 #pragma warning restore 169             
84                 
85                 TypeName fullname;
86                 bool createTypeCalled;
87                 private Type underlying_type;
88
89                 public const int UnspecifiedTypeSize = 0;
90                 
91                 protected override TypeAttributes GetAttributeFlagsImpl ()
92                 {
93                         return attrs;
94                 }
95
96                 internal TypeBuilder (ModuleBuilder mb, TypeAttributes attr, int table_idx)
97                 {
98                         this.parent = null;
99                         this.attrs = attr;
100                         this.class_size = UnspecifiedTypeSize;
101                         this.table_idx = table_idx;
102                         this.tname = table_idx == 1 ? "<Module>" : "type_" + table_idx.ToString ();
103                         this.nspace = String.Empty;
104                         this.fullname = TypeIdentifiers.WithoutEscape(this.tname);
105                         pmodule = mb;
106                 }
107
108                 internal TypeBuilder (ModuleBuilder mb, string name, TypeAttributes attr, Type parent, Type[] interfaces, PackingSize packing_size, int type_size, Type nesting_type)
109                 {
110                         int sep_index;
111                         this.parent = ResolveUserType (parent);
112                         this.attrs = attr;
113                         this.class_size = type_size;
114                         this.packing_size = packing_size;
115                         this.nesting_type = nesting_type;
116
117                         check_name ("fullname", name);
118
119                         if (parent == null && (attr & TypeAttributes.Interface) != 0 && (attr & TypeAttributes.Abstract) == 0)
120                                 throw new InvalidOperationException ("Interface must be declared abstract.");
121
122                         sep_index = name.LastIndexOf('.');
123                         if (sep_index != -1) {
124                                 this.tname = name.Substring (sep_index + 1);
125                                 this.nspace = name.Substring (0, sep_index);
126                         } else {
127                                 this.tname = name;
128                                 this.nspace = String.Empty;
129                         }
130                         if (interfaces != null) {
131                                 this.interfaces = new Type[interfaces.Length];
132                                 System.Array.Copy (interfaces, this.interfaces, interfaces.Length);
133                         }
134                         pmodule = mb;
135
136                         if (((attr & TypeAttributes.Interface) == 0) && (parent == null))
137                                 this.parent = typeof (object);
138
139                         // skip .<Module> ?
140                         table_idx = mb.get_next_table_index (this, 0x02, true);
141                         fullname = GetFullName ();
142                 }
143
144                 public override Assembly Assembly {
145                         get {return pmodule.Assembly;}
146                 }
147
148                 public override string AssemblyQualifiedName {
149                         get {
150                                 return fullname.DisplayName + ", " + Assembly.FullName;
151                         }
152                 }
153
154                 public override Type BaseType {
155                         get {
156                                 return parent;
157                         }
158                 }
159
160                 public override Type DeclaringType {
161                         get { return nesting_type; }
162                 }
163
164                 [ComVisible (true)]
165                 public override bool IsSubclassOf (Type c)
166                 {
167                         Type t;
168                         if (c == null)
169                                 return false;
170                         if (c == this)
171                                 return false;
172                         t = parent;
173                         while (t != null) {
174                                 if (c == t)
175                                         return true;
176                                 t = t.BaseType;
177                         }
178                         return false;
179                 }
180
181                 public override Type UnderlyingSystemType {
182                         get {
183                                 if (is_created)
184                                         return created.UnderlyingSystemType;
185
186                                 if (IsEnum) {
187                                         if (underlying_type != null)
188                                                 return underlying_type;
189                                         throw new InvalidOperationException (
190                                                 "Enumeration type is not defined.");
191                                 }
192
193                                 return this;
194                         }
195                 }
196
197                 TypeName GetFullName ()
198                 {
199                         TypeIdentifier ident = TypeIdentifiers.FromInternal (tname);
200                         if (nesting_type != null)
201                                 return TypeNames.FromDisplay (nesting_type.FullName).NestedName (ident);
202                         if ((nspace != null) && (nspace.Length > 0))
203                                 return TypeIdentifiers.FromInternal (nspace, ident);
204                         return ident;
205                 }
206         
207                 public override string FullName {
208                         get {
209                                 return fullname.DisplayName;
210                         }
211                 }
212         
213                 public override Guid GUID {
214                         get {
215                                 check_created ();
216                                 return created.GUID;
217                         }
218                 }
219
220                 public override Module Module {
221                         get {return pmodule;}
222                 }
223
224                 public override string Name {
225                         get {return tname;}
226                 }
227
228                 public override string Namespace {
229                         get {return nspace;}
230                 }
231
232                 public PackingSize PackingSize {
233                         get {return packing_size;}
234                 }
235
236                 public int Size {
237                         get { return class_size; }
238                 }
239
240                 public override Type ReflectedType {
241                         get { return nesting_type; }
242                 }
243
244                 public void AddDeclarativeSecurity (SecurityAction action, PermissionSet pset)
245                 {
246 #if !MOBILE
247                         if (pset == null)
248                                 throw new ArgumentNullException ("pset");
249                         if ((action == SecurityAction.RequestMinimum) ||
250                                 (action == SecurityAction.RequestOptional) ||
251                                 (action == SecurityAction.RequestRefuse))
252                                 throw new ArgumentOutOfRangeException ("Request* values are not permitted", "action");
253
254                         check_not_created ();
255
256                         if (permissions != null) {
257                                 /* Check duplicate actions */
258                                 foreach (RefEmitPermissionSet set in permissions)
259                                         if (set.action == action)
260                                                 throw new InvalidOperationException ("Multiple permission sets specified with the same SecurityAction.");
261
262                                 RefEmitPermissionSet[] new_array = new RefEmitPermissionSet [permissions.Length + 1];
263                                 permissions.CopyTo (new_array, 0);
264                                 permissions = new_array;
265                         }
266                         else
267                                 permissions = new RefEmitPermissionSet [1];
268
269                         permissions [permissions.Length - 1] = new RefEmitPermissionSet (action, pset.ToXml ().ToString ());
270                         attrs |= TypeAttributes.HasSecurity;
271 #endif
272                 }
273
274                 [ComVisible (true)]
275                 public void AddInterfaceImplementation (Type interfaceType)
276                 {
277                         if (interfaceType == null)
278                                 throw new ArgumentNullException ("interfaceType");
279                         check_not_created ();
280
281                         if (interfaces != null) {
282                                 // Check for duplicates
283                                 foreach (Type t in interfaces)
284                                         if (t == interfaceType)
285                                                 return;
286
287                                 Type[] ifnew = new Type [interfaces.Length + 1];
288                                 interfaces.CopyTo (ifnew, 0);
289                                 ifnew [interfaces.Length] = interfaceType;
290                                 interfaces = ifnew;
291                         } else {
292                                 interfaces = new Type [1];
293                                 interfaces [0] = interfaceType;
294                         }
295                 }
296
297                 protected override ConstructorInfo GetConstructorImpl (BindingFlags bindingAttr, Binder binder,
298                                                                        CallingConventions callConvention, Type[] types,
299                                                                        ParameterModifier[] modifiers)
300                 {
301                         check_created ();
302
303                         if (created == typeof (object)) {
304                                 /* 
305                                  * This happens when building corlib. Calling created.GetConstructor 
306                                  * would return constructors from the real mscorlib, instead of the
307                                  * newly built one.
308                                  */
309
310                                 if (ctors == null)
311                                         return null;
312  
313                                 ConstructorBuilder found = null;
314                                 int count = 0;
315                         
316                                 foreach (ConstructorBuilder cb in ctors) {
317                                         if (callConvention != CallingConventions.Any && cb.CallingConvention != callConvention)
318                                                 continue;
319                                         found = cb;
320                                         count++;
321                                 }
322
323                                 if (count == 0)
324                                         return null;
325                                 if (types == null) {
326                                         if (count > 1)
327                                                 throw new AmbiguousMatchException ();
328                                         return found;
329                                 }
330                                 MethodBase[] match = new MethodBase [count];
331                                 if (count == 1)
332                                         match [0] = found;
333                                 else {
334                                         count = 0;
335                                         foreach (ConstructorInfo m in ctors) {
336                                                 if (callConvention != CallingConventions.Any && m.CallingConvention != callConvention)
337                                                         continue;
338                                                 match [count++] = m;
339                                         }
340                                 }
341                                 if (binder == null)
342                                         binder = DefaultBinder;
343                                 return (ConstructorInfo) binder.SelectMethod (bindingAttr, match,
344                                                                                                                           types, modifiers);
345                         }
346
347                         return created.GetConstructor (bindingAttr, binder, 
348                                 callConvention, types, modifiers);
349                 }
350
351                 public override bool IsDefined (Type attributeType, bool inherit)
352                 {
353                         if (!is_created)
354                                 throw new NotSupportedException ();
355                         /*
356                          * MS throws NotSupported here, but we can't because some corlib
357                          * classes make calls to IsDefined.
358                          */
359                         return MonoCustomAttrs.IsDefined (this, attributeType, inherit);
360                 }
361                 
362                 public override object[] GetCustomAttributes(bool inherit)
363                 {
364                         check_created ();
365
366                         return created.GetCustomAttributes (inherit);
367                 }
368                 
369                 public override object[] GetCustomAttributes(Type attributeType, bool inherit)
370                 {
371                         check_created ();
372
373                         return created.GetCustomAttributes (attributeType, inherit);
374                 }
375
376                 public TypeBuilder DefineNestedType (string name)
377                 {
378                         return DefineNestedType (name, TypeAttributes.NestedPrivate,
379                                 pmodule.assemblyb.corlib_object_type, null);
380                 }
381
382                 public TypeBuilder DefineNestedType (string name, TypeAttributes attr)
383                 {
384                         return DefineNestedType (name, attr, pmodule.assemblyb.corlib_object_type, null);
385                 }
386
387                 public TypeBuilder DefineNestedType (string name, TypeAttributes attr, Type parent)
388                 {
389                         return DefineNestedType (name, attr, parent, null);
390                 }
391
392                 private TypeBuilder DefineNestedType (string name, TypeAttributes attr, Type parent, Type[] interfaces,
393                                                       PackingSize packSize, int typeSize)
394                 {
395                         // Visibility must be NestedXXX
396                         /* This breaks mcs
397                         if (((attrs & TypeAttributes.VisibilityMask) == TypeAttributes.Public) ||
398                                 ((attrs & TypeAttributes.VisibilityMask) == TypeAttributes.NotPublic))
399                                 throw new ArgumentException ("attr", "Bad type flags for nested type.");
400                         */
401                         if (interfaces != null)
402                                 foreach (Type iface in interfaces)
403                                         if (iface == null)
404                                                 throw new ArgumentNullException ("interfaces");
405
406                         TypeBuilder res = new TypeBuilder (pmodule, name, attr, parent, interfaces, packSize, typeSize, this);
407                         res.fullname = res.GetFullName ();
408                         pmodule.RegisterTypeName (res, res.fullname);
409                         if (subtypes != null) {
410                                 TypeBuilder[] new_types = new TypeBuilder [subtypes.Length + 1];
411                                 System.Array.Copy (subtypes, new_types, subtypes.Length);
412                                 new_types [subtypes.Length] = res;
413                                 subtypes = new_types;
414                         } else {
415                                 subtypes = new TypeBuilder [1];
416                                 subtypes [0] = res;
417                         }
418                         return res;
419                 }
420
421                 [ComVisible (true)]
422                 public TypeBuilder DefineNestedType (string name, TypeAttributes attr, Type parent, Type[] interfaces)
423                 {
424                         return DefineNestedType (name, attr, parent, interfaces, PackingSize.Unspecified, UnspecifiedTypeSize);
425                 }
426
427                 public TypeBuilder DefineNestedType (string name, TypeAttributes attr, Type parent, int typeSize)
428                 {
429                         return DefineNestedType (name, attr, parent, null, PackingSize.Unspecified, typeSize);
430                 }
431
432                 public TypeBuilder DefineNestedType (string name, TypeAttributes attr, Type parent, PackingSize packSize)
433                 {
434                         return DefineNestedType (name, attr, parent, null, packSize, UnspecifiedTypeSize);
435                 }
436
437                 public TypeBuilder DefineNestedType (string name, TypeAttributes attr, Type parent, PackingSize packSize,
438                                                      int typeSize)
439                 {
440                         return DefineNestedType (name, attr, parent, null, packSize, typeSize);
441                 }
442
443                 [ComVisible (true)]
444                 public ConstructorBuilder DefineConstructor (MethodAttributes attributes, CallingConventions callingConvention, Type[] parameterTypes)
445                 {
446                         return DefineConstructor (attributes, callingConvention, parameterTypes, null, null);
447                 }
448
449                 [ComVisible (true)]
450                 public ConstructorBuilder DefineConstructor (MethodAttributes attributes, CallingConventions callingConvention, Type[] parameterTypes, Type[][] requiredCustomModifiers, Type[][] optionalCustomModifiers)
451                 {
452                         check_not_created ();
453                         ConstructorBuilder cb = new ConstructorBuilder (this, attributes,
454                                 callingConvention, parameterTypes, requiredCustomModifiers,
455                                 optionalCustomModifiers);
456                         if (ctors != null) {
457                                 ConstructorBuilder[] new_ctors = new ConstructorBuilder [ctors.Length+1];
458                                 System.Array.Copy (ctors, new_ctors, ctors.Length);
459                                 new_ctors [ctors.Length] = cb;
460                                 ctors = new_ctors;
461                         } else {
462                                 ctors = new ConstructorBuilder [1];
463                                 ctors [0] = cb;
464                         }
465                         return cb;
466                 }
467
468                 [ComVisible (true)]
469                 public ConstructorBuilder DefineDefaultConstructor (MethodAttributes attributes)
470                 {
471                         Type parent_type, old_parent_type;
472
473                         if (parent != null)
474                                 parent_type = parent;
475                         else
476                                 parent_type = pmodule.assemblyb.corlib_object_type;
477
478                         old_parent_type = parent_type;
479                         parent_type = parent_type.InternalResolve ();
480                         /*This avoids corlib to have self references.*/
481                         if (parent_type == typeof (object) || parent_type == typeof (ValueType))
482                                 parent_type = old_parent_type;
483
484                         ConstructorInfo parent_constructor =
485                                 parent_type.GetConstructor (
486                                         BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance,
487                                         null, Type.EmptyTypes, null);
488                         if (parent_constructor == null) {
489                                 throw new NotSupportedException ("Parent does"
490                                         + " not have a default constructor."
491                                         + " The default constructor must be"
492                                         + " explicitly defined.");
493                         }
494
495                         ConstructorBuilder cb = DefineConstructor (attributes, 
496                                 CallingConventions.Standard, Type.EmptyTypes);
497                         ILGenerator ig = cb.GetILGenerator ();
498                         ig.Emit (OpCodes.Ldarg_0);
499                         ig.Emit (OpCodes.Call, parent_constructor);
500                         ig.Emit (OpCodes.Ret);
501                         return cb;
502                 }
503
504                 private void append_method (MethodBuilder mb)
505                 {
506                         if (methods != null) {
507                                 if (methods.Length == num_methods) {
508                                         MethodBuilder[] new_methods = new MethodBuilder [methods.Length * 2];
509                                         System.Array.Copy (methods, new_methods, num_methods);
510                                         methods = new_methods;
511                                 }
512                         } else {
513                                 methods = new MethodBuilder [1];
514                         }
515                         methods [num_methods] = mb;
516                         num_methods ++;
517                 }
518
519                 public MethodBuilder DefineMethod (string name, MethodAttributes attributes, Type returnType, Type[] parameterTypes)
520                 {
521                         return DefineMethod (name, attributes, CallingConventions.Standard,
522                                 returnType, parameterTypes);
523                 }
524
525                 public MethodBuilder DefineMethod (string name, MethodAttributes attributes, CallingConventions callingConvention, Type returnType, Type[] parameterTypes)
526                 {
527                         return DefineMethod (name, attributes, callingConvention, returnType,
528                                 null, null, parameterTypes, null, null);
529                 }
530
531                 public MethodBuilder DefineMethod (string name, MethodAttributes attributes, CallingConventions callingConvention, Type returnType, Type[] returnTypeRequiredCustomModifiers, Type[] returnTypeOptionalCustomModifiers, Type[] parameterTypes, Type[][] parameterTypeRequiredCustomModifiers, Type[][] parameterTypeOptionalCustomModifiers)
532                 {
533                         check_name ("name", name);
534                         check_not_created ();
535                         if (IsInterface && (
536                                 !((attributes & MethodAttributes.Abstract) != 0) || 
537                                 !((attributes & MethodAttributes.Virtual) != 0)) &&
538                                 !(((attributes & MethodAttributes.Static) != 0)))
539                                 throw new ArgumentException ("Interface method must be abstract and virtual.");
540
541                         if (returnType == null)
542                                 returnType = pmodule.assemblyb.corlib_void_type;
543                         MethodBuilder res = new MethodBuilder (this, name, attributes, 
544                                 callingConvention, returnType,
545                                 returnTypeRequiredCustomModifiers,
546                                 returnTypeOptionalCustomModifiers, parameterTypes,
547                                 parameterTypeRequiredCustomModifiers,
548                                 parameterTypeOptionalCustomModifiers);
549                         append_method (res);
550                         return res;
551                 }
552
553                 public MethodBuilder DefinePInvokeMethod (string name, string dllName, string entryName, MethodAttributes attributes, CallingConventions callingConvention, Type returnType, Type[] parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet)
554                 {
555                         return DefinePInvokeMethod (name, dllName, entryName, attributes,
556                                 callingConvention, returnType, null, null, parameterTypes,
557                                 null, null, nativeCallConv, nativeCharSet);
558                 }
559
560                 public MethodBuilder DefinePInvokeMethod (
561                                                 string name, 
562                                                 string dllName, 
563                                                 string entryName, MethodAttributes attributes, 
564                                                 CallingConventions callingConvention, 
565                                                 Type returnType, 
566                                                 Type[] returnTypeRequiredCustomModifiers, 
567                                                 Type[] returnTypeOptionalCustomModifiers, 
568                                                 Type[] parameterTypes, 
569                                                 Type[][] parameterTypeRequiredCustomModifiers, 
570                                                 Type[][] parameterTypeOptionalCustomModifiers, 
571                                                 CallingConvention nativeCallConv, 
572                                                 CharSet nativeCharSet)
573                 {
574                         check_name ("name", name);
575                         check_name ("dllName", dllName);
576                         check_name ("entryName", entryName);
577                         if ((attributes & MethodAttributes.Abstract) != 0)
578                                 throw new ArgumentException ("PInvoke methods must be static and native and cannot be abstract.");
579                         if (IsInterface)
580                                 throw new ArgumentException ("PInvoke methods cannot exist on interfaces.");
581                         check_not_created ();
582
583                         MethodBuilder res 
584                                 = new MethodBuilder (
585                                                 this, 
586                                                 name, 
587                                                 attributes, 
588                                                 callingConvention,
589                                                 returnType, 
590                                                 returnTypeRequiredCustomModifiers, 
591                                                 returnTypeOptionalCustomModifiers, 
592                                                 parameterTypes, 
593                                                 parameterTypeRequiredCustomModifiers, 
594                                                 parameterTypeOptionalCustomModifiers,
595                                                 dllName, 
596                                                 entryName, 
597                                                 nativeCallConv, 
598                                                 nativeCharSet);
599                         append_method (res);
600                         return res;
601                 }
602
603                 public MethodBuilder DefinePInvokeMethod (string name, string dllName, MethodAttributes attributes, CallingConventions callingConvention, Type returnType, Type[] parameterTypes, CallingConvention nativeCallConv, CharSet nativeCharSet) {
604                         return DefinePInvokeMethod (name, dllName, name, attributes, callingConvention, returnType, parameterTypes,
605                                 nativeCallConv, nativeCharSet);
606                 }
607
608                 public MethodBuilder DefineMethod (string name, MethodAttributes attributes)
609                 {
610                         return DefineMethod (name, attributes, CallingConventions.Standard);
611                 }
612
613                 public MethodBuilder DefineMethod (string name, MethodAttributes attributes, CallingConventions callingConvention)
614                 {
615                         return DefineMethod (name, attributes, callingConvention, null, null);
616                 }
617
618                 public void DefineMethodOverride (MethodInfo methodInfoBody, MethodInfo methodInfoDeclaration)
619                 {
620                         if (methodInfoBody == null)
621                                 throw new ArgumentNullException ("methodInfoBody");
622                         if (methodInfoDeclaration == null)
623                                 throw new ArgumentNullException ("methodInfoDeclaration");
624                         check_not_created ();
625                         if (methodInfoBody.DeclaringType != this)
626                                 throw new ArgumentException ("method body must belong to this type");
627
628                         if (methodInfoBody is MethodBuilder) {
629                                 MethodBuilder mb = (MethodBuilder)methodInfoBody;
630                                 mb.set_override (methodInfoDeclaration);
631                         }
632                 }
633
634                 public FieldBuilder DefineField (string fieldName, Type type, FieldAttributes attributes)
635                 {
636                         return DefineField (fieldName, type, null, null, attributes);
637                 }
638
639                 public FieldBuilder DefineField (string fieldName, Type type, Type[] requiredCustomModifiers, Type[] optionalCustomModifiers, FieldAttributes attributes)
640                 {
641                         check_name ("fieldName", fieldName);
642                         if (type == typeof (void))
643                                 throw new ArgumentException ("Bad field type in defining field.");
644                         check_not_created ();
645
646                         FieldBuilder res = new FieldBuilder (this, fieldName, type, attributes, requiredCustomModifiers, optionalCustomModifiers);
647                         if (fields != null) {
648                                 if (fields.Length == num_fields) {
649                                         FieldBuilder[] new_fields = new FieldBuilder [fields.Length * 2];
650                                         System.Array.Copy (fields, new_fields, num_fields);
651                                         fields = new_fields;
652                                 }
653                                 fields [num_fields] = res;
654                                 num_fields ++;
655                         } else {
656                                 fields = new FieldBuilder [1];
657                                 fields [0] = res;
658                                 num_fields ++;
659                         }
660
661                         if (IsEnum) {
662                                 if (underlying_type == null && (attributes & FieldAttributes.Static) == 0)
663                                         underlying_type = type;
664                         }
665
666                         return res;
667                 }
668
669                 public PropertyBuilder DefineProperty (string name, PropertyAttributes attributes, Type returnType, Type[] parameterTypes)
670                 {
671                         return DefineProperty (name, attributes, 0, returnType, null, null, parameterTypes, null, null);
672                 }
673                 
674                 public PropertyBuilder DefineProperty (string name, PropertyAttributes attributes, CallingConventions callingConvention, Type returnType, Type[] parameterTypes)
675                 {
676                         return DefineProperty (name, attributes, callingConvention, returnType , null, null, parameterTypes, null, null);
677                 }       
678
679                 public PropertyBuilder DefineProperty (string name, PropertyAttributes attributes, Type returnType, Type[] returnTypeRequiredCustomModifiers, Type[] returnTypeOptionalCustomModifiers, Type[] parameterTypes, Type[][] parameterTypeRequiredCustomModifiers, Type[][] parameterTypeOptionalCustomModifiers)
680                 {
681                         return DefineProperty (name, attributes, 0, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers);
682                 }
683                 
684                 public PropertyBuilder DefineProperty (string name, PropertyAttributes attributes, CallingConventions callingConvention, Type returnType, Type[] returnTypeRequiredCustomModifiers, Type[] returnTypeOptionalCustomModifiers, Type[] parameterTypes, Type[][] parameterTypeRequiredCustomModifiers, Type[][] parameterTypeOptionalCustomModifiers)
685                 {
686                         check_name ("name", name);
687                         if (parameterTypes != null)
688                                 foreach (Type param in parameterTypes)
689                                         if (param == null)
690                                                 throw new ArgumentNullException ("parameterTypes");
691                         check_not_created ();
692
693                         PropertyBuilder res = new PropertyBuilder (this, name, attributes, callingConvention, returnType, returnTypeRequiredCustomModifiers, returnTypeOptionalCustomModifiers, parameterTypes, parameterTypeRequiredCustomModifiers, parameterTypeOptionalCustomModifiers);
694
695                         if (properties != null) {
696                                 Array.Resize (ref properties, properties.Length + 1);
697                                 properties [properties.Length - 1] = res;
698                         } else {
699                                 properties = new PropertyBuilder [1] { res };
700                         }
701                         return res;
702                 }
703
704                 [ComVisible (true)]
705                 public ConstructorBuilder DefineTypeInitializer()
706                 {
707                         return DefineConstructor (MethodAttributes.Public |
708                                 MethodAttributes.Static | MethodAttributes.SpecialName |
709                                 MethodAttributes.RTSpecialName, CallingConventions.Standard,
710                                 null);
711                 }
712
713                 [MethodImplAttribute(MethodImplOptions.InternalCall)]
714                 private extern TypeInfo create_runtime_class ();
715
716                 private bool is_nested_in (Type t)
717                 {
718                         while (t != null) {
719                                 if (t == this)
720                                         return true;
721                                 else
722                                         t = t.DeclaringType;
723                         }
724                         return false;
725                 }
726
727                 // Return whenever this type has a ctor defined using DefineMethod ()
728                 private bool has_ctor_method () {
729                         MethodAttributes ctor_attrs = MethodAttributes.SpecialName | MethodAttributes.RTSpecialName;
730
731                         for (int i = 0; i < num_methods; ++i) {
732                                 MethodBuilder mb = (MethodBuilder)(methods[i]);
733
734                                 if (mb.Name == ConstructorInfo.ConstructorName && (mb.Attributes & ctor_attrs) == ctor_attrs)
735                                         return true;
736                         }
737
738                         return false;
739             }
740
741                 public Type CreateType ()
742                 {
743                         return CreateTypeInfo ();
744                 }
745                 
746                 public
747                 TypeInfo CreateTypeInfo ()
748                 {
749                         /* handle nesting_type */
750                         if (createTypeCalled)
751                                 return created;
752
753                         if (!IsInterface && (parent == null) && (this != pmodule.assemblyb.corlib_object_type) && (FullName != "<Module>")) {
754                                 SetParent (pmodule.assemblyb.corlib_object_type);
755                         }
756
757                         // Fire TypeResolve events for fields whose type is an unfinished
758                         // value type.
759                         if (fields != null) {
760                                 foreach (FieldBuilder fb in fields) {
761                                         if (fb == null)
762                                                 continue;
763                                         Type ft = fb.FieldType;
764                                         if (!fb.IsStatic && (ft is TypeBuilder) && ft.IsValueType && (ft != this) && is_nested_in (ft)) {
765                                                 TypeBuilder tb = (TypeBuilder)ft;
766                                                 if (!tb.is_created) {
767                                                         AppDomain.CurrentDomain.DoTypeResolve (tb);
768                                                         if (!tb.is_created) {
769                                                                 // FIXME: We should throw an exception here,
770                                                                 // but mcs expects that the type is created
771                                                                 // even if the exception is thrown
772                                                                 //throw new TypeLoadException ("Could not load type " + tb);
773                                                         }
774                                                 }
775                                         }
776                                 }
777                         }
778
779                         //
780                         // On classes, define a default constructor if not provided
781                         //
782                         if (!(IsInterface || IsValueType) && (ctors == null) && (tname != "<Module>") && 
783                                 (GetAttributeFlagsImpl () & TypeAttributes.Abstract | TypeAttributes.Sealed) != (TypeAttributes.Abstract | TypeAttributes.Sealed) && !has_ctor_method ())
784                                 DefineDefaultConstructor (MethodAttributes.Public);
785
786                         createTypeCalled = true;
787
788                         if ((parent != null) && parent.IsSealed)
789                                 throw new TypeLoadException ("Could not load type '" + FullName + "' from assembly '" + Assembly + "' because the parent type is sealed.");
790
791                         if (parent == pmodule.assemblyb.corlib_enum_type && methods != null)
792                                 throw new TypeLoadException ("Could not load type '" + FullName + "' from assembly '" + Assembly + "' because it is an enum with methods.");
793                         if (interfaces != null) {
794                                 foreach (var iface in interfaces) {
795                                         if (iface.IsNestedPrivate && iface.Assembly != Assembly)
796                                                 throw new TypeLoadException ("Could not load type '" + FullName + "' from assembly '" + Assembly + "' because it is implements the inaccessible interface '" + iface.FullName + "'.");
797                                 }
798                         }
799
800                         if (methods != null) {
801                                 bool is_concrete = !IsAbstract;
802                                 for (int i = 0; i < num_methods; ++i) {
803                                         MethodBuilder mb = (MethodBuilder)(methods[i]);
804                                         if (is_concrete && mb.IsAbstract)
805                                                 throw new InvalidOperationException ("Type is concrete but has abstract method " + mb);
806                                         mb.check_override ();
807                                         mb.fixup ();
808                                 }
809                         }
810
811                         if (ctors != null){
812                                 foreach (ConstructorBuilder ctor in ctors) 
813                                         ctor.fixup ();
814                         }
815
816                         ResolveUserTypes ();
817
818                         created = create_runtime_class ();
819                         if (created != null)
820                                 return created;
821                         return this;
822                 }
823
824                 void ResolveUserTypes () {
825                         parent = ResolveUserType (parent);
826                         ResolveUserTypes (interfaces);
827                         if (fields != null) {
828                                 foreach (var fb in fields) {
829                                         if (fb != null)
830                                                 fb.ResolveUserTypes ();
831                                 }
832                         }
833                         if (methods != null) {
834                                 foreach (var mb in methods) {
835                                         if (mb != null)
836                                                 mb.ResolveUserTypes ();
837                                 }
838                         }
839                         if (ctors != null) {
840                                 foreach (var cb in ctors) {
841                                         if (cb != null)
842                                                 cb.ResolveUserTypes ();
843                                 }
844                         }
845                 }
846
847                 static internal void ResolveUserTypes (Type[] types) {
848                         if (types != null)
849                                 for (int i = 0; i < types.Length; ++i)
850                                         types [i] = ResolveUserType (types [i]);
851                 }
852
853                 static internal Type ResolveUserType (Type t) {
854                         if (t != null && ((t.GetType ().Assembly != typeof (int).Assembly) || (t is TypeDelegator))) {
855                                 t = t.UnderlyingSystemType;
856                                 if (t != null && ((t.GetType ().Assembly != typeof (int).Assembly) || (t is TypeDelegator)))
857                                         throw new NotSupportedException ("User defined subclasses of System.Type are not yet supported.");
858                                 return t;
859                         } else {
860                                 return t;
861                         }
862                 }
863
864                 internal void FixupTokens (Dictionary<int, int> token_map, Dictionary<int, MemberInfo> member_map) {
865                         if (methods != null) {
866                                 for (int i = 0; i < num_methods; ++i)
867                                         methods[i].FixupTokens (token_map, member_map);
868                         }
869                         if (ctors != null) {
870                                 foreach (var cb in ctors)
871                                         cb.FixupTokens (token_map, member_map);
872                         }
873                 }
874
875                 internal void GenerateDebugInfo (ISymbolWriter symbolWriter)
876                 {
877                         symbolWriter.OpenNamespace (this.Namespace);
878
879                         if (methods != null) {
880                                 for (int i = 0; i < num_methods; ++i) {
881                                         MethodBuilder metb = (MethodBuilder) methods[i]; 
882                                         metb.GenerateDebugInfo (symbolWriter);
883                                 }
884                         }
885
886                         if (ctors != null) {
887                                 foreach (ConstructorBuilder ctor in ctors)
888                                         ctor.GenerateDebugInfo (symbolWriter);
889                         }
890                         
891                         symbolWriter.CloseNamespace ();
892
893                         if (subtypes != null) {
894                                 for (int i = 0; i < subtypes.Length; ++i)
895                                         subtypes [i].GenerateDebugInfo (symbolWriter);
896                         }
897                 }
898
899                 [ComVisible (true)]
900                 public override ConstructorInfo[] GetConstructors (BindingFlags bindingAttr)
901                 {
902                         if (is_created)
903                                 return created.GetConstructors (bindingAttr);
904
905                         throw new NotSupportedException ();
906                 }
907
908                 internal ConstructorInfo[] GetConstructorsInternal (BindingFlags bindingAttr)
909                 {
910                         if (ctors == null)
911                                 return new ConstructorInfo [0];
912                         ArrayList l = new ArrayList ();
913                         bool match;
914                         MethodAttributes mattrs;
915                         
916                         foreach (ConstructorBuilder c in ctors) {
917                                 match = false;
918                                 mattrs = c.Attributes;
919                                 if ((mattrs & MethodAttributes.MemberAccessMask) == MethodAttributes.Public) {
920                                         if ((bindingAttr & BindingFlags.Public) != 0)
921                                                 match = true;
922                                 } else {
923                                         if ((bindingAttr & BindingFlags.NonPublic) != 0)
924                                                 match = true;
925                                 }
926                                 if (!match)
927                                         continue;
928                                 match = false;
929                                 if ((mattrs & MethodAttributes.Static) != 0) {
930                                         if ((bindingAttr & BindingFlags.Static) != 0)
931                                                 match = true;
932                                 } else {
933                                         if ((bindingAttr & BindingFlags.Instance) != 0)
934                                                 match = true;
935                                 }
936                                 if (!match)
937                                         continue;
938                                 l.Add (c);
939                         }
940                         ConstructorInfo[] result = new ConstructorInfo [l.Count];
941                         l.CopyTo (result);
942                         return result;
943                 }
944
945                 public override Type GetElementType ()
946                 {
947                         throw new NotSupportedException ();
948                 }
949
950                 public override EventInfo GetEvent (string name, BindingFlags bindingAttr)
951                 {
952                         check_created ();
953                         return created.GetEvent (name, bindingAttr);
954                 }
955
956                 /* Needed to keep signature compatibility with MS.NET */
957                 public override EventInfo[] GetEvents ()
958                 {
959                         const BindingFlags DefaultBindingFlags = BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance;
960                         return GetEvents (DefaultBindingFlags);
961                 }
962
963                 public override EventInfo[] GetEvents (BindingFlags bindingAttr)
964                 {
965                         if (is_created)
966                                 return created.GetEvents (bindingAttr);
967                         throw new NotSupportedException ();
968                 }
969
970                 public override FieldInfo GetField (string name, BindingFlags bindingAttr)
971                 {
972                         if (created != null)
973                                 return created.GetField (name, bindingAttr);
974
975                         if (fields == null)
976                                 return null;
977
978                         bool match;
979                         FieldAttributes mattrs;
980                         
981                         foreach (FieldInfo c in fields) {
982                                 if (c == null)
983                                         continue;
984                                 if (c.Name != name)
985                                         continue;
986                                 match = false;
987                                 mattrs = c.Attributes;
988                                 if ((mattrs & FieldAttributes.FieldAccessMask) == FieldAttributes.Public) {
989                                         if ((bindingAttr & BindingFlags.Public) != 0)
990                                                 match = true;
991                                 } else {
992                                         if ((bindingAttr & BindingFlags.NonPublic) != 0)
993                                                 match = true;
994                                 }
995                                 if (!match)
996                                         continue;
997                                 match = false;
998                                 if ((mattrs & FieldAttributes.Static) != 0) {
999                                         if ((bindingAttr & BindingFlags.Static) != 0)
1000                                                 match = true;
1001                                 } else {
1002                                         if ((bindingAttr & BindingFlags.Instance) != 0)
1003                                                 match = true;
1004                                 }
1005                                 if (!match)
1006                                         continue;
1007                                 return c;
1008                         }
1009                         return null;
1010                 }
1011
1012                 public override FieldInfo[] GetFields (BindingFlags bindingAttr)
1013                 {
1014                         if (created != null)
1015                                 return created.GetFields (bindingAttr);
1016
1017                         if (fields == null)
1018                                 return new FieldInfo [0];
1019                         ArrayList l = new ArrayList ();
1020                         bool match;
1021                         FieldAttributes mattrs;
1022                         
1023                         foreach (FieldInfo c in fields) {
1024                                 if (c == null)
1025                                         continue;
1026                                 match = false;
1027                                 mattrs = c.Attributes;
1028                                 if ((mattrs & FieldAttributes.FieldAccessMask) == FieldAttributes.Public) {
1029                                         if ((bindingAttr & BindingFlags.Public) != 0)
1030                                                 match = true;
1031                                 } else {
1032                                         if ((bindingAttr & BindingFlags.NonPublic) != 0)
1033                                                 match = true;
1034                                 }
1035                                 if (!match)
1036                                         continue;
1037                                 match = false;
1038                                 if ((mattrs & FieldAttributes.Static) != 0) {
1039                                         if ((bindingAttr & BindingFlags.Static) != 0)
1040                                                 match = true;
1041                                 } else {
1042                                         if ((bindingAttr & BindingFlags.Instance) != 0)
1043                                                 match = true;
1044                                 }
1045                                 if (!match)
1046                                         continue;
1047                                 l.Add (c);
1048                         }
1049                         FieldInfo[] result = new FieldInfo [l.Count];
1050                         l.CopyTo (result);
1051                         return result;
1052                 }
1053
1054                 public override Type GetInterface (string name, bool ignoreCase)
1055                 {
1056                         check_created ();
1057                         return created.GetInterface (name, ignoreCase);
1058                 }
1059                 
1060                 public override Type[] GetInterfaces ()
1061                 {
1062                         if (is_created)
1063                                 return created.GetInterfaces ();
1064
1065                         if (interfaces != null) {
1066                                 Type[] ret = new Type [interfaces.Length];
1067                                 interfaces.CopyTo (ret, 0);
1068                                 return ret;
1069                         } else {
1070                                 return Type.EmptyTypes;
1071                         }
1072                 }
1073
1074                 public override MemberInfo[] GetMember (string name, MemberTypes type,
1075                                                                                                 BindingFlags bindingAttr)
1076                 {
1077                         check_created ();
1078                         return created.GetMember (name, type, bindingAttr);
1079                 }
1080
1081                 public override MemberInfo[] GetMembers (BindingFlags bindingAttr)
1082                 {
1083                         check_created ();
1084                         return created.GetMembers (bindingAttr);
1085                 }
1086
1087                 private MethodInfo[] GetMethodsByName (string name, BindingFlags bindingAttr, bool ignoreCase, Type reflected_type)
1088                 {
1089                         MethodInfo[] candidates;
1090                         bool match;
1091                         MethodAttributes mattrs;
1092
1093                         if (((bindingAttr & BindingFlags.DeclaredOnly) == 0) && (parent != null)) {
1094                                 MethodInfo [] parent_methods = parent.GetMethods (bindingAttr);
1095                                 ArrayList parent_candidates = new ArrayList (parent_methods.Length);
1096
1097                                 bool flatten = (bindingAttr & BindingFlags.FlattenHierarchy) != 0;
1098
1099                                 for (int i = 0; i < parent_methods.Length; i++) {
1100                                         MethodInfo m = parent_methods [i];
1101
1102                                         mattrs = m.Attributes;
1103
1104                                         if (m.IsStatic && !flatten)
1105                                                 continue;
1106
1107                                         switch (mattrs & MethodAttributes.MemberAccessMask) {
1108                                         case MethodAttributes.Public:
1109                                                 match = (bindingAttr & BindingFlags.Public) != 0;
1110                                                 break;
1111                                         case MethodAttributes.Assembly:
1112                                                 match = (bindingAttr & BindingFlags.NonPublic) != 0;
1113                                                 break;
1114                                         case MethodAttributes.Private:
1115                                                 match = false;
1116                                                 break;
1117                                         default:
1118                                                 match = (bindingAttr & BindingFlags.NonPublic) != 0;
1119                                                 break;
1120                                         }
1121
1122                                         if (match)
1123                                                 parent_candidates.Add (m);
1124                                 }
1125
1126                                 if (methods == null) {
1127                                         candidates = new MethodInfo [parent_candidates.Count];
1128                                         parent_candidates.CopyTo (candidates);
1129                                 } else {
1130                                         candidates = new MethodInfo [methods.Length + parent_candidates.Count];
1131                                         parent_candidates.CopyTo (candidates, 0);
1132                                         methods.CopyTo (candidates, parent_candidates.Count);
1133                                 }
1134                         }
1135                         else
1136                                 candidates = methods;
1137
1138                         if (candidates == null)
1139                                 return new MethodInfo [0];
1140
1141                         ArrayList l = new ArrayList ();
1142
1143                         foreach (MethodInfo c in candidates) {
1144                                 if (c == null)
1145                                         continue;
1146                                 if (name != null) {
1147                                         if (String.Compare (c.Name, name, ignoreCase) != 0)
1148                                                 continue;
1149                                 }
1150                                 match = false;
1151                                 mattrs = c.Attributes;
1152                                 if ((mattrs & MethodAttributes.MemberAccessMask) == MethodAttributes.Public) {
1153                                         if ((bindingAttr & BindingFlags.Public) != 0)
1154                                                 match = true;
1155                                 } else {
1156                                         if ((bindingAttr & BindingFlags.NonPublic) != 0)
1157                                                 match = true;
1158                                 }
1159                                 if (!match)
1160                                         continue;
1161                                 match = false;
1162                                 if ((mattrs & MethodAttributes.Static) != 0) {
1163                                         if ((bindingAttr & BindingFlags.Static) != 0)
1164                                                 match = true;
1165                                 } else {
1166                                         if ((bindingAttr & BindingFlags.Instance) != 0)
1167                                                 match = true;
1168                                 }
1169                                 if (!match)
1170                                         continue;
1171                                 l.Add (c);
1172                         }
1173
1174                         MethodInfo[] result = new MethodInfo [l.Count];
1175                         l.CopyTo (result);
1176                         return result;
1177                 }
1178
1179                 public override MethodInfo[] GetMethods (BindingFlags bindingAttr)
1180                 {
1181                         return GetMethodsByName (null, bindingAttr, false, this);
1182                 }
1183
1184                 protected override MethodInfo GetMethodImpl (string name, BindingFlags bindingAttr,
1185                                                              Binder binder,
1186                                                              CallingConventions callConvention,
1187                                                              Type[] types, ParameterModifier[] modifiers)
1188                 {
1189                         check_created ();
1190
1191                         if (types == null)
1192                                 return created.GetMethod (name, bindingAttr);
1193
1194                         return created.GetMethod (name, bindingAttr, binder, callConvention, types, modifiers);
1195                 }
1196
1197                 public override Type GetNestedType (string name, BindingFlags bindingAttr)
1198                 {
1199                         check_created ();
1200
1201                         if (subtypes == null)
1202                                 return null;
1203
1204                         foreach (TypeBuilder t in subtypes) {
1205                                 if (!t.is_created)
1206                                         continue;
1207                                 if ((t.attrs & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPublic) {
1208                                         if ((bindingAttr & BindingFlags.Public) == 0)
1209                                                 continue;
1210                                 } else {
1211                                         if ((bindingAttr & BindingFlags.NonPublic) == 0)
1212                                                 continue;
1213                                 }
1214                                 if (t.Name == name)
1215                                         return t.created;
1216                         }
1217
1218                         return null;
1219                 }
1220
1221                 public override Type[] GetNestedTypes (BindingFlags bindingAttr)
1222                 {
1223                         if (!is_created)
1224                                 throw new NotSupportedException ();
1225
1226                         bool match;
1227                         ArrayList result = new ArrayList ();
1228
1229                         if (subtypes == null)
1230                                 return Type.EmptyTypes;
1231                         foreach (TypeBuilder t in subtypes) {
1232                                 match = false;
1233                                 if ((t.attrs & TypeAttributes.VisibilityMask) == TypeAttributes.NestedPublic) {
1234                                         if ((bindingAttr & BindingFlags.Public) != 0)
1235                                                 match = true;
1236                                 } else {
1237                                         if ((bindingAttr & BindingFlags.NonPublic) != 0)
1238                                                 match = true;
1239                                 }
1240                                 if (!match)
1241                                         continue;
1242                                 result.Add (t);
1243                         }
1244                         Type[] r = new Type [result.Count];
1245                         result.CopyTo (r);
1246                         return r;
1247                 }
1248
1249                 public override PropertyInfo[] GetProperties (BindingFlags bindingAttr)
1250                 {
1251                         if (is_created)
1252                                 return created.GetProperties (bindingAttr);
1253
1254                         if (properties == null)
1255                                 return new PropertyInfo [0];
1256                         ArrayList l = new ArrayList ();
1257                         bool match;
1258                         MethodAttributes mattrs;
1259                         MethodInfo accessor;
1260                         
1261                         foreach (PropertyInfo c in properties) {
1262                                 match = false;
1263                                 accessor = c.GetGetMethod (true);
1264                                 if (accessor == null)
1265                                         accessor = c.GetSetMethod (true);
1266                                 if (accessor == null)
1267                                         continue;
1268                                 mattrs = accessor.Attributes;
1269                                 if ((mattrs & MethodAttributes.MemberAccessMask) == MethodAttributes.Public) {
1270                                         if ((bindingAttr & BindingFlags.Public) != 0)
1271                                                 match = true;
1272                                 } else {
1273                                         if ((bindingAttr & BindingFlags.NonPublic) != 0)
1274                                                 match = true;
1275                                 }
1276                                 if (!match)
1277                                         continue;
1278                                 match = false;
1279                                 if ((mattrs & MethodAttributes.Static) != 0) {
1280                                         if ((bindingAttr & BindingFlags.Static) != 0)
1281                                                 match = true;
1282                                 } else {
1283                                         if ((bindingAttr & BindingFlags.Instance) != 0)
1284                                                 match = true;
1285                                 }
1286                                 if (!match)
1287                                         continue;
1288                                 l.Add (c);
1289                         }
1290                         PropertyInfo[] result = new PropertyInfo [l.Count];
1291                         l.CopyTo (result);
1292                         return result;
1293                 }
1294                 
1295                 protected override PropertyInfo GetPropertyImpl (string name, BindingFlags bindingAttr, Binder binder, Type returnType, Type[] types, ParameterModifier[] modifiers)
1296                 {
1297                         throw not_supported ();
1298                 }
1299
1300                 protected override bool HasElementTypeImpl ()
1301                 {
1302                         // a TypeBuilder can never represent an array, pointer
1303                         if (!is_created)
1304                                 return false;
1305
1306                         return created.HasElementType;
1307                 }
1308
1309                 public override object InvokeMember (string name, BindingFlags invokeAttr, Binder binder, object target, object[] args, ParameterModifier[] modifiers, CultureInfo culture, string[] namedParameters)
1310                 {
1311                         check_created ();
1312                         return created.InvokeMember (name, invokeAttr, binder, target, args, modifiers, culture, namedParameters);
1313                 }
1314
1315                 protected override bool IsArrayImpl ()
1316                 {
1317                         return false; /*A TypeBuilder never represents a non typedef type.*/
1318                 }
1319
1320                 protected override bool IsByRefImpl ()
1321                 {
1322                         return false; /*A TypeBuilder never represents a non typedef type.*/
1323                 }
1324
1325                 protected override bool IsCOMObjectImpl ()
1326                 {
1327                         return ((GetAttributeFlagsImpl () & TypeAttributes.Import) != 0);
1328                 }
1329
1330                 protected override bool IsPointerImpl ()
1331                 {
1332                         return false; /*A TypeBuilder never represents a non typedef type.*/
1333                 }
1334
1335                 protected override bool IsPrimitiveImpl ()
1336                 {
1337                         // FIXME
1338                         return false;
1339                 }
1340
1341                 // FIXME: I doubt just removing this still works.
1342                 protected override bool IsValueTypeImpl ()
1343                 {
1344                         if (this == pmodule.assemblyb.corlib_value_type || this == pmodule.assemblyb.corlib_enum_type)
1345                                 return false;
1346                         Type parent_type = parent;
1347                         while (parent_type != null) {
1348                                 if (parent_type == pmodule.assemblyb.corlib_value_type)
1349                                         return true;
1350                                 parent_type = parent_type.BaseType;
1351                         }
1352                         return false;
1353                 }
1354                 
1355                 public override Type MakeArrayType ()
1356                 {
1357                         return new ArrayType (this, 0);
1358                 }
1359
1360                 public override Type MakeArrayType (int rank)
1361                 {
1362                         if (rank < 1)
1363                                 throw new IndexOutOfRangeException ();
1364                         return new ArrayType (this, rank);
1365                 }
1366
1367                 public override Type MakeByRefType ()
1368                 {
1369                         return new ByRefType (this);
1370                 }
1371
1372                 public override Type MakeGenericType (params Type [] typeArguments)
1373                 {
1374                         //return base.MakeGenericType (typeArguments);
1375
1376                         if (!IsGenericTypeDefinition)
1377                                 throw new InvalidOperationException ("not a generic type definition");
1378                         if (typeArguments == null)
1379                                 throw new ArgumentNullException ("typeArguments");
1380
1381                         if (generic_params.Length != typeArguments.Length)
1382                                 throw new ArgumentException (String.Format ("The type or method has {0} generic parameter(s) but {1} generic argument(s) where provided. A generic argument must be provided for each generic parameter.", generic_params.Length, typeArguments.Length), "typeArguments");
1383
1384                         foreach (Type t in typeArguments) {
1385                                 if (t == null)
1386                                         throw new ArgumentNullException ("typeArguments");                              
1387                         }
1388
1389                         Type[] copy = new Type [typeArguments.Length];
1390                         typeArguments.CopyTo (copy, 0);
1391                         return pmodule.assemblyb.MakeGenericType (this, copy);
1392                 }
1393
1394                 public override Type MakePointerType ()
1395                 {
1396                         return new PointerType (this);
1397                 }
1398
1399                 public override RuntimeTypeHandle TypeHandle {
1400                         get {
1401                                 check_created ();
1402                                 return created.TypeHandle;
1403                         }
1404                 }
1405                 
1406                 public void SetCustomAttribute (CustomAttributeBuilder customBuilder)
1407                 {
1408                         if (customBuilder == null)
1409                                 throw new ArgumentNullException ("customBuilder");
1410
1411                         string attrname = customBuilder.Ctor.ReflectedType.FullName;
1412                         if (attrname == "System.Runtime.InteropServices.StructLayoutAttribute") {
1413                                 byte[] data = customBuilder.Data;
1414                                 int layout_kind; /* the (stupid) ctor takes a short or an int ... */
1415                                 layout_kind = (int)data [2];
1416                                 layout_kind |= ((int)data [3]) << 8;
1417                                 attrs &= ~TypeAttributes.LayoutMask;
1418                                 switch ((LayoutKind)layout_kind) {
1419                                 case LayoutKind.Auto:
1420                                         attrs |= TypeAttributes.AutoLayout;
1421                                         break;
1422                                 case LayoutKind.Explicit:
1423                                         attrs |= TypeAttributes.ExplicitLayout;
1424                                         break;
1425                                 case LayoutKind.Sequential:
1426                                         attrs |= TypeAttributes.SequentialLayout;
1427                                         break;
1428                                 default:
1429                                         // we should ignore it since it can be any value anyway...
1430                                         throw new Exception ("Error in customattr");
1431                                 }
1432                                 
1433                                 var ctor_type = customBuilder.Ctor is ConstructorBuilder ? ((ConstructorBuilder)customBuilder.Ctor).parameters[0] : customBuilder.Ctor.GetParametersInternal()[0].ParameterType;
1434                                 int pos = 6;
1435                                 if (ctor_type.FullName == "System.Int16")
1436                                         pos = 4;
1437                                 int nnamed = (int)data [pos++];
1438                                 nnamed |= ((int)data [pos++]) << 8;
1439                                 for (int i = 0; i < nnamed; ++i) {
1440                                         //byte named_type = data [pos++];
1441                                         pos ++;
1442                                         byte type = data [pos++];
1443                                         int len;
1444                                         string named_name;
1445
1446                                         if (type == 0x55) {
1447                                                 len = CustomAttributeBuilder.decode_len (data, pos, out pos);
1448                                                 //string named_typename = 
1449                                                 CustomAttributeBuilder.string_from_bytes (data, pos, len);
1450                                                 pos += len;
1451                                                 // FIXME: Check that 'named_type' and 'named_typename' match, etc.
1452                                                 //        See related code/FIXME in mono/mono/metadata/reflection.c
1453                                         }
1454
1455                                         len = CustomAttributeBuilder.decode_len (data, pos, out pos);
1456                                         named_name = CustomAttributeBuilder.string_from_bytes (data, pos, len);
1457                                         pos += len;
1458                                         /* all the fields are integers in StructLayout */
1459                                         int value = (int)data [pos++];
1460                                         value |= ((int)data [pos++]) << 8;
1461                                         value |= ((int)data [pos++]) << 16;
1462                                         value |= ((int)data [pos++]) << 24;
1463                                         switch (named_name) {
1464                                         case "CharSet":
1465                                                 switch ((CharSet)value) {
1466                                                 case CharSet.None:
1467                                                 case CharSet.Ansi:
1468                                                         attrs &= ~(TypeAttributes.UnicodeClass | TypeAttributes.AutoClass);
1469                                                         break;
1470                                                 case CharSet.Unicode:
1471                                                         attrs &= ~TypeAttributes.AutoClass;
1472                                                         attrs |= TypeAttributes.UnicodeClass;
1473                                                         break;
1474                                                 case CharSet.Auto:
1475                                                         attrs &= ~TypeAttributes.UnicodeClass;
1476                                                         attrs |= TypeAttributes.AutoClass;
1477                                                         break;
1478                                                 default:
1479                                                         break; // error out...
1480                                                 }
1481                                                 break;
1482                                         case "Pack":
1483                                                 packing_size = (PackingSize)value;
1484                                                 break;
1485                                         case "Size":
1486                                                 class_size = value;
1487                                                 break;
1488                                         default:
1489                                                 break; // error out...
1490                                         }
1491                                 }
1492                                 return;
1493                         } else if (attrname == "System.Runtime.CompilerServices.SpecialNameAttribute") {
1494                                 attrs |= TypeAttributes.SpecialName;
1495                                 return;
1496                         } else if (attrname == "System.SerializableAttribute") {
1497                                 attrs |= TypeAttributes.Serializable;
1498                                 return;
1499                         } else if (attrname == "System.Runtime.InteropServices.ComImportAttribute") {
1500                                 attrs |= TypeAttributes.Import;
1501                                 return;
1502                         } else if (attrname == "System.Security.SuppressUnmanagedCodeSecurityAttribute") {
1503                                 attrs |= TypeAttributes.HasSecurity;
1504                         }
1505
1506                         if (cattrs != null) {
1507                                 CustomAttributeBuilder[] new_array = new CustomAttributeBuilder [cattrs.Length + 1];
1508                                 cattrs.CopyTo (new_array, 0);
1509                                 new_array [cattrs.Length] = customBuilder;
1510                                 cattrs = new_array;
1511                         } else {
1512                                 cattrs = new CustomAttributeBuilder [1];
1513                                 cattrs [0] = customBuilder;
1514                         }
1515                 }
1516
1517                 [ComVisible (true)]
1518                 public void SetCustomAttribute (ConstructorInfo con, byte[] binaryAttribute)
1519                 {
1520                         SetCustomAttribute (new CustomAttributeBuilder (con, binaryAttribute));
1521                 }
1522
1523                 public EventBuilder DefineEvent (string name, EventAttributes attributes, Type eventtype)
1524                 {
1525                         check_name ("name", name);
1526                         if (eventtype == null)
1527                                 throw new ArgumentNullException ("type");
1528                         check_not_created ();
1529
1530                         EventBuilder res = new EventBuilder (this, name, attributes, eventtype);
1531                         if (events != null) {
1532                                 EventBuilder[] new_events = new EventBuilder [events.Length+1];
1533                                 System.Array.Copy (events, new_events, events.Length);
1534                                 new_events [events.Length] = res;
1535                                 events = new_events;
1536                         } else {
1537                                 events = new EventBuilder [1];
1538                                 events [0] = res;
1539                         }
1540                         return res;
1541                 }
1542
1543                 public FieldBuilder DefineInitializedData (string name, byte[] data, FieldAttributes attributes) {
1544                         if (data == null)
1545                                 throw new ArgumentNullException ("data");
1546
1547                         FieldBuilder res = DefineUninitializedData (name, data.Length, attributes);
1548                         res.SetRVAData (data);
1549                         return res;
1550                 }
1551
1552                 public FieldBuilder DefineUninitializedData (string name, int size, FieldAttributes attributes)
1553                 {
1554                         if (name == null)
1555                                 throw new ArgumentNullException ("name");
1556                         if (name.Length == 0)
1557                                 throw new ArgumentException ("Empty name is not legal", "name");
1558                         if ((size <= 0) || (size > 0x3f0000))
1559                                 throw new ArgumentException ("Data size must be > 0 and < 0x3f0000");
1560                         check_not_created ();
1561
1562                         string typeName = "$ArrayType$" + size;
1563                         TypeIdentifier ident = TypeIdentifiers.WithoutEscape (typeName);
1564                         Type datablobtype = pmodule.GetRegisteredType (fullname.NestedName(ident));
1565                         if (datablobtype == null) {
1566                                 TypeBuilder tb = DefineNestedType (typeName,
1567                                         TypeAttributes.NestedPrivate|TypeAttributes.ExplicitLayout|TypeAttributes.Sealed,
1568                                         pmodule.assemblyb.corlib_value_type, null, PackingSize.Size1, size);
1569                                 tb.CreateType ();
1570                                 datablobtype = tb;
1571                         }
1572                         return DefineField (name, datablobtype, attributes|FieldAttributes.Static|FieldAttributes.HasFieldRVA);
1573                 }
1574
1575                 public TypeToken TypeToken {
1576                         get {
1577                                 return new TypeToken (0x02000000 | table_idx);
1578                         }
1579                 }
1580
1581                 public void SetParent (Type parent)
1582                 {
1583                         check_not_created ();
1584
1585                         if (parent == null) {
1586                                 if ((attrs & TypeAttributes.Interface) != 0) {
1587                                         if ((attrs & TypeAttributes.Abstract) == 0)
1588                                                 throw new InvalidOperationException ("Interface must be declared abstract.");
1589                                         this.parent = null;
1590                                 } else {
1591                                         this.parent = typeof (object);
1592                                 }
1593                         } else {
1594                                 this.parent = parent;
1595                         }
1596                         this.parent = ResolveUserType (this.parent);
1597                 }
1598
1599                 internal int get_next_table_index (object obj, int table, bool inc) {
1600                         return pmodule.get_next_table_index (obj, table, inc);
1601                 }
1602
1603                 [ComVisible (true)]
1604                 public override InterfaceMapping GetInterfaceMap (Type interfaceType)
1605                 {
1606                         if (created == null)
1607                                 throw new NotSupportedException ("This method is not implemented for incomplete types.");
1608
1609                         return created.GetInterfaceMap (interfaceType);
1610                 }
1611
1612                 internal override Type InternalResolve ()
1613                 {
1614                         check_created ();
1615                         return created;
1616                 }
1617
1618                 internal override Type RuntimeResolve ()
1619                 {
1620                         check_created ();
1621                         return created;
1622                 }
1623
1624                 internal bool is_created {
1625                         get {
1626                                 return createTypeCalled;
1627                         }
1628                 }
1629
1630                 private Exception not_supported ()
1631                 {
1632                         return new NotSupportedException ("The invoked member is not supported in a dynamic module.");
1633                 }
1634
1635                 private void check_not_created ()
1636                 {
1637                         if (is_created)
1638                                 throw new InvalidOperationException ("Unable to change after type has been created.");
1639                 }
1640
1641                 private void check_created ()
1642                 {
1643                         if (!is_created)
1644                                 throw not_supported ();
1645                 }
1646
1647                 private void check_name (string argName, string name)
1648                 {
1649                         if (name == null)
1650                                 throw new ArgumentNullException (argName);
1651                         if (name.Length == 0)
1652                                 throw new ArgumentException ("Empty name is not legal", argName);
1653                         if (name [0] == ((char)0))
1654                                 throw new ArgumentException ("Illegal name", argName);
1655                 }
1656
1657                 public override String ToString ()
1658                 {
1659                         return FullName;
1660                 }
1661
1662                 [MonoTODO]
1663                 public override bool IsAssignableFrom (Type c)
1664                 {
1665                         return base.IsAssignableFrom (c);
1666                 }
1667
1668                 [MonoTODO ("arrays")]
1669                 internal bool IsAssignableTo (Type c)
1670                 {
1671                         if (c == this)
1672                                 return true;
1673
1674                         if (c.IsInterface) {
1675                                 if (parent != null && is_created) {
1676                                         if (c.IsAssignableFrom (parent))
1677                                                 return true;
1678                                 }
1679
1680                                 if (interfaces == null)
1681                                         return false;
1682                                 foreach (Type t in interfaces)
1683                                         if (c.IsAssignableFrom (t))
1684                                                 return true;
1685                                 if (!is_created)
1686                                         return false;
1687                         }
1688
1689                         if (parent == null)
1690                                 return c == typeof (object);
1691                         else
1692                                 return c.IsAssignableFrom (parent);
1693                 }
1694
1695                 public bool IsCreated ()
1696                 {
1697                         return is_created;
1698                 }
1699
1700                 public override Type[] GetGenericArguments ()
1701                 {
1702                         if (generic_params == null)
1703                                 return null;
1704                         Type[] args = new Type [generic_params.Length];
1705                         generic_params.CopyTo (args, 0);
1706                         return args;
1707                 }
1708
1709                 public override Type GetGenericTypeDefinition ()
1710                 {
1711                         if (generic_params == null)
1712                                 throw new InvalidOperationException ("Type is not generic");
1713                         return this;
1714                 }
1715
1716                 public override bool ContainsGenericParameters {
1717                         get {
1718                                 return generic_params != null;
1719                         }
1720                 }
1721
1722                 public override bool IsGenericParameter {
1723                         get {
1724                                 return false;
1725                         }
1726                 }
1727
1728                 public override GenericParameterAttributes GenericParameterAttributes {
1729                         get { return GenericParameterAttributes.None; }
1730                 }
1731
1732                 public override bool IsGenericTypeDefinition {
1733                         get {
1734                                 return generic_params != null;
1735                         }
1736                 }
1737
1738                 public override bool IsGenericType {
1739                         get { return IsGenericTypeDefinition; }
1740                 }
1741
1742                 [MonoTODO]
1743                 public override int GenericParameterPosition {
1744                         get {
1745                                 return 0;
1746                         }
1747                 }
1748
1749                 public override MethodBase DeclaringMethod {
1750                         get {
1751                                 return null;
1752                         }
1753                 }
1754
1755                 public GenericTypeParameterBuilder[] DefineGenericParameters (params string[] names)
1756                 {
1757                         if (names == null)
1758                                 throw new ArgumentNullException ("names");
1759                         if (names.Length == 0)
1760                                 throw new ArgumentException ("names");
1761
1762                         generic_params = new GenericTypeParameterBuilder [names.Length];
1763                         for (int i = 0; i < names.Length; i++) {
1764                                 string item = names [i];
1765                                 if (item == null)
1766                                         throw new ArgumentNullException ("names");
1767                                 generic_params [i] = new GenericTypeParameterBuilder (this, null, item, i);
1768                         }
1769
1770                         return generic_params;
1771                 }
1772
1773                 public static ConstructorInfo GetConstructor (Type type, ConstructorInfo constructor)
1774                 {
1775                         /*FIXME I would expect the same checks of GetMethod here*/
1776                         if (type == null)
1777                                 throw new ArgumentException ("Type is not generic", "type");
1778
1779                         if (!type.IsGenericType)
1780                                 throw new ArgumentException ("Type is not a generic type", "type");
1781
1782                         if (type.IsGenericTypeDefinition)
1783                                 throw new ArgumentException ("Type cannot be a generic type definition", "type");
1784
1785                         if (constructor == null)
1786                                 throw new NullReferenceException (); //MS raises this instead of an ArgumentNullException
1787
1788                         if (!constructor.DeclaringType.IsGenericTypeDefinition)
1789                                 throw new ArgumentException ("constructor declaring type is not a generic type definition", "constructor");
1790                         if (constructor.DeclaringType != type.GetGenericTypeDefinition ())
1791                                 throw new ArgumentException ("constructor declaring type is not the generic type definition of type", "constructor");
1792
1793                         ConstructorInfo res = type.GetConstructor (constructor);
1794                         if (res == null)
1795                                 throw new ArgumentException ("constructor not found");
1796
1797                         return res;
1798                 }
1799
1800                 static bool IsValidGetMethodType (Type type)
1801                 {
1802                         if (type is TypeBuilder || type is TypeBuilderInstantiation)
1803                                 return true;
1804                         /*GetMethod() must work with TypeBuilders after CreateType() was called.*/
1805                         if (type.Module is ModuleBuilder)
1806                                 return true;
1807                         if (type.IsGenericParameter)
1808                                 return false;
1809
1810                         Type[] inst = type.GetGenericArguments ();
1811                         if (inst == null)
1812                                 return false;
1813                         for (int i = 0; i < inst.Length; ++i) {
1814                                 if (IsValidGetMethodType (inst [i]))
1815                                         return true;
1816                         }
1817                         return false;
1818                 }
1819
1820                 public static MethodInfo GetMethod (Type type, MethodInfo method)
1821                 {
1822                         if (!IsValidGetMethodType (type))
1823                                 throw new ArgumentException ("type is not TypeBuilder but " + type.GetType (), "type");
1824
1825                         if (type is TypeBuilder && type.ContainsGenericParameters)
1826                                 type = type.MakeGenericType (type.GetGenericArguments ());
1827
1828                         if (!type.IsGenericType)
1829                                 throw new ArgumentException ("type is not a generic type", "type");
1830
1831                         if (!method.DeclaringType.IsGenericTypeDefinition)
1832                                 throw new ArgumentException ("method declaring type is not a generic type definition", "method");
1833                         if (method.DeclaringType != type.GetGenericTypeDefinition ())
1834                                 throw new ArgumentException ("method declaring type is not the generic type definition of type", "method");
1835                         if (method == null)
1836                                 throw new NullReferenceException (); //MS raises this instead of an ArgumentNullException
1837
1838                         MethodInfo res = type.GetMethod (method);
1839                         if (res == null)
1840                                 throw new ArgumentException (String.Format ("method {0} not found in type {1}", method.Name, type));
1841                                 
1842                         return res;
1843                 }
1844
1845                 public static FieldInfo GetField (Type type, FieldInfo field)
1846                 {
1847                         if (!type.IsGenericType)
1848                                 throw new ArgumentException ("Type is not a generic type", "type");
1849
1850                         if (type.IsGenericTypeDefinition)
1851                                 throw new ArgumentException ("Type cannot be a generic type definition", "type");
1852
1853                         if (field is FieldOnTypeBuilderInst)
1854                                 throw new ArgumentException ("The specified field must be declared on a generic type definition.", "field");
1855
1856                         if (field.DeclaringType != type.GetGenericTypeDefinition ())
1857                                 throw new ArgumentException ("field declaring type is not the generic type definition of type", "method");
1858
1859                         FieldInfo res = type.GetField (field);
1860                         if (res == null)
1861                                 throw new System.Exception ("field not found");
1862                         else
1863                                 return res;
1864                 }
1865
1866
1867                 void _TypeBuilder.GetIDsOfNames([In] ref Guid riid, IntPtr rgszNames, uint cNames, uint lcid, IntPtr rgDispId)
1868                 {
1869                         throw new NotImplementedException ();
1870                 }
1871
1872                 void _TypeBuilder.GetTypeInfo (uint iTInfo, uint lcid, IntPtr ppTInfo)
1873                 {
1874                         throw new NotImplementedException ();
1875                 }
1876
1877                 void _TypeBuilder.GetTypeInfoCount (out uint pcTInfo)
1878                 {
1879                         throw new NotImplementedException ();
1880                 }
1881
1882                 void _TypeBuilder.Invoke (uint dispIdMember, [In] ref Guid riid, uint lcid, short wFlags, IntPtr pDispParams, IntPtr pVarResult, IntPtr pExcepInfo, IntPtr puArgErr)
1883                 {
1884                         throw new NotImplementedException ();
1885                 }
1886
1887                 internal override bool IsUserType {
1888                         get {
1889                                 return false;
1890                         }
1891                 }
1892
1893                 public override bool IsConstructedGenericType {
1894                         get { return false; }
1895                 }
1896
1897                 public override bool IsAssignableFrom (TypeInfo typeInfo)
1898                 {
1899                         return base.IsAssignableFrom (typeInfo);
1900                 }
1901         }
1902 }
1903 #endif