Example usage for org.objectweb.asm.tree MethodNode MethodNode

List of usage examples for org.objectweb.asm.tree MethodNode MethodNode

Introduction

In this page you can find the example usage for org.objectweb.asm.tree MethodNode MethodNode.

Prototype

public MethodNode(final int access, final String name, final String descriptor, final String signature,
        final String[] exceptions) 

Source Link

Document

Constructs a new MethodNode .

Usage

From source file:net.sandius.rembulan.compiler.gen.asm.ResumeMethod.java

License:Apache License

public MethodNode methodNode() {
    MethodNode node = new MethodNode(ACC_PUBLIC, "resume",
            Type.getMethodType(Type.VOID_TYPE, Type.getType(ExecutionContext.class), Type.getType(Object.class))
                    .getDescriptor(),//from  w ww. j av  a  2s  . co m
            null, runMethod.throwsExceptions());

    if (runMethod.isResumable()) {
        InsnList il = node.instructions;
        List<LocalVariableNode> locals = node.localVariables;

        LabelNode begin = new LabelNode();
        LabelNode vars = new LabelNode();
        LabelNode end = new LabelNode();

        il.add(begin);

        il.add(new VarInsnNode(ALOAD, 2));
        il.add(new TypeInsnNode(CHECKCAST, Type.getInternalName(DefaultSavedState.class)));

        il.add(vars);

        il.add(new VarInsnNode(ASTORE, 3));

        il.add(new VarInsnNode(ALOAD, 0)); // this
        il.add(new VarInsnNode(ALOAD, 1)); // context

        il.add(new VarInsnNode(ALOAD, 3)); // saved state
        il.add(new MethodInsnNode(INVOKEVIRTUAL, Type.getInternalName(DefaultSavedState.class),
                "resumptionPoint", Type.getMethodDescriptor(Type.INT_TYPE), false)); // resumption point

        // registers
        if (context.isVararg() || runMethod.numOfRegisters() > 0) {
            il.add(new VarInsnNode(ALOAD, 3));
            il.add(new MethodInsnNode(INVOKEVIRTUAL, Type.getInternalName(DefaultSavedState.class), "registers",
                    Type.getMethodDescriptor(ASMUtils.arrayTypeFor(Object.class)), false));

            // varargs stored as the 0th element
            int numRegs = runMethod.numOfRegisters() + (context.isVararg() ? 1 : 0);

            for (int i = 0; i < numRegs; i++) {

                // Note: it might be more elegant to use a local variable
                // to store the array instead of having to perform SWAPs

                if (i + 1 < numRegs) {
                    il.add(new InsnNode(DUP));
                }
                il.add(ASMUtils.loadInt(i));
                il.add(new InsnNode(AALOAD));
                if (i == 0 && context.isVararg()) {
                    il.add(new TypeInsnNode(CHECKCAST, ASMUtils.arrayTypeFor(Object.class).getInternalName()));
                }

                if (i + 1 < numRegs) {
                    il.add(new InsnNode(SWAP));
                }
            }
        }

        // call run(...)
        il.add(runMethod.methodInvokeInsn());

        il.add(new InsnNode(RETURN));
        il.add(end);

        locals.add(new LocalVariableNode("this", context.thisClassType().getDescriptor(), null, begin, end, 0));
        locals.add(new LocalVariableNode("context", Type.getDescriptor(ExecutionContext.class), null, begin,
                end, 1));
        locals.add(new LocalVariableNode("suspendedState", context.savedStateClassType().getDescriptor(), null,
                begin, end, 2));
        locals.add(
                new LocalVariableNode("ss", Type.getDescriptor(DefaultSavedState.class), null, vars, end, 3));

        // TODO: maxStack, maxLocals
        node.maxStack = 3 + (runMethod.numOfRegisters() > 0 ? 3 : 0);
        node.maxLocals = 5;
    } else {
        InsnList il = node.instructions;
        List<LocalVariableNode> locals = node.localVariables;

        LabelNode begin = new LabelNode();
        LabelNode end = new LabelNode();

        il.add(begin);
        il.add(new TypeInsnNode(NEW, Type.getInternalName(NonsuspendableFunctionException.class)));
        il.add(new InsnNode(DUP));
        il.add(ASMUtils.ctor(NonsuspendableFunctionException.class));
        il.add(new InsnNode(ATHROW));
        il.add(end);

        locals.add(new LocalVariableNode("this", context.thisClassType().getDescriptor(), null, begin, end, 0));
        locals.add(new LocalVariableNode("context", Type.getDescriptor(ExecutionContext.class), null, begin,
                end, 1));
        locals.add(new LocalVariableNode("suspendedState", context.savedStateClassType().getDescriptor(), null,
                begin, end, 2));

        node.maxStack = 2;
        node.maxLocals = 3;
    }

    return node;
}

