版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。
版权
IL&反射专栏收录该内容
16 篇文章0 订阅
订阅专栏
本人是从0开始学习Emit的,在学习过程中比较困扰我的就是有很多指令不理解、不会用,查了很多资料最终算是搞明白了,记录下来供大家参考。
除了在网上查资料外,学习Emit和MSIL的另一种方式是.Net Reflector和ildasm.exe配合使用,.Net Reflector能把MSIL代码转换成C#代码(Emit中的Opcodes指令与MSIL指令对应),ildasm.exe能把C#代码转换为MSIL,当想用Emit实现某一功能但是不知道怎么写时,可以先把该功能的C#代码写出来,再用ildasm.exe将其转换成MSIL,最后根据转化生成的MSIL代码的逻辑来写Emit代码,这个很实用。

【非静态】Ldstr+OpCodes.Ldarg_1

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) }); ILGenerator ilOfShow = showMethod.GetILGenerator();//非静态方法参数索引从1开始 ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldarg_1); ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret); Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
publicclass StudyOpCodes {// MethodspublicvoidShow(int num1,string text1) {string.Format("姓名:{1} 年龄:{0}", num1, text1); } }

【静态】Ldstr和OpCodes.Ldarg_1

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public | MethodAttributes.Static,null,new Type[] {typeof(int),typeof(string) }); ILGenerator ilOfShow = showMethod.GetILGenerator(); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}");//静态方法必参数索引从0开始 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldarg_1); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret); Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
publicclass StudyOpCodes {// MethodspublicstaticvoidShow(int num1,string text1) {string.Format("姓名:{1} 年龄:{0}", num1, text1); } }

Ldc_I4和Ldc_I8

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) });#region Ldc_I4 ILGenerator ilOfShow = showMethod.GetILGenerator(); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}");//typeof(int)指的是Int32,数字默认是Int32类型 ilOfShow.Emit(OpCodes.Ldc_I4,18);//非静态方法参数索引从1开始 ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion#region Ldc_I8 ILGenerator ilOfShow = showMethod.GetILGenerator(); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}");//typeof(int)指的是Int32,数字默认是Int32类型 ilOfShow.Emit(OpCodes.Ldc_I8, Convert.ToInt64(18));//非静态方法参数索引从1开始 ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(Int64),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
//Ldc_I4publicclass StudyOpCodes {// MethodspublicvoidShow(int,string text1) {string.Format("姓名:{1} 年龄:{0}",0x12, text1); } } //Ldc_I8publicclass StudyOpCodes {// MethodspublicvoidShow(int,string text1) {string.Format("姓名:{1} 年龄:{0}",0x12L, text1); } }

Ldc_R4和Ldc_R8

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) });#region Ldc_R4 ILGenerator ilOfShow = showMethod.GetILGenerator(); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}");//12.3默认是Double类型 ilOfShow.Emit(OpCodes.Ldc_R4, (float)12.3);//非静态方法参数索引从1开始 ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(float),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion#region Ldc_R8 ILGenerator ilOfShow = showMethod.GetILGenerator(); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}");//12.3默认是Double类型 ilOfShow.Emit(OpCodes.Ldc_R8,12.3);//非静态方法参数索引从1开始 ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(double),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
//Ldc_R4publicclass StudyOpCodes {// MethodspublicvoidShow(int,string text1) {string.Format("姓名:{1} 年龄:{0}",12.3f, text1); } } //Ldc_R8publicclass StudyOpCodes {// MethodspublicvoidShow(int,string text1) {string.Format("姓名:{1} 年龄:{0}",12.3, text1); } }

Ldfld和Stfld

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) }); FieldBuilder fieldName = typeBuilder.DefineField("Name",typeof(string), FieldAttributes.Private);#region Ldfld ILGenerator ilOfShow = showMethod.GetILGenerator();//非静态方法参数索引从1开始 ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldc_I4,18);//OpCodes.Ldfld之前必须OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldfld, fieldName); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion#region Stfld ILGenerator ilOfShow = showMethod.GetILGenerator();//*非静态方法参数索引从1开始//OpCodes.Stfld之前必须OpCodes.Ldarg_0//this.Name = text1; ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Stfld, fieldName);//this.Name = "guo"; ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldstr,"guo"); ilOfShow.Emit(OpCodes.Stfld, fieldName);////text1.Name = (string) this;//ilOfShow.Emit(OpCodes.Ldarg_2);//ilOfShow.Emit(OpCodes.Ldarg_0);//ilOfShow.Emit(OpCodes.Stfld, fieldName);////堆栈为空//ilOfShow.Emit(OpCodes.Ldarg_2);//ilOfShow.Emit(OpCodes.Stfld, fieldName);////堆栈为空//ilOfShow.Emit(OpCodes.Ldstr,"guo");//ilOfShow.Emit(OpCodes.Stfld, fieldName); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldc_I4,18);//OpCodes.Ldfld之前必须OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldfld, fieldName); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
//Ldfldpublicclass StudyOpCodes {// Fieldsprivatestring Name;// MethodspublicvoidShow(int,string) {string.Format("姓名:{1} 年龄:{0}",0x12,this.Name); } } //Stfldpublicclass StudyOpCodes {// Fieldsprivatestring Name;// MethodspublicvoidShow(int,string text1) {this.Name = text1;this.Name ="guo";string.Format("姓名:{1} 年龄:{0}",0x12,this.Name); } }

Ldsfld和Stsfld

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) }); FieldBuilder fieldName = typeBuilder.DefineField("Name",typeof(string), FieldAttributes.Private | FieldAttributes.Static);#region Ldsfld ILGenerator ilOfShow = showMethod.GetILGenerator(); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldc_I4,18);//*OpCodes.Ldsfld之前不能有OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldsfld, fieldName); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion#region Stsfld ILGenerator ilOfShow = showMethod.GetILGenerator();//OpCodes.Stsfld之前不能有OpCodes.Ldarg_0,Name = text1; ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Stsfld, fieldName);//OpCodes.Stsfld之前不能有OpCodes.Ldarg_0,Name = "guo"; ilOfShow.Emit(OpCodes.Ldstr,"guo"); ilOfShow.Emit(OpCodes.Stsfld, fieldName); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldc_I4,18);//OpCodes.Ldsfld之前不能有OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldsfld, fieldName); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
//Ldsfldpublicclass StudyOpCodes {// Fieldsprivatestaticstring Name;// MethodspublicvoidShow(int,string) {string.Format("姓名:{1} 年龄:{0}",0x12, Name); } } //Stsfldpublicclass StudyOpCodes {// Fieldsprivatestaticstring Name;// MethodspublicvoidShow(int,string text1) { Name = text1; Name ="guo";string.Format("姓名:{1} 年龄:{0}",0x12, Name); } }

Ldloc和Stloc

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) }); FieldBuilder fieldName = typeBuilder.DefineField("Name",typeof(string), FieldAttributes.Private | FieldAttributes.Static);#region Ldloc ILGenerator ilOfShow = showMethod.GetILGenerator(); LocalBuilder localName = ilOfShow.DeclareLocal(typeof(string)); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldc_I4,18);//*OpCodes.Ldloc之前不能有OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldloc, localName); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion#region Stloc ILGenerator ilOfShow = showMethod.GetILGenerator(); LocalBuilder localName = ilOfShow.DeclareLocal(typeof(string));// OpCodes.Stloc之前不能有OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldarg_2); ilOfShow.Emit(OpCodes.Stloc, localName);// OpCodes.Stloc之前不能有OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldstr,"guo"); ilOfShow.Emit(OpCodes.Stloc, localName);// 【静态字段】str=Name; ilOfShow.Emit(OpCodes.Ldsfld, fieldName); ilOfShow.Emit(OpCodes.Stloc, localName);// 【普通字段】str=this.Name;//ilOfShow.Emit(OpCodes.Ldarg_0);//ilOfShow.Emit(OpCodes.Ldfld, fieldName);//ilOfShow.Emit(OpCodes.Stloc, localName); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldc_I4,18);//OpCodes.Ldloc之前不能有OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldloc, localName); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
//Ldlocpublicclass StudyOpCodes {// Fieldsprivatestaticstring Name;// MethodspublicvoidShow(int,string) {string str;string.Format("姓名:{1} 年龄:{0}",0x12, str); } } //Stlocpublicclass StudyOpCodes {// Fieldsprivatestaticstring Name;// MethodspublicvoidShow(int,string text1) {string name = text1;//此处的局部变量名之所以为name,是因为第三行赋值代码的原因,如果字段名为Address,那此处的局部变量名就会变成address name ="guo"; name = Name;string.Format("姓名:{1} 年龄:{0}",0x12, name); } }

