浏览代码

2006-07-08 Zoltan Varga <[email protected]>

	* DynamicMethod.cs: Create all other DynamicMethod's referenced by
	this method as well. Check for an empty method body.

	* ILGenerator.cs (Emit): Handle DynamicMethod's which might not have a
	declaring type.

svn path=/trunk/mcs/; revision=62369
Zoltan Varga 19 年之前
父节点
当前提交
a1a8b1b63e

+ 8 - 0
mcs/class/corlib/System.Reflection.Emit/ChangeLog

@@ -1,3 +1,11 @@
+2006-07-08  Zoltan Varga  <[email protected]>
+
+	* DynamicMethod.cs: Create all other DynamicMethod's referenced by
+	this method as well. Check for an empty method body.
+
+	* ILGenerator.cs (Emit): Handle DynamicMethod's which might not have a
+	declaring type.
+
 2006-05-15  Zoltan Varga  <[email protected]>
 
 	* AssemblyBuilder.cs (MonoResource): Add a 'stream' field.

+ 23 - 2
mcs/class/corlib/System.Reflection.Emit/DynamicMethod.cs

@@ -63,6 +63,7 @@ namespace System.Reflection.Emit {
 		private Delegate deleg;
 		private MonoMethod method;
 		private ParameterBuilder[] pinfo;
+		internal bool creating;
 
 		public DynamicMethod (string name, Type returnType, Type[] parameterTypes, Module m) : this (name, returnType, parameterTypes, m, false) {
 		}
@@ -110,8 +111,28 @@ namespace System.Reflection.Emit {
 
 		private void CreateDynMethod () {
 			if (mhandle.Value == IntPtr.Zero) {
-				if (ilgen != null)
-					ilgen.label_fixup ();
+				if (ilgen == null)
+					throw new InvalidOperationException ("Method '" + name + "' does not have a method body.");
+
+				ilgen.label_fixup ();
+
+				// Have to create all DynamicMethods referenced by this one
+				try {
+					// Used to avoid cycles
+					creating = true;
+					if (refs != null) {
+						for (int i = 0; i < refs.Length; ++i) {
+							if (refs [i] is DynamicMethod) {
+								DynamicMethod m = (DynamicMethod)refs [i];
+								if (!m.creating)
+									m.CreateDynMethod ();
+							}
+						}
+					}
+				} finally {
+					creating = false;
+				}
+
 				create_dynamic_method (this);
 			}
 		}

+ 12 - 4
mcs/class/corlib/System.Reflection.Emit/ILGenerator.cs

@@ -705,8 +705,12 @@ namespace System.Reflection.Emit {
 			int token = token_gen.GetToken (method);
 			make_room (6);
 			ll_emit (opcode);
-			if (method.DeclaringType.Module == module)
-				add_token_fixup (method);
+			Type declaringType = method.DeclaringType;
+			// Might be a DynamicMethod with no declaring type
+			if (declaringType != null) {
+				if (declaringType.Module == module)
+					add_token_fixup (method);
+			}
 			emit_int (token);
 			if (method.ReturnType != void_type)
 				cur_stack ++;
@@ -719,8 +723,12 @@ namespace System.Reflection.Emit {
 		{
 			make_room (6);
 			ll_emit (opcode);
-			if (method.DeclaringType.Module == module)
-				add_token_fixup (method);
+			// Might be a DynamicMethod with no declaring type
+			Type declaringType = method.DeclaringType;
+			if (declaringType != null) {
+				if (declaringType.Module == module)
+					add_token_fixup (method);
+			}
 			emit_int (token);
 			if (method.ReturnType != void_type)
 				cur_stack ++;