From 98d85c646bbf97e35020dbd2d6fe029f61c2cba5 Mon Sep 17 00:00:00 2001 From: Adam Date: Fri, 19 Jun 2015 23:30:03 -0400 Subject: [PATCH] illegal state exception deob, ff doesnt fully like it yet though --- src/main/java/info/sigterm/deob/Method.java | 6 ++ .../deob/attributes/code/Instructions.java | 11 ++- .../attributes/code/instructions/Goto.java | 7 ++ .../deob/attributes/code/instructions/If.java | 5 ++ .../attributes/code/instructions/If0.java | 5 ++ .../attributes/code/instructions/New.java | 5 ++ .../deobfuscators/IllegalStateExceptions.java | 78 +++++++++++++++++++ 7 files changed, 114 insertions(+), 3 deletions(-) create mode 100644 src/main/java/info/sigterm/deob/deobfuscators/IllegalStateExceptions.java diff --git a/src/main/java/info/sigterm/deob/Method.java b/src/main/java/info/sigterm/deob/Method.java index 1b8f54194b..ea48656a03 100644 --- a/src/main/java/info/sigterm/deob/Method.java +++ b/src/main/java/info/sigterm/deob/Method.java @@ -230,6 +230,12 @@ public class Method code.buildCallGraph(); } + public void clearCallGraph() + { + callsTo.clear(); + callsFrom.clear(); + } + public boolean isUsed() { if (!callsFrom.isEmpty()) diff --git a/src/main/java/info/sigterm/deob/attributes/code/Instructions.java b/src/main/java/info/sigterm/deob/attributes/code/Instructions.java index 524b6bef12..ddfe5836c5 100644 --- a/src/main/java/info/sigterm/deob/attributes/code/Instructions.java +++ b/src/main/java/info/sigterm/deob/attributes/code/Instructions.java @@ -98,9 +98,7 @@ public class Instructions public void buildBlocks() { - for (Instruction i : instructions) - i.block = null; - blocks.clear(); + clearBlockGraph(); Block current = null; for (Instruction i : instructions) @@ -122,6 +120,13 @@ public class Instructions } } + public void clearBlockGraph() + { + for (Instruction i : instructions) + i.block = null; + blocks.clear(); + } + public void write(DataOutputStream out) throws IOException { // generate pool indexes diff --git a/src/main/java/info/sigterm/deob/attributes/code/instructions/Goto.java b/src/main/java/info/sigterm/deob/attributes/code/instructions/Goto.java index 969b083793..dd26304999 100644 --- a/src/main/java/info/sigterm/deob/attributes/code/instructions/Goto.java +++ b/src/main/java/info/sigterm/deob/attributes/code/instructions/Goto.java @@ -24,6 +24,13 @@ public class Goto extends Instruction implements JumpingInstruction length += 2; } + public Goto(Instructions instructions, Instruction to) + { + super(instructions, InstructionType.GOTO, 0); + this.to = to; + length += 2; + } + @Override public void resolve() { diff --git a/src/main/java/info/sigterm/deob/attributes/code/instructions/If.java b/src/main/java/info/sigterm/deob/attributes/code/instructions/If.java index 3258c1fcf3..3fbc8e645b 100644 --- a/src/main/java/info/sigterm/deob/attributes/code/instructions/If.java +++ b/src/main/java/info/sigterm/deob/attributes/code/instructions/If.java @@ -67,4 +67,9 @@ public class If extends Instruction implements JumpingInstruction if (to == oldi) to = newi; } + + public Instruction getTo() + { + return to; + } } diff --git a/src/main/java/info/sigterm/deob/attributes/code/instructions/If0.java b/src/main/java/info/sigterm/deob/attributes/code/instructions/If0.java index c397144d57..e4ae2add3e 100644 --- a/src/main/java/info/sigterm/deob/attributes/code/instructions/If0.java +++ b/src/main/java/info/sigterm/deob/attributes/code/instructions/If0.java @@ -68,4 +68,9 @@ public class If0 extends Instruction implements JumpingInstruction if (to == oldi) to = newi; } + + public Instruction getTo() + { + return to; + } } diff --git a/src/main/java/info/sigterm/deob/attributes/code/instructions/New.java b/src/main/java/info/sigterm/deob/attributes/code/instructions/New.java index dcd50aa928..e315f0bae6 100644 --- a/src/main/java/info/sigterm/deob/attributes/code/instructions/New.java +++ b/src/main/java/info/sigterm/deob/attributes/code/instructions/New.java @@ -45,4 +45,9 @@ public class New extends Instruction frame.addInstructionContext(ins); } + + public Class getNewClass() + { + return clazz; + } } diff --git a/src/main/java/info/sigterm/deob/deobfuscators/IllegalStateExceptions.java b/src/main/java/info/sigterm/deob/deobfuscators/IllegalStateExceptions.java new file mode 100644 index 0000000000..a0ed64f88c --- /dev/null +++ b/src/main/java/info/sigterm/deob/deobfuscators/IllegalStateExceptions.java @@ -0,0 +1,78 @@ +package info.sigterm.deob.deobfuscators; + +import info.sigterm.deob.ClassFile; +import info.sigterm.deob.ClassGroup; +import info.sigterm.deob.Method; +import info.sigterm.deob.attributes.Code; +import info.sigterm.deob.attributes.code.Instruction; +import info.sigterm.deob.attributes.code.Instructions; +import info.sigterm.deob.attributes.code.instructions.AThrow; +import info.sigterm.deob.attributes.code.instructions.Goto; +import info.sigterm.deob.attributes.code.instructions.If; +import info.sigterm.deob.attributes.code.instructions.If0; +import info.sigterm.deob.attributes.code.instructions.New; + +import java.util.ArrayList; +import java.util.List; + +public class IllegalStateExceptions +{ + /* find if, new, ..., athrow, replace with goto */ + public void run(ClassGroup group) + { + int count = 0; + for (ClassFile cf : group.getClasses()) + { + for (Method m : new ArrayList<>(cf.getMethods().getMethods())) + { + Code c = m.getCode(); + if (c == null) + continue; + + Instructions instructions = c.getInstructions(); + instructions.clearBlockGraph(); + + List ilist = instructions.getInstructions(); + for (int i = 0; i < ilist.size(); ++i) + { + Instruction ins = ilist.get(i); + + if (!(ins instanceof If) && !(ins instanceof If0)) + continue; + + Instruction ins2 = ilist.get(i + 1); + if (!(ins2 instanceof New)) + continue; + + New new2 = (New) ins2; + info.sigterm.deob.pool.Class clazz = new2.getNewClass(); + if (!clazz.getName().equals("java/lang/IllegalStateException")) + continue; + + Instruction to = null; + if (ins instanceof If) + to = ((If) ins).getTo(); + else if (ins instanceof If0) + to = ((If0) ins).getTo(); + + // remove up to athrow + do + { + instructions.remove(ins); + ins = ilist.get(i); // don't need to ++i because + } + while (!(ins instanceof AThrow)); + + // remove athrow + instructions.remove(ins); + + // insert goto + ilist.add(i, new Goto(instructions, to)); + + ++count; + } + } + } + System.out.println("Removed " + count + " illegal state exceptions"); + } +}