提交 e50d0d29 编写于 作者: K ksrini

8044046: [asm] refresh internal ASM version to v5.0.3

Reviewed-by: coffeys, psandoz, sundar
上级 4eb6a89c
...@@ -785,11 +785,29 @@ public class ClassWriter extends ClassVisitor { ...@@ -785,11 +785,29 @@ public class ClassWriter extends ClassVisitor {
if (innerClasses == null) { if (innerClasses == null) {
innerClasses = new ByteVector(); innerClasses = new ByteVector();
} }
++innerClassesCount; // Sec. 4.7.6 of the JVMS states "Every CONSTANT_Class_info entry in the
innerClasses.putShort(name == null ? 0 : newClass(name)); // constant_pool table which represents a class or interface C that is
innerClasses.putShort(outerName == null ? 0 : newClass(outerName)); // not a package member must have exactly one corresponding entry in the
innerClasses.putShort(innerName == null ? 0 : newUTF8(innerName)); // classes array". To avoid duplicates we keep track in the intVal field
innerClasses.putShort(access); // of the Item of each CONSTANT_Class_info entry C whether an inner
// class entry has already been added for C (this field is unused for
// class entries, and changing its value does not change the hashcode
// and equality tests). If so we store the index of this inner class
// entry (plus one) in intVal. This hack allows duplicate detection in
// O(1) time.
Item nameItem = newClassItem(name);
if (nameItem.intVal == 0) {
++innerClassesCount;
innerClasses.putShort(nameItem.index);
innerClasses.putShort(outerName == null ? 0 : newClass(outerName));
innerClasses.putShort(innerName == null ? 0 : newUTF8(innerName));
innerClasses.putShort(access);
nameItem.intVal = innerClassesCount;
} else {
// Compare the inner classes entry nameItem.intVal - 1 with the
// arguments of this method and throw an exception if there is a
// difference?
}
} }
@Override @Override
......
...@@ -1455,16 +1455,20 @@ final class Frame { ...@@ -1455,16 +1455,20 @@ final class Frame {
| cw.getMergedType(t & BASE_VALUE, u & BASE_VALUE); | cw.getMergedType(t & BASE_VALUE, u & BASE_VALUE);
} else { } else {
// if u and t are array types, but not with the same element // if u and t are array types, but not with the same element
// type, merge(u,t)=java/lang/Object // type, merge(u,t) = dim(u) - 1 | java/lang/Object
v = OBJECT | cw.addType("java/lang/Object"); int vdim = ELEMENT_OF + (u & DIM);
v = vdim | OBJECT | cw.addType("java/lang/Object");
} }
} else if ((t & BASE_KIND) == OBJECT || (t & DIM) != 0) { } else if ((t & BASE_KIND) == OBJECT || (t & DIM) != 0) {
// if t is any other reference or array type, the merged type // if t is any other reference or array type, the merged type
// is Object, or min(dim(u), dim(t)) | java/lang/Object is u // is min(udim, tdim) | java/lang/Object, where udim is the
// and t have different array dimensions // array dimension of u, minus 1 if u is an array type with a
int tdim = t & DIM; // primitive element type (and similarly for tdim).
int udim = u & DIM; int tdim = (((t & DIM) == 0 || (t & BASE_KIND) == OBJECT) ? 0
v = (udim != tdim ? Math.min(tdim, udim) : 0) | OBJECT : ELEMENT_OF) + (t & DIM);
int udim = (((u & DIM) == 0 || (u & BASE_KIND) == OBJECT) ? 0
: ELEMENT_OF) + (u & DIM);
v = Math.min(tdim, udim) | OBJECT
| cw.addType("java/lang/Object"); | cw.addType("java/lang/Object");
} else { } else {
// if t is any other type, merge(u,t)=TOP // if t is any other type, merge(u,t)=TOP
......
...@@ -237,9 +237,10 @@ final class Item { ...@@ -237,9 +237,10 @@ final class Item {
this.strVal2 = strVal2; this.strVal2 = strVal2;
this.strVal3 = strVal3; this.strVal3 = strVal3;
switch (type) { switch (type) {
case ClassWriter.CLASS:
this.intVal = 0; // intVal of a class must be zero, see visitInnerClass
case ClassWriter.UTF8: case ClassWriter.UTF8:
case ClassWriter.STR: case ClassWriter.STR:
case ClassWriter.CLASS:
case ClassWriter.MTYPE: case ClassWriter.MTYPE:
case ClassWriter.TYPE_NORMAL: case ClassWriter.TYPE_NORMAL:
hashCode = 0x7FFFFFFF & (type + strVal1.hashCode()); hashCode = 0x7FFFFFFF & (type + strVal1.hashCode());
......
...@@ -502,7 +502,7 @@ public class Label { ...@@ -502,7 +502,7 @@ public class Label {
void addToSubroutine(final long id, final int nbSubroutines) { void addToSubroutine(final long id, final int nbSubroutines) {
if ((status & VISITED) == 0) { if ((status & VISITED) == 0) {
status |= VISITED; status |= VISITED;
srcAndRefPositions = new int[(nbSubroutines - 1) / 32 + 1]; srcAndRefPositions = new int[nbSubroutines / 32 + 1];
} }
srcAndRefPositions[(int) (id >>> 32)] |= (int) id; srcAndRefPositions[(int) (id >>> 32)] |= (int) id;
} }
......
...@@ -1430,6 +1430,14 @@ class MethodWriter extends MethodVisitor { ...@@ -1430,6 +1430,14 @@ class MethodWriter extends MethodVisitor {
@Override @Override
public void visitMaxs(final int maxStack, final int maxLocals) { public void visitMaxs(final int maxStack, final int maxLocals) {
if (resize) {
// replaces the temporary jump opcodes introduced by Label.resolve.
if (ClassReader.RESIZE) {
resizeInstructions();
} else {
throw new RuntimeException("Method code too large!");
}
}
if (ClassReader.FRAMES && compute == FRAMES) { if (ClassReader.FRAMES && compute == FRAMES) {
// completes the control flow graph with exception handler blocks // completes the control flow graph with exception handler blocks
Handler handler = firstHandler; Handler handler = firstHandler;
...@@ -1987,43 +1995,43 @@ class MethodWriter extends MethodVisitor { ...@@ -1987,43 +1995,43 @@ class MethodWriter extends MethodVisitor {
stackMap.putByte(v); stackMap.putByte(v);
} }
} else { } else {
StringBuffer buf = new StringBuffer(); StringBuilder sb = new StringBuilder();
d >>= 28; d >>= 28;
while (d-- > 0) { while (d-- > 0) {
buf.append('['); sb.append('[');
} }
if ((t & Frame.BASE_KIND) == Frame.OBJECT) { if ((t & Frame.BASE_KIND) == Frame.OBJECT) {
buf.append('L'); sb.append('L');
buf.append(cw.typeTable[t & Frame.BASE_VALUE].strVal1); sb.append(cw.typeTable[t & Frame.BASE_VALUE].strVal1);
buf.append(';'); sb.append(';');
} else { } else {
switch (t & 0xF) { switch (t & 0xF) {
case 1: case 1:
buf.append('I'); sb.append('I');
break; break;
case 2: case 2:
buf.append('F'); sb.append('F');
break; break;
case 3: case 3:
buf.append('D'); sb.append('D');
break; break;
case 9: case 9:
buf.append('Z'); sb.append('Z');
break; break;
case 10: case 10:
buf.append('B'); sb.append('B');
break; break;
case 11: case 11:
buf.append('C'); sb.append('C');
break; break;
case 12: case 12:
buf.append('S'); sb.append('S');
break; break;
default: default:
buf.append('J'); sb.append('J');
} }
} }
stackMap.putByte(7).putShort(cw.newClass(buf.toString())); stackMap.putByte(7).putShort(cw.newClass(sb.toString()));
} }
} }
} }
...@@ -2051,14 +2059,6 @@ class MethodWriter extends MethodVisitor { ...@@ -2051,14 +2059,6 @@ class MethodWriter extends MethodVisitor {
if (classReaderOffset != 0) { if (classReaderOffset != 0) {
return 6 + classReaderLength; return 6 + classReaderLength;
} }
if (resize) {
// replaces the temporary jump opcodes introduced by Label.resolve.
if (ClassReader.RESIZE) {
resizeInstructions();
} else {
throw new RuntimeException("Method code too large!");
}
}
int size = 8; int size = 8;
if (code.length > 0) { if (code.length > 0) {
if (code.length > 65536) { if (code.length > 65536) {
...@@ -2715,49 +2715,50 @@ class MethodWriter extends MethodVisitor { ...@@ -2715,49 +2715,50 @@ class MethodWriter extends MethodVisitor {
} }
} }
// recomputes the stack map frames // updates the stack map frame labels
if (frameCount > 0) { if (compute == FRAMES) {
if (compute == FRAMES) { Label l = labels;
frameCount = 0; while (l != null) {
stackMap = null;
previousFrame = null;
frame = null;
Frame f = new Frame();
f.owner = labels;
Type[] args = Type.getArgumentTypes(descriptor);
f.initInputFrame(cw, access, args, maxLocals);
visitFrame(f);
Label l = labels;
while (l != null) {
/*
* here we need the original label position. getNewOffset
* must therefore never have been called for this label.
*/
u = l.position - 3;
if ((l.status & Label.STORE) != 0 || (u >= 0 && resize[u])) {
getNewOffset(allIndexes, allSizes, l);
// TODO update offsets in UNINITIALIZED values
visitFrame(l.frame);
}
l = l.successor;
}
} else {
/* /*
* Resizing an existing stack map frame table is really hard. * Detects the labels that are just after an IF instruction that
* Not only the table must be parsed to update the offets, but * has been resized with the IFNOT GOTO_W pattern. These labels
* new frames may be needed for jump instructions that were * are now the target of a jump instruction (the IFNOT
* inserted by this method. And updating the offsets or * instruction). Note that we need the original label position
* inserting frames can change the format of the following * here. getNewOffset must therefore never have been called for
* frames, in case of packed frames. In practice the whole table * this label.
* must be recomputed. For this the frames are marked as
* potentially invalid. This will cause the whole class to be
* reread and rewritten with the COMPUTE_FRAMES option (see the
* ClassWriter.toByteArray method). This is not very efficient
* but is much easier and requires much less code than any other
* method I can think of.
*/ */
cw.invalidFrames = true; u = l.position - 3;
if (u >= 0 && resize[u]) {
l.status |= Label.TARGET;
}
getNewOffset(allIndexes, allSizes, l);
l = l.successor;
} }
// Update the offsets in the uninitialized types
for (i = 0; i < cw.typeTable.length; ++i) {
Item item = cw.typeTable[i];
if (item != null && item.type == ClassWriter.TYPE_UNINIT) {
item.intVal = getNewOffset(allIndexes, allSizes, 0,
item.intVal);
}
}
// The stack map frames are not serialized yet, so we don't need
// to update them. They will be serialized in visitMaxs.
} else if (frameCount > 0) {
/*
* Resizing an existing stack map frame table is really hard. Not
* only the table must be parsed to update the offets, but new
* frames may be needed for jump instructions that were inserted by
* this method. And updating the offsets or inserting frames can
* change the format of the following frames, in case of packed
* frames. In practice the whole table must be recomputed. For this
* the frames are marked as potentially invalid. This will cause the
* whole class to be reread and rewritten with the COMPUTE_FRAMES
* option (see the ClassWriter.toByteArray method). This is not very
* efficient but is much easier and requires much less code than any
* other method I can think of.
*/
cw.invalidFrames = true;
} }
// updates the exception handler block labels // updates the exception handler block labels
Handler h = firstHandler; Handler h = firstHandler;
......
...@@ -585,11 +585,11 @@ public class Type { ...@@ -585,11 +585,11 @@ public class Type {
case DOUBLE: case DOUBLE:
return "double"; return "double";
case ARRAY: case ARRAY:
StringBuffer b = new StringBuffer(getElementType().getClassName()); StringBuilder sb = new StringBuilder(getElementType().getClassName());
for (int i = getDimensions(); i > 0; --i) { for (int i = getDimensions(); i > 0; --i) {
b.append("[]"); sb.append("[]");
} }
return b.toString(); return sb.toString();
case OBJECT: case OBJECT:
return new String(buf, off, len).replace('/', '.'); return new String(buf, off, len).replace('/', '.');
default: default:
......
...@@ -1089,7 +1089,7 @@ public class InstructionAdapter extends MethodVisitor { ...@@ -1089,7 +1089,7 @@ public class InstructionAdapter extends MethodVisitor {
@Deprecated @Deprecated
public void invokestatic(final String owner, final String name, public void invokestatic(final String owner, final String name,
final String desc) { final String desc) {
if (api < Opcodes.ASM5) { if (api >= Opcodes.ASM5) {
invokestatic(owner, name, desc, false); invokestatic(owner, name, desc, false);
return; return;
} }
......
...@@ -205,7 +205,7 @@ public class Method { ...@@ -205,7 +205,7 @@ public class Method {
} }
String returnType = method.substring(0, space); String returnType = method.substring(0, space);
String methodName = method.substring(space + 1, start - 1).trim(); String methodName = method.substring(space + 1, start - 1).trim();
StringBuffer sb = new StringBuffer(); StringBuilder sb = new StringBuilder();
sb.append('('); sb.append('(');
int p; int p;
do { do {
...@@ -229,7 +229,7 @@ public class Method { ...@@ -229,7 +229,7 @@ public class Method {
return type; return type;
} }
StringBuffer sb = new StringBuffer(); StringBuilder sb = new StringBuilder();
int index = 0; int index = 0;
while ((index = type.indexOf("[]", index) + 1) > 0) { while ((index = type.indexOf("[]", index) + 1) > 0) {
sb.append('['); sb.append('[');
......
...@@ -147,17 +147,17 @@ public abstract class Remapper { ...@@ -147,17 +147,17 @@ public abstract class Remapper {
} }
Type[] args = Type.getArgumentTypes(desc); Type[] args = Type.getArgumentTypes(desc);
StringBuffer s = new StringBuffer("("); StringBuilder sb = new StringBuilder("(");
for (int i = 0; i < args.length; i++) { for (int i = 0; i < args.length; i++) {
s.append(mapDesc(args[i].getDescriptor())); sb.append(mapDesc(args[i].getDescriptor()));
} }
Type returnType = Type.getReturnType(desc); Type returnType = Type.getReturnType(desc);
if (returnType == Type.VOID_TYPE) { if (returnType == Type.VOID_TYPE) {
s.append(")V"); sb.append(")V");
return s.toString(); return sb.toString();
} }
s.append(')').append(mapDesc(returnType.getDescriptor())); sb.append(')').append(mapDesc(returnType.getDescriptor()));
return s.toString(); return sb.toString();
} }
public Object mapValue(Object value) { public Object mapValue(Object value) {
......
...@@ -239,7 +239,9 @@ public class SerialVersionUIDAdder extends ClassVisitor { ...@@ -239,7 +239,9 @@ public class SerialVersionUIDAdder extends ClassVisitor {
if (computeSVUID) { if (computeSVUID) {
this.name = name; this.name = name;
this.access = access; this.access = access;
this.interfaces = Arrays.copyOf(interfaces, interfaces.length); this.interfaces = new String[interfaces.length];
System.arraycopy(interfaces, 0, this.interfaces, 0,
interfaces.length);
} }
super.visit(version, access, name, signature, superName, interfaces); super.visit(version, access, name, signature, superName, interfaces);
......
...@@ -351,6 +351,7 @@ public class MethodNode extends MethodVisitor { ...@@ -351,6 +351,7 @@ public class MethodNode extends MethodVisitor {
} }
@Override @Override
@SuppressWarnings("serial")
public AnnotationVisitor visitAnnotationDefault() { public AnnotationVisitor visitAnnotationDefault() {
return new AnnotationNode(new ArrayList<Object>(0) { return new AnnotationNode(new ArrayList<Object>(0) {
@Override @Override
......
...@@ -66,6 +66,7 @@ import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode; ...@@ -66,6 +66,7 @@ import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
* @author Bing Ran * @author Bing Ran
* @author Eric Bruneton * @author Eric Bruneton
*/ */
@SuppressWarnings("serial")
public class AnalyzerException extends Exception { public class AnalyzerException extends Exception {
public final AbstractInsnNode node; public final AbstractInsnNode node;
......
...@@ -754,14 +754,14 @@ public class Frame<V extends Value> { ...@@ -754,14 +754,14 @@ public class Frame<V extends Value> {
*/ */
@Override @Override
public String toString() { public String toString() {
StringBuffer b = new StringBuffer(); StringBuilder sb = new StringBuilder();
for (int i = 0; i < getLocals(); ++i) { for (int i = 0; i < getLocals(); ++i) {
b.append(getLocal(i)); sb.append(getLocal(i));
} }
b.append(' '); sb.append(' ');
for (int i = 0; i < getStackSize(); ++i) { for (int i = 0; i < getStackSize(); ++i) {
b.append(getStack(i).toString()); sb.append(getStack(i).toString());
} }
return b.toString(); return sb.toString();
} }
} }
...@@ -206,7 +206,6 @@ public class ASMifier extends Printer { ...@@ -206,7 +206,6 @@ public class ASMifier extends Printer {
} }
text.add("import java.util.*;\n"); text.add("import java.util.*;\n");
text.add("import jdk.internal.org.objectweb.asm.*;\n"); text.add("import jdk.internal.org.objectweb.asm.*;\n");
text.add("import jdk.internal.org.objectweb.asm.attrs.*;\n");
text.add("public class " + simpleName + "Dump implements Opcodes {\n\n"); text.add("public class " + simpleName + "Dump implements Opcodes {\n\n");
text.add("public static byte[] dump () throws Exception {\n\n"); text.add("public static byte[] dump () throws Exception {\n\n");
text.add("ClassWriter cw = new ClassWriter(0);\n"); text.add("ClassWriter cw = new ClassWriter(0);\n");
......
...@@ -298,26 +298,26 @@ public class CheckClassAdapter extends ClassVisitor { ...@@ -298,26 +298,26 @@ public class CheckClassAdapter extends ClassVisitor {
for (int j = 0; j < method.instructions.size(); ++j) { for (int j = 0; j < method.instructions.size(); ++j) {
method.instructions.get(j).accept(mv); method.instructions.get(j).accept(mv);
StringBuffer s = new StringBuffer(); StringBuilder sb = new StringBuilder();
Frame<BasicValue> f = frames[j]; Frame<BasicValue> f = frames[j];
if (f == null) { if (f == null) {
s.append('?'); sb.append('?');
} else { } else {
for (int k = 0; k < f.getLocals(); ++k) { for (int k = 0; k < f.getLocals(); ++k) {
s.append(getShortName(f.getLocal(k).toString())) sb.append(getShortName(f.getLocal(k).toString()))
.append(' '); .append(' ');
} }
s.append(" : "); sb.append(" : ");
for (int k = 0; k < f.getStackSize(); ++k) { for (int k = 0; k < f.getStackSize(); ++k) {
s.append(getShortName(f.getStack(k).toString())) sb.append(getShortName(f.getStack(k).toString()))
.append(' '); .append(' ');
} }
} }
while (s.length() < method.maxStack + method.maxLocals + 1) { while (sb.length() < method.maxStack + method.maxLocals + 1) {
s.append(' '); sb.append(' ');
} }
pw.print(Integer.toString(j + 100000).substring(1)); pw.print(Integer.toString(j + 100000).substring(1));
pw.print(" " + s + " : " + t.text.get(t.text.size() - 1)); pw.print(" " + sb + " : " + t.text.get(t.text.size() - 1));
} }
for (int j = 0; j < method.tryCatchBlocks.size(); ++j) { for (int j = 0; j < method.tryCatchBlocks.size(); ++j) {
method.tryCatchBlocks.get(j).accept(mv); method.tryCatchBlocks.get(j).accept(mv);
......
...@@ -443,7 +443,7 @@ public class Textifier extends Printer { ...@@ -443,7 +443,7 @@ public class Textifier extends Printer {
} }
buf.append(tab); buf.append(tab);
appendAccess(access); appendAccess(access & ~Opcodes.ACC_VOLATILE);
if ((access & Opcodes.ACC_NATIVE) != 0) { if ((access & Opcodes.ACC_NATIVE) != 0) {
buf.append("native "); buf.append("native ");
} }
......
Path: . Path: .
Working Copy Root Path: /hudson/jobs/objectweb-pull/workspace/asm-svn-2014-03-12 Working Copy Root Path: /hudson/jobs/objectweb-pull/workspace/asm-svn-2014-05-27
URL: file:///svnroot/asm/trunk/asm URL: file:///svnroot/asm/trunk/asm
Repository Root: file:///svnroot/asm Repository Root: file:///svnroot/asm
Repository UUID: 271bd773-ee82-43a6-9b2b-1890ed8ce7f9 Repository UUID: 271bd773-ee82-43a6-9b2b-1890ed8ce7f9
Revision: 1721 Revision: 1748
Node Kind: directory Node Kind: directory
Schedule: normal Schedule: normal
Last Changed Author: ebruneton Last Changed Author: ebruneton
Last Changed Rev: 1721 Last Changed Rev: 1747
Last Changed Date: 2014-03-02 17:25:35 +0100 (Sun, 02 Mar 2014) Last Changed Date: 2014-05-24 10:22:13 +0200 (Sat, 24 May 2014)
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册