den Type und den String will ich dynamisch hinzufügen, deswegen ist es im Beispiel ein String und im anderen Test1 😃
dazu noch der MethodBuilder:
MethodBuilder methodBuilder =
typeBuilder.DefineMethod("get_test1", MethodAttributes.Public, typeof(IList), new Type[] {});
Ich will hier die Methode nicht überschreiben, ich generiere meinen eigenen Type 😃
Hi,
ich probiere gerade einen einfach Getter mit IL-code in c# nachzubauen:
public class Test1
{
public IList test1
{
get
{
return Manager.Load(typeof(Test1), "testsa", this);
}
}
}
public class Manager
{
public static IList Load(Type typeA, string name, object oA)
{
Console.WriteLine("Load(" + typeA + ", " + name + "," + oA + ")");
return null;
}
}
so sieht das ganze nun in C# aus.
Ich möchte aber jetzt die test1-Methode dynamisch mit IL generieren. Natürlich hab ich mir das ganze mit ildasm als IL geholt.
Sieht dann so aus:
.method public hidebysig specialname instance class [mscorlib]System.Collections.IList
get_test1() cil managed
{
// Code size 27 (0x1b)
.maxstack 3
.locals init ([0] class [mscorlib]System.Collections.IList CS$1$0000)
IL_0000: nop
IL_0001: ldtoken ConsoleApplication1.Test1
IL_0006: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle)
IL_000b: ldstr "testsa"
IL_0010: ldarg.0
IL_0011: call class [mscorlib]System.Collections.IList Manager::Load(class [mscorlib]System.Type,
string,
object)
IL_0016: stloc.0
IL_0017: br.s IL_0019
IL_0019: ldloc.0
IL_001a: ret
} // end of method Test1::get_test1
Natürlich hab ich das dann in C# nachgebaut:
ILGenerator ilGenerator = methodBuilder.GetILGenerator();
Type myType = typeof(String);
string myString = "testString";
Label endOfMethod = ilGenerator.DefineLabel();
ilGenerator.Emit(OpCodes.Nop);
ilGenerator.Emit(OpCodes.Ldtoken, myType);
ilGenerator.Emit(OpCodes.Call, typeof(Type).GetMethod("GetTypeFromHandle"));
ilGenerator.Emit(OpCodes.Ldstr, myString);
ilGenerator.Emit(OpCodes.Ldarg_0);
ilGenerator.Emit(OpCodes.Call, typeof(Manager).GetMethod("Load", new Type[] {typeof(Type), typeof(string), typeof(object)}));
ilGenerator.Emit(OpCodes.Stloc_0);
ilGenerator.Emit(OpCodes.Br_S, endOfMethod);
ilGenerator.MarkLabel(endOfMethod);
ilGenerator.Emit(OpCodes.Ldloc_0);
ilGenerator.Emit(OpCodes.Ret);
Beim Ausführen tritt folgende Exception auf:
System.InvalidProgramException: Invalid IL code in TestType:get_test1 (): IL_0016: stloc.0
Habt ihr eine Idee warum das nicht funktioniert? Bin gerade erst dabei mich in IL einzuarbeiten aber ich versteh nicht warum das nicht geht:/
danke.