[jboss-cvs] JBossAS SVN: r105877 - in projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect: util/objectweb/asm and 1 other directory.
jboss-cvs-commits at lists.jboss.org
jboss-cvs-commits at lists.jboss.org
Wed Jun 9 12:51:34 EDT 2010
Author: kabir.khan at jboss.com
Date: 2010-06-09 12:51:33 -0400 (Wed, 09 Jun 2010)
New Revision: 105877
Removed:
projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassAdapter.java
Modified:
projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmBehaviourBytes.java
projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmClassBytes.java
projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmFieldBytes.java
projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/Util.java
projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassReader.java
Log:
[JBREFLECT-125] Don't load/visit things we are not interested in
Modified: projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmBehaviourBytes.java
===================================================================
--- projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmBehaviourBytes.java 2010-06-09 16:49:36 UTC (rev 105876)
+++ projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmBehaviourBytes.java 2010-06-09 16:51:33 UTC (rev 105877)
@@ -27,6 +27,7 @@
import org.jboss.reflect.plugins.bytecode.bytes.BehaviourBytes;
import org.jboss.reflect.util.objectweb.asm.AnnotationVisitor;
+import org.jboss.reflect.util.objectweb.asm.ClassReader;
import org.jboss.reflect.util.objectweb.asm.MethodVisitor;
/**
@@ -70,14 +71,14 @@
public Annotation[][] getParameterAnnotations()
{
LoadParameterAnnotationsVisitor visitor = new LoadParameterAnnotationsVisitor();
- getClazz().getReader().accept(visitor, AsmClassBytes.STANDARD_FLAGS);
+ getClazz().getReader().accept(visitor, AsmClassBytes.STANDARD_FLAGS | ClassReader.INCLUDE_MEHOD_PARAMETER_ANNOTATIONS);
return visitor.getAnnotations();
}
public Annotation[] getAnnotations()
{
LoadBehaviourAnnotationsVisitor visitor = new LoadBehaviourAnnotationsVisitor();
- getClazz().getReader().accept(visitor, AsmClassBytes.STANDARD_FLAGS);
+ getClazz().getReader().accept(visitor, AsmClassBytes.STANDARD_FLAGS | ClassReader.INCLUDE_METHOD_ANNOTATIONS);
return visitor.getAnnotations();
}
Modified: projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmClassBytes.java
===================================================================
--- projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmClassBytes.java 2010-06-09 16:49:36 UTC (rev 105876)
+++ projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmClassBytes.java 2010-06-09 16:51:33 UTC (rev 105877)
@@ -51,8 +51,11 @@
*/
class AsmClassBytes extends JBossObject implements ClassBytes
{
- static final int STANDARD_FLAGS = ClassReader.SKIP_CODE | ClassReader.SKIP_DEBUG | ClassReader.SKIP_FRAMES;
+ static final int STANDARD_FLAGS = ClassReader.SKIP_CODE | ClassReader.SKIP_DEBUG | ClassReader.SKIP_FRAMES
+ | ClassReader.SKIP_OUTER_CLASSES | ClassReader.SKIP_UNKNOWN_ATTRIBUTES;
+ static final int READ_FIELD_FLAGS = STANDARD_FLAGS | ClassReader.INCLUDE_FIELD_OVERVIEW;
+
static final ClassReaderCacheFactory CACHE_FACTORY = ClassReaderCacheFactory.createFromProperties();
static final FieldBytes[] NO_FIELDS = new FieldBytes[0];
@@ -105,7 +108,7 @@
if (fieldBytes == null)
{
FieldsVisitor visitor = new FieldsVisitor();
- getReader().accept(visitor, STANDARD_FLAGS);
+ getReader().accept(visitor, STANDARD_FLAGS | ClassReader.INCLUDE_FIELD_OVERVIEW);
fieldBytes = visitor.getFieldBytes();
}
return fieldBytes;
@@ -202,21 +205,21 @@
public String getGenericSignature()
{
ClassSignatureVisitor visitor = new ClassSignatureVisitor();
- getReader().accept(visitor, STANDARD_FLAGS);
+ getReader().accept(visitor, STANDARD_FLAGS | ClassReader.INCLUDE_HEADER);
return visitor.getSignature();
}
public Annotation[] getAnnotations()
{
AnnotationsVisitor visitor = new AnnotationsVisitor();
- getReader().accept(visitor, STANDARD_FLAGS);
+ getReader().accept(visitor, STANDARD_FLAGS | ClassReader.INCLUDE_CLASS_ANNOTATIONS);
return visitor.getAnnotations();
}
private void initMethodsAndConstructors()
{
ConstructorAndMethodsVisitor visitor = new ConstructorAndMethodsVisitor();
- getReader().accept(visitor, STANDARD_FLAGS);
+ getReader().accept(visitor, STANDARD_FLAGS | ClassReader.INCLUDE_METHOD_OVERVIEW);
methodBytes = visitor.getMethodBytes();
constructorBytes = visitor.getConstructorBytes();
}
Modified: projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmFieldBytes.java
===================================================================
--- projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmFieldBytes.java 2010-06-09 16:49:36 UTC (rev 105876)
+++ projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/AsmFieldBytes.java 2010-06-09 16:51:33 UTC (rev 105877)
@@ -27,6 +27,7 @@
import org.jboss.reflect.plugins.bytecode.bytes.FieldBytes;
import org.jboss.reflect.util.objectweb.asm.AnnotationVisitor;
+import org.jboss.reflect.util.objectweb.asm.ClassReader;
import org.jboss.reflect.util.objectweb.asm.FieldVisitor;
import org.jboss.reflect.util.objectweb.asm.Opcodes;
@@ -46,7 +47,7 @@
public Annotation[] getAnnotations()
{
LoadFieldAnnotationsVisitor visitor = new LoadFieldAnnotationsVisitor();
- getClazz().getReader().accept(visitor, AsmClassBytes.STANDARD_FLAGS);
+ getClazz().getReader().accept(visitor, AsmClassBytes.STANDARD_FLAGS | ClassReader.INCLUDE_FIELD_ANNOTATIONS);
return visitor.getAnnotations();
}
Modified: projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/Util.java
===================================================================
--- projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/Util.java 2010-06-09 16:49:36 UTC (rev 105876)
+++ projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/plugins/bytecode/bytes/asm/Util.java 2010-06-09 16:51:33 UTC (rev 105877)
@@ -24,7 +24,6 @@
import java.lang.annotation.Annotation;
import java.lang.reflect.Array;
import java.util.ArrayList;
-import java.util.EnumSet;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@@ -33,8 +32,8 @@
import org.jboss.reflect.plugins.bytecode.bytes.ClassBytes;
import org.jboss.reflect.util.objectweb.asm.AnnotationVisitor;
import org.jboss.reflect.util.objectweb.asm.Attribute;
+import org.jboss.reflect.util.objectweb.asm.ClassReader;
import org.jboss.reflect.util.objectweb.asm.ClassVisitor;
-import org.jboss.reflect.util.objectweb.asm.ClassVisitorParts;
import org.jboss.reflect.util.objectweb.asm.FieldVisitor;
import org.jboss.reflect.util.objectweb.asm.Label;
import org.jboss.reflect.util.objectweb.asm.MethodVisitor;
@@ -179,7 +178,7 @@
{
defaults = new DefaultAnnotationAttributeReader(loader, allAnnotationAttributesReader);
if (classBytes instanceof AsmClassBytes)
- ((AsmClassBytes)classBytes).getReader().accept(defaults, AsmClassBytes.STANDARD_FLAGS);
+ ((AsmClassBytes)classBytes).getReader().accept(defaults, AsmClassBytes.STANDARD_FLAGS | ClassReader.INCLUDE_DEFAULT_ANNOTATION_VALUES);
}
Object value = defaults.defaultAttributesByName.get(name);
if (value == null)
@@ -206,8 +205,6 @@
{
Map<String, String> returnTypesByName = new HashMap<String, String>();
- final static EnumSet<ClassVisitorParts> PARTS = EnumSet.noneOf(ClassVisitorParts.class);
-
@Override
public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions)
{
@@ -217,11 +214,6 @@
}
return null;
}
-
- public EnumSet<ClassVisitorParts> getParts()
- {
- return PARTS;
- }
}
private static class DefaultAnnotationAttributeReader extends EmptyVisitor
@@ -231,8 +223,6 @@
final ClassLoader loader;
final AllAnnotationAttributesReader allAnnotationAttributesReader;
- final static EnumSet<ClassVisitorParts> PARTS = EnumSet.noneOf(ClassVisitorParts.class);
-
public DefaultAnnotationAttributeReader(ClassLoader loader, AllAnnotationAttributesReader allAnnotationAttributesReader)
{
this.loader = loader;
@@ -245,10 +235,6 @@
return new AnnotationDefaultReader(name);
}
- public EnumSet<ClassVisitorParts> getParts()
- {
- return PARTS;
- }
// @Override
// public void visitEnd()
// {
Deleted: projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassAdapter.java
===================================================================
--- projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassAdapter.java 2010-06-09 16:49:36 UTC (rev 105876)
+++ projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassAdapter.java 2010-06-09 16:51:33 UTC (rev 105877)
@@ -1,121 +0,0 @@
-/***
- * ASM: a very small and fast Java bytecode manipulation framework
- * Copyright (c) 2000-2007 INRIA, France Telecom
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- */
-package org.jboss.reflect.util.objectweb.asm;
-
-/**
- * An empty {@link ClassVisitor} that delegates to another {@link ClassVisitor}.
- * This class can be used as a super class to quickly implement usefull class
- * adapter classes, just by overriding the necessary methods.
- *
- * @author Eric Bruneton
- */
-public class ClassAdapter implements ClassVisitor {
-
- /**
- * The {@link ClassVisitor} to which this adapter delegates calls.
- */
- protected ClassVisitor cv;
-
- /**
- * Constructs a new {@link ClassAdapter} object.
- *
- * @param cv the class visitor to which this adapter must delegate calls.
- */
- public ClassAdapter(final ClassVisitor cv) {
- this.cv = cv;
- }
-
- public void visit(
- final int version,
- final int access,
- final String name,
- final String signature,
- final String superName,
- final String[] interfaces)
- {
- cv.visit(version, access, name, signature, superName, interfaces);
- }
-
- public void visitSource(final String source, final String debug) {
- cv.visitSource(source, debug);
- }
-
- public void visitOuterClass(
- final String owner,
- final String name,
- final String desc)
- {
- cv.visitOuterClass(owner, name, desc);
- }
-
- public AnnotationVisitor visitAnnotation(
- final String desc,
- final boolean visible)
- {
- return cv.visitAnnotation(desc, visible);
- }
-
- public void visitAttribute(final Attribute attr) {
- cv.visitAttribute(attr);
- }
-
- public void visitInnerClass(
- final String name,
- final String outerName,
- final String innerName,
- final int access)
- {
- cv.visitInnerClass(name, outerName, innerName, access);
- }
-
- public FieldVisitor visitField(
- final int access,
- final String name,
- final String desc,
- final String signature,
- final Object value)
- {
- return cv.visitField(access, name, desc, signature, value);
- }
-
- public MethodVisitor visitMethod(
- final int access,
- final String name,
- final String desc,
- final String signature,
- final String[] exceptions)
- {
- return cv.visitMethod(access, name, desc, signature, exceptions);
- }
-
- public void visitEnd() {
- cv.visitEnd();
- }
-}
Modified: projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassReader.java
===================================================================
--- projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassReader.java 2010-06-09 16:49:36 UTC (rev 105876)
+++ projects/jboss-reflect/trunk/src/main/java/org/jboss/reflect/util/objectweb/asm/ClassReader.java 2010-06-09 16:51:33 UTC (rev 105877)
@@ -104,7 +104,36 @@
* ClassWriter which degrades performances quite a lot).
*/
public static final int EXPAND_FRAMES = 8;
+
+ //Extra flags for performance
+ public static final int SKIP_OUTER_CLASSES = 32;
+
+ public static final int SKIP_INNER_CLASSES = 64;
+ public static final int SKIP_UNKNOWN_ATTRIBUTES = 128;
+
+ public static final int INCLUDE_HEADER = 256;
+
+ public static final int INCLUDE_CLASS_ANNOTATIONS = 512;
+
+ public static final int INCLUDE_FIELD_OVERVIEW = 1024;
+
+ public static final int INCLUDE_FIELD_ANNOTATIONS = 2048;
+
+ public static final int INCLUDE_FIELD_UNKNOWN_ATTRIBUTES = 4096;
+
+ public static final int INCLUDE_METHOD_OVERVIEW = 8192;
+
+ public static final int INCLUDE_METHOD_ANNOTATIONS = 16384;
+
+ public static final int INCLUDE_MEHOD_PARAMETER_ANNOTATIONS = 32768;
+
+ public static final int INCLUDE_METHOD_UNKNOWN_ATTRIBUTES = 65536;
+
+ public static final int INCLUDE_DEFAULT_ANNOTATION_VALUES = 131072;
+
+
+
/**
* The class to be parsed. <i>The content of this array must not be
* modified. This field is intended for {@link Attribute} sub classes, and
@@ -462,40 +491,42 @@
*/
public void accept(final ClassVisitor classVisitor, final Attribute[] attrs, final int flags)
{
- byte[] b = this.b; // the bytecode array
char[] c = new char[maxStringLength]; // buffer used to read strings
- int i, j, k; // loop variables
+ int i, j; // loop variables
int u, v, w; // indexes in b
Attribute attr;
int access;
String name;
- String desc;
String attrName;
String signature;
int anns = 0;
int ianns = 0;
Attribute cattrs = null;
+ boolean skipDebug = (flags & SKIP_DEBUG) != 0;
+ boolean skipOuterClasses = (flags & SKIP_OUTER_CLASSES) != 0;
+ boolean skipInnerClasses = (flags & SKIP_INNER_CLASSES) != 0;
+ boolean includeHeader = (flags & INCLUDE_HEADER) != 0;
+ boolean includeClassAnnotations = (flags & INCLUDE_CLASS_ANNOTATIONS) != 0;
+ boolean skipUnknownAttributes = (flags & SKIP_UNKNOWN_ATTRIBUTES) != 0;
+
// visits the header
u = header;
access = readUnsignedShort(u);
name = readClass(u + 2, c);
v = items[readUnsignedShort(u + 4)];
- String superClassName = v == 0 ? null : readUTF8(v, c);
+ String superClassName = v == 0 || includeHeader ? null : readUTF8(v, c);
String[] implementedItfs = new String[readUnsignedShort(u + 6)];
w = 0;
u += 8;
for (i = 0; i < implementedItfs.length; ++i)
{
- implementedItfs[i] = readClass(u, c);
+ if (includeHeader)
+ implementedItfs[i] = readClass(u, c);
u += 2;
}
- boolean skipCode = (flags & SKIP_CODE) != 0;
- boolean skipDebug = (flags & SKIP_DEBUG) != 0;
- boolean unzip = (flags & EXPAND_FRAMES) != 0;
-
// skips fields and methods
v = u;
i = readUnsignedShort(v);
@@ -537,7 +568,8 @@
// (based on frequencies observed on typical classes)
if ("SourceFile".equals(attrName))
{
- sourceFile = readUTF8(v + 6, c);
+ if (!skipDebug)
+ sourceFile = readUTF8(v + 6, c);
}
else if ("InnerClasses".equals(attrName))
{
@@ -545,19 +577,23 @@
}
else if ("EnclosingMethod".equals(attrName))
{
- enclosingOwner = readClass(v + 6, c);
- int item = readUnsignedShort(v + 8);
- if (item != 0)
+ if (!skipOuterClasses)
{
- enclosingName = readUTF8(items[item], c);
- enclosingDesc = readUTF8(items[item] + 2, c);
+ enclosingOwner = readClass(v + 6, c);
+ int item = readUnsignedShort(v + 8);
+ if (item != 0)
+ {
+ enclosingName = readUTF8(items[item], c);
+ enclosingDesc = readUTF8(items[item] + 2, c);
+ }
}
}
else if (SIGNATURES && "Signature".equals(attrName))
{
- signature = readUTF8(v + 6, c);
+ if (includeHeader)
+ signature = readUTF8(v + 6, c);
}
- else if (ANNOTATIONS && "RuntimeVisibleAnnotations".equals(attrName))
+ else if (includeClassAnnotations && "RuntimeVisibleAnnotations".equals(attrName))
{
anns = v + 6;
}
@@ -571,14 +607,17 @@
}
else if ("SourceDebugExtension".equals(attrName))
{
- int len = readInt(v + 2);
- sourceDebug = readUTF(v + 6, len, new char[len]);
+ if (!skipDebug)
+ {
+ int len = readInt(v + 2);
+ sourceDebug = readUTF(v + 6, len, new char[len]);
+ }
}
- else if (ANNOTATIONS && "RuntimeInvisibleAnnotations".equals(attrName))
+ else if (includeClassAnnotations && "RuntimeInvisibleAnnotations".equals(attrName))
{
ianns = v + 6;
}
- else
+ else if (!skipUnknownAttributes)
{
attr = readAttribute(attrs, attrName, v + 6, readInt(v + 2), c, -1, null);
if (attr != null)
@@ -589,8 +628,11 @@
}
v += 6 + readInt(v + 2);
}
+
+
// calls the visit method
- classVisitor.visit(readInt(4), access, name, signature, superClassName, implementedItfs);
+ if (includeHeader)
+ classVisitor.visit(readInt(4), access, name, signature, superClassName, implementedItfs);
// calls the visitSource method
if (!skipDebug && (sourceFile != null || sourceDebug != null))
@@ -599,13 +641,13 @@
}
// calls the visitOuterClass method
- if (enclosingOwner != null)
+ if (enclosingOwner != null && !skipOuterClasses)
{
classVisitor.visitOuterClass(enclosingOwner, enclosingName, enclosingDesc);
}
// visits the class annotations
- if (ANNOTATIONS)
+ if (includeClassAnnotations)
{
for (i = 1; i >= 0; --i)
{
@@ -623,16 +665,19 @@
}
// visits the class attributes
- while (cattrs != null)
+ if (!skipUnknownAttributes)
{
- attr = cattrs.next;
- cattrs.next = null;
- classVisitor.visitAttribute(cattrs);
- cattrs = attr;
+ while (cattrs != null)
+ {
+ attr = cattrs.next;
+ cattrs.next = null;
+ classVisitor.visitAttribute(cattrs);
+ cattrs = attr;
+ }
}
// calls the visitInnerClass method
- if (w != 0)
+ if (w != 0 && !skipInnerClasses)
{
i = readUnsignedShort(w);
w += 2;
@@ -651,91 +696,7 @@
u += 2;
for (; i > 0; --i)
{
- access = readUnsignedShort(u);
- name = readUTF8(u + 2, c);
- desc = readUTF8(u + 4, c);
- // visits the field's attributes and looks for a ConstantValue
- // attribute
- int fieldValueItem = 0;
- signature = null;
- anns = 0;
- ianns = 0;
- cattrs = null;
-
- j = readUnsignedShort(u + 6);
- u += 8;
- for (; j > 0; --j)
- {
- attrName = readUTF8(u, c);
- // tests are sorted in decreasing frequency order
- // (based on frequencies observed on typical classes)
- if ("ConstantValue".equals(attrName))
- {
- fieldValueItem = readUnsignedShort(u + 6);
- }
- else if (SIGNATURES && "Signature".equals(attrName))
- {
- signature = readUTF8(u + 6, c);
- }
- else if ("Deprecated".equals(attrName))
- {
- access |= Opcodes.ACC_DEPRECATED;
- }
- else if ("Synthetic".equals(attrName))
- {
- access |= Opcodes.ACC_SYNTHETIC;
- }
- else if (ANNOTATIONS && "RuntimeVisibleAnnotations".equals(attrName))
- {
- anns = u + 6;
- }
- else if (ANNOTATIONS && "RuntimeInvisibleAnnotations".equals(attrName))
- {
- ianns = u + 6;
- }
- else
- {
- attr = readAttribute(attrs, attrName, u + 6, readInt(u + 2), c, -1, null);
- if (attr != null)
- {
- attr.next = cattrs;
- cattrs = attr;
- }
- }
- u += 6 + readInt(u + 2);
- }
- // visits the field
- FieldVisitor fv = classVisitor.visitField(access, name, desc, signature, fieldValueItem == 0
- ? null
- : readConst(fieldValueItem, c));
- // visits the field annotations and attributes
- if (fv != null)
- {
- if (ANNOTATIONS)
- {
- for (j = 1; j >= 0; --j)
- {
- v = j == 0 ? ianns : anns;
- if (v != 0)
- {
- k = readUnsignedShort(v);
- v += 2;
- for (; k > 0; --k)
- {
- v = readAnnotationValues(v + 2, c, true, fv.visitAnnotation(readUTF8(v, c), j != 0));
- }
- }
- }
- }
- while (cattrs != null)
- {
- attr = cattrs.next;
- cattrs.next = null;
- fv.visitAttribute(cattrs);
- cattrs = attr;
- }
- fv.visitEnd();
- }
+ u = readField(classVisitor, flags, attrs, c, u);
}
// visits the methods
@@ -743,75 +704,110 @@
u += 2;
for (; i > 0; --i)
{
- int u0 = u + 6;
+ u = readMethod(classVisitor, flags, attrs, c, u);
+ }
+
+ // visits the end of the class
+ classVisitor.visitEnd();
+ }
+
+ private int readMethod(final ClassVisitor classVisitor, int flags, final Attribute[] attrs, char[] c, int u)
+ {
+ byte[] b = this.b; // the bytecode array
+ boolean skipCode = (flags & SKIP_CODE) != 0;
+ boolean unzip = (flags & EXPAND_FRAMES) != 0;
+ boolean skipDebug = (flags & EXPAND_FRAMES) != 0;
+ boolean includeMethodOverview = (flags & INCLUDE_METHOD_OVERVIEW) != 0;
+ boolean includeMethodAnnotations = (flags & INCLUDE_METHOD_ANNOTATIONS) != 0;
+ boolean includeMethodParameterAnnotations = (flags & INCLUDE_MEHOD_PARAMETER_ANNOTATIONS) != 0;
+ boolean includeAnnotationDefaultValues = (flags & INCLUDE_DEFAULT_ANNOTATION_VALUES) != 0;
+ boolean includeMethodUnknownAttributes = (flags & INCLUDE_METHOD_UNKNOWN_ATTRIBUTES) != 0;
+
+ int u0 = u + 6;
+ int access = 0;
+ String name = null;
+ String desc = null;
+ if (includeMethodOverview)
+ {
access = readUnsignedShort(u);
- name = readUTF8(u + 2, c);
- desc = readUTF8(u + 4, c);
- signature = null;
- anns = 0;
- ianns = 0;
- int dann = 0;
- int mpanns = 0;
- int impanns = 0;
- cattrs = null;
- v = 0;
- w = 0;
+ }
+ //TODO use index instead and update visitMethod to use that
+ name = readUTF8(u + 2, c);
+ desc = readUTF8(u + 4, c);
+
+
+ String signature = null;
+ int anns = 0;
+ int ianns = 0;
+ int dann = 0;
+ int mpanns = 0;
+ int impanns = 0;
+ Attribute cattrs = null;
+ Attribute attr;
+ int v = 0;
+ int w = 0;
+ int k = 0;
- // looks for Code and Exceptions attributes
- j = readUnsignedShort(u + 6);
- u += 8;
- for (; j > 0; --j)
+ // looks for Code and Exceptions attributes
+ int j = readUnsignedShort(u + 6);
+ u += 8;
+ for (; j > 0; --j)
+ {
+ String attrName = readUTF8(u, c);
+ int attrSize = readInt(u + 2);
+ u += 6;
+ // tests are sorted in decreasing frequency order
+ // (based on frequencies observed on typical classes)
+ if ("Code".equals(attrName))
{
- attrName = readUTF8(u, c);
- int attrSize = readInt(u + 2);
- u += 6;
- // tests are sorted in decreasing frequency order
- // (based on frequencies observed on typical classes)
- if ("Code".equals(attrName))
+ if (!skipCode)
{
- if (!skipCode)
- {
- v = u;
- }
+ v = u;
}
- else if ("Exceptions".equals(attrName))
- {
- w = u;
- }
- else if (SIGNATURES && "Signature".equals(attrName))
- {
+ }
+ else if ("Exceptions".equals(attrName))
+ {
+ w = u;
+ }
+ else if (SIGNATURES && "Signature".equals(attrName))
+ {
+ //if (includeMethodOverview) TODO add this once visitMethod() uses index
signature = readUTF8(u, c);
- }
- else if ("Deprecated".equals(attrName))
- {
+ }
+ else if ("Deprecated".equals(attrName))
+ {
+ if (includeMethodOverview)
access |= Opcodes.ACC_DEPRECATED;
- }
- else if (ANNOTATIONS && "RuntimeVisibleAnnotations".equals(attrName))
- {
+ }
+ else if (includeMethodAnnotations && "RuntimeVisibleAnnotations".equals(attrName))
+ {
anns = u;
- }
- else if (ANNOTATIONS && "AnnotationDefault".equals(attrName))
- {
- dann = u;
- }
- else if ("Synthetic".equals(attrName))
- {
+ }
+ else if (ANNOTATIONS && "AnnotationDefault".equals(attrName))
+ {
+ dann = u;
+ }
+ else if ("Synthetic".equals(attrName))
+ {
+ if (includeMethodOverview)
access |= Opcodes.ACC_SYNTHETIC;
- }
- else if (ANNOTATIONS && "RuntimeInvisibleAnnotations".equals(attrName))
+ }
+ else if (includeMethodAnnotations && "RuntimeInvisibleAnnotations".equals(attrName))
+ {
+ ianns = u;
+ }
+ else if (includeMethodParameterAnnotations && "RuntimeVisibleParameterAnnotations".equals(attrName))
+ {
+ mpanns = u;
+ }
+ else if (includeMethodParameterAnnotations && "RuntimeInvisibleParameterAnnotations".equals(attrName))
+ {
+ impanns = u;
+ }
+ else
+ {
+ if (includeMethodUnknownAttributes)
{
- ianns = u;
- }
- else if (ANNOTATIONS && "RuntimeVisibleParameterAnnotations".equals(attrName))
- {
- mpanns = u;
- }
- else if (ANNOTATIONS && "RuntimeInvisibleParameterAnnotations".equals(attrName))
- {
- impanns = u;
- }
- else
- {
attr = readAttribute(attrs, attrName, u, attrSize, c, -1, null);
if (attr != null)
{
@@ -819,10 +815,13 @@
cattrs = attr;
}
}
- u += attrSize;
}
- // reads declared exceptions
- String[] exceptions;
+ u += attrSize;
+ }
+ // reads declared exceptions
+ String[] exceptions = null;
+ if (includeMethodOverview)
+ {
if (w == 0)
{
exceptions = null;
@@ -837,100 +836,104 @@
w += 2;
}
}
+ }
- // visits the method's code, if any
- MethodVisitor mv = classVisitor.visitMethod(access, name, desc, signature, exceptions);
+ // visits the method's code, if any
+ MethodVisitor mv = classVisitor.visitMethod(access, name, desc, signature, exceptions);
- if (mv != null)
+ if (mv != null)
+ {
+ /*
+ * if the returned MethodVisitor is in fact a MethodWriter, it
+ * means there is no method adapter between the reader and the
+ * writer. If, in addition, the writer's constant pool was
+ * copied from this reader (mw.cw.cr == this), and the signature
+ * and exceptions of the method have not been changed, then it
+ * is possible to skip all visit events and just copy the
+ * original code of the method to the writer (the access, name
+ * and descriptor can have been changed, this is not important
+ * since they are not copied as is from the reader).
+ */
+ if (WRITER && mv instanceof MethodWriter)
{
- /*
- * if the returned MethodVisitor is in fact a MethodWriter, it
- * means there is no method adapter between the reader and the
- * writer. If, in addition, the writer's constant pool was
- * copied from this reader (mw.cw.cr == this), and the signature
- * and exceptions of the method have not been changed, then it
- * is possible to skip all visit events and just copy the
- * original code of the method to the writer (the access, name
- * and descriptor can have been changed, this is not important
- * since they are not copied as is from the reader).
- */
- if (WRITER && mv instanceof MethodWriter)
+ MethodWriter mw = (MethodWriter) mv;
+ if (mw.cw.cr == this)
{
- MethodWriter mw = (MethodWriter) mv;
- if (mw.cw.cr == this)
+ if (signature == mw.signature)
{
- if (signature == mw.signature)
+ boolean sameExceptions = false;
+ if (exceptions == null)
{
- boolean sameExceptions = false;
- if (exceptions == null)
+ sameExceptions = mw.exceptionCount == 0;
+ }
+ else
+ {
+ if (exceptions.length == mw.exceptionCount)
{
- sameExceptions = mw.exceptionCount == 0;
- }
- else
- {
- if (exceptions.length == mw.exceptionCount)
+ sameExceptions = true;
+ for (j = exceptions.length - 1; j >= 0; --j)
{
- sameExceptions = true;
- for (j = exceptions.length - 1; j >= 0; --j)
+ w -= 2;
+ if (mw.exceptions[j] != readUnsignedShort(w))
{
- w -= 2;
- if (mw.exceptions[j] != readUnsignedShort(w))
- {
- sameExceptions = false;
- break;
- }
+ sameExceptions = false;
+ break;
}
}
}
- if (sameExceptions)
- {
- /*
- * we do not copy directly the code into
- * MethodWriter to save a byte array copy
- * operation. The real copy will be done in
- * ClassWriter.toByteArray().
- */
- mw.classReaderOffset = u0;
- mw.classReaderLength = u - u0;
- continue;
- }
}
+ if (sameExceptions)
+ {
+ /*
+ * we do not copy directly the code into
+ * MethodWriter to save a byte array copy
+ * operation. The real copy will be done in
+ * ClassWriter.toByteArray().
+ */
+ mw.classReaderOffset = u0;
+ mw.classReaderLength = u - u0;
+ //continue;
+ return u;
+ }
}
}
+ }
- if (ANNOTATIONS && dann != 0)
+ if (includeAnnotationDefaultValues && dann != 0)
+ {
+ AnnotationVisitor dv = mv.visitAnnotationDefault();
+ readAnnotationValue(dann, c, null, dv);
+ if (dv != null)
{
- AnnotationVisitor dv = mv.visitAnnotationDefault();
- readAnnotationValue(dann, c, null, dv);
- if (dv != null)
- {
- dv.visitEnd();
- }
+ dv.visitEnd();
}
- if (ANNOTATIONS)
+ }
+ if (includeMethodAnnotations)
+ {
+ for (j = 1; j >= 0; --j)
{
- for (j = 1; j >= 0; --j)
+ w = j == 0 ? ianns : anns;
+ if (w != 0)
{
- w = j == 0 ? ianns : anns;
- if (w != 0)
+ k = readUnsignedShort(w);
+ w += 2;
+ for (; k > 0; --k)
{
- k = readUnsignedShort(w);
- w += 2;
- for (; k > 0; --k)
- {
- w = readAnnotationValues(w + 2, c, true, mv.visitAnnotation(readUTF8(w, c), j != 0));
- }
+ w = readAnnotationValues(w + 2, c, true, mv.visitAnnotation(readUTF8(w, c), j != 0));
}
}
}
- if (ANNOTATIONS && mpanns != 0)
- {
- readParameterAnnotations(mpanns, desc, c, true, mv);
- }
- if (ANNOTATIONS && impanns != 0)
- {
- readParameterAnnotations(impanns, desc, c, false, mv);
- }
+ }
+ if (includeMethodParameterAnnotations && mpanns != 0)
+ {
+ readParameterAnnotations(mpanns, desc, c, true, mv);
+ }
+ if (includeMethodParameterAnnotations && impanns != 0)
+ {
+ readParameterAnnotations(impanns, desc, c, false, mv);
+ }
+ if (includeMethodUnknownAttributes)
+ {
while (cattrs != null)
{
attr = cattrs.next;
@@ -939,646 +942,766 @@
cattrs = attr;
}
}
+ }
- if (mv != null && v != 0)
- {
- int maxStack = readUnsignedShort(v);
- int maxLocals = readUnsignedShort(v + 2);
- int codeLength = readInt(v + 4);
- v += 8;
+ if (mv != null && v != 0)
+ {
+ int maxStack = readUnsignedShort(v);
+ int maxLocals = readUnsignedShort(v + 2);
+ int codeLength = readInt(v + 4);
+ v += 8;
- int codeStart = v;
- int codeEnd = v + codeLength;
+ int codeStart = v;
+ int codeEnd = v + codeLength;
- mv.visitCode();
+ mv.visitCode();
- // 1st phase: finds the labels
- int label;
- Label[] labels = new Label[codeLength + 2];
- readLabel(codeLength + 1, labels);
- while (v < codeEnd)
+ // 1st phase: finds the labels
+ int label;
+ Label[] labels = new Label[codeLength + 2];
+ readLabel(codeLength + 1, labels);
+ while (v < codeEnd)
+ {
+ w = v - codeStart;
+ int opcode = b[v] & 0xFF;
+ switch (ClassWriter.TYPE[opcode])
{
- w = v - codeStart;
- int opcode = b[v] & 0xFF;
- switch (ClassWriter.TYPE[opcode])
- {
- case ClassWriter.NOARG_INSN :
- case ClassWriter.IMPLVAR_INSN :
- v += 1;
- break;
- case ClassWriter.LABEL_INSN :
- readLabel(w + readShort(v + 1), labels);
- v += 3;
- break;
- case ClassWriter.LABELW_INSN :
- readLabel(w + readInt(v + 1), labels);
- v += 5;
- break;
- case ClassWriter.WIDE_INSN :
- opcode = b[v + 1] & 0xFF;
- if (opcode == Opcodes.IINC)
- {
- v += 6;
- }
- else
- {
- v += 4;
- }
- break;
- case ClassWriter.TABL_INSN :
- // skips 0 to 3 padding bytes*
- v = v + 4 - (w & 3);
- // reads instruction
+ case ClassWriter.NOARG_INSN :
+ case ClassWriter.IMPLVAR_INSN :
+ v += 1;
+ break;
+ case ClassWriter.LABEL_INSN :
+ readLabel(w + readShort(v + 1), labels);
+ v += 3;
+ break;
+ case ClassWriter.LABELW_INSN :
+ readLabel(w + readInt(v + 1), labels);
+ v += 5;
+ break;
+ case ClassWriter.WIDE_INSN :
+ opcode = b[v + 1] & 0xFF;
+ if (opcode == Opcodes.IINC)
+ {
+ v += 6;
+ }
+ else
+ {
+ v += 4;
+ }
+ break;
+ case ClassWriter.TABL_INSN :
+ // skips 0 to 3 padding bytes*
+ v = v + 4 - (w & 3);
+ // reads instruction
+ readLabel(w + readInt(v), labels);
+ j = readInt(v + 8) - readInt(v + 4) + 1;
+ v += 12;
+ for (; j > 0; --j)
+ {
readLabel(w + readInt(v), labels);
- j = readInt(v + 8) - readInt(v + 4) + 1;
- v += 12;
- for (; j > 0; --j)
- {
- readLabel(w + readInt(v), labels);
- v += 4;
- }
- break;
- case ClassWriter.LOOK_INSN :
- // skips 0 to 3 padding bytes*
- v = v + 4 - (w & 3);
- // reads instruction
- readLabel(w + readInt(v), labels);
- j = readInt(v + 4);
+ v += 4;
+ }
+ break;
+ case ClassWriter.LOOK_INSN :
+ // skips 0 to 3 padding bytes*
+ v = v + 4 - (w & 3);
+ // reads instruction
+ readLabel(w + readInt(v), labels);
+ j = readInt(v + 4);
+ v += 8;
+ for (; j > 0; --j)
+ {
+ readLabel(w + readInt(v + 4), labels);
v += 8;
- for (; j > 0; --j)
- {
- readLabel(w + readInt(v + 4), labels);
- v += 8;
- }
- break;
- case ClassWriter.VAR_INSN :
- case ClassWriter.SBYTE_INSN :
- case ClassWriter.LDC_INSN :
- v += 2;
- break;
- case ClassWriter.SHORT_INSN :
- case ClassWriter.LDCW_INSN :
- case ClassWriter.FIELDORMETH_INSN :
- case ClassWriter.TYPE_INSN :
- case ClassWriter.IINC_INSN :
- v += 3;
- break;
- case ClassWriter.ITFDYNMETH_INSN :
- v += 5;
- break;
- // case MANA_INSN:
- default :
- v += 4;
- break;
- }
+ }
+ break;
+ case ClassWriter.VAR_INSN :
+ case ClassWriter.SBYTE_INSN :
+ case ClassWriter.LDC_INSN :
+ v += 2;
+ break;
+ case ClassWriter.SHORT_INSN :
+ case ClassWriter.LDCW_INSN :
+ case ClassWriter.FIELDORMETH_INSN :
+ case ClassWriter.TYPE_INSN :
+ case ClassWriter.IINC_INSN :
+ v += 3;
+ break;
+ case ClassWriter.ITFDYNMETH_INSN :
+ v += 5;
+ break;
+ // case MANA_INSN:
+ default :
+ v += 4;
+ break;
}
- // parses the try catch entries
- j = readUnsignedShort(v);
- v += 2;
- for (; j > 0; --j)
+ }
+ // parses the try catch entries
+ j = readUnsignedShort(v);
+ v += 2;
+ for (; j > 0; --j)
+ {
+ Label start = readLabel(readUnsignedShort(v), labels);
+ Label end = readLabel(readUnsignedShort(v + 2), labels);
+ Label handler = readLabel(readUnsignedShort(v + 4), labels);
+ int type = readUnsignedShort(v + 6);
+ if (type == 0)
{
- Label start = readLabel(readUnsignedShort(v), labels);
- Label end = readLabel(readUnsignedShort(v + 2), labels);
- Label handler = readLabel(readUnsignedShort(v + 4), labels);
- int type = readUnsignedShort(v + 6);
- if (type == 0)
- {
- mv.visitTryCatchBlock(start, end, handler, null);
- }
- else
- {
- mv.visitTryCatchBlock(start, end, handler, readUTF8(items[type], c));
- }
- v += 8;
+ mv.visitTryCatchBlock(start, end, handler, null);
}
- // parses the local variable, line number tables, and code
- // attributes
- int varTable = 0;
- int varTypeTable = 0;
- int stackMap = 0;
- int frameCount = 0;
- int frameMode = 0;
- int frameOffset = 0;
- int frameLocalCount = 0;
- int frameLocalDiff = 0;
- int frameStackCount = 0;
- Object[] frameLocal = null;
- Object[] frameStack = null;
- boolean zip = true;
- cattrs = null;
- j = readUnsignedShort(v);
- v += 2;
- for (; j > 0; --j)
+ else
{
- attrName = readUTF8(v, c);
- if ("LocalVariableTable".equals(attrName))
+ mv.visitTryCatchBlock(start, end, handler, readUTF8(items[type], c));
+ }
+ v += 8;
+ }
+ // parses the local variable, line number tables, and code
+ // attributes
+ int varTable = 0;
+ int varTypeTable = 0;
+ int stackMap = 0;
+ int frameCount = 0;
+ int frameMode = 0;
+ int frameOffset = 0;
+ int frameLocalCount = 0;
+ int frameLocalDiff = 0;
+ int frameStackCount = 0;
+ Object[] frameLocal = null;
+ Object[] frameStack = null;
+ boolean zip = true;
+ cattrs = null;
+ j = readUnsignedShort(v);
+ v += 2;
+ for (; j > 0; --j)
+ {
+ String attrName = readUTF8(v, c);
+ if ("LocalVariableTable".equals(attrName))
+ {
+ if (!skipDebug)
{
- if (!skipDebug)
+ varTable = v + 6;
+ k = readUnsignedShort(v + 6);
+ w = v + 8;
+ for (; k > 0; --k)
{
- varTable = v + 6;
- k = readUnsignedShort(v + 6);
- w = v + 8;
- for (; k > 0; --k)
+ label = readUnsignedShort(w);
+ if (labels[label] == null)
{
- label = readUnsignedShort(w);
- if (labels[label] == null)
- {
- readLabel(label, labels).status |= Label.DEBUG;
- }
- label += readUnsignedShort(w + 2);
- if (labels[label] == null)
- {
- readLabel(label, labels).status |= Label.DEBUG;
- }
- w += 10;
+ readLabel(label, labels).status |= Label.DEBUG;
}
+ label += readUnsignedShort(w + 2);
+ if (labels[label] == null)
+ {
+ readLabel(label, labels).status |= Label.DEBUG;
+ }
+ w += 10;
}
}
- else if ("LocalVariableTypeTable".equals(attrName))
+ }
+ else if ("LocalVariableTypeTable".equals(attrName))
+ {
+ varTypeTable = v + 6;
+ }
+ else if ("LineNumberTable".equals(attrName))
+ {
+ if (!skipDebug)
{
- varTypeTable = v + 6;
- }
- else if ("LineNumberTable".equals(attrName))
- {
- if (!skipDebug)
+ k = readUnsignedShort(v + 6);
+ w = v + 8;
+ for (; k > 0; --k)
{
- k = readUnsignedShort(v + 6);
- w = v + 8;
- for (; k > 0; --k)
+ label = readUnsignedShort(w);
+ if (labels[label] == null)
{
- label = readUnsignedShort(w);
- if (labels[label] == null)
- {
- readLabel(label, labels).status |= Label.DEBUG;
- }
- labels[label].line = readUnsignedShort(w + 2);
- w += 4;
+ readLabel(label, labels).status |= Label.DEBUG;
}
+ labels[label].line = readUnsignedShort(w + 2);
+ w += 4;
}
}
- else if (FRAMES && "StackMapTable".equals(attrName))
+ }
+ else if (FRAMES && "StackMapTable".equals(attrName))
+ {
+ if ((flags & SKIP_FRAMES) == 0)
{
- if ((flags & SKIP_FRAMES) == 0)
- {
- stackMap = v + 8;
- frameCount = readUnsignedShort(v + 6);
- }
- /*
- * here we do not extract the labels corresponding to
- * the attribute content. This would require a full
- * parsing of the attribute, which would need to be
- * repeated in the second phase (see below). Instead the
- * content of the attribute is read one frame at a time
- * (i.e. after a frame has been visited, the next frame
- * is read), and the labels it contains are also
- * extracted one frame at a time. Thanks to the ordering
- * of frames, having only a "one frame lookahead" is not
- * a problem, i.e. it is not possible to see an offset
- * smaller than the offset of the current insn and for
- * which no Label exist.
- */
- // TODO true for frame offsets,
- // but for UNINITIALIZED type offsets?
+ stackMap = v + 8;
+ frameCount = readUnsignedShort(v + 6);
}
- else if (FRAMES && "StackMap".equals(attrName))
+ /*
+ * here we do not extract the labels corresponding to
+ * the attribute content. This would require a full
+ * parsing of the attribute, which would need to be
+ * repeated in the second phase (see below). Instead the
+ * content of the attribute is read one frame at a time
+ * (i.e. after a frame has been visited, the next frame
+ * is read), and the labels it contains are also
+ * extracted one frame at a time. Thanks to the ordering
+ * of frames, having only a "one frame lookahead" is not
+ * a problem, i.e. it is not possible to see an offset
+ * smaller than the offset of the current insn and for
+ * which no Label exist.
+ */
+ // TODO true for frame offsets,
+ // but for UNINITIALIZED type offsets?
+ }
+ else if (FRAMES && "StackMap".equals(attrName))
+ {
+ if ((flags & SKIP_FRAMES) == 0)
{
- if ((flags & SKIP_FRAMES) == 0)
- {
- stackMap = v + 8;
- frameCount = readUnsignedShort(v + 6);
- zip = false;
- }
- /*
- * IMPORTANT! here we assume that the frames are
- * ordered, as in the StackMapTable attribute, although
- * this is not guaranteed by the attribute format.
- */
+ stackMap = v + 8;
+ frameCount = readUnsignedShort(v + 6);
+ zip = false;
}
- else
+ /*
+ * IMPORTANT! here we assume that the frames are
+ * ordered, as in the StackMapTable attribute, although
+ * this is not guaranteed by the attribute format.
+ */
+ }
+ else
+ {
+ for (k = 0; k < attrs.length; ++k)
{
- for (k = 0; k < attrs.length; ++k)
+ if (attrs[k].type.equals(attrName))
{
- if (attrs[k].type.equals(attrName))
+ attr = attrs[k].read(this, v + 6, readInt(v + 2), c, codeStart - 8, labels);
+ if (attr != null)
{
- attr = attrs[k].read(this, v + 6, readInt(v + 2), c, codeStart - 8, labels);
- if (attr != null)
- {
- attr.next = cattrs;
- cattrs = attr;
- }
+ attr.next = cattrs;
+ cattrs = attr;
}
}
}
- v += 6 + readInt(v + 2);
}
+ v += 6 + readInt(v + 2);
+ }
- // 2nd phase: visits each instruction
- if (FRAMES && stackMap != 0)
+ // 2nd phase: visits each instruction
+ if (FRAMES && stackMap != 0)
+ {
+ // creates the very first (implicit) frame from the method
+ // descriptor
+ frameLocal = new Object[maxLocals];
+ frameStack = new Object[maxStack];
+ if (unzip)
{
- // creates the very first (implicit) frame from the method
- // descriptor
- frameLocal = new Object[maxLocals];
- frameStack = new Object[maxStack];
- if (unzip)
+ int local = 0;
+ if ((access & Opcodes.ACC_STATIC) == 0)
{
- int local = 0;
- if ((access & Opcodes.ACC_STATIC) == 0)
+ if ("<init>".equals(name))
{
- if ("<init>".equals(name))
- {
- frameLocal[local++] = Opcodes.UNINITIALIZED_THIS;
- }
- else
- {
- frameLocal[local++] = readClass(header + 2, c);
- }
+ frameLocal[local++] = Opcodes.UNINITIALIZED_THIS;
}
- j = 1;
- loop : while (true)
+ else
{
- k = j;
- switch (desc.charAt(j++))
- {
- case 'Z' :
- case 'C' :
- case 'B' :
- case 'S' :
- case 'I' :
- frameLocal[local++] = Opcodes.INTEGER;
- break;
- case 'F' :
- frameLocal[local++] = Opcodes.FLOAT;
- break;
- case 'J' :
- frameLocal[local++] = Opcodes.LONG;
- break;
- case 'D' :
- frameLocal[local++] = Opcodes.DOUBLE;
- break;
- case '[' :
- while (desc.charAt(j) == '[')
- {
- ++j;
- }
- if (desc.charAt(j) == 'L')
- {
- ++j;
- while (desc.charAt(j) != ';')
- {
- ++j;
- }
- }
- frameLocal[local++] = desc.substring(k, ++j);
- break;
- case 'L' :
+ frameLocal[local++] = readClass(header + 2, c);
+ }
+ }
+ j = 1;
+ loop : while (true)
+ {
+ k = j;
+ switch (desc.charAt(j++))
+ {
+ case 'Z' :
+ case 'C' :
+ case 'B' :
+ case 'S' :
+ case 'I' :
+ frameLocal[local++] = Opcodes.INTEGER;
+ break;
+ case 'F' :
+ frameLocal[local++] = Opcodes.FLOAT;
+ break;
+ case 'J' :
+ frameLocal[local++] = Opcodes.LONG;
+ break;
+ case 'D' :
+ frameLocal[local++] = Opcodes.DOUBLE;
+ break;
+ case '[' :
+ while (desc.charAt(j) == '[')
+ {
+ ++j;
+ }
+ if (desc.charAt(j) == 'L')
+ {
+ ++j;
while (desc.charAt(j) != ';')
{
++j;
}
- frameLocal[local++] = desc.substring(k + 1, j++);
- break;
- default :
- break loop;
- }
+ }
+ frameLocal[local++] = desc.substring(k, ++j);
+ break;
+ case 'L' :
+ while (desc.charAt(j) != ';')
+ {
+ ++j;
+ }
+ frameLocal[local++] = desc.substring(k + 1, j++);
+ break;
+ default :
+ break loop;
}
- frameLocalCount = local;
}
- /*
- * for the first explicit frame the offset is not
- * offset_delta + 1 but only offset_delta; setting the
- * implicit frame offset to -1 allow the use of the
- * "offset_delta + 1" rule in all cases
- */
- frameOffset = -1;
+ frameLocalCount = local;
}
- v = codeStart;
- Label l;
- while (v < codeEnd)
+ /*
+ * for the first explicit frame the offset is not
+ * offset_delta + 1 but only offset_delta; setting the
+ * implicit frame offset to -1 allow the use of the
+ * "offset_delta + 1" rule in all cases
+ */
+ frameOffset = -1;
+ }
+ v = codeStart;
+ Label l;
+ while (v < codeEnd)
+ {
+ w = v - codeStart;
+
+ l = labels[w];
+ if (l != null)
{
- w = v - codeStart;
+ mv.visitLabel(l);
+ if (!skipDebug && l.line > 0)
+ {
+ mv.visitLineNumber(l.line, l);
+ }
+ }
- l = labels[w];
- if (l != null)
+ while (FRAMES && frameLocal != null && (frameOffset == w || frameOffset == -1))
+ {
+ // if there is a frame for this offset,
+ // makes the visitor visit it,
+ // and reads the next frame if there is one.
+ if (!zip || unzip)
{
- mv.visitLabel(l);
- if (!skipDebug && l.line > 0)
- {
- mv.visitLineNumber(l.line, l);
- }
+ mv.visitFrame(Opcodes.F_NEW, frameLocalCount, frameLocal, frameStackCount, frameStack);
}
+ else if (frameOffset != -1)
+ {
+ mv.visitFrame(frameMode, frameLocalDiff, frameLocal, frameStackCount, frameStack);
+ }
- while (FRAMES && frameLocal != null && (frameOffset == w || frameOffset == -1))
+ if (frameCount > 0)
{
- // if there is a frame for this offset,
- // makes the visitor visit it,
- // and reads the next frame if there is one.
- if (!zip || unzip)
+ int tag, delta, n;
+ if (zip)
{
- mv.visitFrame(Opcodes.F_NEW, frameLocalCount, frameLocal, frameStackCount, frameStack);
+ tag = b[stackMap++] & 0xFF;
}
- else if (frameOffset != -1)
+ else
{
- mv.visitFrame(frameMode, frameLocalDiff, frameLocal, frameStackCount, frameStack);
+ tag = MethodWriter.FULL_FRAME;
+ frameOffset = -1;
}
-
- if (frameCount > 0)
+ frameLocalDiff = 0;
+ if (tag < MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME)
{
- int tag, delta, n;
- if (zip)
+ delta = tag;
+ frameMode = Opcodes.F_SAME;
+ frameStackCount = 0;
+ }
+ else if (tag < MethodWriter.RESERVED)
+ {
+ delta = tag - MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME;
+ stackMap = readFrameType(frameStack, 0, stackMap, c, labels);
+ frameMode = Opcodes.F_SAME1;
+ frameStackCount = 1;
+ }
+ else
+ {
+ delta = readUnsignedShort(stackMap);
+ stackMap += 2;
+ if (tag == MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED)
{
- tag = b[stackMap++] & 0xFF;
+ stackMap = readFrameType(frameStack, 0, stackMap, c, labels);
+ frameMode = Opcodes.F_SAME1;
+ frameStackCount = 1;
}
- else
+ else if (tag >= MethodWriter.CHOP_FRAME && tag < MethodWriter.SAME_FRAME_EXTENDED)
{
- tag = MethodWriter.FULL_FRAME;
- frameOffset = -1;
+ frameMode = Opcodes.F_CHOP;
+ frameLocalDiff = MethodWriter.SAME_FRAME_EXTENDED - tag;
+ frameLocalCount -= frameLocalDiff;
+ frameStackCount = 0;
}
- frameLocalDiff = 0;
- if (tag < MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME)
+ else if (tag == MethodWriter.SAME_FRAME_EXTENDED)
{
- delta = tag;
frameMode = Opcodes.F_SAME;
frameStackCount = 0;
}
- else if (tag < MethodWriter.RESERVED)
+ else if (tag < MethodWriter.FULL_FRAME)
{
- delta = tag - MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME;
- stackMap = readFrameType(frameStack, 0, stackMap, c, labels);
- frameMode = Opcodes.F_SAME1;
- frameStackCount = 1;
+ j = unzip ? frameLocalCount : 0;
+ for (k = tag - MethodWriter.SAME_FRAME_EXTENDED; k > 0; k--)
+ {
+ stackMap = readFrameType(frameLocal, j++, stackMap, c, labels);
+ }
+ frameMode = Opcodes.F_APPEND;
+ frameLocalDiff = tag - MethodWriter.SAME_FRAME_EXTENDED;
+ frameLocalCount += frameLocalDiff;
+ frameStackCount = 0;
}
else
- {
- delta = readUnsignedShort(stackMap);
+ { // if (tag == FULL_FRAME) {
+ frameMode = Opcodes.F_FULL;
+ n = frameLocalDiff = frameLocalCount = readUnsignedShort(stackMap);
stackMap += 2;
- if (tag == MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED)
+ for (j = 0; n > 0; n--)
{
- stackMap = readFrameType(frameStack, 0, stackMap, c, labels);
- frameMode = Opcodes.F_SAME1;
- frameStackCount = 1;
+ stackMap = readFrameType(frameLocal, j++, stackMap, c, labels);
}
- else if (tag >= MethodWriter.CHOP_FRAME && tag < MethodWriter.SAME_FRAME_EXTENDED)
+ n = frameStackCount = readUnsignedShort(stackMap);
+ stackMap += 2;
+ for (j = 0; n > 0; n--)
{
- frameMode = Opcodes.F_CHOP;
- frameLocalDiff = MethodWriter.SAME_FRAME_EXTENDED - tag;
- frameLocalCount -= frameLocalDiff;
- frameStackCount = 0;
+ stackMap = readFrameType(frameStack, j++, stackMap, c, labels);
}
- else if (tag == MethodWriter.SAME_FRAME_EXTENDED)
- {
- frameMode = Opcodes.F_SAME;
- frameStackCount = 0;
- }
- else if (tag < MethodWriter.FULL_FRAME)
- {
- j = unzip ? frameLocalCount : 0;
- for (k = tag - MethodWriter.SAME_FRAME_EXTENDED; k > 0; k--)
- {
- stackMap = readFrameType(frameLocal, j++, stackMap, c, labels);
- }
- frameMode = Opcodes.F_APPEND;
- frameLocalDiff = tag - MethodWriter.SAME_FRAME_EXTENDED;
- frameLocalCount += frameLocalDiff;
- frameStackCount = 0;
- }
- else
- { // if (tag == FULL_FRAME) {
- frameMode = Opcodes.F_FULL;
- n = frameLocalDiff = frameLocalCount = readUnsignedShort(stackMap);
- stackMap += 2;
- for (j = 0; n > 0; n--)
- {
- stackMap = readFrameType(frameLocal, j++, stackMap, c, labels);
- }
- n = frameStackCount = readUnsignedShort(stackMap);
- stackMap += 2;
- for (j = 0; n > 0; n--)
- {
- stackMap = readFrameType(frameStack, j++, stackMap, c, labels);
- }
- }
}
- frameOffset += delta + 1;
- readLabel(frameOffset, labels);
+ }
+ frameOffset += delta + 1;
+ readLabel(frameOffset, labels);
- --frameCount;
+ --frameCount;
+ }
+ else
+ {
+ frameLocal = null;
+ }
+ }
+
+ int opcode = b[v] & 0xFF;
+ switch (ClassWriter.TYPE[opcode])
+ {
+ case ClassWriter.NOARG_INSN :
+ mv.visitInsn(opcode);
+ v += 1;
+ break;
+ case ClassWriter.IMPLVAR_INSN :
+ if (opcode > Opcodes.ISTORE)
+ {
+ opcode -= 59; // ISTORE_0
+ mv.visitVarInsn(Opcodes.ISTORE + (opcode >> 2), opcode & 0x3);
}
else
{
- frameLocal = null;
+ opcode -= 26; // ILOAD_0
+ mv.visitVarInsn(Opcodes.ILOAD + (opcode >> 2), opcode & 0x3);
}
- }
-
- int opcode = b[v] & 0xFF;
- switch (ClassWriter.TYPE[opcode])
- {
- case ClassWriter.NOARG_INSN :
- mv.visitInsn(opcode);
- v += 1;
- break;
- case ClassWriter.IMPLVAR_INSN :
- if (opcode > Opcodes.ISTORE)
- {
- opcode -= 59; // ISTORE_0
- mv.visitVarInsn(Opcodes.ISTORE + (opcode >> 2), opcode & 0x3);
- }
- else
- {
- opcode -= 26; // ILOAD_0
- mv.visitVarInsn(Opcodes.ILOAD + (opcode >> 2), opcode & 0x3);
- }
- v += 1;
- break;
- case ClassWriter.LABEL_INSN :
- mv.visitJumpInsn(opcode, labels[w + readShort(v + 1)]);
- v += 3;
- break;
- case ClassWriter.LABELW_INSN :
- mv.visitJumpInsn(opcode - 33, labels[w + readInt(v + 1)]);
+ v += 1;
+ break;
+ case ClassWriter.LABEL_INSN :
+ mv.visitJumpInsn(opcode, labels[w + readShort(v + 1)]);
+ v += 3;
+ break;
+ case ClassWriter.LABELW_INSN :
+ mv.visitJumpInsn(opcode - 33, labels[w + readInt(v + 1)]);
+ v += 5;
+ break;
+ case ClassWriter.WIDE_INSN :
+ opcode = b[v + 1] & 0xFF;
+ if (opcode == Opcodes.IINC)
+ {
+ mv.visitIincInsn(readUnsignedShort(v + 2), readShort(v + 4));
+ v += 6;
+ }
+ else
+ {
+ mv.visitVarInsn(opcode, readUnsignedShort(v + 2));
+ v += 4;
+ }
+ break;
+ case ClassWriter.TABL_INSN :
+ // skips 0 to 3 padding bytes
+ v = v + 4 - (w & 3);
+ // reads instruction
+ label = w + readInt(v);
+ int min = readInt(v + 4);
+ int max = readInt(v + 8);
+ v += 12;
+ Label[] table = new Label[max - min + 1];
+ for (j = 0; j < table.length; ++j)
+ {
+ table[j] = labels[w + readInt(v)];
+ v += 4;
+ }
+ mv.visitTableSwitchInsn(min, max, labels[label], table);
+ break;
+ case ClassWriter.LOOK_INSN :
+ // skips 0 to 3 padding bytes
+ v = v + 4 - (w & 3);
+ // reads instruction
+ label = w + readInt(v);
+ j = readInt(v + 4);
+ v += 8;
+ int[] keys = new int[j];
+ Label[] values = new Label[j];
+ for (j = 0; j < keys.length; ++j)
+ {
+ keys[j] = readInt(v);
+ values[j] = labels[w + readInt(v + 4)];
+ v += 8;
+ }
+ mv.visitLookupSwitchInsn(labels[label], keys, values);
+ break;
+ case ClassWriter.VAR_INSN :
+ mv.visitVarInsn(opcode, b[v + 1] & 0xFF);
+ v += 2;
+ break;
+ case ClassWriter.SBYTE_INSN :
+ mv.visitIntInsn(opcode, b[v + 1]);
+ v += 2;
+ break;
+ case ClassWriter.SHORT_INSN :
+ mv.visitIntInsn(opcode, readShort(v + 1));
+ v += 3;
+ break;
+ case ClassWriter.LDC_INSN :
+ mv.visitLdcInsn(readConst(b[v + 1] & 0xFF, c));
+ v += 2;
+ break;
+ case ClassWriter.LDCW_INSN :
+ mv.visitLdcInsn(readConst(readUnsignedShort(v + 1), c));
+ v += 3;
+ break;
+ case ClassWriter.FIELDORMETH_INSN :
+ case ClassWriter.ITFDYNMETH_INSN :
+ int cpIndex = items[readUnsignedShort(v + 1)];
+ String iowner;
+ // INVOKEDYNAMIC is receiverless
+ if (opcode == Opcodes.INVOKEDYNAMIC)
+ {
+ iowner = Opcodes.INVOKEDYNAMIC_OWNER;
+ }
+ else
+ {
+ iowner = readClass(cpIndex, c);
+ cpIndex = items[readUnsignedShort(cpIndex + 2)];
+ }
+ String iname = readUTF8(cpIndex, c);
+ String idesc = readUTF8(cpIndex + 2, c);
+ if (opcode < Opcodes.INVOKEVIRTUAL)
+ {
+ mv.visitFieldInsn(opcode, iowner, iname, idesc);
+ }
+ else
+ {
+ mv.visitMethodInsn(opcode, iowner, iname, idesc);
+ }
+ if (opcode == Opcodes.INVOKEINTERFACE || opcode == Opcodes.INVOKEDYNAMIC)
+ {
v += 5;
- break;
- case ClassWriter.WIDE_INSN :
- opcode = b[v + 1] & 0xFF;
- if (opcode == Opcodes.IINC)
- {
- mv.visitIincInsn(readUnsignedShort(v + 2), readShort(v + 4));
- v += 6;
- }
- else
- {
- mv.visitVarInsn(opcode, readUnsignedShort(v + 2));
- v += 4;
- }
- break;
- case ClassWriter.TABL_INSN :
- // skips 0 to 3 padding bytes
- v = v + 4 - (w & 3);
- // reads instruction
- label = w + readInt(v);
- int min = readInt(v + 4);
- int max = readInt(v + 8);
- v += 12;
- Label[] table = new Label[max - min + 1];
- for (j = 0; j < table.length; ++j)
- {
- table[j] = labels[w + readInt(v)];
- v += 4;
- }
- mv.visitTableSwitchInsn(min, max, labels[label], table);
- break;
- case ClassWriter.LOOK_INSN :
- // skips 0 to 3 padding bytes
- v = v + 4 - (w & 3);
- // reads instruction
- label = w + readInt(v);
- j = readInt(v + 4);
- v += 8;
- int[] keys = new int[j];
- Label[] values = new Label[j];
- for (j = 0; j < keys.length; ++j)
- {
- keys[j] = readInt(v);
- values[j] = labels[w + readInt(v + 4)];
- v += 8;
- }
- mv.visitLookupSwitchInsn(labels[label], keys, values);
- break;
- case ClassWriter.VAR_INSN :
- mv.visitVarInsn(opcode, b[v + 1] & 0xFF);
- v += 2;
- break;
- case ClassWriter.SBYTE_INSN :
- mv.visitIntInsn(opcode, b[v + 1]);
- v += 2;
- break;
- case ClassWriter.SHORT_INSN :
- mv.visitIntInsn(opcode, readShort(v + 1));
+ }
+ else
+ {
v += 3;
- break;
- case ClassWriter.LDC_INSN :
- mv.visitLdcInsn(readConst(b[v + 1] & 0xFF, c));
- v += 2;
- break;
- case ClassWriter.LDCW_INSN :
- mv.visitLdcInsn(readConst(readUnsignedShort(v + 1), c));
- v += 3;
- break;
- case ClassWriter.FIELDORMETH_INSN :
- case ClassWriter.ITFDYNMETH_INSN :
- int cpIndex = items[readUnsignedShort(v + 1)];
- String iowner;
- // INVOKEDYNAMIC is receiverless
- if (opcode == Opcodes.INVOKEDYNAMIC)
- {
- iowner = Opcodes.INVOKEDYNAMIC_OWNER;
- }
- else
- {
- iowner = readClass(cpIndex, c);
- cpIndex = items[readUnsignedShort(cpIndex + 2)];
- }
- String iname = readUTF8(cpIndex, c);
- String idesc = readUTF8(cpIndex + 2, c);
- if (opcode < Opcodes.INVOKEVIRTUAL)
- {
- mv.visitFieldInsn(opcode, iowner, iname, idesc);
- }
- else
- {
- mv.visitMethodInsn(opcode, iowner, iname, idesc);
- }
- if (opcode == Opcodes.INVOKEINTERFACE || opcode == Opcodes.INVOKEDYNAMIC)
- {
- v += 5;
- }
- else
- {
- v += 3;
- }
- break;
- case ClassWriter.TYPE_INSN :
- mv.visitTypeInsn(opcode, readClass(v + 1, c));
- v += 3;
- break;
- case ClassWriter.IINC_INSN :
- mv.visitIincInsn(b[v + 1] & 0xFF, b[v + 2]);
- v += 3;
- break;
- // case MANA_INSN:
- default :
- mv.visitMultiANewArrayInsn(readClass(v + 1, c), b[v + 3] & 0xFF);
- v += 4;
- break;
- }
+ }
+ break;
+ case ClassWriter.TYPE_INSN :
+ mv.visitTypeInsn(opcode, readClass(v + 1, c));
+ v += 3;
+ break;
+ case ClassWriter.IINC_INSN :
+ mv.visitIincInsn(b[v + 1] & 0xFF, b[v + 2]);
+ v += 3;
+ break;
+ // case MANA_INSN:
+ default :
+ mv.visitMultiANewArrayInsn(readClass(v + 1, c), b[v + 3] & 0xFF);
+ v += 4;
+ break;
}
- l = labels[codeEnd - codeStart];
- if (l != null)
+ }
+ l = labels[codeEnd - codeStart];
+ if (l != null)
+ {
+ mv.visitLabel(l);
+ }
+ // visits the local variable tables
+ if (!skipDebug && varTable != 0)
+ {
+ int[] typeTable = null;
+ if (varTypeTable != 0)
{
- mv.visitLabel(l);
+ k = readUnsignedShort(varTypeTable) * 3;
+ w = varTypeTable + 2;
+ typeTable = new int[k];
+ while (k > 0)
+ {
+ typeTable[--k] = w + 6; // signature
+ typeTable[--k] = readUnsignedShort(w + 8); // index
+ typeTable[--k] = readUnsignedShort(w); // start
+ w += 10;
+ }
}
- // visits the local variable tables
- if (!skipDebug && varTable != 0)
+ k = readUnsignedShort(varTable);
+ w = varTable + 2;
+ for (; k > 0; --k)
{
- int[] typeTable = null;
- if (varTypeTable != 0)
+ int start = readUnsignedShort(w);
+ int length = readUnsignedShort(w + 2);
+ int index = readUnsignedShort(w + 8);
+ String vsignature = null;
+ if (typeTable != null)
{
- k = readUnsignedShort(varTypeTable) * 3;
- w = varTypeTable + 2;
- typeTable = new int[k];
- while (k > 0)
+ for (int a = 0; a < typeTable.length; a += 3)
{
- typeTable[--k] = w + 6; // signature
- typeTable[--k] = readUnsignedShort(w + 8); // index
- typeTable[--k] = readUnsignedShort(w); // start
- w += 10;
+ if (typeTable[a] == start && typeTable[a + 1] == index)
+ {
+ vsignature = readUTF8(typeTable[a + 2], c);
+ break;
+ }
}
}
- k = readUnsignedShort(varTable);
- w = varTable + 2;
- for (; k > 0; --k)
+ mv.visitLocalVariable(readUTF8(w + 4, c), readUTF8(w + 6, c), vsignature, labels[start], labels[start
+ + length], index);
+ w += 10;
+ }
+ }
+ // visits the other attributes
+ while (cattrs != null)
+ {
+ attr = cattrs.next;
+ cattrs.next = null;
+ mv.visitAttribute(cattrs);
+ cattrs = attr;
+ }
+ // visits the max stack and max locals values
+ mv.visitMaxs(maxStack, maxLocals);
+ }
+
+ if (mv != null)
+ {
+ mv.visitEnd();
+ }
+ return u;
+ }
+
+ private int readField(final ClassVisitor classVisitor, final int flags, final Attribute[] attrs, char[] c, int u)
+ {
+ boolean includeFieldOverview = (flags & INCLUDE_FIELD_OVERVIEW) != 0;
+ boolean includeFieldAnnotations = (flags & INCLUDE_FIELD_ANNOTATIONS) != 0;
+ boolean includeFieldUnknownAttributes = (flags & INCLUDE_FIELD_UNKNOWN_ATTRIBUTES) != 0;
+ int j;
+ int k;
+ int v;
+ Attribute attr;
+ int access = 0;
+ String name = null;
+ String desc = null;
+ String attrName;
+ String signature;
+ int anns;
+ int ianns;
+ Attribute cattrs;
+ if (includeFieldOverview)
+ {
+ access = readUnsignedShort(u);
+ desc = readUTF8(u + 4, c);
+ }
+ //TODO use index instead and update visitField to use that
+ name = readUTF8(u + 2, c);
+
+ // visits the field's attributes and looks for a ConstantValue
+ // attribute
+ int fieldValueItem = 0;
+ signature = null;
+ anns = 0;
+ ianns = 0;
+ cattrs = null;
+
+ j = readUnsignedShort(u + 6);
+ u += 8;
+ for (; j > 0; --j)
+ {
+ attrName = readUTF8(u, c);
+ // tests are sorted in decreasing frequency order
+ // (based on frequencies observed on typical classes)
+ if ("ConstantValue".equals(attrName))
+ {
+ if (includeFieldOverview)
+ fieldValueItem = readUnsignedShort(u + 6);
+ }
+ else if (SIGNATURES && "Signature".equals(attrName))
+ {
+ if (includeFieldOverview)
+ signature = readUTF8(u + 6, c);
+ }
+ else if ("Deprecated".equals(attrName))
+ {
+ if (includeFieldOverview)
+ access |= Opcodes.ACC_DEPRECATED;
+ }
+ else if ("Synthetic".equals(attrName))
+ {
+ if (includeFieldOverview)
+ access |= Opcodes.ACC_SYNTHETIC;
+ }
+ else if (ANNOTATIONS && "RuntimeVisibleAnnotations".equals(attrName))
+ {
+ if (includeFieldAnnotations)
+ anns = u + 6;
+ }
+ else if (ANNOTATIONS && "RuntimeInvisibleAnnotations".equals(attrName))
+ {
+ if (includeFieldAnnotations)
+ ianns = u + 6;
+ }
+ else
+ {
+ if (includeFieldUnknownAttributes)
+ {
+ attr = readAttribute(attrs, attrName, u + 6, readInt(u + 2), c, -1, null);
+ if (attr != null)
{
- int start = readUnsignedShort(w);
- int length = readUnsignedShort(w + 2);
- int index = readUnsignedShort(w + 8);
- String vsignature = null;
- if (typeTable != null)
+ attr.next = cattrs;
+ cattrs = attr;
+ }
+ }
+ }
+ u += 6 + readInt(u + 2);
+ }
+ // visits the field
+ FieldVisitor fv = classVisitor.visitField(access, name, desc, signature, fieldValueItem == 0
+ ? null
+ : readConst(fieldValueItem, c));
+ // visits the field annotations and attributes
+ if (fv != null)
+ {
+ if (includeFieldAnnotations)
+ {
+ for (j = 1; j >= 0; --j)
+ {
+ v = j == 0 ? ianns : anns;
+ if (v != 0)
+ {
+ k = readUnsignedShort(v);
+ v += 2;
+ for (; k > 0; --k)
{
- for (int a = 0; a < typeTable.length; a += 3)
- {
- if (typeTable[a] == start && typeTable[a + 1] == index)
- {
- vsignature = readUTF8(typeTable[a + 2], c);
- break;
- }
- }
+ v = readAnnotationValues(v + 2, c, true, fv.visitAnnotation(readUTF8(v, c), j != 0));
}
- mv.visitLocalVariable(readUTF8(w + 4, c), readUTF8(w + 6, c), vsignature, labels[start], labels[start
- + length], index);
- w += 10;
}
}
- // visits the other attributes
+ }
+ if (includeFieldUnknownAttributes)
+ {
while (cattrs != null)
{
attr = cattrs.next;
cattrs.next = null;
- mv.visitAttribute(cattrs);
+ fv.visitAttribute(cattrs);
cattrs = attr;
}
- // visits the max stack and max locals values
- mv.visitMaxs(maxStack, maxLocals);
}
-
- if (mv != null)
- {
- mv.visitEnd();
- }
+ fv.visitEnd();
}
-
- // visits the end of the class
- classVisitor.visitEnd();
+ return u;
}
-
+
/**
* Reads parameter annotations and makes the given visitor visit them.
*
More information about the jboss-cvs-commits
mailing list