diff options
Diffstat (limited to 'src/proguard/obfuscate/Obfuscator.java')
-rw-r--r-- | src/proguard/obfuscate/Obfuscator.java | 105 |
1 files changed, 71 insertions, 34 deletions
diff --git a/src/proguard/obfuscate/Obfuscator.java b/src/proguard/obfuscate/Obfuscator.java index dce563a..cc79b0d 100644 --- a/src/proguard/obfuscate/Obfuscator.java +++ b/src/proguard/obfuscate/Obfuscator.java @@ -2,7 +2,7 @@ * ProGuard -- shrinking, optimization, obfuscation, and preverification * of Java bytecode. * - * Copyright (c) 2002-2009 Eric Lafortune (eric@graphics.cornell.edu) + * Copyright (c) 2002-2013 Eric Lafortune (eric@graphics.cornell.edu) * * This program 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 @@ -99,19 +99,30 @@ public class Obfuscator libraryClassPool.classesAccept(new AllMemberVisitor(nameMarker)); // Mark attributes that have to be kept. - AttributeUsageMarker requiredAttributeUsageMarker = - new AttributeUsageMarker(); + AttributeVisitor attributeUsageMarker = + new NonEmptyAttributeFilter( + new AttributeUsageMarker()); AttributeVisitor optionalAttributeUsageMarker = configuration.keepAttributes == null ? null : new AttributeNameFilter(new ListParser(new NameParser()).parse(configuration.keepAttributes), - requiredAttributeUsageMarker); + attributeUsageMarker); programClassPool.classesAccept( new AllAttributeVisitor(true, - new RequiredAttributeFilter(requiredAttributeUsageMarker, + new RequiredAttributeFilter(attributeUsageMarker, optionalAttributeUsageMarker))); + // Keep parameter names and types if specified. + if (configuration.keepParameterNames) + { + programClassPool.classesAccept( + new AllMethodVisitor( + new MemberNameFilter( + new AllAttributeVisitor(true, + new ParameterNameMarker(attributeUsageMarker))))); + } + // Remove the attributes that can be discarded. Note that the attributes // may only be discarded after the seeds have been marked, since the // configuration may rely on annotations. @@ -135,17 +146,23 @@ public class Obfuscator reader.pump(keeper); // Print out a summary of the warnings if necessary. - int mappingWarningCount = warningPrinter.getWarningCount(); - if (mappingWarningCount > 0) + int warningCount = warningPrinter.getWarningCount(); + if (warningCount > 0) { - System.err.println("Warning: there were " + mappingWarningCount + - " kept classes and class members that were remapped anyway."); + System.err.println("Warning: there were " + warningCount + + " kept classes and class members that were remapped anyway."); System.err.println(" You should adapt your configuration or edit the mapping file."); if (!configuration.ignoreWarnings) { - System.err.println(" If you are sure this remapping won't hurt,"); - System.err.println(" you could try your luck using the '-ignorewarnings' option."); + System.err.println(" If you are sure this remapping won't hurt, you could try your luck"); + System.err.println(" using the '-ignorewarnings' option."); + } + + System.err.println(" (http://proguard.sourceforge.net/manual/troubleshooting.html#mappingconflict1)"); + + if (!configuration.ignoreWarnings) + { throw new IOException("Please correct the above warnings first."); } } @@ -248,6 +265,19 @@ public class Obfuscator new MemberNameCollector(configuration.overloadAggressively, descriptorMap)))), + // Collect all member names from interfaces of abstract + // classes down the hierarchy. + // Due to an error in the JLS/JVMS, virtual invocations + // may end up at a private method otherwise (Sun/Oracle + // bugs #6691741 and #6684387, ProGuard bug #3471941, + // and ProGuard test #1180). + new ClassHierarchyTraveler(false, false, false, true, + new ClassAccessFilter(ClassConstants.INTERNAL_ACC_ABSTRACT, 0, + new ClassHierarchyTraveler(false, false, true, false, + new AllMemberVisitor( + new MemberNameCollector(configuration.overloadAggressively, + descriptorMap))))), + // Assign new names to all private members in this class. new AllMemberVisitor( new MemberAccessFilter(ClassConstants.INTERNAL_ACC_PRIVATE, 0, @@ -361,6 +391,12 @@ public class Obfuscator { System.err.println(" If you are sure the conflicts are harmless,"); System.err.println(" you could try your luck using the '-ignorewarnings' option."); + } + + System.err.println(" (http://proguard.sourceforge.net/manual/troubleshooting.html#mappingconflict2)"); + + if (!configuration.ignoreWarnings) + { throw new IOException("Please correct the above warnings first."); } } @@ -368,14 +404,20 @@ public class Obfuscator // Print out the mapping, if requested. if (configuration.printMapping != null) { - PrintStream ps = isFile(configuration.printMapping) ? - new PrintStream(new BufferedOutputStream(new FileOutputStream(configuration.printMapping))) : - System.out; + PrintStream ps = + configuration.printMapping == Configuration.STD_OUT ? System.out : + new PrintStream( + new BufferedOutputStream( + new FileOutputStream(configuration.printMapping))); // Print out items that will be removed. programClassPool.classesAcceptAlphabetically(new MappingPrinter(ps)); - if (ps != System.out) + if (ps == System.out) + { + ps.flush(); + } + else { ps.close(); } @@ -398,32 +440,27 @@ public class Obfuscator programClassPool.classesAccept( new AllConstantVisitor( new AccessFixer())); + + // Fix the access flags of the inner classes information. + programClassPool.classesAccept( + new AllAttributeVisitor( + new AllInnerClassesInfoVisitor( + new InnerClassesAccessFixer()))); } + // Fix the bridge method flags. + programClassPool.classesAccept( + new AllMethodVisitor( + new BridgeMethodFixer())); + // Rename the source file attributes, if requested. if (configuration.newSourceFileAttribute != null) { programClassPool.classesAccept(new SourceFileRenamer(configuration.newSourceFileAttribute)); } - // Mark NameAndType constant pool entries that have to be kept - // and remove the other ones. - programClassPool.classesAccept(new NameAndTypeUsageMarker()); - programClassPool.classesAccept(new NameAndTypeShrinker()); - - // Mark Utf8 constant pool entries that have to be kept - // and remove the other ones. - programClassPool.classesAccept(new Utf8UsageMarker()); - programClassPool.classesAccept(new Utf8Shrinker()); - } - - - /** - * Returns whether the given file is actually a file, or just a placeholder - * for the standard output. - */ - private boolean isFile(File file) - { - return file.getPath().length() > 0; + // Remove unused constants. + programClassPool.classesAccept( + new ConstantPoolShrinker()); } } |