From source file:net.sandius.rembulan.compiler.gen.asm.RunMethod.java

License:Apache License

public MethodNode snapshotMethodNode() {
    MethodNode node = new MethodNode(ACC_PRIVATE, snapshotMethodName(), snapshotMethodType().getDescriptor(),
            null, null);/*from  w  ww . j  a  v a2s. com*/

    InsnList il = node.instructions;
    LabelNode begin = new LabelNode();
    LabelNode end = new LabelNode();

    il.add(begin);

    il.add(new TypeInsnNode(NEW, Type.getInternalName(DefaultSavedState.class)));
    il.add(new InsnNode(DUP));

    // resumption point
    il.add(new VarInsnNode(ILOAD, 1));

    // registers
    int numRegs = numOfRegisters() + (context.isVararg() ? 1 : 0);
    int regOffset = context.isVararg() ? 3 : 2;

    il.add(ASMUtils.loadInt(numRegs));
    il.add(new TypeInsnNode(ANEWARRAY, Type.getInternalName(Object.class)));
    {
        for (int i = 0; i < numRegs; i++) {
            il.add(new InsnNode(DUP));
            il.add(ASMUtils.loadInt(i));
            il.add(new VarInsnNode(ALOAD, 2 + i));
            il.add(new InsnNode(AASTORE));
        }
    }

    il.add(ASMUtils.ctor(Type.getType(DefaultSavedState.class), Type.INT_TYPE,
            ASMUtils.arrayTypeFor(Object.class)));

    il.add(new InsnNode(ARETURN));

    il.add(end);

    List<LocalVariableNode> locals = node.localVariables;

    locals.add(new LocalVariableNode("this", context.thisClassType().getDescriptor(), null, begin, end, 0));
    locals.add(new LocalVariableNode("rp", Type.INT_TYPE.getDescriptor(), null, begin, end, 1));
    if (context.isVararg()) {
        locals.add(new LocalVariableNode("varargs", ASMUtils.arrayTypeFor(Object.class).getDescriptor(), null,
                begin, end, 2));
    }
    for (int i = 0; i < numOfRegisters(); i++) {
        locals.add(new LocalVariableNode("r_" + i, Type.getDescriptor(Object.class), null, begin, end,
                regOffset + i));
    }

    node.maxLocals = 2 + numOfRegisters();
    node.maxStack = 4 + 3; // 4 to get register array at top, +3 to add element to it

    return node;
}

From source file:net.sandius.rembulan.compiler.gen.asm.RunMethod.java

License:Apache License

