Java tutorial
/** * Copyright 2012 Douglas Campos <qmx@qmx.me> * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package me.qmx.jitescript; import static me.qmx.jitescript.util.CodegenUtils.ci; import static me.qmx.jitescript.util.CodegenUtils.p; import static me.qmx.jitescript.util.CodegenUtils.params; import static me.qmx.jitescript.util.CodegenUtils.sig; import java.io.PrintStream; import java.util.ArrayList; import java.util.List; import org.objectweb.asm.Handle; import org.objectweb.asm.Label; import org.objectweb.asm.Opcodes; import org.objectweb.asm.tree.*; /** * @author qmx */ public class CodeBlock implements Opcodes { private boolean DEBUG = false; private InsnList instructionList = new InsnList(); private List<TryCatchBlockNode> tryCatchBlockList = new ArrayList<TryCatchBlockNode>(); private List<LocalVariableNode> localVariableList = new ArrayList<LocalVariableNode>(); private List<VisibleAnnotation> annotations = new ArrayList<VisibleAnnotation>(); private int arity = 0; private boolean returns = false; public CodeBlock() { } public CodeBlock(CodeBlock block) { this.arity = block.arity(); prepend(block); } public CodeBlock(int arity) { this.arity = arity; } public static CodeBlock newCodeBlock() { return new CodeBlock(); } public static CodeBlock newCodeBlock(int arity) { return new CodeBlock(arity); } public static CodeBlock newCodeBlock(CodeBlock block) { return new CodeBlock(block); } /** * Short-hand for specifying a set of aloads * * @param args list of aloads you want */ public CodeBlock aloadMany(int... args) { for (int arg : args) { aload(arg); } return this; } public CodeBlock aload(int arg0) { this.instructionList.add(new VarInsnNode(ALOAD, arg0)); return this; } public CodeBlock iload(int arg0) { this.instructionList.add(new VarInsnNode(ILOAD, arg0)); return this; } public CodeBlock lload(int arg0) { this.instructionList.add(new VarInsnNode(LLOAD, arg0)); return this; } public CodeBlock fload(int arg0) { this.instructionList.add(new VarInsnNode(FLOAD, arg0)); return this; } public CodeBlock dload(int arg0) { this.instructionList.add(new VarInsnNode(DLOAD, arg0)); return this; } public CodeBlock astore(int arg0) { this.instructionList.add(new VarInsnNode(ASTORE, arg0)); return this; } public CodeBlock istore(int arg0) { this.instructionList.add(new VarInsnNode(ISTORE, arg0)); return this; } public CodeBlock lstore(int arg0) { this.instructionList.add(new VarInsnNode(LSTORE, arg0)); return this; } public CodeBlock fstore(int arg0) { this.instructionList.add(new VarInsnNode(FSTORE, arg0)); return this; } public CodeBlock dstore(int arg0) { this.instructionList.add(new VarInsnNode(DSTORE, arg0)); return this; } public CodeBlock ldc(Object arg0) { this.instructionList.add(new LdcInsnNode(arg0)); return this; } public CodeBlock bipush(int arg) { this.instructionList.add(new IntInsnNode(BIPUSH, arg)); return this; } public CodeBlock sipush(int arg) { this.instructionList.add(new IntInsnNode(SIPUSH, arg)); return this; } public CodeBlock pushInt(int value) { if (value <= Byte.MAX_VALUE && value >= Byte.MIN_VALUE) { switch (value) { case -1: iconst_m1(); break; case 0: iconst_0(); break; case 1: iconst_1(); break; case 2: iconst_2(); break; case 3: iconst_3(); break; case 4: iconst_4(); break; case 5: iconst_5(); break; default: bipush(value); break; } } else if (value <= Short.MAX_VALUE && value >= Short.MIN_VALUE) { sipush(value); } else { ldc(value); } return this; } public CodeBlock pushBoolean(boolean bool) { if (bool) { iconst_1(); } else { iconst_0(); } return this; } public CodeBlock invokestatic(String arg1, String arg2, String arg3) { this.instructionList.add(new MethodInsnNode(INVOKESTATIC, arg1, arg2, arg3)); return this; } public CodeBlock invokespecial(String arg1, String arg2, String arg3) { this.instructionList.add(new MethodInsnNode(INVOKESPECIAL, arg1, arg2, arg3)); return this; } public CodeBlock invokevirtual(String arg1, String arg2, String arg3) { this.instructionList.add(new MethodInsnNode(INVOKEVIRTUAL, arg1, arg2, arg3)); return this; } public CodeBlock invokeinterface(String arg1, String arg2, String arg3) { this.instructionList.add(new MethodInsnNode(INVOKEINTERFACE, arg1, arg2, arg3)); return this; } public CodeBlock invokedynamic(String arg0, String arg1, Handle arg2, Object... arg3) { this.instructionList.add(new InvokeDynamicInsnNode(arg0, arg1, arg2, arg3)); return this; } public CodeBlock aprintln() { dup(); getstatic(p(System.class), "out", ci(PrintStream.class)); swap(); invokevirtual(p(PrintStream.class), "println", sig(void.class, params(Object.class))); return this; } public CodeBlock iprintln() { dup(); getstatic(p(System.class), "out", ci(PrintStream.class)); swap(); invokevirtual(p(PrintStream.class), "println", sig(void.class, params(int.class))); return this; } public CodeBlock areturn() { this.returns = true; this.instructionList.add(new InsnNode(ARETURN)); return this; } public CodeBlock ireturn() { this.instructionList.add(new InsnNode(IRETURN)); return this; } public CodeBlock freturn() { this.instructionList.add(new InsnNode(FRETURN)); return this; } public CodeBlock lreturn() { this.instructionList.add(new InsnNode(LRETURN)); return this; } public CodeBlock dreturn() { this.instructionList.add(new InsnNode(DRETURN)); return this; } public CodeBlock newobj(String arg0) { this.instructionList.add(new TypeInsnNode(NEW, arg0)); return this; } public CodeBlock dup() { this.instructionList.add(new InsnNode(DUP)); return this; } public CodeBlock swap() { this.instructionList.add(new InsnNode(SWAP)); return this; } public CodeBlock swap2() { dup2_x2(); pop2(); return this; } public CodeBlock getstatic(String arg1, String arg2, String arg3) { this.instructionList.add(new FieldInsnNode(GETSTATIC, arg1, arg2, arg3)); return this; } public CodeBlock putstatic(String arg1, String arg2, String arg3) { this.instructionList.add(new FieldInsnNode(PUTSTATIC, arg1, arg2, arg3)); return this; } public CodeBlock getfield(String arg1, String arg2, String arg3) { this.instructionList.add(new FieldInsnNode(GETFIELD, arg1, arg2, arg3)); return this; } public CodeBlock putfield(String arg1, String arg2, String arg3) { this.instructionList.add(new FieldInsnNode(PUTFIELD, arg1, arg2, arg3)); return this; } public CodeBlock voidreturn() { this.instructionList.add(new InsnNode(RETURN)); return this; } public CodeBlock anewarray(String arg0) { this.instructionList.add(new TypeInsnNode(ANEWARRAY, arg0)); return this; } public CodeBlock multianewarray(String arg0, int dims) { this.instructionList.add(new MultiANewArrayInsnNode(arg0, dims)); return this; } public CodeBlock newarray(int arg0) { this.instructionList.add(new IntInsnNode(NEWARRAY, arg0)); return this; } public CodeBlock iconst_m1() { this.instructionList.add(new InsnNode(ICONST_M1)); return this; } public CodeBlock iconst_0() { this.instructionList.add(new InsnNode(ICONST_0)); return this; } public CodeBlock iconst_1() { this.instructionList.add(new InsnNode(ICONST_1)); return this; } public CodeBlock iconst_2() { this.instructionList.add(new InsnNode(ICONST_2)); return this; } public CodeBlock iconst_3() { this.instructionList.add(new InsnNode(ICONST_3)); return this; } public CodeBlock iconst_4() { this.instructionList.add(new InsnNode(ICONST_4)); return this; } public CodeBlock iconst_5() { this.instructionList.add(new InsnNode(ICONST_5)); return this; } public CodeBlock lconst_0() { this.instructionList.add(new InsnNode(LCONST_0)); return this; } public CodeBlock aconst_null() { this.instructionList.add(new InsnNode(ACONST_NULL)); return this; } public CodeBlock label(LabelNode labelNode) { this.instructionList.add(labelNode); return this; } public CodeBlock nop() { this.instructionList.add(new InsnNode(NOP)); return this; } public CodeBlock pop() { this.instructionList.add(new InsnNode(POP)); return this; } public CodeBlock pop2() { this.instructionList.add(new InsnNode(POP2)); return this; } public CodeBlock arrayload() { this.instructionList.add(new InsnNode(AALOAD)); return this; } public CodeBlock arraystore() { this.instructionList.add(new InsnNode(AASTORE)); return this; } public CodeBlock iarrayload() { this.instructionList.add(new InsnNode(IALOAD)); return this; } public CodeBlock barrayload() { this.instructionList.add(new InsnNode(BALOAD)); return this; } public CodeBlock barraystore() { this.instructionList.add(new InsnNode(BASTORE)); return this; } public CodeBlock aaload() { this.instructionList.add(new InsnNode(AALOAD)); return this; } public CodeBlock aastore() { this.instructionList.add(new InsnNode(AASTORE)); return this; } public CodeBlock iaload() { this.instructionList.add(new InsnNode(IALOAD)); return this; } public CodeBlock iastore() { this.instructionList.add(new InsnNode(IASTORE)); return this; } public CodeBlock laload() { this.instructionList.add(new InsnNode(LALOAD)); return this; } public CodeBlock lastore() { this.instructionList.add(new InsnNode(LASTORE)); return this; } public CodeBlock baload() { this.instructionList.add(new InsnNode(BALOAD)); return this; } public CodeBlock bastore() { this.instructionList.add(new InsnNode(BASTORE)); return this; } public CodeBlock saload() { this.instructionList.add(new InsnNode(SALOAD)); return this; } public CodeBlock sastore() { this.instructionList.add(new InsnNode(SASTORE)); return this; } public CodeBlock caload() { this.instructionList.add(new InsnNode(CALOAD)); return this; } public CodeBlock castore() { this.instructionList.add(new InsnNode(CASTORE)); return this; } public CodeBlock faload() { this.instructionList.add(new InsnNode(FALOAD)); return this; } public CodeBlock fastore() { this.instructionList.add(new InsnNode(FASTORE)); return this; } public CodeBlock daload() { this.instructionList.add(new InsnNode(DALOAD)); return this; } public CodeBlock dastore() { this.instructionList.add(new InsnNode(DASTORE)); return this; } public CodeBlock fcmpl() { this.instructionList.add(new InsnNode(FCMPL)); return this; } public CodeBlock fcmpg() { this.instructionList.add(new InsnNode(FCMPG)); return this; } public CodeBlock dcmpl() { this.instructionList.add(new InsnNode(DCMPL)); return this; } public CodeBlock dcmpg() { this.instructionList.add(new InsnNode(DCMPG)); return this; } public CodeBlock dup_x2() { this.instructionList.add(new InsnNode(DUP_X2)); return this; } public CodeBlock dup_x1() { this.instructionList.add(new InsnNode(DUP_X1)); return this; } public CodeBlock dup2_x2() { this.instructionList.add(new InsnNode(DUP2_X2)); return this; } public CodeBlock dup2_x1() { this.instructionList.add(new InsnNode(DUP2_X1)); return this; } public CodeBlock dup2() { this.instructionList.add(new InsnNode(DUP2)); return this; } public CodeBlock trycatch(LabelNode arg0, LabelNode arg1, LabelNode arg2, String arg3) { this.tryCatchBlockList.add(new TryCatchBlockNode(arg0, arg1, arg2, arg3)); return this; } public CodeBlock trycatch(String type, Runnable body, Runnable catchBody) { LabelNode before = new LabelNode(); LabelNode after = new LabelNode(); LabelNode catchStart = new LabelNode(); LabelNode done = new LabelNode(); trycatch(before, after, catchStart, type); label(before); body.run(); label(after); go_to(done); if (catchBody != null) { label(catchStart); catchBody.run(); } label(done); return this; } public CodeBlock go_to(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(GOTO, arg0)); return this; } public CodeBlock lookupswitch(LabelNode arg0, int[] arg1, LabelNode[] arg2) { this.instructionList.add(new LookupSwitchInsnNode(arg0, arg1, arg2)); return this; } public CodeBlock athrow() { this.instructionList.add(new InsnNode(ATHROW)); return this; } public CodeBlock instance_of(String arg0) { this.instructionList.add(new TypeInsnNode(INSTANCEOF, arg0)); return this; } public CodeBlock ifeq(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFEQ, arg0)); return this; } public CodeBlock iffalse(LabelNode arg0) { ifeq(arg0); return this; } public CodeBlock ifne(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFNE, arg0)); return this; } public CodeBlock iftrue(LabelNode arg0) { ifne(arg0); return this; } public CodeBlock if_acmpne(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ACMPNE, arg0)); return this; } public CodeBlock if_acmpeq(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ACMPEQ, arg0)); return this; } public CodeBlock if_icmple(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ICMPLE, arg0)); return this; } public CodeBlock if_icmpgt(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ICMPGT, arg0)); return this; } public CodeBlock if_icmplt(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ICMPLT, arg0)); return this; } public CodeBlock if_icmpne(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ICMPNE, arg0)); return this; } public CodeBlock if_icmpeq(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ICMPEQ, arg0)); return this; } public CodeBlock if_icmpge(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IF_ICMPGE, arg0)); return this; } public CodeBlock checkcast(String arg0) { this.instructionList.add(new TypeInsnNode(CHECKCAST, arg0)); return this; } public CodeBlock line(int line) { visitLineNumber(line, new LabelNode()); return this; } public CodeBlock line(int line, LabelNode label) { visitLineNumber(line, label); return this; } public CodeBlock ifnonnull(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFNONNULL, arg0)); return this; } public CodeBlock ifnull(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFNULL, arg0)); return this; } public CodeBlock iflt(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFLT, arg0)); return this; } public CodeBlock ifle(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFLE, arg0)); return this; } public CodeBlock ifgt(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFGT, arg0)); return this; } public CodeBlock ifge(LabelNode arg0) { this.instructionList.add(new JumpInsnNode(IFGE, arg0)); return this; } public CodeBlock arraylength() { this.instructionList.add(new InsnNode(ARRAYLENGTH)); return this; } public CodeBlock ishr() { this.instructionList.add(new InsnNode(ISHR)); return this; } public CodeBlock ishl() { this.instructionList.add(new InsnNode(ISHL)); return this; } public CodeBlock iushr() { this.instructionList.add(new InsnNode(IUSHR)); return this; } public CodeBlock lshr() { this.instructionList.add(new InsnNode(LSHR)); return this; } public CodeBlock lshl() { this.instructionList.add(new InsnNode(LSHL)); return this; } public CodeBlock lushr() { this.instructionList.add(new InsnNode(LUSHR)); return this; } public CodeBlock lcmp() { this.instructionList.add(new InsnNode(LCMP)); return this; } public CodeBlock iand() { this.instructionList.add(new InsnNode(IAND)); return this; } public CodeBlock ior() { this.instructionList.add(new InsnNode(IOR)); return this; } public CodeBlock ixor() { this.instructionList.add(new InsnNode(IXOR)); return this; } public CodeBlock land() { this.instructionList.add(new InsnNode(LAND)); return this; } public CodeBlock lor() { this.instructionList.add(new InsnNode(LOR)); return this; } public CodeBlock lxor() { this.instructionList.add(new InsnNode(LXOR)); return this; } public CodeBlock iadd() { this.instructionList.add(new InsnNode(IADD)); return this; } public CodeBlock ladd() { this.instructionList.add(new InsnNode(LADD)); return this; } public CodeBlock fadd() { this.instructionList.add(new InsnNode(FADD)); return this; } public CodeBlock dadd() { this.instructionList.add(new InsnNode(DADD)); return this; } public CodeBlock isub() { this.instructionList.add(new InsnNode(ISUB)); return this; } public CodeBlock lsub() { this.instructionList.add(new InsnNode(LSUB)); return this; } public CodeBlock fsub() { this.instructionList.add(new InsnNode(FSUB)); return this; } public CodeBlock dsub() { this.instructionList.add(new InsnNode(DSUB)); return this; } public CodeBlock idiv() { this.instructionList.add(new InsnNode(IDIV)); return this; } public CodeBlock irem() { this.instructionList.add(new InsnNode(IREM)); return this; } public CodeBlock ineg() { this.instructionList.add(new InsnNode(INEG)); return this; } public CodeBlock i2d() { this.instructionList.add(new InsnNode(I2D)); return this; } public CodeBlock i2l() { this.instructionList.add(new InsnNode(I2L)); return this; } public CodeBlock i2f() { this.instructionList.add(new InsnNode(I2F)); return this; } public CodeBlock i2s() { this.instructionList.add(new InsnNode(I2S)); return this; } public CodeBlock i2c() { this.instructionList.add(new InsnNode(I2C)); return this; } public CodeBlock i2b() { this.instructionList.add(new InsnNode(I2B)); return this; } public CodeBlock ldiv() { this.instructionList.add(new InsnNode(LDIV)); return this; } public CodeBlock lrem() { this.instructionList.add(new InsnNode(LREM)); return this; } public CodeBlock lneg() { this.instructionList.add(new InsnNode(LNEG)); return this; } public CodeBlock l2d() { this.instructionList.add(new InsnNode(L2D)); return this; } public CodeBlock l2i() { this.instructionList.add(new InsnNode(L2I)); return this; } public CodeBlock l2f() { this.instructionList.add(new InsnNode(L2F)); return this; } public CodeBlock fdiv() { this.instructionList.add(new InsnNode(FDIV)); return this; } public CodeBlock frem() { this.instructionList.add(new InsnNode(FREM)); return this; } public CodeBlock fneg() { this.instructionList.add(new InsnNode(FNEG)); return this; } public CodeBlock f2d() { this.instructionList.add(new InsnNode(F2D)); return this; } public CodeBlock f2i() { this.instructionList.add(new InsnNode(F2D)); return this; } public CodeBlock f2l() { this.instructionList.add(new InsnNode(F2L)); return this; } public CodeBlock ddiv() { this.instructionList.add(new InsnNode(DDIV)); return this; } public CodeBlock drem() { this.instructionList.add(new InsnNode(DREM)); return this; } public CodeBlock dneg() { this.instructionList.add(new InsnNode(DNEG)); return this; } public CodeBlock d2f() { this.instructionList.add(new InsnNode(D2F)); return this; } public CodeBlock d2i() { this.instructionList.add(new InsnNode(D2I)); return this; } public CodeBlock d2l() { this.instructionList.add(new InsnNode(D2L)); return this; } public CodeBlock imul() { this.instructionList.add(new InsnNode(IMUL)); return this; } public CodeBlock lmul() { this.instructionList.add(new InsnNode(LMUL)); return this; } public CodeBlock fmul() { this.instructionList.add(new InsnNode(FMUL)); return this; } public CodeBlock dmul() { this.instructionList.add(new InsnNode(DMUL)); return this; } public CodeBlock iinc(int arg0, int arg1) { this.instructionList.add(new IincInsnNode(arg0, arg1)); return this; } public CodeBlock monitorenter() { this.instructionList.add(new InsnNode(MONITORENTER)); return this; } public CodeBlock monitorexit() { this.instructionList.add(new InsnNode(MONITOREXIT)); return this; } public CodeBlock jsr(LabelNode branch) { this.instructionList.add(new JumpInsnNode(JSR, branch)); return this; } public CodeBlock ret(int arg0) { this.instructionList.add(new IntInsnNode(RET, arg0)); return this; } public CodeBlock visitInsn(int arg0) { this.instructionList.add(new InsnNode(arg0)); return this; } public CodeBlock visitIntInsn(int arg0, int arg1) { this.instructionList.add(new IntInsnNode(arg0, arg1)); return this; } public CodeBlock visitInsnNode(int arg0, int arg1) { this.instructionList.add(new IntInsnNode(arg0, arg1)); return this; } public CodeBlock visitTypeInsn(int arg0, String arg1) { this.instructionList.add(new TypeInsnNode(arg0, arg1)); return this; } public CodeBlock visitFieldInsn(int arg0, String arg1, String arg2, String arg3) { this.instructionList.add(new FieldInsnNode(arg0, arg1, arg2, arg3)); return this; } public CodeBlock visitMethodInsn(int arg0, String arg1, String arg2, String arg3) { this.instructionList.add(new MethodInsnNode(arg0, arg1, arg2, arg3)); return this; } public CodeBlock visitInvokeDynamicInsn(String arg0, String arg1, Handle arg2, Object... arg3) { this.instructionList.add(new InvokeDynamicInsnNode(arg0, arg1, arg2, arg3)); return this; } public CodeBlock visitJumpInsn(int arg0, LabelNode arg1) { this.instructionList.add(new JumpInsnNode(arg0, arg1)); return this; } public CodeBlock visitLabel(Label arg0) { this.instructionList.add(new LabelNode(arg0)); return this; } public CodeBlock visitLdcInsn(Object arg0) { this.instructionList.add(new LdcInsnNode(arg0)); return this; } public CodeBlock visitIincInsn(int arg0, int arg1) { this.instructionList.add(new IincInsnNode(arg0, arg1)); return this; } public CodeBlock visitTableSwitchInsn(int arg0, int arg1, LabelNode arg2, LabelNode[] arg3) { this.instructionList.add(new TableSwitchInsnNode(arg0, arg1, arg2, arg3)); return this; } public CodeBlock visitLookupSwitchInsn(LabelNode arg0, int[] arg1, LabelNode[] arg2) { this.instructionList.add(new LookupSwitchInsnNode(arg0, arg1, arg2)); return this; } public CodeBlock visitMultiANewArrayInsn(String arg0, int arg1) { this.instructionList.add(new MultiANewArrayInsnNode(arg0, arg1)); return this; } public CodeBlock visitTryCatchBlock(LabelNode arg0, LabelNode arg1, LabelNode arg2, String arg3) { this.tryCatchBlockList.add(new TryCatchBlockNode(arg0, arg1, arg2, arg3)); return this; } public CodeBlock visitLocalVariable(String arg0, String arg1, String arg2, LabelNode arg3, LabelNode arg4, int arg5) { this.localVariableList.add(new LocalVariableNode(arg0, arg1, arg2, arg3, arg4, arg5)); return this; } public CodeBlock visitLineNumber(int arg0, LabelNode arg1) { this.instructionList.add(new LineNumberNode(arg0, arg1)); return this; } public CodeBlock tableswitch(int min, int max, LabelNode defaultLabel, LabelNode[] cases) { this.instructionList.add(new TableSwitchInsnNode(min, max, defaultLabel, cases)); return this; } public CodeBlock visitFrame(int arg0, int arg1, Object[] arg2, int arg3, Object[] arg4) { this.instructionList.add(new FrameNode(arg0, arg1, arg2, arg3, arg4)); return this; } public InsnList getInstructionList() { return instructionList; } public List<TryCatchBlockNode> getTryCatchBlockList() { return tryCatchBlockList; } public List<LocalVariableNode> getLocalVariableList() { return localVariableList; } public List<VisibleAnnotation> getAnnotations() { return annotations; } /** * adds a compressed frame to the stack * * @param stackArguments the argument types on the stack, represented as "class path names" e.g java/lang/RuntimeException */ public CodeBlock frame_same(Object... stackArguments) { int type; if (stackArguments.length == 0) { type = F_SAME; } else if (stackArguments.length == 1) { type = F_SAME1; } else { throw new IllegalArgumentException("same frame should have 0 or 1 arguments on stack"); } this.instructionList.add(new FrameNode(type, 0, null, stackArguments.length, stackArguments)); return this; } public CodeBlock prepend(CodeBlock codeBlock) { if (codeBlock.returns()) { this.returns = true; } this.annotations.addAll(codeBlock.getAnnotations()); this.getInstructionList().insert(codeBlock.getInstructionList()); return this; } public CodeBlock append(CodeBlock codeBlock) { if (codeBlock.returns()) { this.returns = true; } this.getInstructionList().add(codeBlock.getInstructionList()); this.tryCatchBlockList.addAll(codeBlock.getTryCatchBlockList()); this.annotations.addAll(codeBlock.getAnnotations()); return this; } public VisibleAnnotation annotation(Class<?> type) { VisibleAnnotation annotation = new VisibleAnnotation(ci(type)); addAnnotation(annotation); return annotation; } public CodeBlock addAnnotation(VisibleAnnotation annotation) { annotations.add(annotation); return this; } public int arity() { return this.arity; } public boolean returns() { return returns; } }