this inf loops and keeps changing the same last few fields back and forth etc.?

This commit is contained in:
Adam
2015-09-13 19:41:10 -04:00
parent 95b87c005c
commit 200a82bc83

View File

@@ -37,6 +37,7 @@ public class ModArith implements Deobfuscator
private MultiValueMap<Field, Integer> constantGetters = new MultiValueMap<>(), private MultiValueMap<Field, Integer> constantGetters = new MultiValueMap<>(),
constantSetters = new MultiValueMap<>(); constantSetters = new MultiValueMap<>();
private List<Pair> pairs = new ArrayList<>(); private List<Pair> pairs = new ArrayList<>();
private Set<Field> deobfuscatedFields = new HashSet<>();
private List<Integer> findAssocConstants(Field field, InstructionContext ctx) throws OtherFieldException private List<Integer> findAssocConstants(Field field, InstructionContext ctx) throws OtherFieldException
{ {
@@ -55,7 +56,8 @@ public class ModArith implements Deobfuscator
{ {
FieldInstruction fi = (FieldInstruction) ctx.getInstruction(); FieldInstruction fi = (FieldInstruction) ctx.getInstruction();
if (fi.getMyField() != field) // if the field is already deobbed, constants here don't include it
if (fi.getMyField() != field && !deobfuscatedFields.contains(fi.getMyField()))
throw new OtherFieldException(); throw new OtherFieldException();
} }
@@ -214,30 +216,58 @@ public class ModArith implements Deobfuscator
return p; return p;
} }
private Pair guess(Collection<Integer> getters) private Pair guess(Field field, Collection<Integer> values, boolean getter)
{ {
Map<Integer, Integer> map = CollectionUtils.getCardinalityMap(getters); Map<Integer, Integer> map = CollectionUtils.getCardinalityMap(values); // value -> how many times it occurs
int max = Collections.max(map.values()); int max = Collections.max(map.values()); // largest occurance #
int size = getters.size(); int size = values.size();
if (size < 50) // if (max == size)
return null; // {
// // all getters are the same value
// int constant = getters.iterator().next();
// Pair pair = new Pair();
// pair.getter = constant;
// System.out.println("Guessing " + field.getName() + " getter " + constant + " setter ");
// pair.setter = DMath.modInverse(constant);
// return pair;
// }
//
// if (size < 50)
// return null;
if (((float) max / (float) size) < 0.9) // if (((float) max / (float) size) < 0.9)
return null; // return null;
for (final Map.Entry<Integer, Integer> entry : map.entrySet()) { for (final Map.Entry<Integer, Integer> entry : map.entrySet()) {
if (max == entry.getValue()) { if (max == entry.getValue()) {
int constant = entry.getKey(); int constant = entry.getKey();
int inverse;
try
{
inverse = DMath.modInverse(constant);
}
catch (ArithmeticException ex)
{
break;
}
Pair pair = new Pair(); Pair pair = new Pair();
pair.getter = constant; if (getter)
pair.setter = DMath.modInverse(constant); {
pair.getter = constant;
pair.setter = inverse;
}
else
{
pair.getter = inverse;
pair.setter = constant;
}
return pair; return pair;
} }
} }
assert false;
return null; return null;
} }
@@ -249,16 +279,24 @@ public class ModArith implements Deobfuscator
Collection<Integer> getters = constantGetters.getCollection(f), Collection<Integer> getters = constantGetters.getCollection(f),
setters = constantSetters.getCollection(f); setters = constantSetters.getCollection(f);
if (f.getName().equals("field542"))
{
int i =5;
}
if (getters == null || setters == null) if (getters == null || setters == null)
continue; continue;
Pair answer = reduce(getters, setters); Pair answer = reduce(getters, setters);
if (answer == null) if (answer == null)
{ answer = guess(f, getters, true);
answer = guess(getters);
if (answer == null) if (answer == null)
continue; answer = guess(f, setters, false);
}
if (answer == null)
continue;
answer.field = f; answer.field = f;
pairs.add(answer); pairs.add(answer);
@@ -269,7 +307,13 @@ public class ModArith implements Deobfuscator
public void run(ClassGroup group) public void run(ClassGroup group)
{ {
this.group = group; this.group = group;
while (runOnce() > 0); int passes = 0, total = 0, i;
while ((i = runOnce()) > 0)
{
++passes;
total += i;
}
System.out.println("Finished arith deob on " + total + " fields in " + passes + " passes");
} }
private int runOnce() private int runOnce()
@@ -288,16 +332,13 @@ public class ModArith implements Deobfuscator
reduce(); reduce();
int i = 0; int i = 0;
int start = 0, end = pairs.size(); for (Pair pair : pairs)
for (int j = start; j < end; ++j)
//for (Pair pair : pairs)
{ {
Pair pair = pairs.get(j);
Field field = pair.field; Field field = pair.field;
if (!field.getName().equals("field1980") && !field.getName().equals("field1961")) if (!field.getName().equals("field933") && !field.getName().equals("field743"))
{ {
// continue; // continue;
} }
System.out.println("Processing " + field.getName() + " getter " + pair.getter + " setter " + pair.setter); System.out.println("Processing " + field.getName() + " getter " + pair.getter + " setter " + pair.setter);
@@ -311,7 +352,10 @@ public class ModArith implements Deobfuscator
execution.run(); execution.run();
encr.doChange(); encr.doChange();
System.out.println("Changed " + ++i); System.out.println("Changed " + ++i);
//assert !deobfuscatedFields.contains(field);
deobfuscatedFields.add(field);
} }
Encryption encr = new Encryption(); Encryption encr = new Encryption();