143 lines
4.5 KiB
Java
143 lines
4.5 KiB
Java
|
|
package com.de22.javabytecode.attribute;
|
||
|
|
|
||
|
|
import com.common.util.IIterator;
|
||
|
|
import com.common.util.IList;
|
||
|
|
import com.common.util.LiteList;
|
||
|
|
import com.de22.javabytecode.CodeAttribute;
|
||
|
|
import com.de22.javabytecode.Type;
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Copyright Declarative Engineering LLC 2007<p>
|
||
|
|
*/
|
||
|
|
public class InnerClasses extends CodeAttribute {
|
||
|
|
public static final String DEFAULT_NAME = "InnerClasses";
|
||
|
|
private IList innerClasses = null;
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Identifies a single line number.
|
||
|
|
*/
|
||
|
|
public static class InnerClass {
|
||
|
|
/** References the class constant in the constant pool for the inner class. */
|
||
|
|
public short innerClassInfo = 0;
|
||
|
|
/** References the class constant in the constant pool for the outer class. */
|
||
|
|
public short outerClassInfo = 0;
|
||
|
|
/** References the name of the inner class in the constant pool. */
|
||
|
|
public short innerNameIndex = 0;
|
||
|
|
/** The modifiers for the inner class. */
|
||
|
|
public short innerClassAccessFlags = 0;
|
||
|
|
|
||
|
|
public InnerClass() {
|
||
|
|
}//InnerClass()//
|
||
|
|
public InnerClass(short innerClassInfo, short outerClassInfo, short innerNameIndex, short innerClassAccessFlags) {
|
||
|
|
this.innerClassInfo = innerClassInfo;
|
||
|
|
this.outerClassInfo = outerClassInfo;
|
||
|
|
this.innerNameIndex = innerNameIndex;
|
||
|
|
this.innerClassAccessFlags = innerClassAccessFlags;
|
||
|
|
}//InnerClass()//
|
||
|
|
}//InnerClass//
|
||
|
|
/**
|
||
|
|
* InnerClasses constructor.
|
||
|
|
* @param type
|
||
|
|
*/
|
||
|
|
public InnerClasses(Type type) {
|
||
|
|
super(type);
|
||
|
|
}//InnerClasses()//
|
||
|
|
/**
|
||
|
|
* Gets the count of inner classes.
|
||
|
|
* @return The number of inner classes defined in this code attribute.
|
||
|
|
*/
|
||
|
|
public int getInnerClassesCount() {
|
||
|
|
return innerClasses.getSize();
|
||
|
|
}//getInnerClassesCount()//
|
||
|
|
/**
|
||
|
|
* Gets the inner class data at the given zero based index.
|
||
|
|
* @param index The zero based index of the inner class.
|
||
|
|
* @return The inner class data.
|
||
|
|
*/
|
||
|
|
public InnerClass getInnerClass(int index) {
|
||
|
|
return (InnerClass) innerClasses.get(index);
|
||
|
|
}//getInnerClass()//
|
||
|
|
/**
|
||
|
|
* Gets the attribute's default name as it is stored in the class bytes.
|
||
|
|
* @return The default name identifying the attribute's type.
|
||
|
|
*/
|
||
|
|
public String getDefaultName() {
|
||
|
|
return DEFAULT_NAME;
|
||
|
|
}//getDefaultName()//
|
||
|
|
/**
|
||
|
|
* Gets the size in number of bytes of the component and all subcomponents.
|
||
|
|
* @return The number of bytes required to represent the component and all subcomponents.
|
||
|
|
*/
|
||
|
|
public int getSize() {
|
||
|
|
return 2 + (innerClasses != null ? innerClasses.getSize() * 8 : 0);
|
||
|
|
}//getSize()//
|
||
|
|
/**
|
||
|
|
* Reads this object from the given stream.
|
||
|
|
* @param in The input stream to read this object from.
|
||
|
|
*/
|
||
|
|
public void readExternal(java.io.ObjectInput in) throws java.io.IOException, ClassNotFoundException {
|
||
|
|
int innerClassCount;
|
||
|
|
|
||
|
|
super.readExternal(in);
|
||
|
|
|
||
|
|
in.readInt(); //Read the size of the attribute.//
|
||
|
|
innerClassCount = in.readShort();
|
||
|
|
innerClasses = new LiteList(innerClassCount == 0 ? 1 : innerClassCount, 10);
|
||
|
|
|
||
|
|
while(innerClassCount-- > 0) {
|
||
|
|
innerClasses.add(new InnerClass(in.readShort(), in.readShort(), in.readShort(), in.readShort()));
|
||
|
|
}//while//
|
||
|
|
}//readExternal()//
|
||
|
|
/**
|
||
|
|
* @see Component.toString(StringBuffer, int)
|
||
|
|
*/
|
||
|
|
public void toString(StringBuffer buffer, int tabCount) {
|
||
|
|
IIterator iterator = null;
|
||
|
|
|
||
|
|
if(innerClasses != null) {
|
||
|
|
iterator = innerClasses.iterator();
|
||
|
|
appendTabs(buffer, tabCount);
|
||
|
|
buffer.append("InnerClasses {");
|
||
|
|
appendEndOfLine(buffer);
|
||
|
|
|
||
|
|
while(iterator.hasNext()) {
|
||
|
|
InnerClass innerClass = (InnerClass) iterator.next();
|
||
|
|
appendTabs(buffer, tabCount + 1);
|
||
|
|
buffer.append("LocalVariable (innerClassInfo=");
|
||
|
|
buffer.append(innerClass.innerClassInfo);
|
||
|
|
buffer.append(" outerClassInfo=");
|
||
|
|
buffer.append(innerClass.outerClassInfo);
|
||
|
|
buffer.append(" innerNameIndex=");
|
||
|
|
buffer.append(innerClass.innerNameIndex);
|
||
|
|
buffer.append(" innerClassAccessFlags=");
|
||
|
|
buffer.append(innerClass.innerClassAccessFlags);
|
||
|
|
buffer.append(")");
|
||
|
|
appendEndOfLine(buffer);
|
||
|
|
}//while//
|
||
|
|
|
||
|
|
appendTabs(buffer, tabCount);
|
||
|
|
buffer.append('}');
|
||
|
|
appendEndOfLine(buffer);
|
||
|
|
}//if//
|
||
|
|
}//toString()//
|
||
|
|
/**
|
||
|
|
* Writes this object to the given stream.
|
||
|
|
* @param out The output stream to write this object to.
|
||
|
|
*/
|
||
|
|
public void writeExternal(java.io.ObjectOutput out) throws java.io.IOException {
|
||
|
|
short length = (short) (innerClasses != null ? innerClasses.getSize() : 0);
|
||
|
|
|
||
|
|
super.writeExternal(out);
|
||
|
|
|
||
|
|
out.writeShort(length);
|
||
|
|
|
||
|
|
for(int index = 0; index < length; index++) {
|
||
|
|
InnerClass innerClass = (InnerClass) innerClasses.get(index);
|
||
|
|
|
||
|
|
out.writeShort(innerClass.innerClassInfo);
|
||
|
|
out.writeShort(innerClass.outerClassInfo);
|
||
|
|
out.writeShort(innerClass.innerNameIndex);
|
||
|
|
out.writeShort(innerClass.innerClassAccessFlags);
|
||
|
|
}//for//
|
||
|
|
}//writeExternal()//
|
||
|
|
}//InnerClasses//
|