Box和Unbox

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) }); FieldBuilder fieldAge = typeBuilder.DefineField("objectAge",typeof(object), FieldAttributes.Private);#region Box ILGenerator ilOfShow = showMethod.GetILGenerator();//*此处的OpCodes.Ldarg_0是OpCodes.Stfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldc_I4,18); ilOfShow.Emit(OpCodes.Box,typeof(int)); ilOfShow.Emit(OpCodes.Stfld, fieldAge); ilOfShow.Emit(OpCodes.Ret);#endregion#region Unbox ILGenerator ilOfShow = showMethod.GetILGenerator(); LocalBuilder localAge = ilOfShow.DeclareLocal(typeof(int));//此处的OpCodes.Ldarg_0是OpCodes.Stfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldc_I4,18); ilOfShow.Emit(OpCodes.Box,typeof(int)); ilOfShow.Emit(OpCodes.Stfld, fieldAge);//*此处的OpCodes.Ldarg_0是OpCodes.Ldfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldfld, fieldAge); ilOfShow.Emit(OpCodes.Unbox,typeof(int)); ilOfShow.Emit(OpCodes.Stloc, localAge); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
//Boxpublicclass StudyOpCodes {// Fieldsprivateobject objectAge;// MethodspublicvoidShow(int,string) {this.objectAge =0x12; } } //Unboxpublicclass StudyOpCodes {// Fieldsprivateobject objectAge;// MethodspublicvoidShow(int,string) {this.objectAge =0x12;int objectAge = (int)this.objectAge; } }

Newobj

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) }); FieldBuilder fieldUser = typeBuilder.DefineField("objUser",typeof(User), FieldAttributes.Private | FieldAttributes.Static);#region Newobj ILGenerator ilOfShow = showMethod.GetILGenerator();//*OpCodes.Stsfld不需要OpCodes.Ldarg_0,this.Name = new User(); ilOfShow.Emit(OpCodes.Newobj,typeof(User).GetConstructor(new Type[0])); ilOfShow.Emit(OpCodes.Stsfld, fieldUser); LocalBuilder localName = ilOfShow.DeclareLocal(typeof(string)); ilOfShow.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfShow.Emit(OpCodes.Ldc_I4,18);//OpCodes.Ldloc之前不能有OpCodes.Ldarg_0 ilOfShow.Emit(OpCodes.Ldloc, localName); ilOfShow.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfShow.Emit(OpCodes.Pop); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
publicclass StudyOpCodes {// Fieldsprivatestatic User objUser;// MethodspublicvoidShow(int,string) {string str; objUser =new User();string.Format("姓名:{1} 年龄:{0}",0x12, str); } }

Newarr

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); MethodBuilder showMethod = typeBuilder.DefineMethod("Show", MethodAttributes.Public,null,new Type[] {typeof(int),typeof(string) }); FieldBuilder fieldArray = typeBuilder.DefineField("objUser",typeof(string[]), FieldAttributes.Private);#region 不对数组赋值 ILGenerator ilOfShow = showMethod.GetILGenerator(); LocalBuilder localName = ilOfShow.DeclareLocal(typeof(string));//*objUser = new string[3];//此处的OpCodes.Ldarg_0是OpCodes.Stfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldc_I4,3); ilOfShow.Emit(OpCodes.Newarr,typeof(string)); ilOfShow.Emit(OpCodes.Stfld, fieldArray); ilOfShow.Emit(OpCodes.Ret);#endregion#region 对数组赋值 ILGenerator ilOfShow = showMethod.GetILGenerator(); LocalBuilder localName = ilOfShow.DeclareLocal(typeof(string));//objUser = new string[3];//此处的OpCodes.Ldarg_0是OpCodes.Stfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldc_I4,3); ilOfShow.Emit(OpCodes.Newarr,typeof(string)); ilOfShow.Emit(OpCodes.Stfld, fieldArray);//给数组赋值:objUser = new string[] { "aaa", "bbb", "ccc" };//此处的OpCodes.Ldarg_0是OpCodes.Ldfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldfld, fieldArray); ilOfShow.Emit(OpCodes.Ldc_I4,0); ilOfShow.Emit(OpCodes.Ldstr,"aaa"); ilOfShow.Emit(OpCodes.Stelem_Ref);//此处的OpCodes.Ldarg_0是OpCodes.Ldfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldfld, fieldArray); ilOfShow.Emit(OpCodes.Ldc_I4,1); ilOfShow.Emit(OpCodes.Ldstr,"bbb"); ilOfShow.Emit(OpCodes.Stelem_Ref);//此处的OpCodes.Ldarg_0是OpCodes.Ldfld所需的 ilOfShow.Emit(OpCodes.Ldarg_0); ilOfShow.Emit(OpCodes.Ldfld, fieldArray); ilOfShow.Emit(OpCodes.Ldc_I4,2); ilOfShow.Emit(OpCodes.Ldstr,"ccc"); ilOfShow.Emit(OpCodes.Stelem_Ref); ilOfShow.Emit(OpCodes.Ret);#endregion Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
//不对数组赋值publicclass StudyOpCodes {// Fieldsprivatestring[] objUser;// MethodspublicvoidShow(int,string) {this.objUser =newstring[3]; } } //对数组赋值publicclass StudyOpCodes {// Fieldsprivatestring[] objUser;// MethodspublicvoidShow(int,string) { objUser =newstring[] {"aaa","bbb","ccc" }; } }

【构造方法】Ldstr和OpCodes.Ldarg_1

Emit代码:
publicclass StudyOpCodes {publicvoidTest() { AssemblyName assemblyName =new AssemblyName("Study"); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("StudyModule","StudyOpCodes.dll"); TypeBuilder typeBuilder = moduleBuilder.DefineType("StudyOpCodes", TypeAttributes.Public); ConstructorBuilder ctorMethod = typeBuilder.DefineConstructor(MethodAttributes.Public, CallingConventions.Standard,new Type[] {typeof(int),typeof(string) }); ILGenerator ilOfCtor = ctorMethod.GetILGenerator();//非静态方法参数索引从1开始 ilOfCtor.Emit(OpCodes.Ldstr,"姓名:{1} 年龄:{0}"); ilOfCtor.Emit(OpCodes.Ldarg_1); ilOfCtor.Emit(OpCodes.Ldarg_2); ilOfCtor.Emit(OpCodes.Call,typeof(string).GetMethod("Format",new Type[] {typeof(string),typeof(int),typeof(string) })); ilOfCtor.Emit(OpCodes.Pop); ilOfCtor.Emit(OpCodes.Ret); Type t = typeBuilder.CreateType(); assemblyBuilder.Save("StudyOpCodes.dll"); } }
.Net Reflector转化后的C#代码:
publicclass StudyOpCodes {// MethodspublicStudyOpCodes(int num1,string text1) {string.Format("姓名:{1} 年龄:{0}", num1, text1); } }

总结

除了OpCodes.Ldfld和OpCodes.Stfld命令使用之前需要额外执行OpCodes.Ldarg_0之外,其他命令都不需要。
上面列出了常用的OpCodes指令的使用方法,当然只是一些基本的使用方法,复杂的使用情况(封装、继承、多态等)在此没有举例,不过有了基础再进一步学习复杂功能的写法也会轻松许多,如果遇到问题就上网或使用.Net Reflector和ildasm.exe来解决,希望对大家有帮助。