⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 classreader.java

📁 这是实现Javac功能的GJC的最新源码
💻 JAVA
📖 第 1 页 / 共 3 页
字号:
/** * @(#)ClassReader.java	1.55 03/01/23 * * Copyright 2003 Sun Microsystems, Inc. All rights reserved. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms. */package com.sun.tools.javac.v8.code;import com.sun.tools.javac.v8.util.*;import java.io.*;import java.util.zip.*;import java.util.StringTokenizer;import com.sun.tools.javac.v8.code.Type.*;import com.sun.tools.javac.v8.code.Symbol.*;import com.sun.tools.javac.v8.code.Symtab;/** * This class provides operations to read a classfile into an internal *  representation. The internal representation is anchored in a *  ClassSymbol which contains in its scope symbol representations *  for all other definitions in the classfile. Top-level Classes themselves *  appear as members of the scopes of PackageSymbols. */public class ClassReader extends ClassFile implements Completer, Flags, Kinds,TypeTags {    /**     * The context key for the class reader.     */    private static final Context.Key classReaderKey = new Context.Key();    /**     * The string used as separator in class paths.     */    public static final String pathSep = System.getProperty("path.separator");    /**     * Switch: verbose output.     */    public boolean verbose;    /**     * Switch: check class file for correct minor version, unrecognized     *  attributes.     */    public boolean checkClassFile;    /**     * Switch: read constant pool and code sections. This switch is initially     *  set to false but can be turned on from outside.     */    public boolean readAllOfClassFile = false;    /**     * The log to use for verbose output     */    private final Log log;    /**     * The symbol table.     */    private final Symtab syms;    /**     * The name table.     */    protected final Name.Table names;    /**     * Force a completion failure on this name     */    final Name completionFailureName;    /**     * Can be reassigned from outside:     *  the class path to be searched for user classes.     */    public String classPath;    /**     * The class path to be searched for system classes.     */    public String bootClassPath;    /**     * The path to be searched for sources     */    public String sourceClassPath;    /**     * Can be reassigned from outside:     *  the completer to be used for ".java" files. If this remains unassigned     *  ".java" files will not be loaded.     */    public SourceCompleter sourceCompleter = null;    /**     * A hashtable containing the encountered top-level and member classes,     *  indexed by flat names. The table does not contain local classes.     */    private Hashtable classes;    /**     * A hashtable containing the encountered packages.     */    private Hashtable packages;    /**     * The current scope where type variables are entered.     */    Scope typevars = new Scope(null);    /**     * The path name of the class file currently being read.     */    String currentClassFileName = null;    /**     * The class or method currently being read.     */    Symbol currentOwner = null;    /**     * The buffer containing the currently read class file.     */    byte[] buf = new byte[65520];    /**     * The current input pointer.     */    int bp;    /**     * The objects of the constant pool.     */    Object[] poolObj;    /**     * For every constant pool entry, an index into buf where the     *  defining section of the entry is found.     */    int[] poolIdx;    /**     * Get the ClassReader instance for this invocation.     */    public static ClassReader instance(Context context) {        ClassReader instance = (ClassReader) context.get(classReaderKey);        if (instance == null)            instance = new ClassReader(context, true);        return instance;    }    /**      * Initialize classes and packages, treating this as the definitive classreader.      */    public void init(Symtab syms) {        init(syms, true);    }    /**      * Initialize classes and packages, optionally treating this as      *  the definitive classreader.      */    private void init(Symtab syms, boolean definitive) {        if (classes != null)            return;        if (definitive) {            assert packages == null || packages == syms.packages;            packages = syms.packages;            assert classes == null || classes == syms.classes;            classes = syms.classes;        } else {            packages = new Hashtable();            classes = new Hashtable();        }        packages.put(syms.rootPackage.fullname, syms.rootPackage);        syms.rootPackage.completer = this;        packages.put(syms.emptyPackage.fullname, syms.emptyPackage);        syms.emptyPackage.completer = this;    }    /**      * Construct a new class reader, optionally treated as the      *  definitive classreader for this invocation.      */    protected ClassReader(Context context, boolean definitive) {        super();        if (definitive)            context.put(classReaderKey, this);        names = Name.Table.instance(context);        syms = Symtab.instance(context);        init(syms, definitive);        log = Log.instance(context);        Options options = Options.instance(context);        verbose = options.get("-verbose") != null;        checkClassFile = options.get("-checkclassfile") != null;        setClassPaths(options);        completionFailureName = (options.get("failcomplete") != null) ?                names.fromString((String) options.get("failcomplete")) : null;    }    /**      * Set classPath, bootClassPath, and sourceClassPath.      */    private void setClassPaths(Options options) {        String cp = (String) options.get("-classpath");        if (cp == null)            cp = System.getProperty("env.class.path");        if (cp == null && System.getProperty("application.home") == null)            cp = System.getProperty("java.class.path");        if (cp == null)            cp = ".";        classPath = terminate(cp);        String bp = (String) options.get("-bootclasspath");        if (bp == null) {            bp = System.getProperty("sun.boot.class.path");            if (bp == null)                bp = System.getProperty("java.class.path");            if (bp == null)                bp = ".";        }        String bpp = (String) options.get("-Xbootclasspath/p:");        if (bpp != null)            bp = bpp + System.getProperty("path.separator") + bp;        bootClassPath = terminate(bp);        String ed = (String) options.get("-extdirs");        if (ed == null)            ed = System.getProperty("java.ext.dirs");        if (ed == null)            ed = "";        String extdirs = terminate(ed);        int i = 0;        int edlen = extdirs.length();        while (i < edlen) {            int end = extdirs.indexOf(pathSep, i);            String extdir = extdirs.substring(i, end);            addArchives(extdir);            i = end + 1;        }        String sp = (String) options.get("-sourcepath");        if (sp != null) {            sourceClassPath = terminate(sp);        } else {            sourceClassPath = null;        }    }    /**      * Add all archives in `extdir' to boot class path      */    private void addArchives(String extdir) {        String[] archives = new File(extdir).list();        for (int i = 0; archives != null && i < archives.length; i++) {            if (archives[i].endsWith(".jar")) {                String prefix = (extdir.endsWith(File.separator)) ? extdir :                        (extdir + File.separator);                bootClassPath = bootClassPath + prefix + archives[i] + pathSep;            }        }    }    /**      * Add path separator to string if it does not end in one already      */    private String terminate(String s) {        return (s.endsWith(pathSep)) ? s : s + pathSep;    }    /**      * Add member to class unless it is synthetic      */    private void enterMember(ClassSymbol c, Symbol sym) {        if ((sym.flags_field & SYNTHETIC) == 0)            c.members_field.enter(sym);    }    /**      * Error Diagnoses      */    public static class BadClassFile extends CompletionFailure {        /**         * @param msg A localized message.         */        public BadClassFile(ClassSymbol c, String cname, String msg) {            super(c, Log.getLocalizedString("bad.class.file.header", cname, msg));        }    }    public BadClassFile badClassFile(String key) {        return new BadClassFile(currentOwner.enclClass(), currentClassFileName,                Log.getLocalizedString(key));    }    public BadClassFile badClassFile(String key, String arg0) {        return new BadClassFile(currentOwner.enclClass(), currentClassFileName,                Log.getLocalizedString(key, arg0));    }    public BadClassFile badClassFile(String key, String arg0, String arg1) {        return new BadClassFile(currentOwner.enclClass(), currentClassFileName,                Log.getLocalizedString(key, arg0, arg1));    }    public BadClassFile badClassFile(String key, String arg0, String arg1,            String arg2) {        return new BadClassFile(currentOwner.enclClass(), currentClassFileName,                Log.getLocalizedString(key, arg0, arg1, arg2));    }    public BadClassFile badClassFile(String key, String arg0, String arg1,            String arg2, String arg3) {        return new BadClassFile(currentOwner.enclClass(), currentClassFileName,                Log.getLocalizedString(key, arg0, arg1, arg2, arg3));    }    /**      * Read a character.      */    char nextChar() {        return (char)(((buf[bp++] & 255)<< 8) + (buf[bp++] & 255));    }    /**      * Read an integer.      */    int nextInt() {        return ((buf[bp++] & 255)<< 24) + ((buf[bp++] & 255)<< 16) +                ((buf[bp++] & 255)<< 8) + (buf[bp++] & 255);    }    /**      * Extract a character at position bp from buf.      */    char getChar(int bp) {        return (char)(((buf[bp] & 255)<< 8) + (buf[bp + 1] & 255));    }    /**      * Extract an integer at position bp from buf.      */    int getInt(int bp) {        return ((buf[bp] & 255)<< 24) + ((buf[bp + 1] & 255)<< 16) +                ((buf[bp + 2] & 255)<< 8) + (buf[bp + 3] & 255);    }    /**      * Extract a long integer at position bp from buf.      */    long getLong(int bp) {        DataInputStream bufin =                new DataInputStream(new ByteArrayInputStream(buf, bp, 8));        try {            return bufin.readLong();        } catch (IOException e) {            throw new AssertionError();        }    }    /**      * Extract a float at position bp from buf.      */    float getFloat(int bp) {        DataInputStream bufin =                new DataInputStream(new ByteArrayInputStream(buf, bp, 4));        try {            return bufin.readFloat();        } catch (IOException e) {            throw new AssertionError();        }    }    /**      * Extract a double at position bp from buf.      */    double getDouble(int bp) {        DataInputStream bufin =                new DataInputStream(new ByteArrayInputStream(buf, bp, 8));        try {            return bufin.readDouble();        } catch (IOException e) {            throw new AssertionError();        }    }    /**      * Index all constant pool entries, writing their start addresses into      *  poolIdx.      */    void indexPool() {        poolIdx = new int[nextChar()];        poolObj = new Object[poolIdx.length];        int i = 1;        while (i < poolIdx.length) {            poolIdx[i++] = bp;            byte tag = buf[bp++];            switch (tag) {            case CONSTANT_Utf8:            case CONSTANT_Unicode:                {                    int len = nextChar();                    bp = bp + len;                    break;                }            case CONSTANT_Class:            case CONSTANT_String:                bp = bp + 2;                break;            case CONSTANT_Fieldref:            case CONSTANT_Methodref:            case CONSTANT_InterfaceMethodref:            case CONSTANT_NameandType:            case CONSTANT_Integer:            case CONSTANT_Float:                bp = bp + 4;                break;            case CONSTANT_Long:            case CONSTANT_Double:                bp = bp + 8;                i++;                break;            default:                throw badClassFile("bad.const.pool.tag.at", Byte.toString(tag),                        Integer.toString(bp - 1));            }        }    }    /**      * Read constant pool entry at start address i, use pool as a cache.      */    Object readPool(int i) {        Object result = poolObj[i];        if (result != null)            return result;        int index = poolIdx[i];        if (index == 0)            return null;        byte tag = buf[index];        switch (tag) {        case CONSTANT_Utf8:            poolObj[i] = names.fromUtf(buf, index + 3, getChar(index + 1));            break;        case CONSTANT_Unicode:

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -