diff options
author | Ying Wang <wangying@google.com> | 2012-02-27 18:34:24 -0800 |
---|---|---|
committer | Ying Wang <wangying@google.com> | 2012-02-27 18:34:24 -0800 |
commit | 9f606f95f03a75961498803e24bee6799a7c0885 (patch) | |
tree | a45f4d74feda9b76277a0c9ced55ad15d82248a1 /src/proguard/optimize/info/SideEffectInstructionChecker.java | |
parent | cfead78069f3dc32998dc118ee08cab3867acea2 (diff) | |
download | android_external_proguard-9f606f95f03a75961498803e24bee6799a7c0885.tar.gz android_external_proguard-9f606f95f03a75961498803e24bee6799a7c0885.tar.bz2 android_external_proguard-9f606f95f03a75961498803e24bee6799a7c0885.zip |
Revert "Upgrade from Progaurd 4.4 to 4.7."cm-10.1.3-RC2cm-10.1.3-RC1cm-10.1.3cm-10.1.2cm-10.1.1cm-10.1.0-RC5cm-10.1.0-RC4cm-10.1.0-RC3cm-10.1.0-RC2cm-10.1.0-RC1cm-10.1.0cm-10.1-M3cm-10.1-M2cm-10.1-M1mr1.1-stagingjellybean-stablejellybeancm-10.1
This reverts commit cfead78069f3dc32998dc118ee08cab3867acea2.
Bug: 6079915
Diffstat (limited to 'src/proguard/optimize/info/SideEffectInstructionChecker.java')
-rw-r--r-- | src/proguard/optimize/info/SideEffectInstructionChecker.java | 109 |
1 files changed, 44 insertions, 65 deletions
diff --git a/src/proguard/optimize/info/SideEffectInstructionChecker.java b/src/proguard/optimize/info/SideEffectInstructionChecker.java index 1444e5a..8be9dc1 100644 --- a/src/proguard/optimize/info/SideEffectInstructionChecker.java +++ b/src/proguard/optimize/info/SideEffectInstructionChecker.java @@ -2,7 +2,7 @@ * ProGuard -- shrinking, optimization, obfuscation, and preverification * of Java bytecode. * - * Copyright (c) 2002-2011 Eric Lafortune (eric@graphics.cornell.edu) + * Copyright (c) 2002-2009 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 @@ -29,14 +29,11 @@ import proguard.classfile.instruction.visitor.InstructionVisitor; import proguard.classfile.util.SimplifiedVisitor; import proguard.classfile.visitor.*; -import java.util.*; - /** * This class can tell whether an instruction has any side effects. Return * instructions can be included or not. * * @see ReadWriteFieldMarker - * @see StaticInitializerContainingClassMarker * @see NoSideEffectMethodMarker * @see SideEffectMethodMarker * @author Eric Lafortune @@ -50,7 +47,6 @@ implements InstructionVisitor, private final boolean includeReturnInstructions; // A return value for the visitor methods. - private Clazz referencingClass; private boolean hasSideEffects; @@ -64,7 +60,7 @@ implements InstructionVisitor, { hasSideEffects = false; - instruction.accept(clazz, method, codeAttribute, offset, this); + instruction.accept(clazz, method, codeAttribute, offset, this); return hasSideEffects; } @@ -122,16 +118,14 @@ implements InstructionVisitor, public void visitConstantInstruction(Clazz clazz, Method method, CodeAttribute codeAttribute, int offset, ConstantInstruction constantInstruction) { byte opcode = constantInstruction.opcode; + // Check for instructions that might cause side effects. - if (opcode == InstructionConstants.OP_GETSTATIC || - opcode == InstructionConstants.OP_PUTSTATIC || - opcode == InstructionConstants.OP_GETFIELD || - opcode == InstructionConstants.OP_PUTFIELD || - opcode == InstructionConstants.OP_INVOKEVIRTUAL || - opcode == InstructionConstants.OP_INVOKESPECIAL || - opcode == InstructionConstants.OP_INVOKESTATIC || - opcode == InstructionConstants.OP_INVOKEINTERFACE || - opcode == InstructionConstants.OP_INVOKEDYNAMIC) + if (opcode == InstructionConstants.OP_PUTSTATIC || + opcode == InstructionConstants.OP_PUTFIELD || + opcode == InstructionConstants.OP_INVOKEVIRTUAL || + opcode == InstructionConstants.OP_INVOKESPECIAL || + opcode == InstructionConstants.OP_INVOKESTATIC || + opcode == InstructionConstants.OP_INVOKEINTERFACE) { // Check if the field is write-only or volatile, or if the invoked // method is causing any side effects. @@ -156,36 +150,48 @@ implements InstructionVisitor, // Implementations for ConstantVisitor. - public void visitInvokeDynamicConstant(Clazz clazz, InvokeDynamicConstant invokeDynamicConstant) - { - // We'll have to assume invoking an unknown method has side effects. - hasSideEffects = true; - } - - public void visitFieldrefConstant(Clazz clazz, FieldrefConstant fieldrefConstant) { - // Pass the referencing class. - referencingClass = clazz; - // We'll have to assume accessing an unknown field has side effects. hasSideEffects = true; - // Check the referenced field, if known. + // Check the referenced field. fieldrefConstant.referencedMemberAccept(this); } public void visitAnyMethodrefConstant(Clazz clazz, RefConstant refConstant) { - // Pass the referencing class. - referencingClass = clazz; + Member referencedMember = refConstant.referencedMember; - // We'll have to assume invoking an unknown method has side effects. - hasSideEffects = true; - - // Check the referenced method, if known. - refConstant.referencedMemberAccept(this); + // Do we have a reference to the method? + if (referencedMember == null) + { + // We'll have to assume invoking the unknown method has side effects. + hasSideEffects = true; + } + else + { + // First check the referenced method itself. + refConstant.referencedMemberAccept(this); + + // If the result isn't conclusive, check down the hierarchy. + if (!hasSideEffects) + { + Clazz referencedClass = refConstant.referencedClass; + Method referencedMethod = (Method)referencedMember; + + // Check all other implementations of the method down the class + // hierarchy. + if ((referencedMethod.getAccessFlags() & ClassConstants.INTERNAL_ACC_PRIVATE) == 0) + { + clazz.hierarchyAccept(false, false, false, true, + new NamedMethodVisitor(referencedMethod.getName(referencedClass), + referencedMethod.getDescriptor(referencedClass), + this)); + } + } + } } @@ -193,24 +199,14 @@ implements InstructionVisitor, public void visitProgramField(ProgramClass programClass, ProgramField programField) { - hasSideEffects = - (ReadWriteFieldMarker.isRead(programField) && - ReadWriteFieldMarker.isWritten(programField)) || - ((programField.getAccessFlags() & ClassConstants.INTERNAL_ACC_VOLATILE) != 0) || - (!programClass.equals(referencingClass) && - !initializedSuperClasses(referencingClass).containsAll(initializedSuperClasses(programClass))); + hasSideEffects = ReadWriteFieldMarker.isRead(programField); } public void visitProgramMethod(ProgramClass programClass, ProgramMethod programMethod) { - // Note that side effects already include synchronization of some - // implementation of the method. - hasSideEffects = - !NoSideEffectMethodMarker.hasNoSideEffects(programMethod) && - (SideEffectMethodMarker.hasSideEffects(programMethod) || - (!programClass.equals(referencingClass) && - !initializedSuperClasses(referencingClass).containsAll(initializedSuperClasses(programClass)))); + hasSideEffects = hasSideEffects || + SideEffectMethodMarker.hasSideEffects(programMethod); } @@ -222,24 +218,7 @@ implements InstructionVisitor, public void visitLibraryMethod(LibraryClass libraryClass, LibraryMethod libraryMethod) { - hasSideEffects = - !NoSideEffectMethodMarker.hasNoSideEffects(libraryMethod); - } - - - /** - * Returns the set of superclasses and interfaces that are initialized. - */ - private Set initializedSuperClasses(Clazz clazz) - { - Set set = new HashSet(); - - // Visit all superclasses and interfaces, collecting the ones that have - // static initializers. - clazz.hierarchyAccept(true, true, true, false, - new StaticInitializerContainingClassFilter( - new ClassCollector(set))); - - return set; + hasSideEffects = hasSideEffects || + !NoSideEffectMethodMarker.hasNoSideEffects(libraryMethod); } } |