harmony-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From qi...@apache.org
Subject svn commit: r721077 [9/12] - in /harmony/enhanced/classlib/branches/java6: ./ depends/files/ depends/jars/ depends/manifests/asm-3.1/ depends/manifests/asm-3.1/META-INF/ depends/manifests/bcel-5.2/ make/ modules/accessibility/ modules/accessibility/src...
Date Thu, 27 Nov 2008 05:10:42 GMT
Modified: harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/BcBands.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/BcBands.java?rev=721077&r1=721076&r2=721077&view=diff
==============================================================================
--- harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/BcBands.java
(original)
+++ harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/BcBands.java
Wed Nov 26 21:10:32 2008
@@ -19,437 +19,446 @@
 import java.io.IOException;
 import java.io.OutputStream;
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.List;
+import java.util.Map;
 
-import org.apache.bcel.classfile.Code;
-import org.apache.bcel.classfile.Constant;
-import org.apache.bcel.classfile.ConstantClass;
-import org.apache.bcel.classfile.ConstantDouble;
-import org.apache.bcel.classfile.ConstantFieldref;
-import org.apache.bcel.classfile.ConstantFloat;
-import org.apache.bcel.classfile.ConstantInteger;
-import org.apache.bcel.classfile.ConstantInterfaceMethodref;
-import org.apache.bcel.classfile.ConstantLong;
-import org.apache.bcel.classfile.ConstantMethodref;
-import org.apache.bcel.classfile.ConstantNameAndType;
-import org.apache.bcel.classfile.ConstantPool;
-import org.apache.bcel.classfile.ConstantString;
+import org.objectweb.asm.Label;
 
 /**
  * Bytecode bands
  */
 public class BcBands extends BandSet {
 
-    private CpBands cpBands;
+    private static final Integer MULTIANEWARRAY = new Integer(197);
+    private static final Integer ALOAD_0 = new Integer(42);
+    private final CpBands cpBands;
+    private final Segment segment;
 
-    public BcBands(CpBands cpBands) {
+    public BcBands(CpBands cpBands, Segment segment) {
         this.cpBands = cpBands;
+        this.segment = segment;
     }
 
-    private List bcCodes = new ArrayList();
-    private List bcCaseCount = new ArrayList();
-    private List bcCaseValue = new ArrayList();
-    private List bcByte = new ArrayList();
-    private List bcShort = new ArrayList();
-    private List bcLocal = new ArrayList();
-    private List bcLabel = new ArrayList();
-    private List bcIntref = new ArrayList();
-    private List bcFloatRef = new ArrayList();
-    private List bcLongRef = new ArrayList();
-    private List bcDoubleRef = new ArrayList();
-    private List bcStringRef = new ArrayList();
-    private List bcClassRef = new ArrayList();
-    private List bcFieldRef = new ArrayList();
-    private List bcMethodRef = new ArrayList();
-    private List bcIMethodRef = new ArrayList();
+    private final List bcCodes = new ArrayList();
+    private final List bcCaseCount = new ArrayList();
+    private final List bcCaseValue = new ArrayList();
+    private final List bcByte = new ArrayList();
+    private final List bcShort = new ArrayList();
+    private final List bcLocal = new ArrayList();
+    private final List bcLabel = new ArrayList();
+    private final List bcIntref = new ArrayList();
+    private final List bcFloatRef = new ArrayList();
+    private final List bcLongRef = new ArrayList();
+    private final List bcDoubleRef = new ArrayList();
+    private final List bcStringRef = new ArrayList();
+    private final List bcClassRef = new ArrayList();
+    private final List bcFieldRef = new ArrayList();
+    private final List bcMethodRef = new ArrayList();
+    private final List bcIMethodRef = new ArrayList();
     private List bcThisField = new ArrayList();
-    private List bcSuperField = new ArrayList();
+    private final List bcSuperField = new ArrayList();
     private List bcThisMethod = new ArrayList();
-    private List bcSuperMethod = new ArrayList();
-    private List bcInitRef = new ArrayList();
-//    private List bcEscRef = new ArrayList();
-//    private List bcEscRefSize = new ArrayList();
-//    private List bcEscSize = new ArrayList();
-//    private List bcEscByte = new ArrayList();
-
-    public void addCode(Code obj, String thisClass, String superClass) {
-        ConstantPool cp = obj.getConstantPool();
-        byte[] bytecodes = obj.getCode();
+    private final List bcSuperMethod = new ArrayList();
+    private final List bcInitRef = new ArrayList();
+
+    private String currentClass;
+    private String superClass;
+    private static final Integer WIDE = new Integer(196);
+    private static final Integer INVOKEINTERFACE = new Integer(185);
+    private static final Integer TABLESWITCH = new Integer(170);
+    private static final Integer IINC = new Integer(132);
+    private static final Integer LOOKUPSWITCH = new Integer(171);
+    private static final Integer endMarker = new Integer(255);
+
+    private final List bciRenumbering = new ArrayList();
+    private final Map labelsToOffsets = new HashMap();
+    private int byteCodeOffset;
+    private int renumberedOffset;
+    private final List bcLabelRelativeOffsets = new ArrayList();
+
+    public void setCurrentClass(String name) {
+        currentClass = name;
+    }
+
+    public void setSuperClass(String superName) {
+        superClass = superName;
+    }
+
+    public void finaliseBands() {
+        bcThisField = getIndexInClass(bcThisField);
+        bcThisMethod = getIndexInClass(bcThisMethod);
+    }
+
+    public void pack(OutputStream out) throws IOException, Pack200Exception {
+        out.write(encodeBandInt("bcCodes", listToArray(bcCodes), Codec.BYTE1));
+        out.write(encodeBandInt("bcCaseCount", listToArray(bcCaseCount),
+                Codec.UNSIGNED5));
+        out.write(encodeBandInt("bcCaseValue", listToArray(bcCaseValue),
+                Codec.DELTA5));
+        out.write(encodeBandInt("bcByte", listToArray(bcByte), Codec.BYTE1));
+        out.write(encodeBandInt("bcShort", listToArray(bcShort), Codec.DELTA5));
+        out.write(encodeBandInt("bcLocal", listToArray(bcLocal),
+                Codec.UNSIGNED5));
+        out
+                .write(encodeBandInt("bcLabel", listToArray(bcLabel),
+                        Codec.BRANCH5));
+        out.write(encodeBandInt("bcIntref", cpEntryListToArray(bcIntref),
+                Codec.DELTA5));
+        out.write(encodeBandInt("bcFloatRef", cpEntryListToArray(bcFloatRef),
+                Codec.DELTA5));
+        out.write(encodeBandInt("bcLongRef", cpEntryListToArray(bcLongRef),
+                Codec.DELTA5));
+        out.write(encodeBandInt("bcDoubleRef", cpEntryListToArray(bcDoubleRef),
+                Codec.DELTA5));
+        out.write(encodeBandInt("bcStringRef", cpEntryListToArray(bcStringRef),
+                Codec.DELTA5));
+        out.write(encodeBandInt("bcClassRef",
+                cpEntryOrNullListToArray(bcClassRef), Codec.UNSIGNED5));
+        out.write(encodeBandInt("bcFieldRef", cpEntryListToArray(bcFieldRef),
+                Codec.DELTA5));
+        out.write(encodeBandInt("bcMethodRef", cpEntryListToArray(bcMethodRef),
+                Codec.UNSIGNED5));
+        out.write(encodeBandInt("bcIMethodRef",
+                cpEntryListToArray(bcIMethodRef), Codec.DELTA5));
+        out.write(encodeBandInt("bcThisField", listToArray(bcThisField),
+                Codec.UNSIGNED5));
+        out.write(encodeBandInt("bcSuperField", listToArray(bcSuperField),
+                Codec.UNSIGNED5));
+        out.write(encodeBandInt("bcThisMethod", listToArray(bcThisMethod),
+                Codec.UNSIGNED5));
+        out.write(encodeBandInt("bcSuperMethod",
+                listToArray(bcSuperMethod), Codec.UNSIGNED5));
+        out.write(encodeBandInt("bcInitRef", listToArray(bcInitRef),
+                Codec.UNSIGNED5));
+        // out.write(encodeBandInt(cpEntryListToArray(bcEscRef),
+        // Codec.UNSIGNED5));
+        // out.write(encodeBandInt(listToArray(bcEscRefSize), Codec.UNSIGNED5));
+        // out.write(encodeBandInt(listToArray(bcEscSize), Codec.UNSIGNED5));
+        // out.write(encodeBandInt(listToArray(bcEscByte), Codec.BYTE1));
+    }
+
+    private List getIndexInClass(List cPMethodOrFieldList) {
+        List indices = new ArrayList(cPMethodOrFieldList.size());
+        for (int i = 0; i < cPMethodOrFieldList.size(); i++) {
+            CPMethodOrField cpMF = (CPMethodOrField) cPMethodOrFieldList.get(i);
+            indices.add(new Integer(cpMF.getIndexInClass()));
+        }
+        return indices;
+    }
+
+    public void visitEnd() {
+        for (int i = 0; i < bciRenumbering.size(); i++) {
+            if (bciRenumbering.get(i) == null) {
+                bciRenumbering.remove(i);
+                bciRenumbering.add(i, new Integer(++renumberedOffset));
+            }
+        }
+        if (renumberedOffset + 1 != bciRenumbering.size()) {
+            throw new RuntimeException("Mistake made with renumbering");
+        }
+        for (int i = bcLabel.size() - 1; i >= 0; i--) {
+            Object label = bcLabel.get(i);
+            if (label instanceof Integer) {
+                break;
+            } else if (label instanceof Label) {
+                bcLabel.remove(i);
+                Integer offset = (Integer) labelsToOffsets.get(label);
+                Integer relativeOffset = (Integer) bcLabelRelativeOffsets.get(i);
+                bcLabel.add(i, new Integer(((Integer)bciRenumbering.get(offset.intValue())).intValue()
- ((Integer)bciRenumbering.get(relativeOffset.intValue())).intValue()));
+            }
+        }
+        bcCodes.add(endMarker);
+        segment.getClassBands().doBciRenumbering(bciRenumbering,
+                labelsToOffsets);
+        bciRenumbering.clear();
+        labelsToOffsets.clear();
+        byteCodeOffset = 0;
+        renumberedOffset = 0;
+    }
+
+    public void visitLabel(Label label) {
+        labelsToOffsets.put(label, new Integer(byteCodeOffset));
+    }
+
+    public void visitFieldInsn(int opcode, String owner, String name,
+            String desc) {
+        byteCodeOffset += 3;
+        updateRenumbering();
         boolean aload_0 = false;
-        boolean wide = false;
-        for (int i = 0; i < bytecodes.length; i++) {
-            int bytecode = 0xff & bytecodes[i];
-            switch (bytecode) {
-            case 16: // bipush
-            case 17: // sipush
-                bcCodes.add(new Integer(bytecode));
-                byte b1 = bytecodes[++i];
-                byte b2 = bytecodes[++i];
-                short s = (short) (b1 << 8 | b2);
-                bcShort.add(new Integer(s));
-                break;
-            case 18: // ldc
-                Constant constant = cp.getConstant(bytecodes[++i] & 0xFF);
-                if (constant instanceof ConstantInteger) {
-                    bcCodes.add(new Integer(234)); // ildc
-                    bcIntref.add(cpBands.getCPConstant(constant, cp));
-                } else if (constant instanceof ConstantFloat) {
-                    bcCodes.add(new Integer(235)); // fldc
-                    bcFloatRef.add(cpBands.getCPConstant(constant, cp));
-                } else if (constant instanceof ConstantString) {
-                    bcCodes.add(new Integer(18)); // aldc
-                    bcStringRef.add(cpBands.getCPConstant(constant, cp));
-                } else if (constant instanceof ConstantClass) {
-                    bcCodes.add(new Integer(233)); // cldc
-                    bcClassRef.add(cpBands.getCPConstant(constant, cp));
-                }
-                break;
-            case 19: // aldc_w
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                int index = b1 << 8 | b2;
-                constant = cp.getConstant(index);
-                if (constant instanceof ConstantInteger) {
-                    bcCodes.add(new Integer(237)); // ildc_w
-                    bcIntref.add(cpBands.getCPConstant(constant, cp));
-                } else if (constant instanceof ConstantFloat) {
-                    bcCodes.add(new Integer(238)); // fldc_w
-                    bcFloatRef.add(cpBands.getCPConstant(constant, cp));
-                } else if (constant instanceof ConstantString) {
-                    bcCodes.add(new Integer(19)); // aldc_w
-                    bcStringRef.add(cpBands.getCPConstant(constant, cp));
-                } else if (constant instanceof ConstantClass) {
-                    bcCodes.add(new Integer(236)); // cldc_w
-                    bcClassRef.add(cpBands.getCPConstant(constant, cp));
-                }
-                break;
-            case 20: // ldc2_w
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                index = b1 << 8 | b2;
-                constant = cp.getConstant(index);
-                if (constant instanceof ConstantLong) {
-                    bcCodes.add(new Integer(20)); // lldc2_w
-                    bcLongRef.add(cpBands.getCPConstant(constant, cp));
-                } else if (constant instanceof ConstantDouble) {
-                    bcCodes.add(new Integer(239)); // dldc2_w
-                    bcDoubleRef.add(cpBands.getCPConstant(constant, cp));
-                }
-                break;
-            case 21:
-            case 22:
-            case 23:
-            case 24:
-            case 25:
-            case 54:
-            case 55:
-            case 56:
-            case 57:
-            case 58:
-                bcCodes.add(new Integer(bytecode));
-                if(wide) {
-                    b1 = bytecodes[++i];
-                    b2 = bytecodes[++i];
-                    index = b1 << 8 | b2;
-                    bcLocal.add(new Integer(index));
-                    wide = false;
-                } else {
-                    bcLocal.add(new Integer(0xff & bytecodes[++i]));
-                }
-                break;
-            case 42:
-                int next = 0;
-                if(bytecodes.length >= i) {
-                    next = bytecodes[i+1] & 0xFF;
-                }
-                if(next >= 178 && next <= 184) {
-                    aload_0 = true;
-                } else {
-                    bcCodes.add(new Integer(42));
-                }
-                break;
-            case 132: // iinc
-                bcCodes.add(new Integer(132));
-                if(wide) {
-                    b1 = bytecodes[++i];
-                    b2 = bytecodes[++i];
-                    index = b1 << 8 | b2;
-                    b1 = bytecodes[++i];
-                    b2 = bytecodes[++i];
-                    short cnst = (short) (b1 << 8 | b2);
-                    bcLocal.add(new Integer(index));
-                    bcShort.add(new Integer(cnst));
-                    wide = false;
-                } else {
-                    index = bytecodes[++i];
-                    byte cnst = bytecodes[++i];
-                    bcLocal.add(new Integer(index));
-                    bcByte.add(new Integer(cnst));
-                }
-                break;
-            case 153:
-            case 154:
-            case 155:
-            case 156:
-            case 157:
-            case 158:
-            case 159:
-            case 160:
-            case 161:
-            case 162:
-            case 163:
-            case 164:
-            case 165:
-            case 166:
-            case 198:
-            case 199:
-                bcCodes.add(new Integer(bytecode));
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                index = b1 << 8 | b2;
-                bcLabel.add(new Integer(index));
-                break;
-            case 167: // goto
-            case 168: // jsr
-                bcCodes.add(new Integer(bytecode));
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                int offset = b1 << 8 | b2;
-                bcLabel.add(new Integer(offset));
-                break;
-            case 169: // ret
-                bcCodes.add(new Integer(bytecode));
-                if(wide) {
-                    b1 = bytecodes[++i];
-                    b2 = bytecodes[++i];
-                    index = b1 << 8 | b2;
-                    bcLocal.add(new Integer(index));
-                    wide = false;
-                } else {
-                    bcLocal.add(new Integer(0xff & bytecodes[++i]));
-                }
-                break;
-            case 170: // tableswitch
-                bcCodes.add(new Integer(bytecode));
-                int padding = (i + 1) % 4 == 0 ? 0 : 4 - i + 1;
-                i+= padding;
-                b1 = bytecodes[i];
-                b2 = bytecodes[++i];
-                byte b3 = bytecodes[++i];
-                byte b4 = bytecodes[++i];
-                int defaultValue = (b1 << 24) | (b2 << 16) | (b3 << 8)
| b4;
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                b3 = bytecodes[++i];
-                b4 = bytecodes[++i];
-                int low = (b1 << 24) | (b2 << 16) | (b3 << 8) | b4;
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                b3 = bytecodes[++i];
-                b4 = bytecodes[++i];
-                int high = (b1 << 24) | (b2 << 16) | (b3 << 8) | b4;
-                bcLabel.add(new Integer(defaultValue));
-                bcCaseValue.add(new Integer(low));
-                int count = high - low + 1;
-                bcCaseCount.add(new Integer(count));
-                for (int j = 0; j < count; j++) {
-                    b1 = bytecodes[++i];
-                    b2 = bytecodes[++i];
-                    b3 = bytecodes[++i];
-                    b4 = bytecodes[++i];
-                    int label = (b1 << 24) | (b2 << 16) | (b3 << 8) | b4;
-                    bcLabel.add(new Integer(label));
-                }
-                break;
-            case 171: // lookupswitch
-                bcCodes.add(new Integer(bytecode));
-                padding = (i + 1) % 4 == 0 ? 0 : 4 - i + 1;
-                i+= padding;
-                b1 = bytecodes[i];
-                b2 = bytecodes[++i];
-                b3 = bytecodes[++i];
-                b4 = bytecodes[++i];
-                defaultValue = (b1 << 24) | (b2 << 16) | (b3 << 8) | b4;
-                bcLabel.add(new Integer(defaultValue));
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                b3 = bytecodes[++i];
-                b4 = bytecodes[++i];
-                int npairs = (b1 << 24) | (b2 << 16) | (b3 << 8) | b4;
-                bcCaseCount.add(new Integer(npairs));
-                for (int j = 0; j < npairs; j++) {
-                    b1 = bytecodes[++i];
-                    b2 = bytecodes[++i];
-                    b3 = bytecodes[++i];
-                    b4 = bytecodes[++i];
-                    int caseValue = (b1 << 24) | (b2 << 16) | (b3 << 8)
| b4;
-                    bcCaseValue.add(new Integer(caseValue));
-                    b1 = bytecodes[++i];
-                    b2 = bytecodes[++i];
-                    b3 = bytecodes[++i];
-                    b4 = bytecodes[++i];
-                    int label = (b1 << 24) | (b2 << 16) | (b3 << 8) | b4;
-                    bcLabel.add(new Integer(label));
-                }
-                break;
-            case 178: // getstatic
-            case 179: // putstatic
-            case 180: // getfield
-            case 181: // putfield
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                index = b1 << 8 | b2;
-                ConstantFieldref cfr = (ConstantFieldref) cp.getConstant(index);
-                String className = cfr.getClass(cp);
-                CPMethodOrField cpField = cpBands.getCPMethodOrField(cfr);
-                if(aload_0) {
-                    bytecode += 7;
-                }
-                if(className.equals(thisClass)) {
-                    bytecode += 24; // change to getstatic_this, putstatic_this etc.
-                    bcThisField.add(cpField);
-                } else if (className.equals(superClass)){
-                    bytecode += 38; // change to getstatic_super etc.
-                    bcSuperField.add(cpField);
-                } else {
-                    if(aload_0) {
-                        bytecode -= 7;
-                        bcCodes.add(new Integer(42)); // add aload_0 back in because there's
no special rewrite in this case.
-                    }
-                    bcFieldRef.add(cpField);
-                }
-                aload_0 = false;
-                bcCodes.add(new Integer(bytecode));
-                break;
-            case 182: // invokevirtual
-            case 183: // invokespecial
-            case 184: // invokestatic
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                index = b1 << 8 | b2;
-                ConstantMethodref cmr = (ConstantMethodref) cp.getConstant(index);
-                className = cmr.getClass(cp);
-                CPMethodOrField cpMethod = cpBands.getCPMethodOrField(cmr);
-                if(aload_0) {
-                    bytecode += 7;
-                }
-                if(className.equals(thisClass)) {
-                    if(bytecode == 183) { // invokespecial
-                        ConstantNameAndType cnat = (ConstantNameAndType) cp.getConstant(cmr.getNameAndTypeIndex());
-                        String name = cnat.getName(cp);
-                        if(name.equals("this")) {
-
-                        }
-                    }
-                    bytecode += 24; // change to invokevirtual_this, invokespecial_this etc.
-                    bcThisMethod.add(cpMethod);
-                } else if(className.equals(superClass)) {
-                    bytecode += 38; // change to invokevirtual_super, invokespecial_super
etc.
-                    bcSuperMethod.add(cpMethod);
-                } else {
-                    if(aload_0) {
-                        bytecode -= 7;
-                        bcCodes.add(new Integer(42)); // add aload_0 back in because there's
no special rewrite in this case.
-                    }
-                    bcMethodRef.add(cpMethod);
-                }
-                aload_0 = false;
-                bcCodes.add(new Integer(bytecode));
-                break;
-            case 185: // invokeinterface
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                index = b1 << 8 | b2;
-                ConstantInterfaceMethodref cmir = (ConstantInterfaceMethodref) cp.getConstant(index);
-                className = cmir.getClass(cp);
-                CPMethodOrField cpIMethod = cpBands.getCPMethodOrField(cmir);
-                bcIMethodRef.add(cpIMethod);
-                bcCodes.add(new Integer(bytecode));
-                i+= 2; // ignore count and zero fields as this can be recreated by the decompressor
-                break;
-            case 187: // new
-            case 189: // anewarray
-            case 192: // checkcast
-            case 193: // instanceof
-                bcCodes.add(new Integer(bytecode));
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                index = b1 << 8 | b2;
-                ConstantClass constantClass = (ConstantClass) cp.getConstant(index);
-                bcClassRef.add(cpBands.getCPClass(constantClass.getBytes(cp)));
-                break;
-            case 188: // newarray
-                bcCodes.add(new Integer(bytecode));
-                bcByte.add(new Integer(0xff & bytecodes[++i]));
-                break;
-            case 196: // wide
-                bcCodes.add(new Integer(196));
-                wide = true;
-            case 197: // multianewarray
-                bcCodes.add(new Integer(bytecode));
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                index = b1 << 8 | b2;
-                constantClass = (ConstantClass) cp.getConstant(index);
-                bcClassRef.add(cpBands.getCPClass(constantClass.getBytes(cp)));
-                byte dimensions = bytecodes[++i];
-                bcByte.add(new Integer(0xff & dimensions));
-                break;
-            case 200: // goto_w
-            case 201: // jsr_w
-                bcCodes.add(new Integer(bytecode));
-                b1 = bytecodes[++i];
-                b2 = bytecodes[++i];
-                b3 = bytecodes[++i];
-                b4 = bytecodes[++i];
-                offset = b1 << 24 | b2 << 16 | b3 << 8 | b4;
-                bcLabel.add(new Integer(offset));
-                break;
-//   TODO         case 230: // invokespecial_this_init
-//            case 231: // invokespecial_super_init
-//            case 232: // invokespecial_new_init
-//                bcInitRefCount++;
-//                break;
-            default:
-                if(bytecode >= 202) {
-                    throw new RuntimeException("Non-standard bytecode instructions not supported");
-                } else {
-                    bcCodes.add(new Integer(bytecode));
+        if (bcCodes.size() > 0
+                && ((Integer) bcCodes.get(bcCodes.size() - 1)).equals(ALOAD_0)) {
+            bcCodes.remove(bcCodes.size() - 1);
+            aload_0 = true;
+        }
+        CPMethodOrField cpField = cpBands.getCPField(owner, name, desc);
+        if (aload_0) {
+            opcode += 7;
+        }
+        if (owner.equals(currentClass)) {
+            opcode += 24; // change to getstatic_this, putstatic_this etc.
+            bcThisField.add(cpField);
+//        } else if (owner.equals(superClass)) {
+//            opcode += 38; // change to getstatic_super etc.
+//            bcSuperField.add(cpField);
+        } else {
+            if (aload_0) {
+                opcode -= 7;
+                bcCodes.add(ALOAD_0); // add aload_0 back in because
+                // there's no special rewrite in
+                // this case.
+            }
+            bcFieldRef.add(cpField);
+        }
+        aload_0 = false;
+        bcCodes.add(new Integer(opcode));
+    }
+
+    private void updateRenumbering() {
+        if(bciRenumbering.isEmpty()) {
+            bciRenumbering.add(new Integer(0));
+        }
+        renumberedOffset ++;
+        for (int i = bciRenumbering.size(); i < byteCodeOffset; i++) {
+            bciRenumbering.add(null);
+        }
+        bciRenumbering.add(new Integer(renumberedOffset));
+    }
+
+    public void visitIincInsn(int var, int increment) {
+        if (increment > Byte.MAX_VALUE) {
+            byteCodeOffset += 6;
+            bcCodes.add(WIDE);
+            bcCodes.add(IINC);
+            bcLocal.add(new Integer(var));
+            bcShort.add(new Integer(increment));
+        } else {
+            byteCodeOffset += 3;
+            bcCodes.add(IINC);
+            bcLocal.add(new Integer(var));
+            bcByte.add(new Integer(increment & 0xFF));
+        }
+        updateRenumbering();
+    }
+
+    public void visitInsn(int opcode) {
+        if (opcode >= 202) {
+            throw new RuntimeException(
+                    "Non-standard bytecode instructions not supported");
+        } else {
+            bcCodes.add(new Integer(opcode));
+            byteCodeOffset++;
+            updateRenumbering();
+        }
+    }
+
+    public void visitIntInsn(int opcode, int operand) {
+        switch (opcode) {
+        case 17: // sipush
+            bcCodes.add(new Integer(opcode));
+            bcShort.add(new Integer(operand));
+            byteCodeOffset += 3;
+            break;
+        case 16: // bipush
+        case 188: // newarray
+            bcCodes.add(new Integer(opcode));
+            bcByte.add(new Integer(operand & 0xFF));
+            byteCodeOffset += 2;
+        }
+        updateRenumbering();
+    }
+
+    public void visitJumpInsn(int opcode, Label label) {
+        bcCodes.add(new Integer(opcode));
+        bcLabel.add(label);
+        bcLabelRelativeOffsets.add(new Integer(byteCodeOffset));
+        byteCodeOffset += 3;
+        updateRenumbering();
+    }
+
+    public void visitLdcInsn(Object cst) {
+        CPConstant constant = cpBands.getConstant(cst);
+        if (segment.lastConstantHadWideIndex() || constant instanceof CPLong
+                || constant instanceof CPDouble) {
+            byteCodeOffset += 3;
+            if (constant instanceof CPInt) {
+                bcCodes.add(new Integer(237)); // ildc_w
+                bcIntref.add(constant);
+            } else if (constant instanceof CPFloat) {
+                bcCodes.add(new Integer(238)); // fldc
+                bcFloatRef.add(constant);
+            } else if (constant instanceof CPLong) {
+                bcCodes.add(new Integer(20)); // lldc2_w
+                bcLongRef.add(constant);
+            } else if (constant instanceof CPDouble) {
+                bcCodes.add(new Integer(239)); // dldc2_w
+                bcDoubleRef.add(constant);
+            } else if (constant instanceof CPString) {
+                bcCodes.add(new Integer(19)); // aldc
+                bcStringRef.add(constant);
+            } else if (constant instanceof CPClass) {
+                bcCodes.add(new Integer(236)); // cldc
+                bcClassRef.add(constant);
+            }
+        } else {
+            byteCodeOffset += 2;
+            if (constant instanceof CPInt) {
+                bcCodes.add(new Integer(234)); // ildc
+                bcIntref.add(constant);
+            } else if (constant instanceof CPFloat) {
+                bcCodes.add(new Integer(235)); // fldc
+                bcFloatRef.add(constant);
+            } else if (constant instanceof CPString) {
+                bcCodes.add(new Integer(18)); // aldc
+                bcStringRef.add(constant);
+            } else if (constant instanceof CPClass) {
+                bcCodes.add(new Integer(233)); // cldc
+                bcClassRef.add(constant);
+            }
+        }
+        updateRenumbering();
+    }
+
+    public void visitLookupSwitchInsn(Label dflt, int[] keys, Label[] labels) {
+        bcCodes.add(LOOKUPSWITCH);
+        bcLabel.add(dflt);
+        bcLabelRelativeOffsets.add(new Integer(byteCodeOffset));
+        bcCaseCount.add(new Integer(keys.length));
+        for (int i = 0; i < labels.length; i++) {
+            bcCaseValue.add(new Integer(keys[i]));
+            bcLabel.add(labels[i]);
+            bcLabelRelativeOffsets.add(new Integer(byteCodeOffset));
+        }
+        int padding = (byteCodeOffset + 1) % 4 == 0 ? 0 : 4 - byteCodeOffset + 1;
+        byteCodeOffset += padding + 8 + 8 * keys.length;
+        updateRenumbering();
+    }
+
+    public void visitMethodInsn(int opcode, String owner, String name,
+            String desc) {
+        byteCodeOffset += 3;
+        updateRenumbering();
+        switch (opcode) {
+        case 182: // invokevirtual
+        case 183: // invokespecial
+        case 184: // invokestatic
+            boolean aload_0 = false;
+            if (bcCodes.size() > 0
+                    && ((Integer) bcCodes.get(bcCodes.size() - 1))
+                            .equals(ALOAD_0)) {
+                bcCodes.remove(bcCodes.size() - 1);
+                aload_0 = true;
+                opcode += 7;
+            }
+
+//            if (opcode == 183 && name.equals("<init>") && !aload_0
+//                    && owner.equals(currentClass)) {
+//                opcode = 230;
+//            } else if (opcode == 183 && name.equals("<init>") &&
!aload_0
+//                    && owner.equals(superClass)) {
+//                opcode = 231;
+//                // TODO: 232
+//            } else
+            if (owner.equals(currentClass)) {
+                opcode += 24; // change to invokevirtual_this,
+                // invokespecial_this etc.
+                bcThisMethod.add(cpBands.getCPMethod(owner, name, desc));
+//            } else if (owner.equals(superClass)) { // TODO
+//                opcode += 38; // change to invokevirtual_super,
+//                // invokespecial_super etc.
+//                bcSuperMethod.add(cpBands.getCPMethod(owner, name, desc));
+            } else {
+                if (aload_0) {
+                    opcode -= 7;
+                    bcCodes.add(ALOAD_0); // add aload_0 back in
+                    // because there's no
+                    // special rewrite in this
+                    // case.
                 }
+                bcMethodRef.add(cpBands.getCPMethod(owner, name, desc));
             }
+            bcCodes.add(new Integer(opcode));
+            break;
+        case 185: // invokeinterface
+            CPMethodOrField cpIMethod = cpBands.getCPIMethod(owner, name, desc);
+            bcIMethodRef.add(cpIMethod);
+            bcCodes.add(INVOKEINTERFACE);
+            break;
         }
     }
 
-    public void finaliseBands() {
+    public void visitMultiANewArrayInsn(String desc, int dimensions) {
+        byteCodeOffset += 4;
+        updateRenumbering();
+        bcCodes.add(MULTIANEWARRAY);
+        bcClassRef.add(cpBands.getCPClass(desc));
+        bcByte.add(new Integer(dimensions & 0xFF));
+    }
+
+    public void visitTableSwitchInsn(int min, int max, Label dflt,
+            Label[] labels) {
+        bcCodes.add(TABLESWITCH);
+        bcLabel.add(dflt);
+        bcLabelRelativeOffsets.add(new Integer(byteCodeOffset));
+        bcCaseValue.add(new Integer(min));
+        int count = labels.length;
+        bcCaseCount.add(new Integer(count));
+        for (int i = 0; i < count; i++) {
+            bcLabel.add(labels[i]);
+            bcLabelRelativeOffsets.add(new Integer(byteCodeOffset));
+        }
+        int padding = (byteCodeOffset + 1) % 4 == 0 ? 0 : 4 - byteCodeOffset + 1;
+        byteCodeOffset+= (padding + 12 + 4 * labels.length);
+        updateRenumbering();
+    }
 
+    public void visitTypeInsn(int opcode, String type) {
+        // NEW, ANEWARRAY, CHECKCAST or INSTANCEOF
+        byteCodeOffset += 3;
+        updateRenumbering();
+        bcCodes.add(new Integer(opcode));
+        bcClassRef.add(cpBands.getCPClass(type));
     }
 
-    public void pack(OutputStream out) throws IOException, Pack200Exception {
-        out.write(encodeBandInt(listToArray(bcCodes), Codec.BYTE1));
-        out.write(encodeBandInt(listToArray(bcCaseCount), Codec.UNSIGNED5));
-        out.write(encodeBandInt(listToArray(bcCaseValue), Codec.DELTA5));
-        out.write(encodeBandInt(listToArray(bcByte), Codec.BYTE1));
-        out.write(encodeBandInt(listToArray(bcShort), Codec.DELTA5));
-        out.write(encodeBandInt(listToArray(bcLocal), Codec.UNSIGNED5));
-        out.write(encodeBandInt(listToArray(bcLabel), Codec.BRANCH5));
-        out.write(encodeBandInt(cpEntryListToArray(bcIntref), Codec.DELTA5));
-        out.write(encodeBandInt(cpEntryListToArray(bcFloatRef), Codec.DELTA5));
-        out.write(encodeBandInt(cpEntryListToArray(bcLongRef), Codec.DELTA5));
-        out.write(encodeBandInt(cpEntryListToArray(bcDoubleRef), Codec.DELTA5));
-        out.write(encodeBandInt(cpEntryListToArray(bcStringRef), Codec.DELTA5));
-        out.write(encodeBandInt(cpEntryOrNullListToArray(bcClassRef), Codec.UNSIGNED5));
-        out.write(encodeBandInt(cpEntryListToArray(bcFieldRef), Codec.DELTA5));
-        out.write(encodeBandInt(cpEntryListToArray(bcMethodRef), Codec.UNSIGNED5));
-        out.write(encodeBandInt(cpEntryListToArray(bcIMethodRef), Codec.DELTA5));
-        out.write(encodeBandInt(listToArray(bcThisField), Codec.UNSIGNED5));
-        out.write(encodeBandInt(listToArray(bcSuperField), Codec.UNSIGNED5));
-        out.write(encodeBandInt(listToArray(bcThisMethod), Codec.UNSIGNED5));
-        out.write(encodeBandInt(listToArray(bcSuperMethod), Codec.UNSIGNED5));
-        out.write(encodeBandInt(listToArray(bcInitRef), Codec.UNSIGNED5));
-//        out.write(encodeBandInt(cpEntryListToArray(bcEscRef), Codec.UNSIGNED5));
-//        out.write(encodeBandInt(listToArray(bcEscRefSize), Codec.UNSIGNED5));
-//        out.write(encodeBandInt(listToArray(bcEscSize), Codec.UNSIGNED5));
-//        out.write(encodeBandInt(listToArray(bcEscByte), Codec.BYTE1));
+    public void visitVarInsn(int opcode, int var) {
+        // ILOAD, LLOAD, FLOAD, DLOAD, ALOAD, ISTORE, LSTORE, FSTORE, DSTORE, ASTORE or RET
+        if (var > Byte.MAX_VALUE) {
+            byteCodeOffset += 4;
+            bcCodes.add(WIDE);
+            bcCodes.add(new Integer(opcode));
+            bcLocal.add(new Integer(var));
+        } else {
+            if(var > 3 || opcode == 169 /* RET */) {
+                byteCodeOffset += 2;
+                bcCodes.add(new Integer(opcode));
+                bcLocal.add(new Integer(var));
+            } else {
+                byteCodeOffset +=1;
+                switch(opcode) {
+                case 21: // ILOAD
+                case 54: // ISTORE
+                    bcCodes.add(new Integer(opcode + 5 + var));
+                    break;
+                case 22: // LLOAD
+                case 55: // LSTORE
+                    bcCodes.add(new Integer(opcode + 8 + var));
+                    break;
+                case 23: // FLOAD
+                case 56: // FSTORE
+                    bcCodes.add(new Integer(opcode + 11 + var));
+                    break;
+                case 24: // DLOAD
+                case 57: // DSTORE
+                    bcCodes.add(new Integer(opcode + 14 + var));
+                    break;
+                case 25: // A_LOAD
+                case 58: // A_STORE
+                    bcCodes.add(new Integer(opcode + 17 + var));
+                    break;
+                }
+            }
+        }
+        updateRenumbering();
     }
 
 }

Modified: harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPInt.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPInt.java?rev=721077&r1=721076&r2=721077&view=diff
==============================================================================
--- harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPInt.java
(original)
+++ harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPInt.java
Wed Nov 26 21:10:32 2008
@@ -19,14 +19,20 @@
 
 public class CPInt extends CPConstant {
 
-    private int theInt;
+    private final int theInt;
 
     public CPInt(int theInt) {
         this.theInt = theInt;
     }
 
     public int compareTo(Object obj) {
-        return theInt - ((CPInt)obj).theInt;
+        if(theInt > ((CPInt)obj).theInt) {
+            return 1;
+        } else if (theInt == ((CPInt)obj).theInt) {
+            return 0;
+        } else {
+            return -1;
+        }
     }
 
     public int getInt() {

Modified: harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPLong.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPLong.java?rev=721077&r1=721076&r2=721077&view=diff
==============================================================================
--- harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPLong.java
(original)
+++ harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPLong.java
Wed Nov 26 21:10:32 2008
@@ -19,18 +19,28 @@
 
 public class CPLong extends CPConstant {
 
-    private long theLong;
+    private final long theLong;
 
     public CPLong(long theLong) {
         this.theLong = theLong;
     }
 
     public int compareTo(Object obj) {
-        return (int) (theLong - ((CPLong)obj).theLong);
+        if(theLong > ((CPLong)obj).theLong) {
+            return 1;
+        } else if (theLong == ((CPLong)obj).theLong) {
+            return 0;
+        } else {
+            return -1;
+        }
     }
 
     public long getLong() {
         return theLong;
     }
 
+    public String toString() {
+        return "" + theLong;
+    }
+
 }

Modified: harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPMethodOrField.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPMethodOrField.java?rev=721077&r1=721076&r2=721077&view=diff
==============================================================================
--- harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPMethodOrField.java
(original)
+++ harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPMethodOrField.java
Wed Nov 26 21:10:32 2008
@@ -16,10 +16,11 @@
  */
 package org.apache.harmony.pack200;
 
-public class CPMethodOrField implements Comparable {
+public class CPMethodOrField extends ConstantPoolEntry implements Comparable {
 
     private final CPClass className;
     private final CPNameAndType nameAndType;
+    private int indexInClass;
 
     public CPMethodOrField(CPClass className, CPNameAndType nameAndType) {
         this.className = className;
@@ -59,7 +60,23 @@
         return className.getIndex();
     }
 
+    public CPClass getClassName() {
+        return className;
+    }
+
     public int getDescIndex() {
         return nameAndType.getIndex();
     }
+
+    public CPNameAndType getDesc() {
+        return nameAndType;
+    }
+
+    public int getIndexInClass() {
+        return indexInClass;
+    }
+
+    public void setIndexInClass(int index) {
+        indexInClass = index;
+    }
 }
\ No newline at end of file

Modified: harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPNameAndType.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPNameAndType.java?rev=721077&r1=721076&r2=721077&view=diff
==============================================================================
--- harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPNameAndType.java
(original)
+++ harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPNameAndType.java
Wed Nov 26 21:10:32 2008
@@ -45,11 +45,11 @@
     public int compareTo(Object obj) {
         if (obj instanceof CPNameAndType) {
             CPNameAndType nat = (CPNameAndType) obj;
-            int compareName = name.compareTo(nat.name);
-            if (compareName == 0) {
-                return signature.compareTo(nat.signature);
+            int compareSignature = signature.compareTo(nat.signature);;
+            if(compareSignature == 0) {
+                return name.compareTo(nat.name);
             } else {
-                return compareName;
+                return compareSignature;
             }
         }
         return 0;

Modified: harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPSignature.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPSignature.java?rev=721077&r1=721076&r2=721077&view=diff
==============================================================================
--- harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPSignature.java
(original)
+++ harmony/enhanced/classlib/branches/java6/modules/pack200/src/main/java/org/apache/harmony/pack200/CPSignature.java
Wed Nov 26 21:10:32 2008
@@ -23,15 +23,43 @@
     private final CPUTF8 signatureForm;
     private final List classes;
     private final String signature;
+    private final boolean formStartsWithBracket;
 
     public CPSignature(String signature, CPUTF8 signatureForm, List classes) {
         this.signature = signature;
         this.signatureForm = signatureForm;
         this.classes = classes;
+        formStartsWithBracket = signatureForm.toString().startsWith("(");
     }
 
     public int compareTo(Object arg0) {
-        return signature.compareTo(((CPSignature)arg0).signature);
+        if(signature.equals(((CPSignature) arg0).signature)) {
+            return 0;
+        }
+        if (formStartsWithBracket
+                && !((CPSignature) arg0).formStartsWithBracket) {
+            return 1;
+        }
+        if (((CPSignature) arg0).formStartsWithBracket
+                && !formStartsWithBracket) {
+            return -1;
+        }
+        if (classes.size() - ((CPSignature) arg0).classes.size() != 0) {
+            return classes.size() - ((CPSignature) arg0).classes.size();
+        }
+        if (classes.size() > 0) {
+            int classComp = 0;
+            for (int i = classes.size() - 1; i >=0; i--) {
+                CPClass cpClass = (CPClass) classes.get(i);
+                CPClass compareClass = (CPClass) ((CPSignature) arg0).classes
+                        .get(i);
+                classComp = classComp * 10 + cpClass.compareTo(compareClass);
+            }
+            if(classComp != 0) {
+                return classComp;
+            }
+        }
+        return signature.compareTo(((CPSignature) arg0).signature);
     }
 
     public int getIndexInCpUtf8() {



Mime
View raw message