--- old/src/java.xml/share/classes/com/sun/org/apache/bcel/internal/classfile/Attribute.java 2017-08-08 16:04:23.174893951 -0700
+++ new/src/java.xml/share/classes/com/sun/org/apache/bcel/internal/classfile/Attribute.java 2017-08-08 16:04:23.090889745 -0700
@@ -1,6 +1,5 @@
/*
- * reserved comment block
- * DO NOT REMOVE OR ALTER!
+ * Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved.
*/
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
@@ -18,255 +17,295 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-
package com.sun.org.apache.bcel.internal.classfile;
-
-import com.sun.org.apache.bcel.internal.Constants;
-import java.io.*;
+import java.io.DataInput;
+import java.io.DataInputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
import java.util.HashMap;
+import java.util.Map;
+
+import com.sun.org.apache.bcel.internal.Const;
/**
* Abstract super class for Attribute objects. Currently the
* ConstantValue, SourceFile, Code,
* Exceptiontable, LineNumberTable,
* LocalVariableTable, InnerClasses and
- * Synthetic attributes are supported. The
- * Unknown attribute stands for non-standard-attributes.
+ * Synthetic attributes are supported. The Unknown
+ * attribute stands for non-standard-attributes.
*
- * @author M. Dahm
- * @see ConstantValue
- * @see SourceFile
- * @see Code
- * @see Unknown
- * @see ExceptionTable
- * @see LineNumberTable
- * @see LocalVariableTable
- * @see InnerClasses
- * @see Synthetic
- * @see Deprecated
- * @see Signature
-*/
-public abstract class Attribute implements Cloneable, Node, Serializable {
- protected int name_index; // Points to attribute name in constant pool
- protected int length; // Content length of attribute field
- protected byte tag; // Tag to distiguish subclasses
- protected ConstantPool constant_pool;
-
- protected Attribute(byte tag, int name_index, int length,
- ConstantPool constant_pool) {
- this.tag = tag;
- this.name_index = name_index;
- this.length = length;
- this.constant_pool = constant_pool;
- }
-
- /**
- * Called by objects that are traversing the nodes of the tree implicitely
- * defined by the contents of a Java class. I.e., the hierarchy of methods,
- * fields, attributes, etc. spawns a tree of objects.
- *
- * @param v Visitor object
- */
- public abstract void accept(Visitor v);
-
- /**
- * Dump attribute to file stream in binary format.
- *
- * @param file Output file stream
- * @throws IOException
- */
- public void dump(DataOutputStream file) throws IOException
- {
- file.writeShort(name_index);
- file.writeInt(length);
- }
-
- private static HashMap readers = new HashMap();
-
- /** Add an Attribute reader capable of parsing (user-defined) attributes
- * named "name". You should not add readers for the standard attributes
- * such as "LineNumberTable", because those are handled internally.
- *
- * @param name the name of the attribute as stored in the class file
- * @param r the reader object
- */
- public static void addAttributeReader(String name, AttributeReader r) {
- readers.put(name, r);
- }
-
- /** Remove attribute reader
- *
- * @param name the name of the attribute as stored in the class file
- */
- public static void removeAttributeReader(String name) {
- readers.remove(name);
- }
-
- /* Class method reads one attribute from the input data stream.
- * This method must not be accessible from the outside. It is
- * called by the Field and Method constructor methods.
- *
- * @see Field
- * @see Method
- * @param file Input stream
- * @param constant_pool Array of constants
- * @return Attribute
- * @throws IOException
- * @throws ClassFormatException
- */
- public static final Attribute readAttribute(DataInputStream file,
- ConstantPool constant_pool)
- throws IOException, ClassFormatException
- {
- ConstantUtf8 c;
- String name;
- int name_index;
- int length;
- byte tag = Constants.ATTR_UNKNOWN; // Unknown attribute
-
- // Get class name from constant pool via `name_index' indirection
- name_index = (int)file.readUnsignedShort();
- c = (ConstantUtf8)constant_pool.getConstant(name_index,
- Constants.CONSTANT_Utf8);
- name = c.getBytes();
-
- // Length of data in bytes
- length = file.readInt();
-
- // Compare strings to find known attribute
- for(byte i=0; i < Constants.KNOWN_ATTRIBUTES; i++) {
- if(name.equals(Constants.ATTRIBUTE_NAMES[i])) {
- tag = i; // found!
- break;
- }
- }
-
- // Call proper constructor, depending on `tag'
- switch(tag) {
- case Constants.ATTR_UNKNOWN:
- AttributeReader r = (AttributeReader)readers.get(name);
-
- if(r != null)
- return r.createAttribute(name_index, length, file, constant_pool);
- else
- return new Unknown(name_index, length, file, constant_pool);
-
- case Constants.ATTR_CONSTANT_VALUE:
- return new ConstantValue(name_index, length, file, constant_pool);
-
- case Constants.ATTR_SOURCE_FILE:
- return new SourceFile(name_index, length, file, constant_pool);
-
- case Constants.ATTR_CODE:
- return new Code(name_index, length, file, constant_pool);
-
- case Constants.ATTR_EXCEPTIONS:
- return new ExceptionTable(name_index, length, file, constant_pool);
-
- case Constants.ATTR_LINE_NUMBER_TABLE:
- return new LineNumberTable(name_index, length, file, constant_pool);
-
- case Constants.ATTR_LOCAL_VARIABLE_TABLE:
- return new LocalVariableTable(name_index, length, file, constant_pool);
-
- case Constants.ATTR_LOCAL_VARIABLE_TYPE_TABLE:
- return new LocalVariableTypeTable(name_index, length, file, constant_pool);
-
- case Constants.ATTR_INNER_CLASSES:
- return new InnerClasses(name_index, length, file, constant_pool);
-
- case Constants.ATTR_SYNTHETIC:
- return new Synthetic(name_index, length, file, constant_pool);
-
- case Constants.ATTR_DEPRECATED:
- return new Deprecated(name_index, length, file, constant_pool);
-
- case Constants.ATTR_PMG:
- return new PMGClass(name_index, length, file, constant_pool);
-
- case Constants.ATTR_SIGNATURE:
- return new Signature(name_index, length, file, constant_pool);
-
- case Constants.ATTR_STACK_MAP:
- return new StackMap(name_index, length, file, constant_pool);
-
- default: // Never reached
- throw new IllegalStateException("Ooops! default case reached.");
- }
- }
-
- /**
- * @return Length of attribute field in bytes.
- */
- public final int getLength() { return length; }
-
- /**
- * @param Attribute length in bytes.
- */
- public final void setLength(int length) {
- this.length = length;
- }
-
- /**
- * @param name_index of attribute.
- */
- public final void setNameIndex(int name_index) {
- this.name_index = name_index;
- }
-
- /**
- * @return Name index in constant pool of attribute name.
- */
- public final int getNameIndex() { return name_index; }
-
- /**
- * @return Tag of attribute, i.e., its type. Value may not be altered, thus
- * there is no setTag() method.
- */
- public final byte getTag() { return tag; }
-
- /**
- * @return Constant pool used by this object.
- * @see ConstantPool
- */
- public final ConstantPool getConstantPool() { return constant_pool; }
-
- /**
- * @param constant_pool Constant pool to be used for this object.
- * @see ConstantPool
- */
- public final void setConstantPool(ConstantPool constant_pool) {
- this.constant_pool = constant_pool;
- }
-
- /**
- * Use copy() if you want to have a deep copy(), i.e., with all references
- * copied correctly.
- *
- * @return shallow copy of this attribute
- */
- public Object clone() {
- Object o = null;
-
- try {
- o = super.clone();
- } catch(CloneNotSupportedException e) {
- e.printStackTrace(); // Never occurs
- }
-
- return o;
- }
-
- /**
- * @return deep copy of this attribute
- */
- public abstract Attribute copy(ConstantPool constant_pool);
-
- /**
- * @return attribute name.
- */
- public String toString() {
- return Constants.ATTRIBUTE_NAMES[tag];
- }
+ * @version $Id: Attribute.java 1750029 2016-06-23 22:14:38Z sebb $
+ * @see ConstantValue
+ * @see SourceFile
+ * @see Code
+ * @see Unknown
+ * @see ExceptionTable
+ * @see LineNumberTable
+ * @see LocalVariableTable
+ * @see InnerClasses
+ * @see Synthetic
+ * @see Deprecated
+ * @see Signature
+ */
+public abstract class Attribute implements Cloneable, Node {
+
+ private int name_index; // Points to attribute name in constant pool
+ private int length; // Content length of attribute field
+ private final byte tag; // Tag to distinguish subclasses
+ private ConstantPool constant_pool;
+
+ protected Attribute(final byte tag, final int name_index, final int length, final ConstantPool constant_pool) {
+ this.tag = tag;
+ this.name_index = name_index;
+ this.length = length;
+ this.constant_pool = constant_pool;
+ }
+
+ /**
+ * Called by objects that are traversing the nodes of the tree implicitely
+ * defined by the contents of a Java class. I.e., the hierarchy of methods,
+ * fields, attributes, etc. spawns a tree of objects.
+ *
+ * @param v Visitor object
+ */
+ @Override
+ public abstract void accept(Visitor v);
+
+ /**
+ * Dump attribute to file stream in binary format.
+ *
+ * @param file Output file stream
+ * @throws IOException
+ */
+ public void dump(final DataOutputStream file) throws IOException {
+ file.writeShort(name_index);
+ file.writeInt(length);
+ }
+
+ private static final Map readers = new HashMap<>();
+
+ /**
+ * Add an Attribute reader capable of parsing (user-defined) attributes
+ * named "name". You should not add readers for the standard attributes such
+ * as "LineNumberTable", because those are handled internally.
+ *
+ * @param name the name of the attribute as stored in the class file
+ * @param r the reader object
+ */
+ public static void addAttributeReader(final String name, final UnknownAttributeReader r) {
+ readers.put(name, r);
+ }
+
+ /**
+ * Remove attribute reader
+ *
+ * @param name the name of the attribute as stored in the class file
+ */
+ public static void removeAttributeReader(final String name) {
+ readers.remove(name);
+ }
+
+ /**
+ * Class method reads one attribute from the input data stream. This method
+ * must not be accessible from the outside. It is called by the Field and
+ * Method constructor methods.
+ *
+ * @see Field
+ * @see Method
+ *
+ * @param file Input stream
+ * @param constant_pool Array of constants
+ * @return Attribute
+ * @throws IOException
+ * @throws ClassFormatException
+ */
+ public static Attribute readAttribute(final DataInputStream file, final ConstantPool constant_pool)
+ throws IOException, ClassFormatException {
+ return readAttribute((DataInput) file, constant_pool);
+ }
+
+ /**
+ * Class method reads one attribute from the input data stream. This method
+ * must not be accessible from the outside. It is called by the Field and
+ * Method constructor methods.
+ *
+ * @see Field
+ * @see Method
+ *
+ * @param file Input stream
+ * @param constant_pool Array of constants
+ * @return Attribute
+ * @throws IOException
+ * @throws ClassFormatException
+ * @since 6.0
+ */
+ public static Attribute readAttribute(final DataInput file, final ConstantPool constant_pool)
+ throws IOException, ClassFormatException {
+ byte tag = Const.ATTR_UNKNOWN; // Unknown attribute
+ // Get class name from constant pool via `name_index' indirection
+ final int name_index = file.readUnsignedShort();
+ final ConstantUtf8 c = (ConstantUtf8) constant_pool.getConstant(name_index, Const.CONSTANT_Utf8);
+ final String name = c.getBytes();
+
+ // Length of data in bytes
+ final int length = file.readInt();
+
+ // Compare strings to find known attribute
+ for (byte i = 0; i < Const.KNOWN_ATTRIBUTES; i++) {
+ if (name.equals(Const.getAttributeName(i))) {
+ tag = i; // found!
+ break;
+ }
+ }
+
+ // Call proper constructor, depending on `tag'
+ switch (tag) {
+ case Const.ATTR_UNKNOWN:
+ final Object r = readers.get(name);
+ if (r instanceof UnknownAttributeReader) {
+ return ((UnknownAttributeReader) r).createAttribute(name_index, length, file, constant_pool);
+ }
+ return new Unknown(name_index, length, file, constant_pool);
+ case Const.ATTR_CONSTANT_VALUE:
+ return new ConstantValue(name_index, length, file, constant_pool);
+ case Const.ATTR_SOURCE_FILE:
+ return new SourceFile(name_index, length, file, constant_pool);
+ case Const.ATTR_CODE:
+ return new Code(name_index, length, file, constant_pool);
+ case Const.ATTR_EXCEPTIONS:
+ return new ExceptionTable(name_index, length, file, constant_pool);
+ case Const.ATTR_LINE_NUMBER_TABLE:
+ return new LineNumberTable(name_index, length, file, constant_pool);
+ case Const.ATTR_LOCAL_VARIABLE_TABLE:
+ return new LocalVariableTable(name_index, length, file, constant_pool);
+ case Const.ATTR_INNER_CLASSES:
+ return new InnerClasses(name_index, length, file, constant_pool);
+ case Const.ATTR_SYNTHETIC:
+ return new Synthetic(name_index, length, file, constant_pool);
+ case Const.ATTR_DEPRECATED:
+ return new Deprecated(name_index, length, file, constant_pool);
+ case Const.ATTR_PMG:
+ return new PMGClass(name_index, length, file, constant_pool);
+ case Const.ATTR_SIGNATURE:
+ return new Signature(name_index, length, file, constant_pool);
+ case Const.ATTR_STACK_MAP:
+ return new StackMap(name_index, length, file, constant_pool);
+ case Const.ATTR_RUNTIME_VISIBLE_ANNOTATIONS:
+ return new RuntimeVisibleAnnotations(name_index, length, file, constant_pool);
+ case Const.ATTR_RUNTIME_INVISIBLE_ANNOTATIONS:
+ return new RuntimeInvisibleAnnotations(name_index, length, file, constant_pool);
+ case Const.ATTR_RUNTIME_VISIBLE_PARAMETER_ANNOTATIONS:
+ return new RuntimeVisibleParameterAnnotations(name_index, length, file, constant_pool);
+ case Const.ATTR_RUNTIME_INVISIBLE_PARAMETER_ANNOTATIONS:
+ return new RuntimeInvisibleParameterAnnotations(name_index, length, file, constant_pool);
+ case Const.ATTR_ANNOTATION_DEFAULT:
+ return new AnnotationDefault(name_index, length, file, constant_pool);
+ case Const.ATTR_LOCAL_VARIABLE_TYPE_TABLE:
+ return new LocalVariableTypeTable(name_index, length, file, constant_pool);
+ case Const.ATTR_ENCLOSING_METHOD:
+ return new EnclosingMethod(name_index, length, file, constant_pool);
+ case Const.ATTR_STACK_MAP_TABLE:
+ return new StackMap(name_index, length, file, constant_pool);
+ case Const.ATTR_BOOTSTRAP_METHODS:
+ return new BootstrapMethods(name_index, length, file, constant_pool);
+ case Const.ATTR_METHOD_PARAMETERS:
+ return new MethodParameters(name_index, length, file, constant_pool);
+ default:
+ // Never reached
+ throw new IllegalStateException("Unrecognized attribute type tag parsed: " + tag);
+ }
+ }
+
+ /**
+ * @return Name of attribute
+ * @since 6.0
+ */
+ public String getName() {
+ final ConstantUtf8 c = (ConstantUtf8) constant_pool.getConstant(name_index, Const.CONSTANT_Utf8);
+ return c.getBytes();
+ }
+
+ /**
+ * @return Length of attribute field in bytes.
+ */
+ public final int getLength() {
+ return length;
+ }
+
+ /**
+ * @param length length in bytes.
+ */
+ public final void setLength(final int length) {
+ this.length = length;
+ }
+
+ /**
+ * @param name_index of attribute.
+ */
+ public final void setNameIndex(final int name_index) {
+ this.name_index = name_index;
+ }
+
+ /**
+ * @return Name index in constant pool of attribute name.
+ */
+ public final int getNameIndex() {
+ return name_index;
+ }
+
+ /**
+ * @return Tag of attribute, i.e., its type. Value may not be altered, thus
+ * there is no setTag() method.
+ */
+ public final byte getTag() {
+ return tag;
+ }
+
+ /**
+ * @return Constant pool used by this object.
+ * @see ConstantPool
+ */
+ public final ConstantPool getConstantPool() {
+ return constant_pool;
+ }
+
+ /**
+ * @param constant_pool Constant pool to be used for this object.
+ * @see ConstantPool
+ */
+ public final void setConstantPool(final ConstantPool constant_pool) {
+ this.constant_pool = constant_pool;
+ }
+
+ /**
+ * Use copy() if you want to have a deep copy(), i.e., with all references
+ * copied correctly.
+ *
+ * @return shallow copy of this attribute
+ */
+ @Override
+ public Object clone() {
+ Attribute attr = null;
+ try {
+ attr = (Attribute) super.clone();
+ } catch (final CloneNotSupportedException e) {
+ throw new Error("Clone Not Supported"); // never happens
+ }
+ return attr;
+ }
+
+ /**
+ * @return deep copy of this attribute
+ */
+ public abstract Attribute copy(ConstantPool _constant_pool);
+
+ /**
+ * @return attribute name.
+ */
+ @Override
+ public String toString() {
+ return Const.getAttributeName(tag);
+ }
}