Example usage for org.objectweb.asm.tree AbstractInsnNode getOpcode

List of usage examples for org.objectweb.asm.tree AbstractInsnNode getOpcode

Introduction

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

Prototype

public int getOpcode() 

Source Link

Document

Returns the opcode of this instruction.

Usage

From source file:org.diorite.inject.controller.TransformerFieldInjector.java

License:Open Source License

private void injectFieldsIn(MethodNode rootNode) {
    InsnList instructions = rootNode.instructions;
    if (instructions.size() == 0) {
        return;/* w  w w  .  j  a v a  2 s .  c om*/
    }
    AbstractInsnNode node = instructions.getFirst();
    while (node != null) {
        while (!(node instanceof FieldInsnNode) || !AsmUtils.isPutField(node.getOpcode())) {
            node = node.getNext();
            if (node == null) {
                return;
            }
        }
        this.trackFieldToInject((FieldInsnNode) node, rootNode.instructions);
        node = node.getNext();
    }
}

From source file:org.diorite.inject.controller.TransformerInjectTracker.java

License:Open Source License

private AbstractInsnNode skipCheckCastBackwards(AbstractInsnNode node) {
    // skip possible (?) ALOAD 0 if not static
    if (!this.isStatic && (node instanceof VarInsnNode) && (node.getOpcode() == ALOAD)
            && (((VarInsnNode) node).var == 0)) {
        node = node.getPrevious();//  w  ww  .j  a va2  s  . co m
    }

    // skip possible check cast
    if ((node instanceof TypeInsnNode) && (node.getOpcode() == CHECKCAST)) {
        node = node.getPrevious();
    }

    // skip possible (?) ALOAD 0 if not static
    if (!this.isStatic && (node instanceof VarInsnNode) && (node.getOpcode() == ALOAD)
            && (((VarInsnNode) node).var == 0)) {
        node = node.getPrevious();
    }
    return node;
}

From source file:org.diorite.inject.controller.TransformerInjectTracker.java

License:Open Source License

private InjectionType checkIndirect() {
    AbstractInsnNode previous = this.getPrevious(true);

    // find var index
    if ((previous instanceof VarInsnNode) && AsmUtils.isLoadCode(previous.getOpcode())) {
        this.loadCode = new LoadCode((VarInsnNode) previous);

        // XLOAD 0 don't exist here in any case.
        if (!this.isStatic && (this.loadCode.getIndex() == 0)) {
            throw new AnalyzeError("Unexpected loading of `this` variable!");
        }/*from   w w w  .ja v  a  2 s .co  m*/
        previous = previous.getPrevious();
    } else {
        return InjectionType.UNKNOWN;
    }
    // track all local variable changes
    previous = this.trackLoadBackwards(previous);

    // final check for placeholder method
    PlaceholderType injectPlaceholder = Transformer.isInjectPlaceholder(previous);

    if (injectPlaceholder != PlaceholderType.INVALID) {
        assert previous instanceof MethodInsnNode;
        this.placeholderNode = (MethodInsnNode) previous;
        this.placeholderType = injectPlaceholder;
        this.injectionType = InjectionType.INDIRECT;
        return this.injectionType;
    }
    return InjectionType.UNKNOWN;
}

From source file:org.diorite.inject.controller.TransformerInjectTracker.java

License:Open Source License

private AbstractInsnNode trackLoadBackwards(AbstractInsnNode node) {
    assert this.loadCode != null;
    // skip checkcast and possible XLOAD 0
    node = this.skipCheckCastBackwards(node);

    // find compatible STORE node.
    while ((!(node instanceof VarInsnNode)) || !this.loadCode.isCompatible((VarInsnNode) node)) {
        node = node.getPrevious();/*  ww w .j  av a 2 s.co m*/
    }
    // one more to skip STORE
    node = node.getPrevious();

    // node is STORE opcode for our variable, there might be checkcast here:
    node = this.skipCheckCastBackwards(node);

    // now there might be INVOKESTATIC or some other indirections:

    // if there is XLOAD different than 0 (if not static), then we have next layer of indirect store.
    if ((node instanceof VarInsnNode) && (!this.isStatic && (((VarInsnNode) node).var != 0))
            && (((VarInsnNode) node).var != this.loadCode.getIndex())
            && AsmUtils.isLoadCode(node.getOpcode())) {
        this.loadCode = new LoadCode((VarInsnNode) node);
        node = this.trackLoadBackwards(node);
    }
    // but if there is INVOKE* instead, then we need to go inside invoked method and keep looking for injection placeholder! But skip void methods.
    else if ((node instanceof MethodInsnNode) && AsmUtils.isInvokeCode(node.getOpcode())
            && !((MethodInsnNode) node).desc.endsWith("V")) {
        MethodInsnNode methodInvoke = (MethodInsnNode) node;

        // maybe this is already placeholder invoke?
        if (Transformer.isInjectPlaceholder(methodInvoke) != PlaceholderType.INVALID) {
            return node;
        }

        node = this.trackMethod(methodInvoke);
    } else {
        throw new AnalyzeError("Can't track given field!");
    }

    // now there should be finally INVOKESTATIC, so we can return.
    return node;
}

From source file:org.diorite.inject.controller.TransformerInjectTracker.java

License:Open Source License

private InjectionType checkDelegated() {
    // skip any checks and get previous node
    AbstractInsnNode previous = this.getPrevious(true);

    // now this should be INVOKE* opcode, if it isn't we are all doomed.
    if (!(previous instanceof MethodInsnNode) || !AsmUtils.isInvokeCode(previous.getOpcode())) {
        return InjectionType.UNKNOWN;
    }/* w w  w .jav  a 2s.  c om*/
    MethodInsnNode methodInvoke = (MethodInsnNode) previous;
    previous = this.trackMethod(methodInvoke);

    // final check for placeholder method
    PlaceholderType injectPlaceholder = Transformer.isInjectPlaceholder(previous);

    if (injectPlaceholder != PlaceholderType.INVALID) {
        assert previous instanceof MethodInsnNode;
        this.placeholderNode = (MethodInsnNode) previous;
        this.placeholderType = injectPlaceholder;
        this.injectionType = InjectionType.DELEGATED;
        return this.injectionType;
    }
    return InjectionType.UNKNOWN;
}

From source file:org.eclipse.objectteams.otredyn.bytecode.asm.AbstractTransformableClassNode.java

License:Open Source License

/**
 * Replace all return statements in the given instructions with new 
 * statements that convert the real return value to {@link Object}
 * and return this new {@link Object}//  w w w  .j  ava2s .c  om
 * 
 * @param instructions
 * @param returnType
 */
protected void replaceReturn(InsnList instructions, Type returnType) {
    if (returnType.getSort() != Type.OBJECT && returnType.getSort() != Type.ARRAY
            && returnType.getSort() != Type.VOID) {
        ListIterator<AbstractInsnNode> orgMethodIter = instructions.iterator();
        while (orgMethodIter.hasNext()) {
            AbstractInsnNode orgMethodNode = orgMethodIter.next();
            if (orgMethodNode.getOpcode() == returnType.getOpcode(Opcodes.IRETURN)) {
                instructions.insertBefore(orgMethodNode, AsmTypeHelper.getBoxingInstructionForType(returnType));
                instructions.insertBefore(orgMethodNode, new InsnNode(Opcodes.ARETURN));
                instructions.remove(orgMethodNode);
            }
        }
    } else if (returnType.getSort() == Type.VOID) {
        ListIterator<AbstractInsnNode> orgMethodIter = instructions.iterator();
        while (orgMethodIter.hasNext()) {
            AbstractInsnNode orgMethodNode = orgMethodIter.next();
            if (orgMethodNode.getOpcode() == Opcodes.RETURN) {
                instructions.insertBefore(orgMethodNode, new InsnNode(Opcodes.ACONST_NULL));
                instructions.insertBefore(orgMethodNode, new InsnNode(Opcodes.ARETURN));
                instructions.remove(orgMethodNode);
            }
        }
    }
}

From source file:org.eclipse.objectteams.otredyn.bytecode.asm.MoveCodeToCallOrigAdapter.java

License:Open Source License

/** To avoid infinite recursion, calls super.m(a1, a2) must be translated to super.callOrig(boundMethodId, new Object[] {a1, a2}). */
private void adjustSuperCalls(InsnList instructions, String selector, Type[] args, Type returnType,
        int boundMethodIdSlot) {
    // search:/*from   w ww.ja v  a  2  s. c  o m*/
    List<MethodInsnNode> toReplace = new ArrayList<MethodInsnNode>();
    ListIterator<AbstractInsnNode> orgMethodIter = instructions.iterator();
    while (orgMethodIter.hasNext()) {
        AbstractInsnNode orgMethodNode = orgMethodIter.next();
        if (orgMethodNode.getOpcode() == Opcodes.INVOKESPECIAL
                && ((MethodInsnNode) orgMethodNode).name.equals(selector))
            toReplace.add((MethodInsnNode) orgMethodNode);
    }
    if (toReplace.isEmpty())
        return;
    // replace:
    for (MethodInsnNode oldNode : toReplace) {
        // we need to insert into the loading sequence before the invocation, find the insertion points:
        AbstractInsnNode[] insertionPoints = StackBalanceAnalyzer.findInsertionPointsBefore(oldNode, args);
        AbstractInsnNode firstInsert = insertionPoints.length > 0 ? insertionPoints[0] : oldNode;

        // push first arg to _OT$callOrig():
        instructions.insertBefore(firstInsert, new IntInsnNode(Opcodes.ILOAD, boundMethodIdSlot));

        // prepare array as second arg to _OT$callOrig():
        instructions.insertBefore(firstInsert, new IntInsnNode(Opcodes.BIPUSH, args.length));
        instructions.insertBefore(firstInsert, new TypeInsnNode(Opcodes.ANEWARRAY, "java/lang/Object"));

        for (int i = 0; i < insertionPoints.length; i++) {
            // NB: each iteration has an even stack balance, where the top is the Object[].
            instructions.insertBefore(insertionPoints[i], new InsnNode(Opcodes.DUP));
            instructions.insertBefore(insertionPoints[i], new IntInsnNode(Opcodes.BIPUSH, i));
            // leave the original loading sequence in tact and continue at the next point:
            AbstractInsnNode insertAt = (i + 1 < insertionPoints.length) ? insertionPoints[i + 1] : oldNode;
            instructions.insertBefore(insertAt, AsmTypeHelper.getBoxingInstructionForType(args[i]));
            instructions.insertBefore(insertAt, new InsnNode(Opcodes.AASTORE));
        }

        if (returnType == Type.VOID_TYPE)
            instructions.insert(oldNode, new InsnNode(Opcodes.POP));
        else
            instructions.insert(oldNode, AsmTypeHelper.getUnboxingInstructionForType(returnType));

        instructions.set(oldNode, new MethodInsnNode(Opcodes.INVOKESPECIAL, ((MethodInsnNode) oldNode).owner,
                callOrig.getName(), callOrig.getSignature()));
    }
}

From source file:org.eclipse.objectteams.otredyn.bytecode.asm.StackBalanceAnalyzer.java

License:Open Source License

/**
 * Answer the closest point in the instruction list before 'location'
 * where the stack has 'stackDifference' more bytes than at 'location'.
 * Negative 'stackDifference' means we are looking for smaller stack.
 * //from   w ww.  j av a  2 s  .  c om
 * @param location start searching here
 * @param stackDifference 
 * @return the last instruction before which the required stack size was present 
 */
public static AbstractInsnNode findInsertionPointBefore(AbstractInsnNode location, int stackDifference) {
    int offset = 0;
    AbstractInsnNode current = location;
    while (offset != stackDifference) {
        current = location.getPrevious();
        if (current == null)
            return null;
        offset -= SIZE[current.getOpcode()];
    }
    return current;
}

