diff --git a/jode/jode/bytecode/Opcodes.java b/jode/jode/bytecode/Opcodes.java index cb3d7a7..60b7638 100644 --- a/jode/jode/bytecode/Opcodes.java +++ b/jode/jode/bytecode/Opcodes.java @@ -355,6 +355,7 @@ public abstract class Opcodes { } } case opc_ret: + stream.skip(1); return new int[] { 2 }; case opc_jsr_w: diff --git a/jode/jode/expr/InvokeOperator.java b/jode/jode/expr/InvokeOperator.java index cc79ea7..104bb6a 100644 --- a/jode/jode/expr/InvokeOperator.java +++ b/jode/jode/expr/InvokeOperator.java @@ -91,8 +91,8 @@ public final class InvokeOperator extends Operator { public String toString(String[] operands) { String object = null; if (specialFlag) { + Class clazz = codeAnalyzer.method.classAnalyzer.clazz; if (operands[0].equals("this")) { - Class clazz = codeAnalyzer.method.classAnalyzer.clazz; object = ""; while (clazz != null && !classType.equals(Type.tType(clazz))) { @@ -101,9 +101,11 @@ public final class InvokeOperator extends Operator { } if (clazz == null) - object = "ERROR-SPECIAL"; - } else - object = "ERROR-SPECIAL"; + object = "SPECIAL"; + } else if (classType.equals(Type.tType(clazz))) + object = operands[0]; + else + object = "SPECIAL "+operands[0]; } object = (object != null) ? object diff --git a/jode/jode/flow/VariableSet.java b/jode/jode/flow/VariableSet.java index 2c449bd..950c469 100644 --- a/jode/jode/flow/VariableSet.java +++ b/jode/jode/flow/VariableSet.java @@ -29,20 +29,98 @@ import jode.LocalInfo; * Note that a variable set can contain LocalInfos that use the same * slot, but are different. */ -public class VariableSet extends java.util.Vector { +public class VariableSet implements Cloneable { + LocalInfo[] locals; + int count; + /** * Creates a new empty variable set */ public VariableSet() { - super(0, 0); + locals = null; + count = 0; + } + + /** + * Creates a new pre initialized variable set + */ + public VariableSet(LocalInfo[] locals) { + count = locals.length; + this.locals = locals; + } + + public final void grow(int size) { + if (locals != null) { + size += count; + if (size > locals.length) { + int nextSize = locals.length * 2; +// System.err.println("wanted: "+size+" next: "+nextSize); + LocalInfo[] newLocals + = new LocalInfo[nextSize > size ? nextSize : size]; + System.arraycopy(locals, 0, newLocals, 0, count); + locals = newLocals; + } + } else if (size > 0) + locals = new LocalInfo[size]; } /** - * Adds a local variable to the variable set. - * @param li The local variable of type LocalInfo. + * Adds a local info to this variable set. It doesn't check for + * duplicates. */ public void addElement(LocalInfo li) { - super.addElement((Object)li); + grow(1); + locals[count++] = li; + } + + /** + * Checks if the variable set contains the given local info. + */ + public boolean contains(LocalInfo li) { + li = li.getLocalInfo(); + for (int i=0; i 0) { + other.locals = new LocalInfo[count]; + System.arraycopy(locals, 0, other.locals, 0, count); + } + return other; + } catch (CloneNotSupportedException ex) { + throw new jode.AssertError("Clone?"); + } } /** @@ -50,22 +128,30 @@ public class VariableSet extends java.util.Vector { * in both variable sets, all corresponding LocalInfos are merged. * The variable sets are not changed (use union for this). * @return The merged variables. - * @param vs the other variable set. - */ + * @param vs the other variable set. */ public VariableSet merge(VariableSet vs) { VariableSet merged = new VariableSet(); - for (int i=0; i=0; i--) { - LocalInfo li1 = (LocalInfo) elementData[i]; - for (int j=0; j=0; i--) { - LocalInfo li1 = (LocalInfo) elementData[i]; - for (int j=0; j