diff options
Diffstat (limited to 'src/main/javassist/bytecode/analysis')
8 files changed, 131 insertions, 94 deletions
diff --git a/src/main/javassist/bytecode/analysis/Analyzer.java b/src/main/javassist/bytecode/analysis/Analyzer.java index 656a1741..5d1250dd 100644 --- a/src/main/javassist/bytecode/analysis/Analyzer.java +++ b/src/main/javassist/bytecode/analysis/Analyzer.java @@ -15,8 +15,6 @@ */ package javassist.bytecode.analysis; -import java.util.Iterator; - import javassist.ClassPool; import javassist.CtClass; import javassist.CtMethod; @@ -363,9 +361,7 @@ public class Analyzer implements Opcode { if (subroutine == null) throw new BadBytecode("Ret on no subroutine! [pos = " + pos + "]"); - Iterator callerIter = subroutine.callers().iterator(); - while (callerIter.hasNext()) { - int caller = ((Integer) callerIter.next()).intValue(); + for (int caller:subroutine.callers()) { int returnLoc = getNext(iter, caller, pos); boolean changed = false; @@ -377,8 +373,7 @@ public class Analyzer implements Opcode { changed = old.mergeStack(frame); } - for (Iterator i = subroutine.accessed().iterator(); i.hasNext(); ) { - int index = ((Integer)i.next()).intValue(); + for (int index:subroutine.accessed()) { Type oldType = old.getLocal(index); Type newType = frame.getLocal(index); if (oldType != newType) { diff --git a/src/main/javassist/bytecode/analysis/ControlFlow.java b/src/main/javassist/bytecode/analysis/ControlFlow.java index 0bf76a3d..e47c00d3 100644 --- a/src/main/javassist/bytecode/analysis/ControlFlow.java +++ b/src/main/javassist/bytecode/analysis/ControlFlow.java @@ -17,6 +17,8 @@ package javassist.bytecode.analysis; import java.util.ArrayList; +import java.util.List; + import javassist.CtClass; import javassist.CtMethod; import javassist.bytecode.BadBytecode; @@ -64,9 +66,11 @@ public class ControlFlow { methodInfo = minfo; frames = null; basicBlocks = (Block[])new BasicBlock.Maker() { + @Override protected BasicBlock makeBlock(int pos) { return new Block(pos, methodInfo); } + @Override protected BasicBlock[] makeArray(int size) { return new Block[size]; } @@ -156,7 +160,9 @@ public class ControlFlow { } Access access = new Access(nodes) { + @Override BasicBlock[] exits(Node n) { return n.block.getExit(); } + @Override BasicBlock[] entrances(Node n) { return n.block.entrances; } }; nodes[0].makeDepth1stTree(null, visited, 0, distance, access); @@ -202,7 +208,9 @@ public class ControlFlow { } Access access = new Access(nodes) { + @Override BasicBlock[] exits(Node n) { return n.block.entrances; } + @Override BasicBlock[] entrances(Node n) { return n.block.getExit(); } }; @@ -252,6 +260,7 @@ public class ControlFlow { method = minfo; } + @Override protected void toString2(StringBuffer sbuf) { super.toString2(sbuf); sbuf.append(", incoming{"); @@ -314,14 +323,14 @@ public class ControlFlow { * in this block. */ public Catcher[] catchers() { - ArrayList catchers = new ArrayList(); + List<Catcher> catchers = new ArrayList<Catcher>(); BasicBlock.Catch c = toCatch; while (c != null) { catchers.add(new Catcher(c)); c = c.next; } - return (Catcher[])catchers.toArray(new Catcher[catchers.size()]); + return catchers.toArray(new Catcher[catchers.size()]); } } @@ -349,6 +358,7 @@ public class ControlFlow { /** * Returns a <code>String</code> representation. */ + @Override public String toString() { StringBuffer sbuf = new StringBuffer(); sbuf.append("Node[pos=").append(block().position()); @@ -473,7 +483,7 @@ public class ControlFlow { Node n = all[i]; Node p = n.parent; if (p != null) - p.children[nchildren[p.block.index]++] = n; + p.children[nchildren[p.block.index]++] = n; } } } diff --git a/src/main/javassist/bytecode/analysis/Frame.java b/src/main/javassist/bytecode/analysis/Frame.java index 1a2b46a9..28c62e35 100644 --- a/src/main/javassist/bytecode/analysis/Frame.java +++ b/src/main/javassist/bytecode/analysis/Frame.java @@ -229,6 +229,7 @@ public class Frame { return changed; } + @Override public String toString() { StringBuffer buffer = new StringBuffer(); diff --git a/src/main/javassist/bytecode/analysis/MultiArrayType.java b/src/main/javassist/bytecode/analysis/MultiArrayType.java index 1d1b90b0..e430b850 100644 --- a/src/main/javassist/bytecode/analysis/MultiArrayType.java +++ b/src/main/javassist/bytecode/analysis/MultiArrayType.java @@ -34,6 +34,7 @@ public class MultiArrayType extends Type { this.dims = dims; } + @Override public CtClass getCtClass() { CtClass clazz = component.getCtClass(); if (clazz == null) @@ -52,30 +53,37 @@ public class MultiArrayType extends Type { } } + @Override boolean popChanged() { return component.popChanged(); } + @Override public int getDimensions() { return dims; } + @Override public Type getComponent() { return dims == 1 ? (Type)component : new MultiArrayType(component, dims - 1); } + @Override public int getSize() { return 1; } + @Override public boolean isArray() { return true; } + @Override public boolean isAssignableFrom(Type type) { throw new UnsupportedOperationException("Not implemented"); } + @Override public boolean isReference() { return true; } @@ -115,6 +123,13 @@ public class MultiArrayType extends Type { return component.isAssignableTo(typeRoot); } + + @Override + public int hashCode() { + return component.hashCode() + dims; + } + + @Override public boolean equals(Object o) { if (! (o instanceof MultiArrayType)) return false; @@ -123,6 +138,7 @@ public class MultiArrayType extends Type { return component.equals(multi.component) && dims == multi.dims; } + @Override public String toString() { // follows the same detailed formating scheme as component return arrayName(component.toString(), dims); diff --git a/src/main/javassist/bytecode/analysis/MultiType.java b/src/main/javassist/bytecode/analysis/MultiType.java index 7baa661a..a8f6fc67 100644 --- a/src/main/javassist/bytecode/analysis/MultiType.java +++ b/src/main/javassist/bytecode/analysis/MultiType.java @@ -16,7 +16,6 @@ package javassist.bytecode.analysis; import java.util.HashMap; -import java.util.Iterator; import java.util.Map; import javassist.CtClass; @@ -47,17 +46,17 @@ import javassist.CtClass; * changes, and somehow communicating assignment changes to the Analyzer */ public class MultiType extends Type { - private Map interfaces; + private Map<String,CtClass> interfaces; private Type resolved; private Type potentialClass; private MultiType mergeSource; private boolean changed = false; - public MultiType(Map interfaces) { + public MultiType(Map<String,CtClass> interfaces) { this(interfaces, null); } - public MultiType(Map interfaces, Type potentialClass) { + public MultiType(Map<String,CtClass> interfaces, Type potentialClass) { super(null); this.interfaces = interfaces; this.potentialClass = potentialClass; @@ -67,6 +66,7 @@ public class MultiType extends Type { * Gets the class that corresponds with this type. If this information * is not yet known, java.lang.Object will be returned. */ + @Override public CtClass getCtClass() { if (resolved != null) return resolved.getCtClass(); @@ -77,6 +77,7 @@ public class MultiType extends Type { /** * Always returns null since this type is never used for an array. */ + @Override public Type getComponent() { return null; } @@ -84,6 +85,7 @@ public class MultiType extends Type { /** * Always returns 1, since this type is a reference. */ + @Override public int getSize() { return 1; } @@ -91,6 +93,7 @@ public class MultiType extends Type { /** * Always reutnrs false since this type is never used for an array */ + @Override public boolean isArray() { return false; } @@ -98,12 +101,14 @@ public class MultiType extends Type { /** * Returns true if the internal state has changed. */ + @Override boolean popChanged() { boolean changed = this.changed; this.changed = false; return changed; } + @Override public boolean isAssignableFrom(Type type) { throw new UnsupportedOperationException("Not implemented"); } @@ -118,11 +123,11 @@ public class MultiType extends Type { if (potentialClass != null && !type.isAssignableFrom(potentialClass)) potentialClass = null; - Map map = mergeMultiAndSingle(this, type); + Map<String,CtClass> map = mergeMultiAndSingle(this, type); if (map.size() == 1 && potentialClass == null) { // Update previous merge paths to the same resolved type - resolved = Type.get((CtClass)map.values().iterator().next()); + resolved = Type.get(map.values().iterator().next()); propogateResolved(); return true; @@ -168,16 +173,15 @@ public class MultiType extends Type { * * @return true */ + @Override public boolean isReference() { return true; } - private Map getAllMultiInterfaces(MultiType type) { - Map map = new HashMap(); + private Map<String,CtClass> getAllMultiInterfaces(MultiType type) { + Map<String,CtClass> map = new HashMap<String,CtClass>(); - Iterator iter = type.interfaces.values().iterator(); - while (iter.hasNext()) { - CtClass intf = (CtClass)iter.next(); + for (CtClass intf:type.interfaces.values()) { map.put(intf.getName(), intf); getAllInterfaces(intf, map); } @@ -186,16 +190,16 @@ public class MultiType extends Type { } - private Map mergeMultiInterfaces(MultiType type1, MultiType type2) { - Map map1 = getAllMultiInterfaces(type1); - Map map2 = getAllMultiInterfaces(type2); + private Map<String,CtClass> mergeMultiInterfaces(MultiType type1, MultiType type2) { + Map<String,CtClass> map1 = getAllMultiInterfaces(type1); + Map<String,CtClass> map2 = getAllMultiInterfaces(type2); return findCommonInterfaces(map1, map2); } - private Map mergeMultiAndSingle(MultiType multi, Type single) { - Map map1 = getAllMultiInterfaces(multi); - Map map2 = getAllInterfaces(single.getCtClass(), null); + private Map<String,CtClass> mergeMultiAndSingle(MultiType multi, Type single) { + Map<String,CtClass> map1 = getAllMultiInterfaces(multi); + Map<String,CtClass> map2 = getAllInterfaces(single.getCtClass(), null); return findCommonInterfaces(map1, map2); } @@ -211,6 +215,7 @@ public class MultiType extends Type { return false; } + @Override public Type merge(Type type) { if (this == type) return this; @@ -235,7 +240,7 @@ public class MultiType extends Type { } } - Map merged; + Map<String,CtClass> merged; if (type instanceof MultiType) { MultiType multi = (MultiType)type; @@ -254,14 +259,13 @@ public class MultiType extends Type { // Keep all previous merge paths up to date if (merged.size() > 1 || (merged.size() == 1 && potentialClass != null)) { // Check for changes - if (merged.size() != interfaces.size()) { + if (merged.size() != interfaces.size()) changed = true; - } else if (changed == false){ - Iterator iter = merged.keySet().iterator(); - while (iter.hasNext()) - if (! interfaces.containsKey(iter.next())) + else if (changed == false) + for (String key:merged.keySet()) + if (!interfaces.containsKey(key)) changed = true; - } + interfaces = merged; propogateState(); @@ -269,19 +273,27 @@ public class MultiType extends Type { return this; } - if (merged.size() == 1) { - resolved = Type.get((CtClass) merged.values().iterator().next()); - } else if (potentialClass != null){ + if (merged.size() == 1) + resolved = Type.get(merged.values().iterator().next()); + else if (potentialClass != null) resolved = potentialClass; - } else { + else resolved = OBJECT; - } propogateResolved(); return resolved; } + @Override + public int hashCode() { + if (resolved != null) + return resolved.hashCode(); + + return interfaces.keySet().hashCode(); + } + + @Override public boolean equals(Object o) { if (! (o instanceof MultiType)) return false; @@ -295,19 +307,18 @@ public class MultiType extends Type { return interfaces.keySet().equals(multi.interfaces.keySet()); } + @Override public String toString() { if (resolved != null) return resolved.toString(); StringBuffer buffer = new StringBuffer("{"); - Iterator iter = interfaces.keySet().iterator(); - while (iter.hasNext()) { - buffer.append(iter.next()); - buffer.append(", "); - } - buffer.setLength(buffer.length() - 2); + for (String key:interfaces.keySet()) + buffer.append(key).append(", "); if (potentialClass != null) - buffer.append(", *").append(potentialClass.toString()); + buffer.append("*").append(potentialClass.toString()); + else + buffer.setLength(buffer.length() - 2); buffer.append("}"); return buffer.toString(); } diff --git a/src/main/javassist/bytecode/analysis/Subroutine.java b/src/main/javassist/bytecode/analysis/Subroutine.java index 381ed6ab..dff3084a 100644 --- a/src/main/javassist/bytecode/analysis/Subroutine.java +++ b/src/main/javassist/bytecode/analysis/Subroutine.java @@ -28,17 +28,17 @@ import java.util.Set; */ public class Subroutine { //private Set callers = new HashSet(); - private List callers = new ArrayList(); - private Set access = new HashSet(); + private List<Integer> callers = new ArrayList<Integer>(); + private Set<Integer> access = new HashSet<Integer>(); private int start; public Subroutine(int start, int caller) { this.start = start; - callers.add(Integer.valueOf(caller)); + callers.add(caller); } public void addCaller(int caller) { - callers.add(Integer.valueOf(caller)); + callers.add(caller); } public int start() { @@ -46,21 +46,22 @@ public class Subroutine { } public void access(int index) { - access.add(Integer.valueOf(index)); + access.add(index); } public boolean isAccessed(int index) { - return access.contains(Integer.valueOf(index)); + return access.contains(index); } - public Collection accessed() { + public Collection<Integer> accessed() { return access; } - public Collection callers() { + public Collection<Integer> callers() { return callers; } + @Override public String toString() { return "start = " + start + " callers = " + callers.toString(); } diff --git a/src/main/javassist/bytecode/analysis/SubroutineScanner.java b/src/main/javassist/bytecode/analysis/SubroutineScanner.java index c0af816a..f9816267 100644 --- a/src/main/javassist/bytecode/analysis/SubroutineScanner.java +++ b/src/main/javassist/bytecode/analysis/SubroutineScanner.java @@ -35,8 +35,8 @@ import javassist.bytecode.Opcode; public class SubroutineScanner implements Opcode { private Subroutine[] subroutines; - Map subTable = new HashMap(); - Set done = new HashSet(); + Map<Integer,Subroutine> subTable = new HashMap<Integer,Subroutine>(); + Set<Integer> done = new HashSet<Integer>(); public Subroutine[] scan(MethodInfo method) throws BadBytecode { @@ -62,10 +62,10 @@ public class SubroutineScanner implements Opcode { private void scan(int pos, CodeIterator iter, Subroutine sub) throws BadBytecode { // Skip already processed blocks - if (done.contains(Integer.valueOf(pos))) + if (done.contains(pos)) return; - done.add(Integer.valueOf(pos)); + done.add(pos); int old = iter.lookAhead(); iter.move(pos); @@ -103,10 +103,10 @@ public class SubroutineScanner implements Opcode { if (Util.isJumpInstruction(opcode)) { int target = Util.getJumpTarget(pos, iter); if (opcode == JSR || opcode == JSR_W) { - Subroutine s = (Subroutine) subTable.get(Integer.valueOf(target)); + Subroutine s = subTable.get(target); if (s == null) { s = new Subroutine(target, pos); - subTable.put(Integer.valueOf(target), s); + subTable.put(target, s); scan(target, iter, s); } else { s.addCaller(pos); diff --git a/src/main/javassist/bytecode/analysis/Type.java b/src/main/javassist/bytecode/analysis/Type.java index ce02c172..db02df35 100644 --- a/src/main/javassist/bytecode/analysis/Type.java +++ b/src/main/javassist/bytecode/analysis/Type.java @@ -15,10 +15,8 @@ */ package javassist.bytecode.analysis; -import java.util.ArrayList; import java.util.HashMap; import java.util.IdentityHashMap; -import java.util.Iterator; import java.util.Map; import javassist.ClassPool; @@ -44,7 +42,7 @@ public class Type { private final CtClass clazz; private final boolean special; - private static final Map prims = new IdentityHashMap(); + private static final Map<CtClass,Type> prims = new IdentityHashMap<CtClass,Type>(); /** Represents the double primitive type */ public static final Type DOUBLE = new Type(CtClass.doubleType); /** Represents the boolean primitive type */ @@ -451,7 +449,7 @@ public class Type { // If its Object, then try and find a common interface(s) if (superClass.getSuperclass() == null) { - Map interfaces = findCommonInterfaces(type); + Map<String,CtClass> interfaces = findCommonInterfaces(type); if (interfaces.size() == 1) return new Type((CtClass) interfaces.values().iterator().next()); if (interfaces.size() > 1) @@ -462,7 +460,7 @@ public class Type { } // Check for a common interface that is not on the found supertype - Map commonDeclared = findExclusiveDeclaredInterfaces(type, superClass); + Map<String,CtClass> commonDeclared = findExclusiveDeclaredInterfaces(type, superClass); if (commonDeclared.size() > 0) { return new MultiType(commonDeclared, new Type(superClass)); } @@ -470,21 +468,19 @@ public class Type { return new Type(superClass); } - private Map findCommonInterfaces(Type type) { - Map typeMap = getAllInterfaces(type.clazz, null); - Map thisMap = getAllInterfaces(this.clazz, null); + private Map<String,CtClass> findCommonInterfaces(Type type) { + Map<String,CtClass> typeMap = getAllInterfaces(type.clazz, null); + Map<String,CtClass> thisMap = getAllInterfaces(this.clazz, null); return findCommonInterfaces(typeMap, thisMap); } - private Map findExclusiveDeclaredInterfaces(Type type, CtClass exclude) { - Map typeMap = getDeclaredInterfaces(type.clazz, null); - Map thisMap = getDeclaredInterfaces(this.clazz, null); - Map excludeMap = getAllInterfaces(exclude, null); + private Map<String,CtClass> findExclusiveDeclaredInterfaces(Type type, CtClass exclude) { + Map<String,CtClass> typeMap = getDeclaredInterfaces(type.clazz, null); + Map<String,CtClass> thisMap = getDeclaredInterfaces(this.clazz, null); + Map<String,CtClass> excludeMap = getAllInterfaces(exclude, null); - Iterator i = excludeMap.keySet().iterator(); - while (i.hasNext()) { - Object intf = i.next(); + for (String intf:excludeMap.keySet()) { typeMap.remove(intf); thisMap.remove(intf); } @@ -493,19 +489,21 @@ public class Type { } - Map findCommonInterfaces(Map typeMap, Map alterMap) { - Iterator i = alterMap.keySet().iterator(); - while (i.hasNext()) { - if (! typeMap.containsKey(i.next())) - i.remove(); - } + Map<String,CtClass> findCommonInterfaces(Map<String,CtClass> typeMap, Map<String,CtClass> alterMap) { + if (alterMap == null) + alterMap = new HashMap<String,CtClass>(); + + if (typeMap == null||typeMap.isEmpty()) + alterMap.clear(); + + for (String name:alterMap.keySet()) + if (!typeMap.containsKey(name)) + alterMap.remove(name); // Reduce to subinterfaces // This does not need to be recursive since we make a copy, // and that copy contains all super types for the whole hierarchy - i = new ArrayList(alterMap.values()).iterator(); - while (i.hasNext()) { - CtClass intf = (CtClass) i.next(); + for (CtClass intf:alterMap.values()) { CtClass[] interfaces; try { interfaces = intf.getInterfaces(); @@ -513,24 +511,23 @@ public class Type { throw new RuntimeException(e); } - for (int c = 0; c < interfaces.length; c++) - alterMap.remove(interfaces[c].getName()); + for (CtClass c:interfaces) + alterMap.remove(c.getName()); } return alterMap; } - Map getAllInterfaces(CtClass clazz, Map map) { + Map<String,CtClass> getAllInterfaces(CtClass clazz, Map<String,CtClass> map) { if (map == null) - map = new HashMap(); + map = new HashMap<String,CtClass>(); if (clazz.isInterface()) map.put(clazz.getName(), clazz); do { try { CtClass[] interfaces = clazz.getInterfaces(); - for (int i = 0; i < interfaces.length; i++) { - CtClass intf = interfaces[i]; + for (CtClass intf:interfaces) { map.put(intf.getName(), intf); getAllInterfaces(intf, map); } @@ -544,9 +541,9 @@ public class Type { return map; } - Map getDeclaredInterfaces(CtClass clazz, Map map) { + Map<String,CtClass> getDeclaredInterfaces(CtClass clazz, Map<String,CtClass> map) { if (map == null) - map = new HashMap(); + map = new HashMap<String,CtClass>(); if (clazz.isInterface()) map.put(clazz.getName(), clazz); @@ -558,8 +555,7 @@ public class Type { throw new RuntimeException(e); } - for (int i = 0; i < interfaces.length; i++) { - CtClass intf = interfaces[i]; + for (CtClass intf:interfaces) { map.put(intf.getName(), intf); getDeclaredInterfaces(intf, map); } @@ -567,6 +563,12 @@ public class Type { return map; } + @Override + public int hashCode() { + return getClass().hashCode() + clazz.hashCode(); + } + + @Override public boolean equals(Object o) { if (! (o instanceof Type)) return false; @@ -578,6 +580,7 @@ public class Type { return one == two || (one != null && two != null && one.getName().equals(two.getName())); } + @Override public String toString() { if (this == BOGUS) return "BOGUS"; |