Class Bytecode

java.lang.Object
javassist.bytecode.Bytecode
All Implemented Interfaces:
Cloneable, Opcode

public class Bytecode extends Object implements Cloneable, Opcode
A utility class for producing a bytecode sequence.

A Bytecode object is an unbounded array containing bytecode. For example,

 ConstPool cp = ...;    // constant pool table
 Bytecode b = new Bytecode(cp, 1, 0);
 b.addIconst(3);
 b.addReturn(CtClass.intType);
 CodeAttribute ca = b.toCodeAttribute();

This program produces a Code attribute including a bytecode sequence:

 iconst_3
 ireturn
See Also:
  • Field Details

    • THIS

      public static final CtClass THIS
      Represents the CtClass file using the constant pool table given to this Bytecode object.
  • Constructor Details

    • Bytecode

      public Bytecode(ConstPool cp, int stacksize, int localvars)
      Constructs a Bytecode object with an empty bytecode sequence.

      The parameters stacksize and localvars specify initial values of max_stack and max_locals. They can be changed later.

      Parameters:
      cp - constant pool table.
      stacksize - max_stack.
      localvars - max_locals.
    • Bytecode

      public Bytecode(ConstPool cp)
      Constructs a Bytecode object with an empty bytecode sequence. The initial values of max_stack and max_locals are zero.
      Parameters:
      cp - constant pool table.
      See Also:
  • Method Details

    • clone

      public Object clone()
      Creates and returns a copy of this object. The constant pool object is shared between this object and the cloned object.
    • getConstPool

      public ConstPool getConstPool()
      Gets a constant pool table.
    • getExceptionTable

      public ExceptionTable getExceptionTable()
      Returns exception_table.
    • toCodeAttribute

      public CodeAttribute toCodeAttribute()
      Converts to a CodeAttribute.
    • length

      public int length()
      Returns the length of the bytecode sequence.
    • get

      public byte[] get()
      Returns the produced bytecode sequence.
    • getMaxStack

      public int getMaxStack()
      Gets max_stack.
    • setMaxStack

      public void setMaxStack(int size)
      Sets max_stack.

      This value may be automatically updated when an instruction is appended. A Bytecode object maintains the current stack depth whenever an instruction is added by addOpcode(). For example, if DUP is appended, the current stack depth is increased by one. If the new stack depth is more than max_stack, then it is assigned to max_stack. However, if branch instructions are appended, the current stack depth may not be correctly maintained.

      See Also:
    • getMaxLocals

      public int getMaxLocals()
      Gets max_locals.
    • setMaxLocals

      public void setMaxLocals(int size)
      Sets max_locals.
    • setMaxLocals

      public void setMaxLocals(boolean isStatic, CtClass[] params, int locals)
      Sets max_locals.

      This computes the number of local variables used to pass method parameters and sets max_locals to that number plus locals.

      Parameters:
      isStatic - true if params must be interpreted as parameters to a static method.
      params - parameter types.
      locals - the number of local variables excluding ones used to pass parameters.
    • incMaxLocals

      public void incMaxLocals(int diff)
      Increments max_locals.
    • addExceptionHandler

      public void addExceptionHandler(int start, int end, int handler, CtClass type)
      Adds a new entry of exception_table.
    • addExceptionHandler

      public void addExceptionHandler(int start, int end, int handler, String type)
      Adds a new entry of exception_table.
      Parameters:
      type - the fully-qualified name of a throwable class.
    • addExceptionHandler

      public void addExceptionHandler(int start, int end, int handler, int type)
      Adds a new entry of exception_table.
    • currentPc

      public int currentPc()
      Returns the length of bytecode sequence that have been added so far.
    • read

      public int read(int offset)
      Reads a signed 8bit value at the offset from the beginning of the bytecode sequence.
      Throws:
      ArrayIndexOutOfBoundsException - if offset is invalid.
    • read16bit

      public int read16bit(int offset)
      Reads a signed 16bit value at the offset from the beginning of the bytecode sequence.
    • read32bit

      public int read32bit(int offset)
      Reads a signed 32bit value at the offset from the beginning of the bytecode sequence.
    • write

      public void write(int offset, int value)
      Writes an 8bit value at the offset from the beginning of the bytecode sequence.
      Throws:
      ArrayIndexOutOfBoundsException - if offset is invalid.
    • write16bit

      public void write16bit(int offset, int value)
      Writes an 16bit value at the offset from the beginning of the bytecode sequence.
    • write32bit

      public void write32bit(int offset, int value)
      Writes an 32bit value at the offset from the beginning of the bytecode sequence.
    • add

      public void add(int code)
      Appends an 8bit value to the end of the bytecode sequence.
    • add32bit

      public void add32bit(int value)
      Appends a 32bit value to the end of the bytecode sequence.
    • addGap

      public void addGap(int length)
      Appends the length-byte gap to the end of the bytecode sequence.
      Parameters:
      length - the gap length in byte.
    • addOpcode

      public void addOpcode(int code)
      Appends an 8bit opcode to the end of the bytecode sequence. The current stack depth is updated. max_stack is updated if the current stack depth is the deepest so far.

      Note: some instructions such as INVOKEVIRTUAL does not update the current stack depth since the increment depends on the method signature. growStack() must be explicitly called.

    • growStack

      public void growStack(int diff)
      Increases the current stack depth. It also updates max_stack if the current stack depth is the deepest so far.
      Parameters:
      diff - the number added to the current stack depth.
    • getStackDepth

      public int getStackDepth()
      Returns the current stack depth.
    • setStackDepth

      public void setStackDepth(int depth)
      Sets the current stack depth. It also updates max_stack if the current stack depth is the deepest so far.
      Parameters:
      depth - new value.
    • addIndex

      public void addIndex(int index)
      Appends a 16bit value to the end of the bytecode sequence. It never changes the current stack depth.
    • addAload

      public void addAload(int n)
      Appends ALOAD or (WIDE) ALOAD_<n>
      Parameters:
      n - an index into the local variable array.
    • addAstore

      public void addAstore(int n)
      Appends ASTORE or (WIDE) ASTORE_<n>
      Parameters:
      n - an index into the local variable array.
    • addIconst

      public void addIconst(int n)
      Appends ICONST or ICONST_<n>
      Parameters:
      n - the pushed integer constant.
    • addConstZero

      public void addConstZero(CtClass type)
      Appends an instruction for pushing zero or null on the stack. If the type is void, this method does not append any instruction.
      Parameters:
      type - the type of the zero value (or null).
    • addIload

      public void addIload(int n)
      Appends ILOAD or (WIDE) ILOAD_<n>
      Parameters:
      n - an index into the local variable array.
    • addIstore

      public void addIstore(int n)
      Appends ISTORE or (WIDE) ISTORE_<n>
      Parameters:
      n - an index into the local variable array.
    • addLconst

      public void addLconst(long n)
      Appends LCONST or LCONST_<n>
      Parameters:
      n - the pushed long integer constant.
    • addLload

      public void addLload(int n)
      Appends LLOAD or (WIDE) LLOAD_<n>
      Parameters:
      n - an index into the local variable array.
    • addLstore

      public void addLstore(int n)
      Appends LSTORE or LSTORE_<n>
      Parameters:
      n - an index into the local variable array.
    • addDconst

      public void addDconst(double d)
      Appends DCONST or DCONST_<n>
      Parameters:
      d - the pushed double constant.
    • addDload

      public void addDload(int n)
      Appends DLOAD or (WIDE) DLOAD_<n>
      Parameters:
      n - an index into the local variable array.
    • addDstore

      public void addDstore(int n)
      Appends DSTORE or (WIDE) DSTORE_<n>
      Parameters:
      n - an index into the local variable array.
    • addFconst

      public void addFconst(float f)
      Appends FCONST or FCONST_<n>
      Parameters:
      f - the pushed float constant.
    • addFload

      public void addFload(int n)
      Appends FLOAD or (WIDE) FLOAD_<n>
      Parameters:
      n - an index into the local variable array.
    • addFstore

      public void addFstore(int n)
      Appends FSTORE or FSTORE_<n>
      Parameters:
      n - an index into the local variable array.
    • addLoad

      public int addLoad(int n, CtClass type)
      Appends an instruction for loading a value from the local variable at the index n.
      Parameters:
      n - the index.
      type - the type of the loaded value.
      Returns:
      the size of the value (1 or 2 word).
    • addStore

      public int addStore(int n, CtClass type)
      Appends an instruction for storing a value into the local variable at the index n.
      Parameters:
      n - the index.
      type - the type of the stored value.
      Returns:
      2 if the type is long or double. Otherwise 1.
    • addLoadParameters

      public int addLoadParameters(CtClass[] params, int offset)
      Appends instructions for loading all the parameters onto the operand stack.
      Parameters:
      offset - the index of the first parameter. It is 0 if the method is static. Otherwise, it is 1.
    • addCheckcast

      public void addCheckcast(CtClass c)
      Appends CHECKCAST.
      Parameters:
      c - the type.
    • addCheckcast

      public void addCheckcast(String classname)
      Appends CHECKCAST.
      Parameters:
      classname - a fully-qualified class name.
    • addInstanceof

      public void addInstanceof(String classname)
      Appends INSTANCEOF.
      Parameters:
      classname - the class name.
    • addGetfield

      public void addGetfield(CtClass c, String name, String type)
      Appends GETFIELD.
      Parameters:
      c - the class.
      name - the field name.
      type - the descriptor of the field type.
      See Also:
    • addGetfield

      public void addGetfield(String c, String name, String type)
      Appends GETFIELD.
      Parameters:
      c - the fully-qualified class name.
      name - the field name.
      type - the descriptor of the field type.
      See Also:
    • addGetstatic

      public void addGetstatic(CtClass c, String name, String type)
      Appends GETSTATIC.
      Parameters:
      c - the class
      name - the field name
      type - the descriptor of the field type.
      See Also:
    • addGetstatic

      public void addGetstatic(String c, String name, String type)
      Appends GETSTATIC.
      Parameters:
      c - the fully-qualified class name
      name - the field name
      type - the descriptor of the field type.
      See Also:
    • addInvokespecial

      public void addInvokespecial(CtClass clazz, String name, CtClass returnType, CtClass[] paramTypes)
      Appends INVOKESPECIAL.
      Parameters:
      clazz - the target class.
      name - the method name.
      returnType - the return type.
      paramTypes - the parameter types.
    • addInvokespecial

      public void addInvokespecial(CtClass clazz, String name, String desc)
      Appends INVOKESPECIAL.
      Parameters:
      clazz - the target class.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokespecial

      public void addInvokespecial(String clazz, String name, String desc)
      Appends INVOKESPECIAL. The invoked method must not be a default method declared in an interface.
      Parameters:
      clazz - the fully-qualified class name.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokespecial

      public void addInvokespecial(int clazz, String name, String desc)
      Appends INVOKESPECIAL. The invoked method must not be a default method declared in an interface.
      Parameters:
      clazz - the index of CONSTANT_Class_info structure.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokespecial

      public void addInvokespecial(boolean isInterface, int clazz, String name, String desc)
      Appends INVOKESPECIAL.
      Parameters:
      isInterface - true if the invoked method is a default method declared in an interface.
      clazz - the index of CONSTANT_Class_info structure.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokespecial

      public void addInvokespecial(int index, String desc)
      Appends INVOKESPECIAL.
      Parameters:
      index - the index of CONSTANT_Methodref_info or CONSTANT_InterfaceMethodref_info
      desc - the descriptor of the method signature.
      See Also:
    • addInvokestatic

      public void addInvokestatic(CtClass clazz, String name, CtClass returnType, CtClass[] paramTypes)
      Appends INVOKESTATIC.
      Parameters:
      clazz - the target class.
      name - the method name
      returnType - the return type.
      paramTypes - the parameter types.
    • addInvokestatic

      public void addInvokestatic(CtClass clazz, String name, String desc)
      Appends INVOKESTATIC.
      Parameters:
      clazz - the target class.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokestatic

      public void addInvokestatic(String classname, String name, String desc)
      Appends INVOKESTATIC.
      Parameters:
      classname - the fully-qualified class name. It must not be an interface-type name.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokestatic

      public void addInvokestatic(int clazz, String name, String desc)
      Appends INVOKESTATIC.
      Parameters:
      clazz - the index of CONSTANT_Class_info structure. It must not be an interface type.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokevirtual

      public void addInvokevirtual(CtClass clazz, String name, CtClass returnType, CtClass[] paramTypes)
      Appends INVOKEVIRTUAL.

      The specified method must not be an inherited method. It must be directly declared in the class specified in clazz.

      Parameters:
      clazz - the target class.
      name - the method name
      returnType - the return type.
      paramTypes - the parameter types.
    • addInvokevirtual

      public void addInvokevirtual(CtClass clazz, String name, String desc)
      Appends INVOKEVIRTUAL.

      The specified method must not be an inherited method. It must be directly declared in the class specified in clazz.

      Parameters:
      clazz - the target class.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokevirtual

      public void addInvokevirtual(String classname, String name, String desc)
      Appends INVOKEVIRTUAL.

      The specified method must not be an inherited method. It must be directly declared in the class specified in classname.

      Parameters:
      classname - the fully-qualified class name.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokevirtual

      public void addInvokevirtual(int clazz, String name, String desc)
      Appends INVOKEVIRTUAL.

      The specified method must not be an inherited method. It must be directly declared in the class specified by clazz.

      Parameters:
      clazz - the index of CONSTANT_Class_info structure.
      name - the method name
      desc - the descriptor of the method signature.
      See Also:
    • addInvokeinterface

      public void addInvokeinterface(CtClass clazz, String name, CtClass returnType, CtClass[] paramTypes, int count)
      Appends INVOKEINTERFACE.
      Parameters:
      clazz - the target class.
      name - the method name
      returnType - the return type.
      paramTypes - the parameter types.
      count - the count operand of the instruction.
    • addInvokeinterface

      public void addInvokeinterface(CtClass clazz, String name, String desc, int count)
      Appends INVOKEINTERFACE.
      Parameters:
      clazz - the target class.
      name - the method name
      desc - the descriptor of the method signature.
      count - the count operand of the instruction.
      See Also:
    • addInvokeinterface

      public void addInvokeinterface(String classname, String name, String desc, int count)
      Appends INVOKEINTERFACE.
      Parameters:
      classname - the fully-qualified class name.
      name - the method name
      desc - the descriptor of the method signature.
      count - the count operand of the instruction.
      See Also:
    • addInvokeinterface

      public void addInvokeinterface(int clazz, String name, String desc, int count)
      Appends INVOKEINTERFACE.
      Parameters:
      clazz - the index of CONSTANT_Class_info structure.
      name - the method name
      desc - the descriptor of the method signature.
      count - the count operand of the instruction.
      See Also:
    • addInvokedynamic

      public void addInvokedynamic(int bootstrap, String name, String desc)
      Appends INVOKEDYNAMIC.
      Parameters:
      bootstrap - an index into the bootstrap_methods array of the bootstrap method table.
      name - the method name.
      desc - the method descriptor.
      Since:
      3.17
      See Also:
    • addLdc

      public void addLdc(String s)
      Appends LDC or LDC_W. The pushed item is a String object.
      Parameters:
      s - the character string pushed by LDC or LDC_W.
    • addLdc

      public void addLdc(int i)
      Appends LDC or LDC_W.
      Parameters:
      i - index into the constant pool.
    • addLdc2w

      public void addLdc2w(long l)
      Appends LDC2_W. The pushed item is a long value.
    • addLdc2w

      public void addLdc2w(double d)
      Appends LDC2_W. The pushed item is a double value.
    • addNew

      public void addNew(CtClass clazz)
      Appends NEW.
      Parameters:
      clazz - the class of the created instance.
    • addNew

      public void addNew(String classname)
      Appends NEW.
      Parameters:
      classname - the fully-qualified class name.
    • addAnewarray

      public void addAnewarray(String classname)
      Appends ANEWARRAY.
      Parameters:
      classname - the qualified class name of the element type.
    • addAnewarray

      public void addAnewarray(CtClass clazz, int length)
      Appends ICONST and ANEWARRAY.
      Parameters:
      clazz - the elememnt type.
      length - the array length.
    • addNewarray

      public void addNewarray(int atype, int length)
      Appends NEWARRAY for primitive types.
      Parameters:
      atype - T_BOOLEAN, T_CHAR, ...
      See Also:
    • addMultiNewarray

      public int addMultiNewarray(CtClass clazz, int[] dimensions)
      Appends MULTINEWARRAY.
      Parameters:
      clazz - the array type.
      dimensions - the sizes of all dimensions.
      Returns:
      the length of dimensions.
    • addMultiNewarray

      public int addMultiNewarray(CtClass clazz, int dim)
      Appends MULTINEWARRAY. The size of every dimension must have been already pushed on the stack.
      Parameters:
      clazz - the array type.
      dim - the number of the dimensions.
      Returns:
      the value of dim.
    • addMultiNewarray

      public int addMultiNewarray(String desc, int dim)
      Appends MULTINEWARRAY.
      Parameters:
      desc - the type descriptor of the created array.
      dim - dimensions.
      Returns:
      the value of dim.
    • addPutfield

      public void addPutfield(CtClass c, String name, String desc)
      Appends PUTFIELD.
      Parameters:
      c - the target class.
      name - the field name.
      desc - the descriptor of the field type.
    • addPutfield

      public void addPutfield(String classname, String name, String desc)
      Appends PUTFIELD.
      Parameters:
      classname - the fully-qualified name of the target class.
      name - the field name.
      desc - the descriptor of the field type.
    • addPutstatic

      public void addPutstatic(CtClass c, String name, String desc)
      Appends PUTSTATIC.
      Parameters:
      c - the target class.
      name - the field name.
      desc - the descriptor of the field type.
    • addPutstatic

      public void addPutstatic(String classname, String fieldName, String desc)
      Appends PUTSTATIC.
      Parameters:
      classname - the fully-qualified name of the target class.
      fieldName - the field name.
      desc - the descriptor of the field type.
    • addReturn

      public void addReturn(CtClass type)
      Appends ARETURN, IRETURN, .., or RETURN.
      Parameters:
      type - the return type.
    • addRet

      public void addRet(int var)
      Appends RET.
      Parameters:
      var - local variable
    • addPrintln

      public void addPrintln(String message)
      Appends instructions for executing java.lang.System.println(message).
      Parameters:
      message - printed message.
    • getSize

      public final int getSize()
    • copy

      public final byte[] copy()
    • add

      public void add(int b1, int b2)
    • add

      public void add(int b1, int b2, int b3, int b4)