private MethodNode emitRunMethod(String methodName, Type returnType, BytecodeEmitVisitor visitor,
        List<BasicBlock> blocks, boolean sub) {
    MethodNode node = new MethodNode(ACC_PRIVATE, methodName, methodType(returnType).getDescriptor(), null,
            throwsExceptions());// w w  w .  jav a 2s . c  o m

    InsnList insns = node.instructions;

    LabelNode l_begin = new LabelNode();
    LabelNode l_end = new LabelNode();

    visitor.visitBlocks(blocks);

    InsnList prefix = new InsnList();
    InsnList suffix = new InsnList();

    final LabelNode l_head;
    final List<LabelNode> els = new ArrayList<>();
    if (sub) {
        assert (!blocks.isEmpty());
        for (int i = blocks.size() - 1; i >= 0; i--) {
            BasicBlock blk = blocks.get(i);
            LabelNode l = visitor.labels.get(blk.label());
            assert (l != null);
            els.add(l);
        }
        l_head = visitor.labels.get(blocks.get(0).label());
    } else {
        l_head = new LabelNode();
        els.add(l_head);
    }

    assert (l_head != null);

    if (visitor.isResumable()) {
        LabelNode l_error_state = new LabelNode();
        LabelNode l_handler_begin = new LabelNode();

        List<LabelNode> rls = visitor.resumptionLabels();

        assert (!rls.isEmpty() || !els.isEmpty());

        prefix.add(dispatchTable(els, rls, l_error_state));

        final LabelNode l_entry = l_head;

        if (!sub) {
            prefix.add(l_entry);
            prefix.add(ASMUtils.frameSame());
        }

        suffix.add(errorState(l_error_state));
        suffix.add(resumptionHandler(l_handler_begin));

        node.tryCatchBlocks.add(new TryCatchBlockNode(l_entry, l_error_state, l_handler_begin,
                Type.getInternalName(UnresolvedControlThrowable.class)));
    }

    insns.add(l_begin);
    insns.add(prefix);
    insns.add(visitor.instructions());
    insns.add(suffix);
    insns.add(l_end);

    addLocals(node, l_begin, l_end, visitor);

    return node;
}

From source file:net.sandius.rembulan.compiler.gen.asm.RunMethod.java

License:Apache License

private MethodNode emitSegmentedRunMethod(int numOfSegments) {
    MethodNode node = new MethodNode(ACC_PRIVATE, methodName(), methodType().getDescriptor(), null,
            throwsExceptions());//from   w w  w  .j  a v  a 2s  . c o m

    InsnList il = node.instructions;

    int lvOffset = slotOffset() + numOfRegisters();

    int lv_rpp = lvOffset + 0;
    int lv_methodIdx = lvOffset + 1;
    int lv_jmpIdx = lvOffset + 2;
    int lv_stateIdx = lvOffset + 3;
    int lv_savedState = lvOffset + 4;

    LabelNode l_top = new LabelNode();
    LabelNode l_ret = new LabelNode();
    LabelNode l_end = new LabelNode();

    LabelNode l_rpp = new LabelNode();
    LabelNode l_methodIdx = new LabelNode();
    LabelNode l_jmpIdx = new LabelNode();
    LabelNode l_stateIdx = new LabelNode();
    LabelNode l_savedState = new LabelNode();

    il.add(l_top);
    il.add(new FrameNode(F_SAME, 0, null, 0, null));

    // rpp = rp & ((1 << ST_SHIFT_SEGMENT) - 1)
    il.add(new VarInsnNode(ILOAD, LV_RESUME));
    il.add(ASMUtils.loadInt((1 << ST_SHIFT_SEGMENT) - 1));
    il.add(new InsnNode(IAND));
    il.add(new VarInsnNode(ISTORE, lv_rpp));
    il.add(l_rpp);
    il.add(new FrameNode(F_APPEND, 1, new Object[] { Opcodes.INTEGER }, 0, null));

    // methodIdx = rp >>> ST_SHIFT_SEGMENT
    il.add(new VarInsnNode(ILOAD, LV_RESUME));
    il.add(ASMUtils.loadInt(ST_SHIFT_SEGMENT));
    il.add(new InsnNode(IUSHR));
    il.add(new VarInsnNode(ISTORE, lv_methodIdx));
    il.add(l_methodIdx);
    il.add(new FrameNode(F_APPEND, 1, new Object[] { Opcodes.INTEGER }, 0, null));

    // jmpIdx = rpp >>> ST_SHIFT_LABELIDX
    il.add(new VarInsnNode(ILOAD, lv_rpp));
    il.add(ASMUtils.loadInt(ST_SHIFT_LABELIDX));
    il.add(new InsnNode(IUSHR));
    il.add(new VarInsnNode(ISTORE, lv_jmpIdx));
    il.add(l_jmpIdx);
    il.add(new FrameNode(F_APPEND, 1, new Object[] { Opcodes.INTEGER }, 0, null));

    // stateIdx = (rp & ((1 << ST_SHIFT_LABELIDX) - 1)) - jmpIdx
    il.add(new VarInsnNode(ILOAD, LV_RESUME));
    il.add(ASMUtils.loadInt((1 << ST_SHIFT_LABELIDX) - 1));
    il.add(new InsnNode(IAND));
    il.add(new VarInsnNode(ILOAD, lv_jmpIdx));
    il.add(new InsnNode(ISUB));
    il.add(new VarInsnNode(ISTORE, lv_stateIdx));
    il.add(l_stateIdx);
    il.add(new FrameNode(F_APPEND, 1, new Object[] { Opcodes.INTEGER }, 0, null));

    // savedState = null
    il.add(new InsnNode(ACONST_NULL));
    il.add(new VarInsnNode(ASTORE, lv_savedState));
    il.add(l_savedState);
    il.add(new FrameNode(F_APPEND, 1, new Object[] { context.savedStateClassType().getInternalName() }, 0,
            null));

    // switch on methodIdx

    LabelNode l_after = new LabelNode();

    LabelNode l_error = new LabelNode();
    LabelNode[] l_invokes = new LabelNode[numOfSegments];
    for (int i = 0; i < numOfSegments; i++) {
        l_invokes[i] = new LabelNode();
    }

    il.add(new VarInsnNode(ILOAD, lv_methodIdx));
    il.add(new TableSwitchInsnNode(0, numOfSegments - 1, l_error, l_invokes));

    for (int i = 0; i < numOfSegments; i++) {
        il.add(l_invokes[i]);
        il.add(new FrameNode(F_SAME, 0, null, 0, null));
        // push arguments to stack
        il.add(new VarInsnNode(ALOAD, 0));
        il.add(new VarInsnNode(ALOAD, LV_CONTEXT));
        il.add(new VarInsnNode(ILOAD, lv_stateIdx)); // pass stateIdx to the sub-method
        if (context.isVararg()) {
            il.add(new VarInsnNode(ALOAD, LV_VARARGS));
        }
        for (int j = 0; j < numOfRegisters(); j++) {
            il.add(new VarInsnNode(ALOAD, slotOffset() + j));
        }

        il.add(new MethodInsnNode(INVOKESPECIAL, context.thisClassType().getInternalName(), subRunMethodName(i),
                subMethodType().getDescriptor(), false));

        il.add(new VarInsnNode(ASTORE, lv_savedState));
        il.add(new JumpInsnNode(GOTO, l_after));
    }

    // error state
    il.add(errorState(l_error));

    il.add(l_after);
    il.add(new FrameNode(F_SAME, 0, null, 0, null));

    il.add(new VarInsnNode(ALOAD, lv_savedState));
    il.add(new JumpInsnNode(IFNULL, l_ret)); // savedState == null ?

    // continuing: savedState != null

    // FIXME: taken from ResumeMethod -- beware of code duplication!

    il.add(new VarInsnNode(ALOAD, lv_savedState)); // saved state
    il.add(new MethodInsnNode(INVOKEVIRTUAL, Type.getInternalName(DefaultSavedState.class), "resumptionPoint",
            Type.getMethodDescriptor(Type.INT_TYPE), false)); // resumption point
    il.add(new VarInsnNode(ISTORE, LV_RESUME));

    // registers
    if (context.isVararg() || numOfRegisters() > 0) {
        il.add(new VarInsnNode(ALOAD, lv_savedState));
        il.add(new MethodInsnNode(INVOKEVIRTUAL, Type.getInternalName(DefaultSavedState.class), "registers",
                Type.getMethodDescriptor(ASMUtils.arrayTypeFor(Object.class)), false));

        int numRegs = numOfRegisters() + (context.isVararg() ? 1 : 0);

        for (int i = 0; i < numRegs; i++) {
            if (i + 1 < numRegs) {
                il.add(new InsnNode(DUP));
            }
            il.add(ASMUtils.loadInt(i));
            il.add(new InsnNode(AALOAD));
            if (i == 0 && context.isVararg()) {
                il.add(new TypeInsnNode(CHECKCAST, ASMUtils.arrayTypeFor(Object.class).getInternalName()));
            }
            il.add(new VarInsnNode(ASTORE, LV_VARARGS + i));
        }
    }

    // loop back to the beginning
    il.add(new JumpInsnNode(GOTO, l_top));

    // got a null, that's the end
    il.add(l_ret);
    il.add(new FrameNode(F_SAME, 0, null, 0, null));
    il.add(new InsnNode(RETURN));

    il.add(l_end);

    // add local variables
    node.localVariables.addAll(baseLocals(l_top, l_end));
    node.localVariables
            .add(new LocalVariableNode("rpp", Type.INT_TYPE.getDescriptor(), null, l_rpp, l_ret, lv_rpp));
    node.localVariables.add(new LocalVariableNode("methodIdx", Type.INT_TYPE.getDescriptor(), null, l_methodIdx,
            l_ret, lv_methodIdx));
    node.localVariables.add(
            new LocalVariableNode("jmpIdx", Type.INT_TYPE.getDescriptor(), null, l_jmpIdx, l_ret, lv_jmpIdx));
    node.localVariables.add(new LocalVariableNode("stateIdx", Type.INT_TYPE.getDescriptor(), null, l_stateIdx,
            l_ret, lv_stateIdx));
    node.localVariables.add(new LocalVariableNode("savedState", context.savedStateClassType().getDescriptor(),
            null, l_savedState, l_ret, lv_savedState));

    return node;
}

