protected override void Execute(ConfuserContext context, ProtectionParameters parameters) { foreach (ModuleDef module in parameters.Targets.OfType<ModuleDef>()) { TypeRef attrRef = module.CorLibTypes.GetTypeRef("System.Runtime.CompilerServices", "SuppressIldasmAttribute"); var ctorRef = new MemberRefUser(module, ".ctor", MethodSig.CreateInstance(module.CorLibTypes.Void), attrRef); var attr = new CustomAttribute(ctorRef); module.CustomAttributes.Add(attr); } }
public static void Run() { // Create a new module. The string passed in is the name of the module, // not the file name. ModuleDef mod = new ModuleDefUser("MyModule.exe"); // It's a console application mod.Kind = ModuleKind.Console; // Add the module to an assembly AssemblyDef asm = new AssemblyDefUser("MyAssembly", new Version(1, 2, 3, 4), null, null); asm.Modules.Add(mod); // Add a .NET resource byte[] resourceData = Encoding.UTF8.GetBytes("Hello, world!"); mod.Resources.Add(new EmbeddedResource("My.Resource", resourceData, ManifestResourceAttributes.Private)); // Add the startup type. It derives from System.Object. TypeDef startUpType = new TypeDefUser("My.Namespace", "Startup", mod.CorLibTypes.Object.TypeDefOrRef); startUpType.Attributes = TypeAttributes.NotPublic | TypeAttributes.AutoLayout | TypeAttributes.Class | TypeAttributes.AnsiClass; // Add the type to the module mod.Types.Add(startUpType); // Create the entry point method MethodDef entryPoint = new MethodDefUser("Main", MethodSig.CreateStatic(mod.CorLibTypes.Int32, new SZArraySig(mod.CorLibTypes.String))); entryPoint.Attributes = MethodAttributes.Private | MethodAttributes.Static | MethodAttributes.HideBySig | MethodAttributes.ReuseSlot; entryPoint.ImplAttributes = MethodImplAttributes.IL | MethodImplAttributes.Managed; // Name the 1st argument (argument 0 is the return type) entryPoint.ParamDefs.Add(new ParamDefUser("args", 1)); // Add the method to the startup type startUpType.Methods.Add(entryPoint); // Set module entry point mod.EntryPoint = entryPoint; // Create a TypeRef to System.Console TypeRef consoleRef = new TypeRefUser(mod, "System", "Console", mod.CorLibTypes.AssemblyRef); // Create a method ref to 'System.Void System.Console::WriteLine(System.String)' MemberRef consoleWrite1 = new MemberRefUser(mod, "WriteLine", MethodSig.CreateStatic(mod.CorLibTypes.Void, mod.CorLibTypes.String), consoleRef); // Add a CIL method body to the entry point method CilBody epBody = new CilBody(); entryPoint.Body = epBody; epBody.Instructions.Add(OpCodes.Ldstr.ToInstruction("Hello World!")); epBody.Instructions.Add(OpCodes.Call.ToInstruction(consoleWrite1)); epBody.Instructions.Add(OpCodes.Ldc_I4_0.ToInstruction()); epBody.Instructions.Add(OpCodes.Ret.ToInstruction()); // Save the assembly to a file on disk mod.Write(@"C:\saved-assembly.exe"); }
/// <summary> /// Resolve an IField from its name and a declaring TypeSpec. /// </summary> /// <param name="declaringType">Declaring TypeSpec</param> /// <param name="fieldName">Field name</param> /// <returns>IField, or null if none found</returns> public IField ResolveField(TypeSpec declaringType, String fieldName) { TypeDef typeDef = declaringType.ResolveTypeDef(); if (typeDef == null) return null; FieldDef fieldDef = typeDef.FindField(fieldName); if (fieldDef == null) return null; MemberRef memberRef = new MemberRefUser(_module, fieldDef.Name, fieldDef.FieldSig, declaringType); return this.Importer.Import(memberRef); }
void InitializeCtors(TypeDef manager, MethodDefAndDeclaringTypeDict<IMethod> ctors) { if (manager == null) return; foreach (var ctor in manager.Methods) { if (ctor.Name != ".ctor") continue; var newCtor = new MemberRefUser(module, ctor.Name, ctor.MethodSig.Clone(), manager.BaseType); module.UpdateRowId(newCtor); ctors.Add(ctor, newCtor); } }
IMDTokenProvider Create_SystemArray_get_Length() { if (Create_SystemArray_get_Length_result_initd) return Create_SystemArray_get_Length_result; Create_SystemArray_get_Length_result_initd = true; var module = GetModule(); if (module == null) return null; const string propName = "Length"; var type = module.CorLibTypes.GetTypeRef("System", "Array"); var retType = module.CorLibTypes.Int32; var mr = new MemberRefUser(module, "get_" + propName, MethodSig.CreateInstance(retType), type); Create_SystemArray_get_Length_result = mr; var md = mr.ResolveMethod(); if (md == null || md.DeclaringType == null) return mr; var prop = md.DeclaringType.FindProperty(propName); if (prop == null) return mr; Create_SystemArray_get_Length_result = prop; return prop; }
IMethod ResolveMethod_NoLock(TypeSpec declaringSpec, MethodData data) { // Find a method that matches the signature (factoring in possible generic vars/mvars) MethodSig matchedSig = null; MethodDef method = FindMethodCheckBaseType(declaringSpec, data, out matchedSig); if (matchedSig == null || method == null) { throw new Exception(String.Format( "Unable to find generic method from the declaring/base types: DeclaringType={0}, MethodName={1}", declaringSpec.ReflectionFullName, data.Name)); } MemberRef memberRef = new MemberRefUser(this.Module, method.Name, matchedSig, declaringSpec); if (data.HasGenericArguments) return this.Importer.Import(new MethodSpecUser(memberRef, ToGenericInstMethodSig(data))); else return this.Importer.Import(memberRef); }
public IMethod ReadMethodRef() { var babelMethodRef = new MethodRefReader(this, reader).Read(); var method = GetMethodRef(babelMethodRef); if (method == null) { throw new ApplicationException(string.Format("Could not find method '{0}' in type '{1}'", Utils.RemoveNewlines(babelMethodRef.Name), Utils.RemoveNewlines(babelMethodRef.DeclaringType))); } var git = babelMethodRef.DeclaringType.ToGenericInstSig(); if (git == null) return method; var mr = new MemberRefUser(module, method.Name, method.MethodSig.Clone(), babelMethodRef.DeclaringType.ToTypeDefOrRef()); return module.UpdateRowId(mr); }
IMDTokenProvider Create_SystemType_get_TypeHandle() { if (Create_SystemType_get_TypeHandle_initd) return Create_SystemType_get_TypeHandle_result; Create_SystemType_get_TypeHandle_initd = true; const string propName = "TypeHandle"; var type = corLib.GetTypeRef("System", "Type"); var retType = new ValueTypeSig(corLib.GetTypeRef("System", "RuntimeTypeHandle")); var mr = new MemberRefUser(methodDef.Module, "get_" + propName, MethodSig.CreateInstance(retType), type); Create_SystemType_get_TypeHandle_result = mr; var md = mr.ResolveMethod(); if (md == null || md.DeclaringType == null) return mr; var prop = md.DeclaringType.FindProperty(propName); if (prop == null) return mr; Create_SystemType_get_TypeHandle_result = prop; return prop; }
public static void Run() { // This is the file that will be created string newFileName = @"C:\ctor-test.exe"; // Create the module var mod = new ModuleDefUser("ctor-test", Guid.NewGuid(), new AssemblyRefUser(new AssemblyNameInfo(typeof(int).Assembly.GetName().FullName))); // It's a console app mod.Kind = ModuleKind.Console; // Create the assembly and add the created module to it new AssemblyDefUser("ctor-test", new Version(1, 2, 3, 4)).Modules.Add(mod); // Create System.Console type reference var systemConsole = mod.CorLibTypes.GetTypeRef("System", "Console"); // Create 'void System.Console.WriteLine(string,object)' method reference var writeLine2 = new MemberRefUser(mod, "WriteLine", MethodSig.CreateStatic(mod.CorLibTypes.Void, mod.CorLibTypes.String, mod.CorLibTypes.Object), systemConsole); // Create System.Object::.ctor method reference. This is the default constructor var objectCtor = new MemberRefUser(mod, ".ctor", MethodSig.CreateInstance(mod.CorLibTypes.Void), mod.CorLibTypes.Object.TypeDefOrRef); CilBody body; // Create the base class var bclass = new TypeDefUser("Ctor.Test", "BaseClass", mod.CorLibTypes.Object.TypeDefOrRef); // Add it to the module mod.Types.Add(bclass); // Create Ctor.Test.BaseClass constructor: BaseClass() var bctor = new MethodDefUser(".ctor", MethodSig.CreateInstance(mod.CorLibTypes.Void), MethodImplAttributes.IL | MethodImplAttributes.Managed, MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName); // Add the method to BaseClass bclass.Methods.Add(bctor); // Create method body and add a few instructions bctor.Body = body = new CilBody(); // Make sure we call the base class' constructor body.Instructions.Add(OpCodes.Ldarg_0.ToInstruction()); body.Instructions.Add(OpCodes.Call.ToInstruction(objectCtor)); body.Instructions.Add(OpCodes.Ldstr.ToInstruction("BaseClass: Default .ctor called")); body.Instructions.Add(OpCodes.Ldnull.ToInstruction()); body.Instructions.Add(OpCodes.Call.ToInstruction(writeLine2)); body.Instructions.Add(OpCodes.Ret.ToInstruction()); // Create the Ctor.Test.Main type which derives from Ctor.Test.BaseClass var main = new TypeDefUser("Ctor.Test", "Main", bclass); // Add it to the module mod.Types.Add(main); // Create the static 'void Main()' method var entryPoint = new MethodDefUser("Main", MethodSig.CreateStatic(mod.CorLibTypes.Void), MethodImplAttributes.IL | MethodImplAttributes.Managed, MethodAttributes.Public | MethodAttributes.Static); // Set entry point to entryPoint and add it as a Ctor.Test.Main method mod.EntryPoint = entryPoint; main.Methods.Add(entryPoint); // Create first Ctor.Test.Main constructor: Main() var ctor0 = new MethodDefUser(".ctor", MethodSig.CreateInstance(mod.CorLibTypes.Void), MethodImplAttributes.IL | MethodImplAttributes.Managed, MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName); // Add the method to Main main.Methods.Add(ctor0); // Create method body and add a few instructions ctor0.Body = body = new CilBody(); // Make sure we call the base class' constructor body.Instructions.Add(OpCodes.Ldarg_0.ToInstruction()); body.Instructions.Add(OpCodes.Call.ToInstruction(bctor)); body.Instructions.Add(OpCodes.Ldstr.ToInstruction("Default .ctor called")); body.Instructions.Add(OpCodes.Ldnull.ToInstruction()); body.Instructions.Add(OpCodes.Call.ToInstruction(writeLine2)); body.Instructions.Add(OpCodes.Ret.ToInstruction()); // Create second Ctor.Test.Main constructor: Main(int,string) var ctor1 = new MethodDefUser(".ctor", MethodSig.CreateInstance(mod.CorLibTypes.Void, mod.CorLibTypes.Int32, mod.CorLibTypes.String), MethodImplAttributes.IL | MethodImplAttributes.Managed, MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName); // Add the method to Main main.Methods.Add(ctor1); // Create names for the arguments. This is optional. Since this is an instance method // (it's a constructor), the first arg is the 'this' pointer. The normal arguments // begin at index 1. ctor1.Parameters[1].CreateParamDef(); ctor1.Parameters[1].ParamDef.Name = "count"; ctor1.Parameters[2].CreateParamDef(); ctor1.Parameters[2].ParamDef.Name = "name"; // Create method body and add a few instructions ctor1.Body = body = new CilBody(); // Make sure we call the base class' constructor body.Instructions.Add(OpCodes.Ldarg_0.ToInstruction()); body.Instructions.Add(OpCodes.Call.ToInstruction(bctor)); body.Instructions.Add(OpCodes.Ldstr.ToInstruction(".ctor(Int32) called with arg {0}")); body.Instructions.Add(OpCodes.Ldarg_1.ToInstruction()); body.Instructions.Add(OpCodes.Box.ToInstruction(mod.CorLibTypes.Int32)); body.Instructions.Add(OpCodes.Call.ToInstruction(writeLine2)); body.Instructions.Add(OpCodes.Ret.ToInstruction()); // Create the entry point method body and add instructions to allocate a new Main() // object and call the two created ctors. entryPoint.Body = body = new CilBody(); body.Instructions.Add(OpCodes.Newobj.ToInstruction(ctor0)); body.Instructions.Add(OpCodes.Pop.ToInstruction()); body.Instructions.Add(OpCodes.Ldc_I4.ToInstruction(12345)); body.Instructions.Add(OpCodes.Ldnull.ToInstruction()); body.Instructions.Add(OpCodes.Newobj.ToInstruction(ctor1)); body.Instructions.Add(OpCodes.Pop.ToInstruction()); body.Instructions.Add(OpCodes.Ret.ToInstruction()); // Save the assembly mod.Write(newFileName); }
public static void Run() { // This is the file that will be created string newFileName = @"GenericExample1.exe"; // Create the module var mod = new ModuleDefUser("GenericExample1", Guid.NewGuid(), new AssemblyRefUser(new AssemblyNameInfo(typeof(int).Assembly.GetName().FullName))); // It's a console app mod.Kind = ModuleKind.Console; // Create the assembly and add the created module to it new AssemblyDefUser("GenericExample1", new Version(1, 2, 3, 4)).Modules.Add(mod); // Add the startup type. It derives from System.Object. TypeDef startUpType = new TypeDefUser("My.Namespace", "Startup", mod.CorLibTypes.Object.TypeDefOrRef); startUpType.Attributes = TypeAttributes.NotPublic | TypeAttributes.AutoLayout | TypeAttributes.Class | TypeAttributes.AnsiClass; // Add the type to the module mod.Types.Add(startUpType); // Create the entry point method MethodDef entryPoint = new MethodDefUser("Main", MethodSig.CreateStatic(mod.CorLibTypes.Int32, new SZArraySig(mod.CorLibTypes.String))); entryPoint.Attributes = MethodAttributes.Private | MethodAttributes.Static | MethodAttributes.HideBySig | MethodAttributes.ReuseSlot; entryPoint.ImplAttributes = MethodImplAttributes.IL | MethodImplAttributes.Managed; // Name the 1st argument (argument 0 is the return type) entryPoint.ParamDefs.Add(new ParamDefUser("args", 1)); // Add the method to the startup type startUpType.Methods.Add(entryPoint); // Set module entry point mod.EntryPoint = entryPoint; // Create System.Console type reference var systemConsole = mod.CorLibTypes.GetTypeRef("System", "Console"); // Create 'void System.Console.WriteLine(string,object)' method reference var writeLine2 = new MemberRefUser(mod, "WriteLine", MethodSig.CreateStatic(mod.CorLibTypes.Void, mod.CorLibTypes.String, mod.CorLibTypes.Object), systemConsole); // // Method 1: Create List<String> inst signature by importing (easy way) // -------------------------------------------------------------------- //Importer importer = new Importer(mod); //var listGenericInstSig = importer.ImportAsTypeSig(typeof(System.Collections.Generic.List<String>)); // // Method 2: Create List<String> inst signature manually (harder way) // ------------------------------------------------------------------ var assemblyRef = mod.CorLibTypes.AssemblyRef; var listRef = new TypeRefUser(mod, @"System.Collections.Generic", "List`1", assemblyRef); // Create the GenericInstSig from a ClassSig with <String> generic arg var listGenericInstSig = new GenericInstSig(new ClassSig(listRef), mod.CorLibTypes.String); // Create TypeSpec from GenericInstSig var listTypeSpec = new TypeSpecUser(listGenericInstSig); // Create System.Collections.Generic.List<String>::.ctor method reference var listCtor = new MemberRefUser(mod, ".ctor", MethodSig.CreateInstance(mod.CorLibTypes.Void), listTypeSpec); // Create Add(!0) method reference, !0 signifying first generic argument of declaring type // In this case, would be Add(String item) // (GenericMVar would be used for method generic argument, such as Add<!!0>(!!0)) var listAdd = new MemberRefUser(mod, "Add", MethodSig.CreateInstance(mod.CorLibTypes.Void, new GenericVar(0)), listTypeSpec); var listGetCount = new MemberRefUser(mod, "get_Count", MethodSig.CreateInstance(mod.CorLibTypes.Int32), listTypeSpec); IList<Local> locals = new List<Local>(); locals.Add(new Local(listGenericInstSig)); // local[0]: class [mscorlib]System.Collections.Generic.List`1<string> var body = new CilBody(true, new List<Instruction>(), new List<ExceptionHandler>(), locals); // Call the list .ctor body.Instructions.Add(OpCodes.Newobj.ToInstruction(listCtor)); body.Instructions.Add(OpCodes.Stloc_0.ToInstruction()); // Store list to local[0] // list.Add("Item 1") body.Instructions.Add(OpCodes.Ldloc_0.ToInstruction()); body.Instructions.Add(OpCodes.Ldstr.ToInstruction("Item 1")); body.Instructions.Add(OpCodes.Callvirt.ToInstruction(listAdd)); // WriteLine("Array: {0}", list.ToArray()); //body.Instructions.Add(OpCodes.Ldstr.ToInstruction("Array: {0}")); //body.Instructions.Add(OpCodes.Ldloc_0.ToInstruction()); // Load list from local[0] //body.Instructions.Add(OpCodes.Callvirt.ToInstruction(listToArray)); //body.Instructions.Add(OpCodes.Call.ToInstruction(writeLine2)); // WriteLine("Count: {0}", list.Count) body.Instructions.Add(OpCodes.Ldstr.ToInstruction("Count: {0}")); body.Instructions.Add(OpCodes.Ldloc_0.ToInstruction()); // Load list from local[0] body.Instructions.Add(OpCodes.Callvirt.ToInstruction(listGetCount)); body.Instructions.Add(OpCodes.Box.ToInstruction(mod.CorLibTypes.Int32)); body.Instructions.Add(OpCodes.Call.ToInstruction(writeLine2)); // return 0; body.Instructions.Add(OpCodes.Ldc_I4_0.ToInstruction()); body.Instructions.Add(OpCodes.Ret.ToInstruction()); entryPoint.Body = body; // Save the assembly mod.Write(newFileName); }
MemberRef SimpleClone(MethodDef methodRef, ITypeDefOrRef declaringType) { if (module == null) return new MemberRefUser(null, methodRef.Name, methodRef.MethodSig, declaringType); var mr = new MemberRefUser(module.ModuleDefMD, methodRef.Name, methodRef.MethodSig, declaringType); return module.ModuleDefMD.UpdateRowId(mr); }
public MemberRef CreateInitializeArrayMethod() { if (_initializeArrayMethod == null) { var runtimeHelpersType = FindOrCreateTypeRef(_module, _module.CorLibTypes.AssemblyRef, "System.Runtime.CompilerServices", "RuntimeHelpers", false); var systemArrayType = FindOrCreateTypeRef(_module, _module.CorLibTypes.AssemblyRef, "System", "Array", false); var runtimeFieldHandleType = FindOrCreateTypeRef(_module, _module.CorLibTypes.AssemblyRef, "System", "RuntimeFieldHandle", true); var methodSig = MethodSig.CreateStatic(_module.CorLibTypes.Void, systemArrayType, runtimeFieldHandleType); _initializeArrayMethod = _module.UpdateRowId(new MemberRefUser(_module, "InitializeArray", methodSig, runtimeHelpersType.TypeDefOrRef)); } return _initializeArrayMethod; }
private void pasteToolStripMenuItem_Click(object sender, EventArgs e) { int instructionIndex = dgBody.SelectedRows.TopmostRow().Index + 1; foreach (Instruction instruction in _copiedInstructions.OrderByDescending(i => i.Offset)) { var newInstruction = new Instruction(instruction.OpCode); if (instruction.Operand != null) switch (instruction.OpCode.OperandType) { case OperandType.InlineField: var field = instruction.Operand as IField; if (field.DeclaringType.DefinitionAssembly != CurrentAssembly.ManifestModule.Assembly || field.Module != CurrentAssembly.ManifestModule) { var fieldRef = new MemberRefUser(field.Module, field.Name, field.FieldSig, field.DeclaringType); newInstruction.Operand = CurrentAssembly.ManifestModule.Import(fieldRef); } else { newInstruction.Operand = CurrentAssembly.ManifestModule.ResolveField(field.Rid); } break; case OperandType.InlineMethod: var method = instruction.Operand as IMethod; if (method.DeclaringType.DefinitionAssembly != CurrentAssembly.ManifestModule.Assembly || method.Module != CurrentAssembly.ManifestModule) { var methodRef = new MemberRefUser(method.Module, method.Name, method.MethodSig, method.DeclaringType); newInstruction.Operand = CurrentAssembly.ManifestModule.Import(methodRef); } else { newInstruction.Operand = CurrentAssembly.ManifestModule.ResolveMethod(method.Rid); } break; case OperandType.InlineType: var type = instruction.Operand as ITypeDefOrRef; if (type.DefinitionAssembly != CurrentAssembly.ManifestModule.Assembly || type.Module != CurrentAssembly.ManifestModule) { var typeRef = new TypeRefUser(type.Module, type.Namespace, type.Name, CurrentAssembly.ManifestModule.CorLibTypes.AssemblyRef); newInstruction.Operand = CurrentAssembly.ManifestModule.Import(typeRef); } else { newInstruction.Operand = CurrentAssembly.ManifestModule.ResolveTypeDefOrRef(type.Rid); } break; default: newInstruction.Operand = instruction.Operand; break; } CurrentAssembly.Method.Body.Instructions.Insert(instructionIndex, newInstruction); } FixBranches(); CurrentAssembly.Method.Body.Instructions.UpdateInstructionOffsets(); DataGridViewHandler.ReadMethod(CurrentAssembly.Method); }
public static void Run() { // This is the file that will be created string newFileName = @"GenericExample2.exe"; // Create the module var mod = new ModuleDefUser("GenericExample2", Guid.NewGuid(), new AssemblyRefUser(new AssemblyNameInfo(typeof(int).Assembly.GetName().FullName))); // It's a console app mod.Kind = ModuleKind.Console; // Create the assembly and add the created module to it new AssemblyDefUser("GenericExample2", new Version(1, 2, 3, 4)).Modules.Add(mod); // Add the startup type. It derives from System.Object. TypeDef startUpType = new TypeDefUser("My.Namespace", "Startup", mod.CorLibTypes.Object.TypeDefOrRef); startUpType.Attributes = TypeAttributes.NotPublic | TypeAttributes.AutoLayout | TypeAttributes.Class | TypeAttributes.AnsiClass; // Add the type to the module mod.Types.Add(startUpType); // Create the entry point method MethodDef entryPoint = new MethodDefUser("Main", MethodSig.CreateStatic(mod.CorLibTypes.Int32, new SZArraySig(mod.CorLibTypes.String))); entryPoint.Attributes = MethodAttributes.Private | MethodAttributes.Static | MethodAttributes.HideBySig | MethodAttributes.ReuseSlot; entryPoint.ImplAttributes = MethodImplAttributes.IL | MethodImplAttributes.Managed; // Name the 1st argument (argument 0 is the return type) entryPoint.ParamDefs.Add(new ParamDefUser("args", 1)); // Add the method to the startup type startUpType.Methods.Add(entryPoint); // Set module entry point mod.EntryPoint = entryPoint; // Create System.Console type reference var systemConsole = mod.CorLibTypes.GetTypeRef("System", "Console"); // Create 'void System.Console.WriteLine(string,object)' method reference var writeLine2 = new MemberRefUser(mod, "WriteLine", MethodSig.CreateStatic(mod.CorLibTypes.Void, mod.CorLibTypes.String, mod.CorLibTypes.Object), systemConsole); var assemblyRef = mod.CorLibTypes.AssemblyRef; // Create 'System.Collections.ObjectModel.ReadOnlyCollection`1' type ref var roCollectionRef = new TypeRefUser(mod, "System.Collections.ObjectModel", "ReadOnlyCollection`1", assemblyRef); // Create 'ReadOnlyCollection<!!0>' signature for return type var roCollectionSig = new GenericInstSig(new ClassSig(roCollectionRef), new GenericMVar(0)); // Return type // Create 'ReadOnlyCollection<Int32>' type spec var roCollectionTypeSpec = new TypeSpecUser(new GenericInstSig(new ClassSig(roCollectionRef), mod.CorLibTypes.Int32)); // Create 'ReadOnlyCollection<Int32>.get_Count()' method reference var roCollectionGetCount = new MemberRefUser(mod, "get_Count", MethodSig.CreateInstance(mod.CorLibTypes.Int32), roCollectionTypeSpec); // Create 'System.Array' type ref var arrayRef = new TypeRefUser(mod, "System", "Array", assemblyRef); // Create 'ReadOnlyCollection<T> Array.AsReadOnly<T>(T[] array)' method reference // Apparently CreateStaticGeneric should be used only if at least one GenericMVar is used? Not 100% certain. var asReadOnly = new MemberRefUser(mod, "AsReadOnly", MethodSig.CreateStaticGeneric(1, roCollectionSig, new SZArraySig(new GenericMVar(0))), arrayRef); // Create 'Array.AsReadOnly<Int32>' method spec var asReadOnlySpec = new MethodSpecUser(asReadOnly, new GenericInstMethodSig(mod.CorLibTypes.Int32)); // Create 'ReadOnlyCollection<Int32>' signature for local var roCollectionInt32 = roCollectionTypeSpec.TryGetGenericInstSig(); // Method body locals IList<Local> locals = new List<Local>(); locals.Add(new Local(new SZArraySig(mod.CorLibTypes.Int32))); // local[0]: Int32[] locals.Add(new Local(roCollectionInt32)); // local[1]: class [mscorlib]System.Collections.ObjectModel.ReadOnlyCollection`1<Int32> var body = new CilBody(true, new List<Instruction>(), new List<ExceptionHandler>(), locals); // array = new Int32[2]; body.Instructions.Add(OpCodes.Ldc_I4_2.ToInstruction()); body.Instructions.Add(OpCodes.Newarr.ToInstruction(mod.CorLibTypes.Int32)); body.Instructions.Add(OpCodes.Stloc_0.ToInstruction()); // Store array to local[0] // array[0] = 5; body.Instructions.Add(OpCodes.Ldloc_0.ToInstruction()); body.Instructions.Add(OpCodes.Ldc_I4_0.ToInstruction()); body.Instructions.Add(OpCodes.Ldc_I4_5.ToInstruction()); body.Instructions.Add(OpCodes.Stelem_I4.ToInstruction()); // array[1] = 111; body.Instructions.Add(OpCodes.Ldloc_0.ToInstruction()); body.Instructions.Add(OpCodes.Ldc_I4_1.ToInstruction()); body.Instructions.Add(OpCodes.Ldc_I4.ToInstruction(111)); body.Instructions.Add(OpCodes.Stelem_I4.ToInstruction()); // collection = Array.AsReadOnly<Int32>(array) body.Instructions.Add(OpCodes.Ldloc_0.ToInstruction()); body.Instructions.Add(OpCodes.Call.ToInstruction(asReadOnlySpec)); body.Instructions.Add(OpCodes.Stloc_1.ToInstruction()); // Console.WriteLine("Count: {0}", collection.Count) body.Instructions.Add(OpCodes.Ldstr.ToInstruction("Count: {0}")); body.Instructions.Add(OpCodes.Ldloc_1.ToInstruction()); body.Instructions.Add(OpCodes.Callvirt.ToInstruction(roCollectionGetCount)); body.Instructions.Add(OpCodes.Box.ToInstruction(mod.CorLibTypes.Int32)); body.Instructions.Add(OpCodes.Call.ToInstruction(writeLine2)); // return 0; body.Instructions.Add(OpCodes.Ldc_I4_0.ToInstruction()); body.Instructions.Add(OpCodes.Ret.ToInstruction()); entryPoint.Body = body; // Save the assembly mod.Write(newFileName); }
/// <summary> /// Creates a custom ObfuscationAttribute that can be added to a method. /// </summary> /// <param name="module">Module</param> /// <param name="feature">Obfuscation feature name</param> /// <param name="exclude">true if exclude, false if include</param> /// <returns>CustomAttribute</returns> CustomAttribute CreateAttribute(ModuleDef module, String feature, Boolean exclude) { TypeSig stringSig = module.CorLibTypes.String; TypeSig booleanSig = module.CorLibTypes.Boolean; CANamedArgument[] args = new CANamedArgument[] { // Feature new CANamedArgument( false, stringSig, "Feature", new CAArgument(stringSig, feature)), // Exclude new CANamedArgument( false, booleanSig, "Exclude", new CAArgument(booleanSig, exclude)) }; TypeRef obfuscationRef = new TypeRefUser( module, "System.Reflection", "ObfuscationAttribute", module.CorLibTypes.AssemblyRef); MemberRef obfuscationCtor = new MemberRefUser(module, ".ctor", MethodSig.CreateInstance(module.CorLibTypes.Void), obfuscationRef); CustomAttribute attr = new CustomAttribute( obfuscationCtor, new CAArgument[0], args ); return attr; }
/// <summary> /// Calli. /// </summary> /// <param name="module">Module</param> /// <param name="mainType">Main type</param> /// <returns>Instructions</returns> static IList<Instruction> GetCalliInstructions(ModuleDef module, TypeDef mainType) { TypeRef consoleRef = new TypeRefUser(module, "System", "Console", module.CorLibTypes.AssemblyRef); MemberRef consoleWrite0 = new MemberRefUser(module, "WriteLine", MethodSig.CreateStatic(module.CorLibTypes.Void), consoleRef); var all = new List<Instruction>(); all.Add(OpCodes.Ldftn.ToInstruction(consoleWrite0)); all.Add(OpCodes.Calli.ToInstruction(consoleWrite0.MethodSig)); all.Add(OpCodes.Ret.ToInstruction()); return all; }