From source file:org.epoxide.surge.asm.ASMUtils.java

License:Creative Commons License

/**
 * Creates a string representation of an AbstractInsnNode.
 *
 * @param node The node to look at.//from   ww w  .j  a  v a2 s .  c  o m
 *
 * @return The resulting string.
 */
public static String getInstructionString(AbstractInsnNode node) {

    final String type = node.getType() < 0 || node.getType() > INSN_TYPES.length ? "Invalid"
            : INSN_TYPES[node.getType()];
    final String opcode = node.getOpcode() < 0 || node.getOpcode() > OPCODES.length ? "N/A"
            : OPCODES[node.getOpcode()];
    return "Type: " + type + " Opcode: " + opcode;
}

From source file:org.evosuite.graphs.cfg.BytecodeInstructionPool.java

License:Open Source License

/**
 * Determine how many bytes the current instruction occupies together with
 * its operands//w  w w. j ava 2 s.  c o  m
 * 
 * @return
 */
private int getBytecodeIncrement(AbstractInsnNode instructionNode) {
    int opcode = instructionNode.getOpcode();
    switch (opcode) {
    case Opcodes.ALOAD: // index
    case Opcodes.ASTORE: // index
    case Opcodes.DLOAD:
    case Opcodes.DSTORE:
    case Opcodes.FLOAD:
    case Opcodes.FSTORE:
    case Opcodes.ILOAD:
    case Opcodes.ISTORE:
    case Opcodes.LLOAD:
    case Opcodes.LSTORE:
        VarInsnNode varNode = (VarInsnNode) instructionNode;
        if (varNode.var > 3)
            return 1;
        else
            return 0;
    case Opcodes.BIPUSH: // byte
    case Opcodes.NEWARRAY:
    case Opcodes.RET:
        return 1;
    case Opcodes.LDC:
        LdcInsnNode ldcNode = (LdcInsnNode) instructionNode;
        if (ldcNode.cst instanceof Double || ldcNode.cst instanceof Long)
            return 2; // LDC2_W
        else
            return 1;
    case 19: //LDC_W
    case 20: //LDC2_W
        return 2;
    case Opcodes.ANEWARRAY: // indexbyte1, indexbyte2
    case Opcodes.CHECKCAST: // indexbyte1, indexbyte2
    case Opcodes.GETFIELD:
    case Opcodes.GETSTATIC:
    case Opcodes.GOTO:
    case Opcodes.IF_ACMPEQ:
    case Opcodes.IF_ACMPNE:
    case Opcodes.IF_ICMPEQ:
    case Opcodes.IF_ICMPNE:
    case Opcodes.IF_ICMPGE:
    case Opcodes.IF_ICMPGT:
    case Opcodes.IF_ICMPLE:
    case Opcodes.IF_ICMPLT:
    case Opcodes.IFLE:
    case Opcodes.IFLT:
    case Opcodes.IFGE:
    case Opcodes.IFGT:
    case Opcodes.IFNE:
    case Opcodes.IFEQ:
    case Opcodes.IFNONNULL:
    case Opcodes.IFNULL:
    case Opcodes.IINC:
    case Opcodes.INSTANCEOF:
    case Opcodes.INVOKESPECIAL:
    case Opcodes.INVOKESTATIC:
    case Opcodes.INVOKEVIRTUAL:
    case Opcodes.JSR:
    case Opcodes.NEW:
    case Opcodes.PUTFIELD:
    case Opcodes.PUTSTATIC:
    case Opcodes.SIPUSH:
        // case Opcodes.LDC_W
        // case Opcodes.LDC2_W

        return 2;
    case Opcodes.MULTIANEWARRAY:
        return 3;
    case Opcodes.INVOKEDYNAMIC:
    case Opcodes.INVOKEINTERFACE:
        return 4;

    case Opcodes.LOOKUPSWITCH:
    case Opcodes.TABLESWITCH:
        // TODO: Could be more
        return 4;
    // case Opcodes.GOTO_W 
    // case Opcodes.JSR_W
    }
    return 0;
}