diff --git a/de4dot.code/de4dot.code.csproj b/de4dot.code/de4dot.code.csproj
index 9f48a2e0..a56d2163 100644
--- a/de4dot.code/de4dot.code.csproj
+++ b/de4dot.code/de4dot.code.csproj
@@ -88,12 +88,10 @@
-
-
-
+
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM1.bin b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM1.bin
new file mode 100644
index 00000000..e32fb05e
Binary files /dev/null and b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM1.bin differ
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM1_v2.bin b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM1_v2.bin
deleted file mode 100644
index 156f0777..00000000
Binary files a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM1_v2.bin and /dev/null differ
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM2.bin b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM2.bin
new file mode 100644
index 00000000..e1e577a5
Binary files /dev/null and b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM2.bin differ
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM2_v2.bin b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM2_v2.bin
deleted file mode 100644
index 81bd5ae6..00000000
Binary files a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM2_v2.bin and /dev/null differ
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM3.bin b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM3.bin
new file mode 100644
index 00000000..7378faf9
Binary files /dev/null and b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM3.bin differ
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM3_v2.bin b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM3_v2.bin
deleted file mode 100644
index a86daab3..00000000
Binary files a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM3_v2.bin and /dev/null differ
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM4.bin b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM4.bin
new file mode 100644
index 00000000..85439b6e
Binary files /dev/null and b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CSVM4.bin differ
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeHandlerDetector.cs b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeHandlerDetector.cs
index 9ae1debc..fc0452e6 100644
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeHandlerDetector.cs
+++ b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeHandlerDetector.cs
@@ -25,19 +25,17 @@ using de4dot.blocks;
namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
class CompositeHandlerDetector {
- readonly List handlers;
+ readonly List handlers;
- public CompositeHandlerDetector(IList handlers) {
- this.handlers = new List(handlers.Count);
- OpCodeHandler nop = null;
- foreach (var handler in handlers) {
- if (nop == null && handler.OpCodeHandlerInfo.TypeCode == HandlerTypeCode.Nop)
- nop = handler;
- else
- this.handlers.Add(handler);
- }
- if (nop != null)
- this.handlers.Add(nop);
+ public CompositeHandlerDetector(IList handlers) {
+ this.handlers = new List(handlers);
+
+ this.handlers.Sort((a, b) => {
+ int r = b.BlockSigInfos.Count.CompareTo(a.BlockSigInfos.Count);
+ if (r != 0)
+ return r;
+ return b.BlockSigInfos[0].Hashes.Count.CompareTo(a.BlockSigInfos[0].Hashes.Count);
+ });
}
struct MatchState {
@@ -51,27 +49,18 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
}
struct HandlerState {
- public readonly HandlerMethod HandlerMethod;
- public readonly IList Blocks;
+ public readonly List BlockSigInfos;
public readonly int BlockIndex;
- public int InstructionIndex;
+ public int HashIndex;
- public HandlerState(HandlerMethod handlerMethod, int blockIndex, int instructionIndex) {
- this.HandlerMethod = handlerMethod;
- this.Blocks = handlerMethod.Blocks.MethodBlocks.GetAllBlocks();
+ public HandlerState(List blockSigInfos, int blockIndex, int instructionIndex) {
+ this.BlockSigInfos = blockSigInfos;
this.BlockIndex = blockIndex;
- this.InstructionIndex = instructionIndex;
- }
-
- public HandlerState(HandlerMethod handlerMethod, IList blocks, int blockIndex, int instructionIndex) {
- this.HandlerMethod = handlerMethod;
- this.Blocks = blocks;
- this.BlockIndex = blockIndex;
- this.InstructionIndex = instructionIndex;
+ this.HashIndex = instructionIndex;
}
public HandlerState Clone() {
- return new HandlerState(HandlerMethod, Blocks, BlockIndex, InstructionIndex);
+ return new HandlerState(BlockSigInfos, BlockIndex, HashIndex);
}
}
@@ -98,22 +87,22 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
}
public bool FindHandlers(CompositeOpCodeHandler composite) {
- composite.OpCodeHandlerInfos.Clear();
- var compositeExecState = new FindHandlerState(new HandlerState(composite.ExecMethod, 0, 0));
+ composite.TypeCodes.Clear();
+ var compositeExecState = new FindHandlerState(new HandlerState(composite.BlockSigInfos, 0, 0));
while (!compositeExecState.Done) {
var handler = FindHandlerMethod(ref compositeExecState);
if (handler == null)
return false;
- composite.OpCodeHandlerInfos.Add(handler.OpCodeHandlerInfo);
+ composite.TypeCodes.Add(handler.TypeCode);
}
- return composite.OpCodeHandlerInfos.Count != 0;
+ return composite.TypeCodes.Count != 0;
}
- OpCodeHandler FindHandlerMethod(ref FindHandlerState findExecState) {
+ MethodSigInfo FindHandlerMethod(ref FindHandlerState findExecState) {
foreach (var handler in handlers) {
FindHandlerState findExecStateNew = findExecState.Clone();
- if (!Matches(handler.ExecMethod, ref findExecStateNew))
+ if (!Matches(handler.BlockSigInfos, ref findExecStateNew))
continue;
findExecState = findExecStateNew;
@@ -123,14 +112,14 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
}
Stack stack = new Stack();
- bool Matches(HandlerMethod handler, ref FindHandlerState findState) {
+ bool Matches(List handler, ref FindHandlerState findState) {
HandlerState? nextState = null;
stack.Clear();
stack.Push(new MatchState(new HandlerState(handler, 0, 0), findState.CompositeState));
while (stack.Count > 0) {
var matchState = stack.Pop();
- if (matchState.CompositeState.InstructionIndex == 0) {
+ if (matchState.CompositeState.HashIndex == 0) {
if (findState.VisitedCompositeBlocks.ContainsKey(matchState.CompositeState.BlockIndex))
continue;
findState.VisitedCompositeBlocks[matchState.CompositeState.BlockIndex] = true;
@@ -143,193 +132,83 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
if (!Compare(ref matchState.OtherState, ref matchState.CompositeState))
return false;
- var hblock = matchState.OtherState.Blocks[matchState.OtherState.BlockIndex];
- var hinstrs = hblock.Instructions;
- int hi = matchState.OtherState.InstructionIndex;
- var cblock = matchState.CompositeState.Blocks[matchState.CompositeState.BlockIndex];
- var cinstrs = cblock.Instructions;
- int ci = matchState.CompositeState.InstructionIndex;
+ var hblock = matchState.OtherState.BlockSigInfos[matchState.OtherState.BlockIndex];
+ var hinstrs = hblock.Hashes;
+ int hi = matchState.OtherState.HashIndex;
+ var cblock = matchState.CompositeState.BlockSigInfos[matchState.CompositeState.BlockIndex];
+ var cinstrs = cblock.Hashes;
+ int ci = matchState.CompositeState.HashIndex;
if (hi < hinstrs.Count)
return false;
if (ci < cinstrs.Count) {
- if (hblock.CountTargets() != 0)
+ if (hblock.Targets.Count != 0)
return false;
- if (hblock.LastInstr.OpCode.Code == Code.Ret) {
+ if (hblock.EndsInRet) {
if (nextState != null)
return false;
nextState = matchState.CompositeState;
}
}
else {
- if (cblock.CountTargets() != hblock.CountTargets())
+ if (cblock.Targets.Count != hblock.Targets.Count)
+ return false;
+ if (cblock.HasFallThrough != hblock.HasFallThrough)
return false;
- if (cblock.FallThrough != null || hblock.FallThrough != null) {
- if (cblock.FallThrough == null || hblock.FallThrough == null)
- return false;
- var hs = CreateHandlerState(handler, matchState.OtherState.Blocks, hblock.FallThrough);
- var cs = CreateHandlerState(findState.CompositeState.HandlerMethod, findState.CompositeState.Blocks, cblock.FallThrough);
+ for (int i = 0; i < cblock.Targets.Count; i++) {
+ var hs = new HandlerState(handler, hblock.Targets[i], 0);
+ var cs = new HandlerState(findState.CompositeState.BlockSigInfos, cblock.Targets[i], 0);
stack.Push(new MatchState(hs, cs));
}
- if (cblock.Targets != null || hblock.Targets != null) {
- if (cblock.Targets == null || hblock.Targets == null ||
- cblock.Targets.Count != hblock.Targets.Count)
- return false;
-
- for (int i = 0; i < cblock.Targets.Count; i++) {
- var hs = CreateHandlerState(handler, matchState.OtherState.Blocks, hblock.Targets[i]);
- var cs = CreateHandlerState(findState.CompositeState.HandlerMethod, findState.CompositeState.Blocks, cblock.Targets[i]);
- stack.Push(new MatchState(hs, cs));
- }
- }
}
}
if (nextState == null) {
+ if (findState.VisitedCompositeBlocks.Count != findState.CompositeState.BlockSigInfos.Count)
+ return false;
findState.Done = true;
return true;
}
else {
if (findState.CompositeState.BlockIndex == nextState.Value.BlockIndex &&
- findState.CompositeState.InstructionIndex == nextState.Value.InstructionIndex)
+ findState.CompositeState.HashIndex == nextState.Value.HashIndex)
return false;
findState.CompositeState = nextState.Value;
+ if (findState.CompositeState.HashIndex == 0)
+ findState.VisitedCompositeBlocks.Remove(findState.CompositeState.BlockIndex);
return true;
}
}
- static HandlerState CreateHandlerState(HandlerMethod handler, IList blocks, Block target) {
- return new HandlerState(handler, blocks.IndexOf(target), 0);
- }
-
static bool Compare(ref HandlerState handler, ref HandlerState composite) {
- var hinstrs = handler.Blocks[handler.BlockIndex].Instructions;
- int hi = handler.InstructionIndex;
- var cinstrs = composite.Blocks[composite.BlockIndex].Instructions;
- int ci = composite.InstructionIndex;
+ var hhashes = handler.BlockSigInfos[handler.BlockIndex].Hashes;
+ int hi = handler.HashIndex;
+ var chashes = composite.BlockSigInfos[composite.BlockIndex].Hashes;
+ int ci = composite.HashIndex;
while (true) {
- if (hi >= hinstrs.Count && ci >= cinstrs.Count)
+ if (hi >= hhashes.Count && ci >= chashes.Count)
break;
- if (hi >= hinstrs.Count || ci >= cinstrs.Count)
+
+ if (hi >= hhashes.Count) {
+ if (handler.BlockSigInfos[handler.BlockIndex].EndsInRet)
+ break;
+ }
+
+ if (hi >= hhashes.Count || ci >= chashes.Count)
return false;
- var hinstr = hinstrs[hi++];
- var cinstr = cinstrs[ci++];
- if (hinstr.OpCode.Code == Code.Nop ||
- cinstr.OpCode.Code == Code.Nop) {
- if (hinstr.OpCode.Code != Code.Nop)
- hi--;
- if (cinstr.OpCode.Code != Code.Nop)
- ci--;
- continue;
- }
+ var hhash = hhashes[hi++];
+ var chash = chashes[ci++];
- if (hi == hinstrs.Count && hinstr.OpCode.Code == Code.Ret) {
- if (cinstr.OpCode.Code != Code.Br && cinstr.OpCode.Code != Code.Ret)
- ci--;
- break;
- }
-
- if (hinstr.OpCode.Code != cinstr.OpCode.Code)
- return false;
-
- if (hinstr.OpCode.Code == Code.Ldfld &&
- hi + 1 < hinstrs.Count && ci + 1 < cinstrs.Count) {
- var hfield = hinstr.Operand as FieldDef;
- var cfield = cinstr.Operand as FieldDef;
- if (hfield != null && cfield != null &&
- !hfield.IsStatic && !cfield.IsStatic &&
- hfield.DeclaringType == handler.HandlerMethod.Method.DeclaringType &&
- cfield.DeclaringType == composite.HandlerMethod.Method.DeclaringType &&
- SignatureEqualityComparer.Instance.Equals(hfield.Signature, cfield.Signature)) {
- cinstr = cinstrs[ci++];
- hinstr = hinstrs[hi++];
- if (cinstr.OpCode.Code != Code.Ldc_I4 ||
- hinstr.OpCode.Code != Code.Ldc_I4)
- return false;
- continue;
- }
- }
-
- if (!CompareOperand(hinstr.OpCode.OperandType, cinstr.Operand, hinstr.Operand))
+ if (chash != hhash)
return false;
}
- handler.InstructionIndex = hi;
- composite.InstructionIndex = ci;
+ handler.HashIndex = hi;
+ composite.HashIndex = ci;
return true;
}
-
- static bool CompareOperand(OperandType opType, object a, object b) {
- switch (opType) {
- case OperandType.ShortInlineI:
- return (a is byte && b is byte && (byte)a == (byte)b) ||
- (a is sbyte && b is sbyte && (sbyte)a == (sbyte)b);
-
- case OperandType.InlineI:
- return a is int && b is int && (int)a == (int)b;
-
- case OperandType.InlineI8:
- return a is long && b is long && (long)a == (long)b;
-
- case OperandType.ShortInlineR:
- return a is float && b is float && (float)a == (float)b;
-
- case OperandType.InlineR:
- return a is double && b is double && (double)a == (double)b;
-
- case OperandType.InlineField:
- return FieldEqualityComparer.CompareDeclaringTypes.Equals(a as IField, b as IField);
-
- case OperandType.InlineMethod:
- return MethodEqualityComparer.CompareDeclaringTypes.Equals(a as IMethod, b as IMethod);
-
- case OperandType.InlineSig:
- return SignatureEqualityComparer.Instance.Equals(a as MethodSig, b as MethodSig);
-
- case OperandType.InlineString:
- return string.Equals(a as string, b as string);
-
- case OperandType.InlineSwitch:
- var al = a as IList;
- var bl = b as IList;
- return al != null && bl != null && al.Count == bl.Count;
-
- case OperandType.InlineTok:
- var fa = a as IField;
- var fb = b as IField;
- if (fa != null && fb != null)
- return FieldEqualityComparer.CompareDeclaringTypes.Equals(fa, fb);
- var ma = a as IMethod;
- var mb = b as IMethod;
- if (ma != null && mb != null)
- return MethodEqualityComparer.CompareDeclaringTypes.Equals(ma, mb);
- return TypeEqualityComparer.Instance.Equals(a as ITypeDefOrRef, b as ITypeDefOrRef);
-
- case OperandType.InlineType:
- return TypeEqualityComparer.Instance.Equals(a as ITypeDefOrRef, b as ITypeDefOrRef);
-
- case OperandType.InlineVar:
- case OperandType.ShortInlineVar:
- var la = a as Local;
- var lb = b as Local;
- if (la != null && lb != null)
- return true;
- var pa = a as Parameter;
- var pb = b as Parameter;
- return pa != null && pb != null && pa.Index == pb.Index;
-
- case OperandType.InlineBrTarget:
- case OperandType.ShortInlineBrTarget:
- case OperandType.InlineNone:
- case OperandType.InlinePhi:
- return true;
-
- default:
- return false;
- }
- }
}
}
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeOpCodeHandler.cs b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeOpCodeHandler.cs
index 2508d020..cc6afe0e 100644
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeOpCodeHandler.cs
+++ b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CompositeOpCodeHandler.cs
@@ -23,45 +23,17 @@ using dnlib.DotNet;
using de4dot.blocks;
namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
- class HandlerMethod {
- public MethodDef Method { get; private set; }
- public Blocks Blocks { get; private set; }
-
- public HandlerMethod(MethodDef method) {
- this.Method = method;
- this.Blocks = new Blocks(method);
- }
- }
-
- class PrimitiveHandlerMethod : HandlerMethod {
- public MethodSigInfo Sig { get; set; }
-
- public PrimitiveHandlerMethod(MethodDef method)
- : base(method) {
- }
- }
-
class CompositeOpCodeHandler {
- public TypeDef HandlerType { get; private set; }
- public HandlerMethod ExecMethod { get; private set; }
- public List OpCodeHandlerInfos { get; private set; }
+ public List BlockSigInfos { get; private set; }
+ public List TypeCodes { get; private set; }
- public CompositeOpCodeHandler(TypeDef handlerType, HandlerMethod execMethod) {
- this.HandlerType = handlerType;
- this.ExecMethod = execMethod;
- this.OpCodeHandlerInfos = new List();
+ public CompositeOpCodeHandler(List blockSigInfos) {
+ this.BlockSigInfos = blockSigInfos;
+ this.TypeCodes = new List();
}
public override string ToString() {
- if (OpCodeHandlerInfos.Count == 0)
- return "";
- var sb = new StringBuilder();
- foreach (var handler in OpCodeHandlerInfos) {
- if (sb.Length != 0)
- sb.Append(", ");
- sb.Append(handler.Name);
- }
- return sb.ToString();
+ return OpCodeHandlerInfo.GetCompositeName(TypeCodes);
}
}
}
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmInfo.cs b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmInfo.cs
index 815cc53d..a5d1c557 100644
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmInfo.cs
+++ b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmInfo.cs
@@ -594,45 +594,79 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
}
public bool FindUnaryOpsMethods() {
- UnaryNot = FindUnaryOpMethod(Code.Not);
- UnaryNeg = FindUnaryOpMethod(Code.Neg);
- return UnaryNot != null && UnaryNeg != null;
+ UnaryNot = FindUnaryOpMethod1(Code.Not);
+ UnaryNeg = FindUnaryOpMethod1(Code.Neg);
+ if (UnaryNot != null && UnaryNeg != null)
+ return true;
+
+ return FindUnaryOpMethod2();
}
- MethodDef FindUnaryOpMethod(Code code) {
+ MethodDef FindUnaryOpMethod1(Code code) {
foreach (var type in module.Types) {
if (type.BaseType != VmHandlerBaseType)
continue;
if (type.Methods.Count != 4)
continue;
- foreach (var method in type.Methods) {
- if (!method.HasBody || !method.IsStatic)
- continue;
- if (!DotNetUtils.IsMethod(method, "System.Object", "(System.Object)"))
- continue;
- if (CountThrows(method) != 1)
- continue;
- var instrs = method.Body.Instructions;
- for (int i = 0; i < instrs.Count - 4; i++) {
- var ldarg = instrs[i];
- if (!ldarg.IsLdarg() || ldarg.GetParameterIndex() != 0)
- continue;
- if (!CheckUnboxAny(instrs[i + 1], ElementType.I4))
- continue;
- if (instrs[i + 2].OpCode.Code != code)
- continue;
- if (!CheckBox(instrs[i + 3], ElementType.I4))
- continue;
- if (!instrs[i + 4].IsStloc())
- continue;
-
- return method;
- }
- }
+ var method = FindUnaryMethod(type, code);
+ if (method != null)
+ return method;
}
return null;
}
+ bool FindUnaryOpMethod2() {
+ foreach (var type in module.Types) {
+ if (type.BaseType == null || type.BaseType.FullName != "System.Object")
+ continue;
+ if (type.Methods.Count != 3)
+ continue;
+
+ UnaryNot = FindUnaryMethod(type, Code.Not);
+ UnaryNeg = FindUnaryMethod(type, Code.Neg);
+ if (UnaryNot != null && UnaryNeg != null)
+ return true;
+ }
+ return false;
+ }
+
+ MethodDef FindUnaryMethod(TypeDef type, Code code) {
+ foreach (var method in type.Methods) {
+ if (!IsUnsaryMethod(method, code))
+ continue;
+
+ return method;
+ }
+ return null;
+ }
+
+ bool IsUnsaryMethod(MethodDef method, Code code) {
+ if (!method.HasBody || !method.IsStatic)
+ return false;
+ if (!DotNetUtils.IsMethod(method, "System.Object", "(System.Object)"))
+ return false;
+ if (CountThrows(method) != 1)
+ return false;
+ var instrs = method.Body.Instructions;
+ for (int i = 0; i < instrs.Count - 4; i++) {
+ var ldarg = instrs[i];
+ if (!ldarg.IsLdarg() || ldarg.GetParameterIndex() != 0)
+ continue;
+ if (!CheckUnboxAny(instrs[i + 1], ElementType.I4))
+ continue;
+ if (instrs[i + 2].OpCode.Code != code)
+ continue;
+ if (!CheckBox(instrs[i + 3], ElementType.I4))
+ continue;
+ if (!instrs[i + 4].IsStloc())
+ continue;
+
+ return true;
+ }
+
+ return false;
+ }
+
static int CountThrows(MethodDef method) {
if (method == null || method.Body == null)
return 0;
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.Designer.cs b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.Designer.cs
index 6153040b..3a090f84 100644
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.Designer.cs
+++ b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.Designer.cs
@@ -63,9 +63,9 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
///
/// Looks up a localized resource of type System.Byte[].
///
- internal static byte[] CSVM1_v2 {
+ internal static byte[] CSVM1 {
get {
- object obj = ResourceManager.GetObject("CSVM1_v2", resourceCulture);
+ object obj = ResourceManager.GetObject("CSVM1", resourceCulture);
return ((byte[])(obj));
}
}
@@ -73,9 +73,9 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
///
/// Looks up a localized resource of type System.Byte[].
///
- internal static byte[] CSVM2_v2 {
+ internal static byte[] CSVM2 {
get {
- object obj = ResourceManager.GetObject("CSVM2_v2", resourceCulture);
+ object obj = ResourceManager.GetObject("CSVM2", resourceCulture);
return ((byte[])(obj));
}
}
@@ -83,9 +83,19 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
///
/// Looks up a localized resource of type System.Byte[].
///
- internal static byte[] CSVM3_v2 {
+ internal static byte[] CSVM3 {
get {
- object obj = ResourceManager.GetObject("CSVM3_v2", resourceCulture);
+ object obj = ResourceManager.GetObject("CSVM3", resourceCulture);
+ return ((byte[])(obj));
+ }
+ }
+
+ ///
+ /// Looks up a localized resource of type System.Byte[].
+ ///
+ internal static byte[] CSVM4 {
+ get {
+ object obj = ResourceManager.GetObject("CSVM4", resourceCulture);
return ((byte[])(obj));
}
}
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.resx b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.resx
index 254aef83..17159be0 100644
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.resx
+++ b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmResources.resx
@@ -117,14 +117,17 @@
System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
-
-
- CSVM1_v2.bin;System.Byte[], mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ CSVM1.bin;System.Byte[], mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
-
- CSVM2_v2.bin;System.Byte[], mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+ CSVM2.bin;System.Byte[], mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
-
- CSVM3_v2.bin;System.Byte[], mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+ CSVM3.bin;System.Byte[], mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ CSVM4.bin;System.Byte[], mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
\ No newline at end of file
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmToCilMethodConverter.cs b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmToCilMethodConverter.cs
index 3cc2f2f6..7d76cf59 100644
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmToCilMethodConverter.cs
+++ b/de4dot.code/deobfuscators/Agile_NET/vm/v2/CsvmToCilMethodConverter.cs
@@ -45,11 +45,11 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
uint offset = 0;
for (int vmInstrIndex = 0; vmInstrIndex < numVmInstrs; vmInstrIndex++) {
var composite = opCodeDetector.Handlers[vmInstrs[vmInstrIndex]];
- var handlerInfos = composite.OpCodeHandlerInfos;
+ IList handlerInfos = composite.HandlerTypeCodes;
if (handlerInfos.Count == 0)
- handlerInfos = new List() { new OpCodeHandlerInfo(HandlerTypeCode.Nop, null) };
+ handlerInfos = new HandlerTypeCode[] { HandlerTypeCode.Nop };
for (int hi = 0; hi < handlerInfos.Count; hi++) {
- var instr = handlerInfoReader.Read(handlerInfos[hi].TypeCode, reader);
+ var instr = handlerInfoReader.Read(handlerInfos[hi], reader);
instr.Offset = offset;
offset += (uint)GetInstructionSize(instr);
SetCilToVmIndex(instr, vmInstrIndex);
@@ -58,6 +58,7 @@ namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
instrs.Add(instr);
}
}
+
return instrs;
}
}
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/MethodFinder.cs b/de4dot.code/deobfuscators/Agile_NET/vm/v2/MethodFinder.cs
deleted file mode 100644
index ca206830..00000000
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/MethodFinder.cs
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- Copyright (C) 2011-2013 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 .
-*/
-
-using System.Collections.Generic;
-
-namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
- class MethodFinder {
- readonly IList handlerInfos;
- readonly PrimitiveHandlerMethod handlerMethod;
-
- class SigState {
- public readonly MethodSigInfo SigInfo;
-
- public SigState(PrimitiveHandlerMethod handlerMethod) {
- this.SigInfo = handlerMethod.Sig;
- }
- }
-
- public MethodFinder(IList handlerInfos, PrimitiveHandlerMethod handlerMethod) {
- this.handlerInfos = handlerInfos;
- this.handlerMethod = handlerMethod;
- }
-
- public OpCodeHandler FindHandler() {
- var handler = FindHandler(new SigState(handlerMethod));
- if (handler == null)
- return null;
-
- return new OpCodeHandler(handler, handlerMethod.Method.DeclaringType, handlerMethod);
- }
-
- OpCodeHandlerInfo FindHandler(SigState execSigState) {
- foreach (var handler in handlerInfos) {
- if (Matches(handler.ExecSig, execSigState))
- return handler;
- }
- return null;
- }
-
- struct MatchInfo {
- public int HandlerIndex;
- public int SigIndex;
-
- public MatchInfo(int handlerIndex, int sigIndex) {
- this.HandlerIndex = handlerIndex;
- this.SigIndex = sigIndex;
- }
- }
-
- Dictionary sigIndexToHandlerIndex = new Dictionary();
- Dictionary handlerIndexToSigIndex = new Dictionary();
- Stack stack = new Stack();
- bool Matches(MethodSigInfo handlerSig, SigState sigState) {
- stack.Clear();
- sigIndexToHandlerIndex.Clear();
- handlerIndexToSigIndex.Clear();
- var handlerInfos = handlerSig.BlockInfos;
- var sigInfos = sigState.SigInfo.BlockInfos;
-
- stack.Push(new MatchInfo(0, 0));
- while (stack.Count > 0) {
- var info = stack.Pop();
-
- int handlerIndex, sigIndex;
- bool hasVisitedHandler = handlerIndexToSigIndex.TryGetValue(info.HandlerIndex, out sigIndex);
- bool hasVisitedSig = sigIndexToHandlerIndex.TryGetValue(info.SigIndex, out handlerIndex);
- if (hasVisitedHandler != hasVisitedSig)
- return false;
- if (hasVisitedHandler) {
- if (handlerIndex != info.HandlerIndex || sigIndex != info.SigIndex)
- return false;
- continue;
- }
- handlerIndexToSigIndex[info.HandlerIndex] = info.SigIndex;
- sigIndexToHandlerIndex[info.SigIndex] = info.HandlerIndex;
-
- var handlerBlock = handlerInfos[info.HandlerIndex];
- var sigBlock = sigInfos[info.SigIndex];
-
- if (!handlerBlock.Equals(sigBlock))
- return false;
-
- for (int i = 0; i < handlerBlock.Targets.Count; i++) {
- int handlerTargetIndex = handlerBlock.Targets[i];
- int sigTargetIndex = sigBlock.Targets[i];
- stack.Push(new MatchInfo(handlerTargetIndex, sigTargetIndex));
- }
- }
-
- return true;
- }
- }
-}
diff --git a/de4dot.code/deobfuscators/Agile_NET/vm/v2/MethodSigInfoCreator.cs b/de4dot.code/deobfuscators/Agile_NET/vm/v2/MethodSigInfoCreator.cs
deleted file mode 100644
index c311e0a9..00000000
--- a/de4dot.code/deobfuscators/Agile_NET/vm/v2/MethodSigInfoCreator.cs
+++ /dev/null
@@ -1,737 +0,0 @@
-/*
- Copyright (C) 2011-2013 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 .
-*/
-
-using System;
-using System.Collections.Generic;
-using System.IO;
-using System.Security.Cryptography;
-using dnlib.DotNet;
-using dnlib.DotNet.Emit;
-using dnlib.DotNet.MD;
-using de4dot.blocks;
-
-namespace de4dot.code.deobfuscators.Agile_NET.vm.v2 {
- class MethodSigInfo {
- readonly List blockInfos;
-
- public List BlockInfos {
- get { return blockInfos; }
- }
-
- public MethodSigInfo() {
- this.blockInfos = new List();
- }
-
- public MethodSigInfo(IEnumerable blockInfos) {
- this.blockInfos = new List(blockInfos);
- }
- }
-
- class BlockInfo : IEquatable {
- readonly List targets;
-
- public byte[] Hash { get; set; }
- public List Targets {
- get { return targets; }
- }
-
- public BlockInfo() {
- this.targets = new List();
- }
-
- public BlockInfo(byte[] hash, IEnumerable targets) {
- this.Hash = hash;
- this.targets = new List(targets);
- }
-
- public override string ToString() {
- if (Hash == null)
- return "";
- return BitConverter.ToString(Hash).Replace("-", string.Empty);
- }
-
- public bool Equals(BlockInfo other) {
- return Equals(Hash, other.Hash) &&
- Targets.Count == other.Targets.Count;
- }
-
- bool Equals(byte[] a, byte[] b) {
- if (a == b)
- return true;
- if (a == null || b == null)
- return false;
- if (a.Length != b.Length)
- return false;
- for (int i = 0; i < a.Length; i++) {
- if (a[i] != b[i])
- return false;
- }
- return true;
- }
- }
-
- class MethodSigInfoCreator {
- MethodSigInfo methodSigInfo;
- Blocks blocks;
- IList allBlocks;
- Dictionary blockToInfo;
- Dictionary