From source file:net.sandius.rembulan.compiler.gen.asm.StaticConstructorMethod.java

License:Apache License

public MethodNode methodNode() {

    MethodNode node = new MethodNode(ACC_STATIC, "<clinit>", "()V", null, null);

    InsnList il = node.instructions;//  ww w  . ja  v a 2  s.  c o  m

    LabelNode begin = new LabelNode();
    LabelNode end = new LabelNode();

    il.add(begin);

    if (!context.hasUpvalues()) {
        il.add(new TypeInsnNode(NEW, context.thisClassType().getInternalName()));
        il.add(new InsnNode(DUP));

        il.add(new MethodInsnNode(INVOKESPECIAL, context.thisClassType().getInternalName(), "<init>",
                ctorMethod.methodType().getDescriptor(), false));

        il.add(new FieldInsnNode(PUTSTATIC, context.thisClassType().getInternalName(),
                context.instanceFieldName(), context.thisClassType().getDescriptor()));
    }

    if (!runMethod.constFields().isEmpty()) {
        for (RunMethod.ConstFieldInstance cfi : runMethod.constFields()) {
            il.add(cfi.instantiateInsns());
        }
    }

    il.add(new InsnNode(RETURN));
    il.add(end);

    return node;
}

From source file:net.sourceforge.cobertura.instrument.FirstPassMethodInstrumenter.java

License:Open Source License

public FirstPassMethodInstrumenter(ClassData classData, final MethodVisitor mv, final String owner,
        final int access, final String name, final String desc, final String signature,
        final String[] exceptions, final Collection ignoreRegexs, final Collection ignoreBranchesRegexs) {
    super(new MethodNode(access, name, desc, signature, exceptions));
    writerMethodVisitor = mv;/*from ww  w.j  av  a  2  s  .co m*/
    this.ownerClass = owner;
    this.methodNode = (MethodNode) this.mv;
    this.classData = classData;
    this.myAccess = access;
    this.myName = name;
    this.myDescriptor = desc;
    this.ignoreRegexs = ignoreRegexs;
    this.ignoreBranchesRegexs = ignoreBranchesRegexs;
    this.jumpTargetLabels = new HashMap();
    this.switchTargetLabels = new HashMap();
    this.lineLabels = new HashMap();
    this.currentLine = 0;
}

From source file:org.apache.commons.weaver.privilizer.BlueprintingVisitor.java

License:Apache License

