📄 classwriter.java
字号:
/*** * ASM: a very small and fast Java bytecode manipulation framework * Copyright (C) 2000 INRIA, France Telecom * Copyright (C) 2002 France Telecom * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * Contact: Eric.Bruneton@rd.francetelecom.com * * Author: Eric Bruneton */package org.objectweb.asm;/** * A {@link ClassVisitor ClassVisitor} that generates Java class files. More * precisely this visitor generates a byte array conforming to the Java class * file format. It can be used alone, to generate a Java class "from scratch", * or with one or more {@link ClassReader ClassReader} and adapter class * visitor to generate a modified class from one or more existing Java classes. */public class ClassWriter implements ClassVisitor { /** * The type of CONSTANT_Class constant pool items. */ final static int CLASS = 7; /** * The type of CONSTANT_Fieldref constant pool items. */ final static int FIELD = 9; /** * The type of CONSTANT_Methodref constant pool items. */ final static int METH = 10; /** * The type of CONSTANT_InterfaceMethodref constant pool items. */ final static int IMETH = 11; /** * The type of CONSTANT_String constant pool items. */ final static int STR = 8; /** * The type of CONSTANT_Integer constant pool items. */ final static int INT = 3; /** * The type of CONSTANT_Float constant pool items. */ final static int FLOAT = 4; /** * The type of CONSTANT_Long constant pool items. */ final static int LONG = 5; /** * The type of CONSTANT_Double constant pool items. */ final static int DOUBLE = 6; /** * The type of CONSTANT_NameAndType constant pool items. */ final static int NAME_TYPE = 12; /** * The type of CONSTANT_Utf8 constant pool items. */ final static int UTF8 = 1; /** * Index of the next item to be added in the constant pool. */ private short index; /** * The constant pool of this class. */ private ByteVector pool; /** * The constant pool's hash table data. */ private Item[] table; /** * The threshold of the constant pool's hash table. */ private int threshold; /** * The access flags of this class. */ private int access; /** * The constant pool item that contains the internal name of this class. */ private int name; /** * The constant pool item that contains the internal name of the super class * of this class. */ private int superName; /** * Number of interfaces implemented or extended by this class or interface. */ private int interfaceCount; /** * The interfaces implemented or extended by this class or interface. More * precisely, this array contains the indexes of the constant pool items * that contain the internal names of these interfaces. */ private int[] interfaces; /** * The constant pool item that contains the name of the source file from * which this class was compiled. */ private Item sourceFile; /** * Number of fields of this class. */ private int fieldCount; /** * The fields of this class. */ private ByteVector fields; /** * <tt>true</tt> if the maximum stack size and number of local variables must * be automatically computed. */ private boolean computeMaxs; /** * The methods of this class. These methods are stored in a linked list of * {@link CodeWriter CodeWriter} objects, linked to each other by their {@link * CodeWriter#next} field. This field stores the first element of this list. */ CodeWriter firstMethod; /** * The methods of this class. These methods are stored in a linked list of * {@link CodeWriter CodeWriter} objects, linked to each other by their {@link * CodeWriter#next} field. This field stores the last element of this list. */ CodeWriter lastMethod; /** * The number of entries in the InnerClasses attribute. */ private int innerClassesCount; /** * The InnerClasses attribute. */ private ByteVector innerClasses; /** * A reusable key used to look for items in the hash {@link #table table}. */ Item key; /** * A reusable key used to look for items in the hash {@link #table table}. */ Item key2; /** * A reusable key used to look for items in the hash {@link #table table}. */ Item key3; /** * The type of instructions without any label. */ final static int NOARG_INSN = 0; /** * The type of instructions with an signed byte label. */ final static int SBYTE_INSN = 1; /** * The type of instructions with an signed short label. */ final static int SHORT_INSN = 2; /** * The type of instructions with a local variable index label. */ final static int VAR_INSN = 3; /** * The type of instructions with an implicit local variable index label. */ final static int IMPLVAR_INSN = 4; /** * The type of instructions with a type descriptor argument. */ final static int TYPE_INSN = 5; /** * The type of field and method invocations instructions. */ final static int FIELDORMETH_INSN = 6; /** * The type of the INVOKEINTERFACE instruction. */ final static int ITFMETH_INSN = 7; /** * The type of instructions with a 2 bytes bytecode offset label. */ final static int LABEL_INSN = 8; /** * The type of instructions with a 4 bytes bytecode offset label. */ final static int LABELW_INSN = 9; /** * The type of the LDC instruction. */ final static int LDC_INSN = 10; /** * The type of the LDC_W and LDC2_W instructions. */ final static int LDCW_INSN = 11; /** * The type of the IINC instruction. */ final static int IINC_INSN = 12; /** * The type of the TABLESWITCH instruction. */ final static int TABL_INSN = 13; /** * The type of the LOOKUPSWITCH instruction. */ final static int LOOK_INSN = 14; /** * The type of the MULTIANEWARRAY instruction. */ final static int MANA_INSN = 15; /** * The type of the WIDE instruction. */ final static int WIDE_INSN = 16; /** * The instruction types of all JVM opcodes. */ static byte[] TYPE; // -------------------------------------------------------------------------- // Static initializer // -------------------------------------------------------------------------- /** * Computes the instruction types of JVM opcodes. */ static { int i; byte[] b = new byte[220]; String s = "AAAAAAAAAAAAAAAABCKLLDDDDDEEEEEEEEEEEEEEEEEEEEAAAAAAAADDDDDEEEEEEEEE" + "EEEEEEEEEEEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAMAAA" + "AAAAAAAAAAAAAAAAAIIIIIIIIIIIIIIIIDNOAAAAAAGGGGGGGHAFBFAAFFAAQPIIJJII" + "IIIIIIIIIIIIIIII"; for (i = 0; i < b.length; ++i) { b[i] = (byte)(s.charAt(i) - 'A'); } TYPE = b; /* code to generate the above string // SBYTE_INSN instructions b[Constants.NEWARRAY] = SBYTE_INSN; b[Constants.BIPUSH] = SBYTE_INSN; // SHORT_INSN instructions b[Constants.SIPUSH] = SHORT_INSN; // (IMPL)VAR_INSN instructions b[Constants.RET] = VAR_INSN; for (i = Constants.ILOAD; i <= Constants.ALOAD; ++i) { b[i] = VAR_INSN; } for (i = Constants.ISTORE; i <= Constants.ASTORE; ++i) { b[i] = VAR_INSN; } for (i = 26; i <= 45; ++i) { // ILOAD_0 to ALOAD_3 b[i] = IMPLVAR_INSN; } for (i = 59; i <= 78; ++i) { // ISTORE_0 to ASTORE_3 b[i] = IMPLVAR_INSN; } // TYPE_INSN instructions b[Constants.NEW] = TYPE_INSN; b[Constants.ANEWARRAY] = TYPE_INSN; b[Constants.CHECKCAST] = TYPE_INSN; b[Constants.INSTANCEOF] = TYPE_INSN; // (Set)FIELDORMETH_INSN instructions for (i = Constants.GETSTATIC; i <= Constants.INVOKESTATIC; ++i) { b[i] = FIELDORMETH_INSN; } b[Constants.INVOKEINTERFACE] = ITFMETH_INSN; // LABEL(W)_INSN instructions for (i = Constants.IFEQ; i <= Constants.JSR; ++i) { b[i] = LABEL_INSN; } b[Constants.IFNULL] = LABEL_INSN; b[Constants.IFNONNULL] = LABEL_INSN; b[200] = LABELW_INSN; // GOTO_W b[201] = LABELW_INSN; // JSR_W // temporary opcodes used internally by ASM - see Label and CodeWriter for (i = 202; i < 220; ++i) { b[i] = LABEL_INSN; } // LDC(_W) instructions b[Constants.LDC] = LDC_INSN; b[19] = LDCW_INSN; // LDC_W b[20] = LDCW_INSN; // LDC2_W // special instructions b[Constants.IINC] = IINC_INSN; b[Constants.TABLESWITCH] = TABL_INSN; b[Constants.LOOKUPSWITCH] = LOOK_INSN; b[Constants.MULTIANEWARRAY] = MANA_INSN; b[196] = WIDE_INSN; // WIDE for (i = 0; i < b.length; ++i) { System.err.print((char)('A' + b[i])); } System.err.println(); */ } // -------------------------------------------------------------------------- // Constructor // -------------------------------------------------------------------------- /** * Constructs a new {@link ClassWriter ClassWriter} object. * * @param computeMaxs <tt>true</tt> if the maximum stack size and the maximum * number of local variables must be automatically computed. If this flag * is <tt>true</tt>, then the arguments of the {@link * CodeVisitor#visitMaxs visitMaxs} method of the {@link CodeVisitor * CodeVisitor} returned by the {@link #visitMethod visitMethod} method * will be ignored, and computed automatically from the signature and * the bytecode of each method. */ public ClassWriter (final boolean computeMaxs) { index = 1; pool = new ByteVector(); table = new Item[64]; threshold = (int)(0.75d*table.length); key = new Item(); key2 = new Item(); key3 = new Item(); this.computeMaxs = computeMaxs; } // -------------------------------------------------------------------------- // Implementation of the ClassVisitor interface // -------------------------------------------------------------------------- public void visit ( final int access, final String name, final String superName, final String[] interfaces, final String sourceFile) { this.access = access; this.name = newClass(name).index; this.superName = superName == null ? 0 : newClass(superName).index; if (interfaces != null && interfaces.length > 0) { interfaceCount = interfaces.length; this.interfaces = new int[interfaceCount]; for (int i = 0; i < interfaceCount; ++i) { this.interfaces[i] = newClass(interfaces[i]).index; } }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -