Merge pull request #5714 from alexischr/update_bockbuild
[mono.git] / mono / tests / generic-type-builder.2.cs
1 /* This test case is taken verbatim from the corlib test suite.  The
2  * reason we need it here, too, is that the corlib tests don't run
3  * with generic code sharing enabled for all code.  Once that is
4  * enabled by default in Mono, this test should be removed from the
5  * runtime test suite.
6  */
7
8 using System;
9 using System.Threading;
10 using System.Reflection;
11 using System.Reflection.Emit;
12 using System.IO;
13
14 public class main {
15         private static AssemblyBuilder assembly;
16
17         private static ModuleBuilder module;
18
19         static string ASSEMBLY_NAME = "MonoTests.System.Reflection.Emit.TypeBuilderTest";
20
21         protected static void SetUp ()
22         {
23                 AssemblyName assemblyName = new AssemblyName ();
24                 assemblyName.Name = ASSEMBLY_NAME;
25
26                 assembly =
27                         Thread.GetDomain ().DefineDynamicAssembly (
28                                 assemblyName, AssemblyBuilderAccess.RunAndSave, Path.GetTempPath ());
29
30                 module = assembly.DefineDynamicModule ("module1");
31         }
32
33         public static int GetField ()
34         {
35                 TypeBuilder tb = module.DefineType ("bla", TypeAttributes.Public);
36                 GenericTypeParameterBuilder [] typeParams = tb.DefineGenericParameters ("T");
37
38                 ConstructorBuilder cb = tb.DefineDefaultConstructor (MethodAttributes.Public);
39
40                 FieldBuilder fb1 = tb.DefineField ("field1", typeParams [0], FieldAttributes.Public);
41
42                 Type t = tb.MakeGenericType (typeof (int));
43
44                 // Chect that calling MakeArrayType () does not initialize the class
45                 // (bug #351172)
46                 t.MakeArrayType ();
47
48                 // Check that the instantiation of a type builder contains live data
49                 TypeBuilder.GetField (t, fb1);
50                 FieldBuilder fb2 = tb.DefineField ("field2", typeParams [0], FieldAttributes.Public);
51                 FieldInfo fi2 = TypeBuilder.GetField (t, fb1);
52
53                 MethodBuilder mb = tb.DefineMethod ("get_int", MethodAttributes.Public|MethodAttributes.Static, typeof (int), Type.EmptyTypes);
54                 ILGenerator ilgen = mb.GetILGenerator ();
55                 ilgen.Emit (OpCodes.Newobj, TypeBuilder.GetConstructor (t, cb));
56                 ilgen.Emit (OpCodes.Dup);
57                 ilgen.Emit (OpCodes.Ldc_I4, 42);
58                 ilgen.Emit (OpCodes.Stfld, fi2);
59                 ilgen.Emit (OpCodes.Ldfld, fi2);
60                 ilgen.Emit (OpCodes.Ret);
61
62                 // Check GetField on a type instantiated with type parameters
63                 Type t3 = tb.MakeGenericType (typeParams [0]);
64                 FieldBuilder fb3 = tb.DefineField ("field3", typeParams [0], FieldAttributes.Public);
65                 FieldInfo fi3 = TypeBuilder.GetField (t3, fb3);
66
67                 MethodBuilder mb3 = tb.DefineMethod ("get_T", MethodAttributes.Public|MethodAttributes.Static, typeParams [0], Type.EmptyTypes);
68                 ILGenerator ilgen3 = mb3.GetILGenerator ();
69                 ilgen3.Emit (OpCodes.Newobj, TypeBuilder.GetConstructor (t3, cb));
70                 ilgen3.Emit (OpCodes.Ldfld, fi3);
71                 ilgen3.Emit (OpCodes.Ret);
72
73                 Type created = tb.CreateType ();
74
75                 Type inst = created.MakeGenericType (typeof (object));
76
77                 if ((int)(inst.GetMethod ("get_int").Invoke (null, null)) != 42)
78                         return 1;
79
80                 if (inst.GetMethod ("get_T").Invoke (null, null) != null)
81                         return 1;
82
83                 return 0;
84         }
85
86         public static int Main () {
87                 SetUp ();
88                 return GetField ();
89         }
90 }