private String importMethod(final Pair<Type, Method> key) {
    if (importedMethods.containsKey(key)) {
        return importedMethods.get(key);
    }//from  ww w .  j  a  v a 2 s. c o m
    final String result = new StringBuilder(key.getLeft().getInternalName().replace('/', '_')).append("$$")
            .append(key.getRight().getName()).toString();
    importedMethods.put(key, result);
    privilizer().env.debug("importing %s#%s as %s", key.getLeft().getClassName(), key.getRight(), result);
    final int access = Opcodes.ACC_PRIVATE + Opcodes.ACC_STATIC + Opcodes.ACC_SYNTHETIC;

    final MethodNode source = typeInfo(key.getLeft()).methods.get(key.getRight());

    final String[] exceptions = source.exceptions.toArray(ArrayUtils.EMPTY_STRING_ARRAY);

    // non-public fields accessed
    final Set<FieldAccess> fieldAccesses = new LinkedHashSet<>();

    source.accept(new MethodVisitor(Privilizer.ASM_VERSION) {
        @Override
        public void visitFieldInsn(final int opcode, final String owner, final String name, final String desc) {
            final FieldAccess fieldAccess = fieldAccess(Type.getObjectType(owner), name);

            super.visitFieldInsn(opcode, owner, name, desc);
            if (!Modifier.isPublic(fieldAccess.access)) {
                fieldAccesses.add(fieldAccess);
            }
        }
    });

    final MethodNode withAccessibleAdvice = new MethodNode(access, result, source.desc, source.signature,
            exceptions);

    // spider own methods:
    MethodVisitor mv = new NestedMethodInvocationHandler(withAccessibleAdvice, key); //NOPMD

    if (!fieldAccesses.isEmpty()) {
        mv = new AccessibleAdvisor(mv, access, result, source.desc, new ArrayList<>(fieldAccesses));
    }
    source.accept(mv);

    // private can only be called by other privileged methods, so no need to mark as privileged
    if (!Modifier.isPrivate(source.access)) {
        withAccessibleAdvice.visitAnnotation(Type.getType(Privileged.class).getDescriptor(), false).visitEnd();
    }
    withAccessibleAdvice.accept(this.cv);

    return result;
}

From source file:org.apache.felix.ipojo.manipulator.metadata.annotation.ClassMetadataCollector.java

License:Apache License

/**
 * Visit a method./*from ww w .j  a  va2 s . com*/
 * Call the method collector visitor.
 *
 * @param access     : method access
 * @param name       : method name
 * @param desc       : method descriptor
 * @param signature  : method signature
 * @param exceptions : method exceptions
 * @return the Method Visitor.
 * @see org.objectweb.asm.ClassVisitor#visitMethod(int, java.lang.String, java.lang.String, java.lang.String, java.lang.String[])
 */
public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) {
    return new MethodMetadataCollector(workbench, new MethodNode(access, name, desc, signature, exceptions),
            reporter);
}

From source file:org.apache.felix.ipojo.manipulator.metadata.annotation.registry.SelectionTestCase.java

License:Apache License

private MethodNode methodNode() {
    return new MethodNode(0, "method", "(java/lang/String)V", null, null);
}

From source file:org.coldswap.transformer.ClInitTransformer.java

License:Open Source License

@SuppressWarnings("unchecked")
@Override//from ww  w . j a  v  a2 s .  c  o m
public byte[] transform(ClassLoader classLoader, String s, Class<?> aClass, ProtectionDomain protectionDomain,
        byte[] bytes) throws IllegalClassFormatException {
    if (s != null && !"".equals(s)) {
        for (String pack : ClassUtil.skipTransforming) {
            if (s.startsWith(pack)) {
                return bytes;
            }
        }

        ClassNode cn = new ClassNode(Opcodes.ASM5);
        ClassReader cr = new ClassReader(bytes);
        ClassWriter cw = new ClassWriter(cr, ClassWriter.COMPUTE_FRAMES | ClassWriter.COMPUTE_MAXS);
        // create adapter for method insertion.
        cr.accept(cn, 0);
        // insert <clinit>V if it is not inserted
        List methods = cn.methods;
        boolean clInitFound = false;
        for (MethodNode methodNode : (List<MethodNode>) methods) {
            if ("<clinit>".equals(methodNode.name)) {
                clInitFound = true;
            }
        }

        if (!clInitFound) {
            MethodNode mn = new MethodNode(Opcodes.ACC_STATIC, "<clinit>", "()V", null, null);
            InsnList insnList = mn.instructions;
            insnList.add(new LabelNode());
            insnList.add(new InsnNode(Opcodes.RETURN));
            cn.methods.add(mn);
        }

        cn.accept(cw);
        byte[] toRet = cw.toByteArray();
        if (toRet != null) {
            logger.info("Successful transformation!");
            return toRet;
        } else {
            logger.severe("Could not transform class");
            return bytes;
        }
    }
    return bytes;
}