📄 classfile.java
字号:
/* * Copyright (c) 2000 Sun Microsystems, Inc., 901 San Antonio Road, * Palo Alto, CA 94303, U.S.A. All Rights Reserved. * * Sun Microsystems, Inc. has intellectual property rights relating * to the technology embodied in this software. In particular, and * without limitation, these intellectual property rights may include * one or more U.S. patents, foreign patents, or pending * applications. Sun, Sun Microsystems, the Sun logo, Java, KJava, * and all Sun-based and Java-based marks are trademarks or * registered trademarks of Sun Microsystems, Inc. in the United * States and other countries. * * This software is distributed under licenses restricting its use, * copying, distribution, and decompilation. No part of this * software may be reproduced in any form by any means without prior * written authorization of Sun and its licensors, if any. * * FEDERAL ACQUISITIONS: Commercial Software -- Government Users * Subject to Standard License Terms and Conditions */package kdp.classparser;import kdp.classparser.constantpoolclasses.*;import kdp.classparser.attributes.*;import kdp.Log;import java.io.*;import java.util.*;/** * Encapsulation of a Java class file. Stores all * the contents of a class file in memory. * Has methods for reading a class file and displaying * the contents of a class file in an easy to read * manner. * * It is assumed the reader has read and understands * Sun's documentation of the Java class file format. * It is available in the Java VM Specification documentation. * * @author Aaron Dietrich * @version $Id: ClassFile.java,v 1.2 2000/08/14 19:49:10 zmm3876 Exp $ * * Revision History * $Log: ClassFile.java,v $ * Revision 1.2 2000/08/14 19:49:10 zmm3876 * *** empty log message *** * * Revision 1.1 2000/08/09 16:11:48 zmm3876 * *** empty log message *** * * Revision 1.1.1.1 2000/07/07 13:34:23 jrv * Initial import of kdp code * * Revision 1.1.1.1 2000/05/31 19:14:47 ritsun * Initial import of kvmdt to CVS * * Revision 1.1 2000/04/25 00:36:43 ritsun * Initial revision * */public class ClassFile { /** Numeric ID of java.lang.Object's super class */ private static final int OBJECT_SUPER_CLASS_ID = 0; /** Tag type from VMConstants.java */ final byte TYPE_TAG_ARRAY = 3; /** base name of class */ private String baseName; /** className of this class */ private String className; /** name of the class file this represents */ private String classSignature; /** signature of this class name */ private FileReference classFile; /** identifies class file format, always 0xCAFEBABE */ private int magic; /** version number of the class file */ private int majorVersion, minorVersion; /** number of items in the constant pool */ private int constantPoolCount; /** array of items in the constant pool */ private ConstantPoolInfo constantPool[]; /** access flags of this class */ private AccessFlags accessFlags; /** name of this class */ private int thisClass; /** name of super class */ private int superClass; /** number of interfaces this class implements */ private int interfacesCount; /** array of indices into the constant pool table that contain the names of the interfaces this class implements */ private int interfaces[]; /** number of fields of this class */ private int fieldsCount; /** array of FieldInfo objects containing information about all the fields of this class */ private FieldInfo fieldInfo[]; /** number of methods of this class */ private int methodsCount; /** array of MethodInfo objects containing information about all the methods of this class */ private MethodInfo methodInfo[]; /** number of attributes of this class */ private int attributesCount; /** attributes of this class */ private AttributeInfo attributes[]; /** JDWP type type tag */ private byte typeTag; /** the class ID of this class as told to us by the KVM itself */ int classID; int classStatus; /** * Constructor. * * @param classFile reference to the class file this object will represent * * */ public ClassFile (FileReference classFile, String className, byte typeTag) { int index; this.classFile = classFile; this.className = className; if ((index = className.lastIndexOf('/')) != -1) this.baseName = className.substring(index+1); else this.baseName = className; this.typeTag = typeTag; if (typeTag == TYPE_TAG_ARRAY) { /* restore the className which already includes its signature */ classSignature = className; } else { /* Make up the signature for this class * Add 'L' at the beginning, and the ';' at the end. */ classSignature = "L" + className.replace('.', '/') + ";"; } } public boolean equals(String newclassName) { return className.equals(newclassName); } public String getBaseName() { return baseName; } public String getClassName() { return className; } public String getClassSignature() { return classSignature; } /** * Returns the class filename */ public String getClassFileName() { return (classFile.toString()); } public byte getJDWPTypeTag() { return typeTag; } public void setClassID(int classID) { this.classID = classID; } public int getClassID() { return (classID); } public void setClassStatus(int status) { this.classStatus = status; } public int getClassStatus() { return (classStatus); } /** * Reads a Java class file from the filename passed to the constructor. */ public void readClassFile () throws IOException { DataInputStream iStream; try { //create the data input stream and start reading in the //class file iStream = new DataInputStream (classFile.getInputStream()); magic = iStream.readInt (); minorVersion = iStream.readUnsignedShort (); majorVersion = iStream.readUnsignedShort (); readConstantPool (iStream); accessFlags = new AccessFlags (iStream); thisClass = iStream.readUnsignedShort (); superClass = iStream.readUnsignedShort (); readInterfaces (iStream); readFieldInfo (iStream); readMethodInfo (iStream); readAttributes (iStream); iStream.close (); } catch (IOException e) {//something bad happened with the IO. System.out.println ("Caught IO Exception - " + e.getMessage ()); throw(e); } } /** * Reads in the constant pool from a Java class file. * * @param iStream the stream on which to read data * * @return int the number of items in the * constant pool * * @exception IOException just pass any IOExceptions up */ private int readConstantPool (DataInputStream iStream) throws IOException { //read the number of items in the constant pool constantPoolCount = iStream.readUnsignedShort (); //allocate space for the constant pool constantPool = new ConstantPoolInfo[constantPoolCount]; //read in all the items of the constant pool for (int lcv=1; lcv < constantPoolCount; ++lcv) { //the tag identifies what type of constant pool item //this is so read it in, then branch and create the //appropriate object byte tag = iStream.readByte (); switch (tag) { case ConstantPoolInfo.CONSTANT_Class : constantPool[lcv] = new ConstantClassInfo (iStream); break; case ConstantPoolInfo.CONSTANT_Fieldref : constantPool[lcv] = new ConstantFieldrefInfo (iStream); break; case ConstantPoolInfo.CONSTANT_Methodref : constantPool[lcv] = new ConstantMethodrefInfo (iStream); break; case ConstantPoolInfo.CONSTANT_InterfaceMethodref : constantPool[lcv] = new ConstantInterfaceMethodrefInfo (iStream); break; case ConstantPoolInfo.CONSTANT_String : constantPool[lcv] = new ConstantStringInfo (iStream); break; case ConstantPoolInfo.CONSTANT_Integer : constantPool[lcv] = new ConstantIntegerInfo (iStream); break; case ConstantPoolInfo.CONSTANT_Float : constantPool[lcv] = new ConstantFloatInfo (iStream); break; case ConstantPoolInfo.CONSTANT_Long : constantPool[lcv] = new ConstantLongInfo (iStream); ++lcv; //longs "take" two constant pool entries break; case ConstantPoolInfo.CONSTANT_Double : constantPool[lcv] = new ConstantDoubleInfo (iStream); ++lcv; //doubles "take" two constant pool entries break; case ConstantPoolInfo.CONSTANT_NameAndType : constantPool[lcv] = new ConstantNameAndTypeInfo (iStream); break; case ConstantPoolInfo.CONSTANT_Utf8 : constantPool[lcv] = new ConstantUtf8Info (iStream); break; default : break; } } return constantPoolCount; } /**
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -