summaryrefslogtreecommitdiff
path: root/src/cuchaz/enigma/analysis/JarIndex.java
diff options
context:
space:
mode:
Diffstat (limited to 'src/cuchaz/enigma/analysis/JarIndex.java')
-rw-r--r--src/cuchaz/enigma/analysis/JarIndex.java65
1 files changed, 21 insertions, 44 deletions
diff --git a/src/cuchaz/enigma/analysis/JarIndex.java b/src/cuchaz/enigma/analysis/JarIndex.java
index 4b03a33..c96d3bc 100644
--- a/src/cuchaz/enigma/analysis/JarIndex.java
+++ b/src/cuchaz/enigma/analysis/JarIndex.java
@@ -114,8 +114,8 @@ public class JarIndex {
114 // step 3: index extends, implements, fields, and methods 114 // step 3: index extends, implements, fields, and methods
115 for (CtClass c : JarClassIterator.classes(jar)) { 115 for (CtClass c : JarClassIterator.classes(jar)) {
116 ClassRenamer.moveAllClassesOutOfDefaultPackage(c, Constants.NonePackage); 116 ClassRenamer.moveAllClassesOutOfDefaultPackage(c, Constants.NonePackage);
117 m_translationIndex.indexClass(c);
117 String className = Descriptor.toJvmName(c.getName()); 118 String className = Descriptor.toJvmName(c.getName());
118 m_translationIndex.addSuperclass(className, Descriptor.toJvmName(c.getClassFile().getSuperclass()));
119 for (String interfaceName : c.getClassFile().getInterfaces()) { 119 for (String interfaceName : c.getClassFile().getInterfaces()) {
120 className = Descriptor.toJvmName(className); 120 className = Descriptor.toJvmName(className);
121 interfaceName = Descriptor.toJvmName(interfaceName); 121 interfaceName = Descriptor.toJvmName(interfaceName);
@@ -191,8 +191,6 @@ public class JarIndex {
191 String className = Descriptor.toJvmName(field.getDeclaringClass().getName()); 191 String className = Descriptor.toJvmName(field.getDeclaringClass().getName());
192 FieldEntry fieldEntry = new FieldEntry(new ClassEntry(className), field.getName()); 192 FieldEntry fieldEntry = new FieldEntry(new ClassEntry(className), field.getName());
193 193
194 m_translationIndex.addField(className, field.getName());
195
196 // is the field a class type? 194 // is the field a class type?
197 if (field.getSignature().startsWith("L")) { 195 if (field.getSignature().startsWith("L")) {
198 ClassEntry fieldTypeEntry = new ClassEntry(field.getSignature().substring(1, field.getSignature().length() - 1)); 196 ClassEntry fieldTypeEntry = new ClassEntry(field.getSignature().substring(1, field.getSignature().length() - 1));
@@ -230,13 +228,12 @@ public class JarIndex {
230 behavior.instrument(new ExprEditor() { 228 behavior.instrument(new ExprEditor() {
231 @Override 229 @Override
232 public void edit(MethodCall call) { 230 public void edit(MethodCall call) {
233 String className = Descriptor.toJvmName(call.getClassName());
234 MethodEntry calledMethodEntry = new MethodEntry( 231 MethodEntry calledMethodEntry = new MethodEntry(
235 new ClassEntry(className), 232 new ClassEntry(Descriptor.toJvmName(call.getClassName())),
236 call.getMethodName(), 233 call.getMethodName(),
237 call.getSignature() 234 call.getSignature()
238 ); 235 );
239 ClassEntry resolvedClassEntry = resolveEntryClass(calledMethodEntry); 236 ClassEntry resolvedClassEntry = m_translationIndex.resolveEntryClass(calledMethodEntry);
240 if (resolvedClassEntry != null && !resolvedClassEntry.equals(calledMethodEntry.getClassEntry())) { 237 if (resolvedClassEntry != null && !resolvedClassEntry.equals(calledMethodEntry.getClassEntry())) {
241 calledMethodEntry = new MethodEntry( 238 calledMethodEntry = new MethodEntry(
242 resolvedClassEntry, 239 resolvedClassEntry,
@@ -254,12 +251,11 @@ public class JarIndex {
254 251
255 @Override 252 @Override
256 public void edit(FieldAccess call) { 253 public void edit(FieldAccess call) {
257 String className = Descriptor.toJvmName(call.getClassName());
258 FieldEntry calledFieldEntry = new FieldEntry( 254 FieldEntry calledFieldEntry = new FieldEntry(
259 new ClassEntry(className), 255 new ClassEntry(Descriptor.toJvmName(call.getClassName())),
260 call.getFieldName() 256 call.getFieldName()
261 ); 257 );
262 ClassEntry resolvedClassEntry = resolveEntryClass(calledFieldEntry); 258 ClassEntry resolvedClassEntry = m_translationIndex.resolveEntryClass(calledFieldEntry);
263 if (resolvedClassEntry != null && !resolvedClassEntry.equals(calledFieldEntry.getClassEntry())) { 259 if (resolvedClassEntry != null && !resolvedClassEntry.equals(calledFieldEntry.getClassEntry())) {
264 calledFieldEntry = new FieldEntry(resolvedClassEntry, call.getFieldName()); 260 calledFieldEntry = new FieldEntry(resolvedClassEntry, call.getFieldName());
265 } 261 }
@@ -273,9 +269,8 @@ public class JarIndex {
273 269
274 @Override 270 @Override
275 public void edit(ConstructorCall call) { 271 public void edit(ConstructorCall call) {
276 String className = Descriptor.toJvmName(call.getClassName());
277 ConstructorEntry calledConstructorEntry = new ConstructorEntry( 272 ConstructorEntry calledConstructorEntry = new ConstructorEntry(
278 new ClassEntry(className), 273 new ClassEntry(Descriptor.toJvmName(call.getClassName())),
279 call.getSignature() 274 call.getSignature()
280 ); 275 );
281 EntryReference<BehaviorEntry,BehaviorEntry> reference = new EntryReference<BehaviorEntry,BehaviorEntry>( 276 EntryReference<BehaviorEntry,BehaviorEntry> reference = new EntryReference<BehaviorEntry,BehaviorEntry>(
@@ -288,9 +283,8 @@ public class JarIndex {
288 283
289 @Override 284 @Override
290 public void edit(NewExpr call) { 285 public void edit(NewExpr call) {
291 String className = Descriptor.toJvmName(call.getClassName());
292 ConstructorEntry calledConstructorEntry = new ConstructorEntry( 286 ConstructorEntry calledConstructorEntry = new ConstructorEntry(
293 new ClassEntry(className), 287 new ClassEntry(Descriptor.toJvmName(call.getClassName())),
294 call.getSignature() 288 call.getSignature()
295 ); 289 );
296 EntryReference<BehaviorEntry,BehaviorEntry> reference = new EntryReference<BehaviorEntry,BehaviorEntry>( 290 EntryReference<BehaviorEntry,BehaviorEntry> reference = new EntryReference<BehaviorEntry,BehaviorEntry>(
@@ -306,25 +300,6 @@ public class JarIndex {
306 } 300 }
307 } 301 }
308 302
309 public ClassEntry resolveEntryClass(Entry obfEntry) {
310
311 // this entry could refer to a method on a class where the method is not actually implemented
312 // travel up the inheritance tree to find the closest implementation
313 while (!containsObfEntry(obfEntry)) {
314 // is there a parent class?
315 String superclassName = m_translationIndex.getSuperclassName(obfEntry.getClassName());
316 if (superclassName == null) {
317 // this is probably a method from a class in a library
318 // we can't trace the implementation up any higher unless we index the library
319 return null;
320 }
321
322 // move up to the parent class
323 obfEntry = obfEntry.cloneToNewClass(new ClassEntry(superclassName));
324 }
325 return obfEntry.getClassEntry();
326 }
327
328 private CtMethod getBridgedMethod(CtMethod method) { 303 private CtMethod getBridgedMethod(CtMethod method) {
329 304
330 // bridge methods just call another method, cast it to the return type, and return the result 305 // bridge methods just call another method, cast it to the return type, and return the result
@@ -402,9 +377,9 @@ public class JarIndex {
402 if (reference.entry instanceof ConstructorEntry && reference.context instanceof ConstructorEntry) { 377 if (reference.entry instanceof ConstructorEntry && reference.context instanceof ConstructorEntry) {
403 378
404 // is the entry a superclass of the context? 379 // is the entry a superclass of the context?
405 String calledClassName = reference.entry.getClassName(); 380 ClassEntry calledClassEntry = reference.entry.getClassEntry();
406 String callerSuperclassName = m_translationIndex.getSuperclassName(reference.context.getClassName()); 381 ClassEntry superclassEntry = m_translationIndex.getSuperclass(reference.context.getClassEntry());
407 if (callerSuperclassName != null && callerSuperclassName.equals(calledClassName)) { 382 if (superclassEntry != null && superclassEntry.equals(calledClassEntry)) {
408 // it's a super call, skip 383 // it's a super call, skip
409 continue; 384 continue;
410 } 385 }
@@ -599,7 +574,9 @@ public class JarIndex {
599 // get the root node 574 // get the root node
600 List<String> ancestry = Lists.newArrayList(); 575 List<String> ancestry = Lists.newArrayList();
601 ancestry.add(obfClassEntry.getName()); 576 ancestry.add(obfClassEntry.getName());
602 ancestry.addAll(m_translationIndex.getAncestry(obfClassEntry.getName())); 577 for (ClassEntry classEntry : m_translationIndex.getAncestry(obfClassEntry)) {
578 ancestry.add(classEntry.getName());
579 }
603 ClassInheritanceTreeNode rootNode = new ClassInheritanceTreeNode( 580 ClassInheritanceTreeNode rootNode = new ClassInheritanceTreeNode(
604 deobfuscatingTranslator, 581 deobfuscatingTranslator,
605 ancestry.get(ancestry.size() - 1) 582 ancestry.get(ancestry.size() - 1)
@@ -625,21 +602,21 @@ public class JarIndex {
625 public MethodInheritanceTreeNode getMethodInheritance(Translator deobfuscatingTranslator, MethodEntry obfMethodEntry) { 602 public MethodInheritanceTreeNode getMethodInheritance(Translator deobfuscatingTranslator, MethodEntry obfMethodEntry) {
626 603
627 // travel to the ancestor implementation 604 // travel to the ancestor implementation
628 String baseImplementationClassName = obfMethodEntry.getClassName(); 605 ClassEntry baseImplementationClassEntry = obfMethodEntry.getClassEntry();
629 for (String ancestorClassName : m_translationIndex.getAncestry(obfMethodEntry.getClassName())) { 606 for (ClassEntry ancestorClassEntry : m_translationIndex.getAncestry(obfMethodEntry.getClassEntry())) {
630 MethodEntry ancestorMethodEntry = new MethodEntry( 607 MethodEntry ancestorMethodEntry = new MethodEntry(
631 new ClassEntry(ancestorClassName), 608 new ClassEntry(ancestorClassEntry),
632 obfMethodEntry.getName(), 609 obfMethodEntry.getName(),
633 obfMethodEntry.getSignature() 610 obfMethodEntry.getSignature()
634 ); 611 );
635 if (containsObfBehavior(ancestorMethodEntry)) { 612 if (containsObfBehavior(ancestorMethodEntry)) {
636 baseImplementationClassName = ancestorClassName; 613 baseImplementationClassEntry = ancestorClassEntry;
637 } 614 }
638 } 615 }
639 616
640 // make a root node at the base 617 // make a root node at the base
641 MethodEntry methodEntry = new MethodEntry( 618 MethodEntry methodEntry = new MethodEntry(
642 new ClassEntry(baseImplementationClassName), 619 baseImplementationClassEntry,
643 obfMethodEntry.getName(), 620 obfMethodEntry.getName(),
644 obfMethodEntry.getSignature() 621 obfMethodEntry.getSignature()
645 ); 622 );
@@ -781,8 +758,8 @@ public class JarIndex {
781 public Set<String> getInterfaces(String className) { 758 public Set<String> getInterfaces(String className) {
782 Set<String> interfaceNames = new HashSet<String>(); 759 Set<String> interfaceNames = new HashSet<String>();
783 interfaceNames.addAll(m_interfaces.get(className)); 760 interfaceNames.addAll(m_interfaces.get(className));
784 for (String ancestor : m_translationIndex.getAncestry(className)) { 761 for (ClassEntry ancestor : m_translationIndex.getAncestry(new ClassEntry(className))) {
785 interfaceNames.addAll(m_interfaces.get(ancestor)); 762 interfaceNames.addAll(m_interfaces.get(ancestor.getName()));
786 } 763 }
787 return interfaceNames; 764 return interfaceNames;
788 } 765 }
@@ -795,7 +772,7 @@ public class JarIndex {
795 String interfaceName = entry.getValue(); 772 String interfaceName = entry.getValue();
796 if (interfaceName.equals(targetInterfaceName)) { 773 if (interfaceName.equals(targetInterfaceName)) {
797 classNames.add(className); 774 classNames.add(className);
798 m_translationIndex.getSubclassNamesRecursively(classNames, className); 775 m_translationIndex.getSubclassNamesRecursively(classNames, new ClassEntry(className));
799 } 776 }
800 } 777 }
801 return classNames; 778 return classNames;