Restore calls to CodeDomProvider and ICodeCompiler

This commit is contained in:
de4dot 2012-04-29 04:03:10 +02:00
parent 9333e2415c
commit 48b9c461f5
5 changed files with 195 additions and 2 deletions

View File

@ -151,6 +151,7 @@
<Compile Include="deobfuscators\dotNET_Reactor\v3\DecryptMethod.cs" />
<Compile Include="deobfuscators\dotNET_Reactor\v3\MemoryPatcher.cs" />
<Compile Include="deobfuscators\Eazfuscator_NET\AssemblyResolver.cs" />
<Compile Include="deobfuscators\Eazfuscator_NET\CodeCompilerMethodCallRestorer.cs" />
<Compile Include="deobfuscators\Eazfuscator_NET\ConstantsReader.cs" />
<Compile Include="deobfuscators\Eazfuscator_NET\DecrypterType.cs" />
<Compile Include="deobfuscators\Eazfuscator_NET\Deobfuscator.cs" />

View File

@ -38,6 +38,7 @@ namespace de4dot.code.deobfuscators.Eazfuscator_NET {
List<AssemblyInfo> assemblyInfos = new List<AssemblyInfo>();
FrameworkType frameworkType;
byte[] decryptKey;
CodeCompilerMethodCallRestorer codeCompilerMethodCallRestorer;
public class AssemblyInfo {
public bool IsEncrypted { get; set; }
@ -79,6 +80,7 @@ namespace de4dot.code.deobfuscators.Eazfuscator_NET {
this.module = module;
this.frameworkType = DotNetUtils.getFrameworkType(module);
this.decrypterType = decrypterType;
this.codeCompilerMethodCallRestorer = new CodeCompilerMethodCallRestorer(module);
}
public void find() {
@ -110,6 +112,7 @@ namespace de4dot.code.deobfuscators.Eazfuscator_NET {
decryptMethod = getDecryptMethod();
updateDecrypterType();
findCodeDomMethods();
return true;
}
@ -152,7 +155,7 @@ namespace de4dot.code.deobfuscators.Eazfuscator_NET {
bool checkInitMethod(MethodDefinition method) {
var type = method.DeclaringType;
if (type.NestedTypes.Count != 3)
if (type.NestedTypes.Count < 2 || type.NestedTypes.Count > 6)
return false;
if (DotNetUtils.getPInvokeMethod(type, "kernel32", "MoveFileEx") == null)
return false;
@ -420,5 +423,69 @@ namespace de4dot.code.deobfuscators.Eazfuscator_NET {
return null;
}
public void deobfuscate(Blocks blocks) {
codeCompilerMethodCallRestorer.deobfuscate(blocks);
}
void findCodeDomMethods() {
if (resolverType == null)
return;
foreach (var nestedType in resolverType.NestedTypes) {
if (nestedType.Fields.Count != 0)
continue;
var CompileAssemblyFromDom1 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.CodeDomProvider", "CompileAssemblyFromDom", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.CodeDom.CodeCompileUnit[]");
var CompileAssemblyFromFile1 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.CodeDomProvider", "CompileAssemblyFromFile", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.String[]");
var CompileAssemblyFromSource1 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.CodeDomProvider", "CompileAssemblyFromSource", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.String[]");
var CompileAssemblyFromDom2 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.ICodeCompiler", "CompileAssemblyFromDom", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.CodeDom.CodeCompileUnit");
var CompileAssemblyFromDomBatch2 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.ICodeCompiler", "CompileAssemblyFromDomBatch", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.CodeDom.CodeCompileUnit[]");
var CompileAssemblyFromFile2 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.ICodeCompiler", "CompileAssemblyFromFile", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.String");
var CompileAssemblyFromFileBatch2 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.ICodeCompiler", "CompileAssemblyFromFileBatch", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.String[]");
var CompileAssemblyFromSource2 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.ICodeCompiler", "CompileAssemblyFromSource", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.String");
var CompileAssemblyFromSourceBatch2 = getTheOnlyMethod(nestedType, "System.CodeDom.Compiler.ICodeCompiler", "CompileAssemblyFromSourceBatch", "System.CodeDom.Compiler.CompilerResults", "System.CodeDom.Compiler.CompilerParameters,System.String[]");
if (CompileAssemblyFromDom1 == null && CompileAssemblyFromFile1 == null &&
CompileAssemblyFromSource1 == null && CompileAssemblyFromDom2 == null &&
CompileAssemblyFromDomBatch2 == null && CompileAssemblyFromFile2 == null &&
CompileAssemblyFromFileBatch2 == null && CompileAssemblyFromSource2 == null &&
CompileAssemblyFromSourceBatch2 == null) {
continue;
}
codeCompilerMethodCallRestorer.add_CodeDomProvider_CompileAssemblyFromDom(CompileAssemblyFromDom1);
codeCompilerMethodCallRestorer.add_CodeDomProvider_CompileAssemblyFromFile(CompileAssemblyFromFile1);
codeCompilerMethodCallRestorer.add_CodeDomProvider_CompileAssemblyFromSource(CompileAssemblyFromSource1);
codeCompilerMethodCallRestorer.add_ICodeCompiler_CompileAssemblyFromDom(CompileAssemblyFromDom2);
codeCompilerMethodCallRestorer.add_ICodeCompiler_CompileAssemblyFromDomBatch(CompileAssemblyFromDomBatch2);
codeCompilerMethodCallRestorer.add_ICodeCompiler_CompileAssemblyFromFile(CompileAssemblyFromFile2);
codeCompilerMethodCallRestorer.add_ICodeCompiler_CompileAssemblyFromFileBatch(CompileAssemblyFromFileBatch2);
codeCompilerMethodCallRestorer.add_ICodeCompiler_CompileAssemblyFromSource(CompileAssemblyFromSource2);
codeCompilerMethodCallRestorer.add_ICodeCompiler_CompileAssemblyFromSourceBatch(CompileAssemblyFromSourceBatch2);
break;
}
}
static MethodDefinition getTheOnlyMethod(TypeDefinition type, string typeName, string methodName, string returnType, string parameters) {
MethodDefinition foundMethod = null;
foreach (var method in type.Methods) {
if (!method.IsStatic || method.Body == null || method.HasGenericParameters)
continue;
if (method.IsPrivate)
continue;
if (!DotNetUtils.isMethod(method, returnType, "(" + typeName + "," + parameters + ")"))
continue;
if (!DotNetUtils.callsMethod(method, returnType + " " + typeName + "::" + methodName + "(" + parameters + ")"))
continue;
if (foundMethod != null)
return null;
foundMethod = method;
}
return foundMethod;
}
}
}

View File

@ -0,0 +1,120 @@
/*
Copyright (C) 2011-2012 de4dot@gmail.com
This file is part of de4dot.
de4dot is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
de4dot is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with de4dot. If not, see <http://www.gnu.org/licenses/>.
*/
using Mono.Cecil;
namespace de4dot.code.deobfuscators.Eazfuscator_NET {
class CodeCompilerMethodCallRestorer : MethodCallRestorerBase {
TypeReference CodeDomProvider {
get {
return builder.type("System.CodeDom.Compiler", "CodeDomProvider", "System");
}
}
TypeReference ICodeCompiler {
get {
return builder.type("System.CodeDom.Compiler", "ICodeCompiler", "System");
}
}
TypeReference CompilerResults {
get {
return builder.type("System.CodeDom.Compiler", "CompilerResults", "System");
}
}
TypeReference CompilerParameters {
get {
return builder.type("System.CodeDom.Compiler", "CompilerParameters", "System");
}
}
TypeReference CodeCompileUnit {
get {
return builder.type("System.CodeDom", "CodeCompileUnit", "System");
}
}
TypeReference CodeCompileUnitArray {
get { return builder.array(CodeCompileUnit); }
}
TypeReference StringArray {
get { return builder.array(builder.String); }
}
public CodeCompilerMethodCallRestorer(ModuleDefinition module)
: base(module) {
}
public void add_CodeDomProvider_CompileAssemblyFromDom(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromDom", CodeDomProvider, CompilerResults, CompilerParameters, CodeCompileUnitArray));
}
public void add_CodeDomProvider_CompileAssemblyFromFile(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromFile", CodeDomProvider, CompilerResults, CompilerParameters, StringArray));
}
public void add_CodeDomProvider_CompileAssemblyFromSource(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromSource", CodeDomProvider, CompilerResults, CompilerParameters, StringArray));
}
public void add_ICodeCompiler_CompileAssemblyFromDom(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromDom", ICodeCompiler, CompilerResults, CompilerParameters, CodeCompileUnit));
}
public void add_ICodeCompiler_CompileAssemblyFromDomBatch(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromDomBatch", ICodeCompiler, CompilerResults, CompilerParameters, CodeCompileUnitArray));
}
public void add_ICodeCompiler_CompileAssemblyFromFile(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromFile", ICodeCompiler, CompilerResults, CompilerParameters, builder.String));
}
public void add_ICodeCompiler_CompileAssemblyFromFileBatch(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromFileBatch", ICodeCompiler, CompilerResults, CompilerParameters, StringArray));
}
public void add_ICodeCompiler_CompileAssemblyFromSource(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromSource", ICodeCompiler, CompilerResults, CompilerParameters, builder.String));
}
public void add_ICodeCompiler_CompileAssemblyFromSourceBatch(MethodDefinition oldMethod) {
if (oldMethod == null)
return;
add(oldMethod, builder.instanceMethod("CompileAssemblyFromSourceBatch", ICodeCompiler, CompilerResults, CompilerParameters, StringArray));
}
}
}

View File

@ -144,6 +144,7 @@ namespace de4dot.code.deobfuscators.Eazfuscator_NET {
public override void deobfuscateMethodEnd(Blocks blocks) {
resourceMethodsRestorer.deobfuscate(blocks);
assemblyResolver.deobfuscate(blocks);
base.deobfuscateMethodEnd(blocks);
}

View File

@ -90,7 +90,11 @@ namespace de4dot.code.deobfuscators {
add(oldMethod, newMethod, OpCodes.Newobj);
}
void add(MethodDefinition oldMethod, MethodReference newMethod, OpCode opCode) {
protected void add(MethodDefinition oldMethod, MethodReference newMethod) {
add(oldMethod, newMethod, OpCodes.Callvirt);
}
protected void add(MethodDefinition oldMethod, MethodReference newMethod, OpCode opCode) {
if (oldMethod == null)
return;
oldToNewMethod.add(oldMethod, new NewMethodInfo(opCode, newMethod));