Example usage for org.objectweb.asm Opcodes GOTO

List of usage examples for org.objectweb.asm Opcodes GOTO

Introduction

In this page you can find the example usage for org.objectweb.asm Opcodes GOTO.

Prototype

int GOTO

To view the source code for org.objectweb.asm Opcodes GOTO.

Click Source Link

Usage

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.BaseTypeWidget.java

@Override
public ComparisonAdapter getComparisionAdapter() {
    Preconditions.checkState(!isPrimitive(), "BaseTypeWidget should not be handling a primitive type");
    return new ComparisonAdapter() {
        @Override//w w  w. j  ava 2s  .  c  om
        public void coerceBoolean(CodeEmitter scope, Label isTrue, Label isFalse, Label isNull) {
            // null or true
            if (isNullable()) {
                scope.getMethodVisitor().visitJumpInsn(Opcodes.IFNULL, isNull);
            } else {
                scope.pop(BaseTypeWidget.this);
            }
            scope.getMethodVisitor().visitJumpInsn(Opcodes.GOTO, isTrue);
        }
    };
}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.CollectionSizeExpression.java

@Override
public void generate(CodeEmitter code) {
    Label done = new Label();
    Label isNull = new Label();
    MethodVisitor mv = code.getMethodVisitor();
    code.exec(target);/*www.j av a2  s.  com*/
    boolean nullable = code.nullTest(target.getType(), isNull);
    code.getMethodVisitor().visitMethodInsn(Opcodes.INVOKEINTERFACE, Type.getInternalName(Collection.class),
            "size", Type.getMethodDescriptor(Type.INT_TYPE), true);
    if (nullable) {
        mv.visitJumpInsn(Opcodes.GOTO, done);
        mv.visitLabel(isNull);
        mv.visitInsn(Opcodes.ICONST_0);
        mv.visitLabel(done);
    }
}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.GotoSequence.java

@Override
public void generate(CodeEmitter code) {
    code.getMethodVisitor().visitJumpInsn(Opcodes.GOTO, label);
}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.IntegerSwitchSequence.java

@Override
public void generate(CodeEmitter code) {
    Map<Integer, Label> labelMap = Maps.newHashMapWithExpectedSize(sequenceMap.size());
    for (Integer key : sequenceMap.keySet()) {
        labelMap.put(key, new Label());
    }//from   ww  w  .j a v a  2  s. c  o  m
    Label done = new Label();
    Label defaultCase = defaultSequence == BytecodeSequence.NOOP ? done : new Label();
    code.emitIntegerSwitch(labelMap, defaultCase);
    MethodVisitor mv = code.getMethodVisitor();
    for (Map.Entry<Integer, BytecodeSequence> e : sequenceMap.entrySet()) {
        mv.visitLabel(labelMap.get(e.getKey()));
        code.exec(e.getValue());
        mv.visitJumpInsn(Opcodes.GOTO, done);
    }
    if (defaultCase != done) {
        mv.visitLabel(defaultCase);
        code.exec(defaultSequence);
    }
    mv.visitLabel(done);

}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.IterateFirstSequence.java

@Override
public void generate(CodeEmitter start) {
    CodeEmitter code = start.createScope();
    Label done = new Label();
    Label isNull = new Label();
    MethodVisitor mv = code.getMethodVisitor();
    BytecodeExpression tgt = code.evaluateOnce(target);
    tgt.generate(code);/*w w  w  .  j  a v  a2 s. co  m*/
    code.emitInstanceCheck(tgt.getType(), Iterable.class, isNull);
    AssignableValue iterator = code.allocate(Iterator.class);
    mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, Type.getInternalName(Iterable.class), "iterator",
            Type.getMethodDescriptor(Type.getType(Iterator.class)), true);
    code.exec(iterator.write(code.adapt(Iterator.class)));
    code.exec(iterator.read());
    mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, Type.getInternalName(Iterator.class), "hasNext",
            Type.getMethodDescriptor(Type.BOOLEAN_TYPE), true);
    mv.visitJumpInsn(Opcodes.IFEQ, isNull);
    code.exec(iterator.read());
    mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, Type.getInternalName(Iterator.class), "next",
            Type.getMethodDescriptor(Type.getType(Object.class)), true);
    code.cast(valueType, AnyTypeWidget.getInstance(), isNull);
    mv.visitJumpInsn(Opcodes.GOTO, done);
    mv.visitLabel(isNull);
    mv.visitInsn(Opcodes.ACONST_NULL);
    mv.visitLabel(done);
}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.IterateSequence.java

@Override
public void generate(CodeEmitter code) {
    Label done = new Label();
    Label next = new Label();
    MethodVisitor mv = code.getMethodVisitor();
    BytecodeExpression tgt = code.evaluateOnce(target);
    code.exec(tgt);//w w w.  j ava2  s . c  om
    code.emitInstanceCheck(tgt.getType(), Iterable.class, done);
    AssignableValue item = this.item == null ? code.allocate(valueType) : this.item;
    AssignableValue iterator = code.allocate(Iterator.class);
    mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, Type.getInternalName(Iterable.class), "iterator",
            Type.getMethodDescriptor(Type.getType(Iterator.class)), true);
    code.exec(iterator.write(code.adapt(Iterator.class)));
    mv.visitLabel(next);
    code.exec(iterator.read());
    mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, Type.getInternalName(Iterator.class), "hasNext",
            Type.getMethodDescriptor(Type.BOOLEAN_TYPE), true);
    mv.visitJumpInsn(Opcodes.IFEQ, done);
    code.exec(iterator.read());
    mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, Type.getInternalName(Iterator.class), "next",
            Type.getMethodDescriptor(Type.getType(Object.class)), true);
    code.cast(valueType, AnyTypeWidget.getInstance()); // , next);   // don't skip nulls
    code.exec(item.write(item.getType()));
    loop.item(code, item.read(), done, next);
    mv.visitJumpInsn(Opcodes.GOTO, next);
    mv.visitLabel(done);
}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.NullTestingSerializationAdapter.java

@Override
public BytecodeSequence serializeTo(final BytecodeExpression input, final BytecodeExpression generator) {
    return new BytecodeSequence() {
        @Override/*  ww  w . jav  a2 s  .c o  m*/
        public void generate(CodeEmitter code) {
            Label isNull = new Label();
            Label done = new Label();
            BytecodeExpression source = code.evaluateOnce(input);
            code.gotoIfNull(source, isNull);
            MethodVisitor mv = code.getMethodVisitor();
            code.exec(targetAdapter.serializeTo(source, generator));
            mv.visitJumpInsn(Opcodes.GOTO, done);
            mv.visitLabel(isNull);
            switch (encoding) {
            case TBIN:
                code.exec(generator);
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(TBinEncoder.class), "writeNull",
                        Type.getMethodDescriptor(Type.VOID_TYPE), false);
                break;
            case JSON:
                code.exec(generator);
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(JsonGenerator.class),
                        "writeNull", Type.getMethodDescriptor(Type.VOID_TYPE), false);
                break;
            default:
                throw new UnsupportedOperationException("unknown NativeEncoding: " + encoding);
            }
            mv.visitLabel(done);
        }
    };
}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.PrimitiveTypeWidget.java

@Override
public ComparisonAdapter getComparisionAdapter() {
    return new ComparisonAdapter() {
        @Override/*from w w w.  ja v  a 2 s.  c  o m*/
        public void coerceBoolean(CodeEmitter scope, Label isTrue, Label isFalse, Label isNull) {
            MethodVisitor mv = scope.getMethodVisitor();
            switch (getJVMType().getSort()) {
            case Type.BOOLEAN:
            case Type.SHORT:
            case Type.INT:
            case Type.CHAR:
                mv.visitJumpInsn(Opcodes.IFEQ, isFalse);
                mv.visitJumpInsn(Opcodes.GOTO, isTrue);
                break;
            case Type.FLOAT:
                mv.visitInsn(Opcodes.FCONST_0);
                mv.visitInsn(Opcodes.FCMPG);
                mv.visitJumpInsn(Opcodes.IFEQ, isTrue);
                mv.visitJumpInsn(Opcodes.GOTO, isFalse);
                break;
            case Type.LONG:
                mv.visitInsn(Opcodes.LCONST_0);
                mv.visitInsn(Opcodes.LCMP);
                mv.visitJumpInsn(Opcodes.IFEQ, isTrue);
                mv.visitJumpInsn(Opcodes.GOTO, isFalse);
                break;
            case Type.DOUBLE:
                mv.visitInsn(Opcodes.DCONST_0);
                mv.visitInsn(Opcodes.DCMPG);
                mv.visitJumpInsn(Opcodes.IFEQ, isTrue);
                mv.visitJumpInsn(Opcodes.GOTO, isFalse);
                break;
            default:
                throw new UnsupportedOperationException("Unsupported JVM type: " + getJVMType());

            }
        }
    };
}

From source file:com.yahoo.yqlplus.engine.internal.plan.types.base.StringSwitchSequence.java

@Override
public void generate(CodeEmitter code) {
    Map<String, Label> labelMap = Maps.newHashMapWithExpectedSize(sequenceMap.size());
    for (String key : sequenceMap.keySet()) {
        labelMap.put(key, new Label());
    }//from w w w. j  a  v  a 2  s . c  o  m
    Label done = new Label();
    Label defaultCase = defaultSequence == BytecodeSequence.NOOP ? done : new Label();
    code.exec(input);
    code.emitInstanceCheck(input.getType(), String.class, defaultCase);
    code.emitStringSwitch(labelMap, defaultCase, caseInsensitive);
    MethodVisitor mv = code.getMethodVisitor();
    for (Map.Entry<String, BytecodeSequence> e : sequenceMap.entrySet()) {
        mv.visitLabel(labelMap.get(e.getKey()));
        code.exec(e.getValue());
        mv.visitJumpInsn(Opcodes.GOTO, done);
    }
    if (defaultCase != done) {
        mv.visitLabel(defaultCase);
        code.exec(defaultSequence);
    }
    mv.visitLabel(done);

}

From source file:de.codesourcery.asm.controlflow.ControlFlowAnalyzer.java

License:Apache License

@SuppressWarnings("unchecked")
public ControlFlowGraph analyze(String owner, final MethodNode mn) throws AnalyzerException {
    // line numbers with associated block
    // initially we'll create one block per line and merge adjacent ones later if control flow permits it  
    final Map<Integer, IBlock> blocks = new HashMap<>();

    final ListIterator<AbstractInsnNode> it = mn.instructions.iterator();

    IBlock currentLine = null;/*from w w  w  .j a va2  s  . c om*/
    Object previousMetadata = null;
    IBlock previous = null;
    final IBlock methodExit = new MethodExit();
    for (int instrCounter = 0; it.hasNext(); instrCounter++) {
        final AbstractInsnNode instruction = it.next();
        currentLine = getBlockForInstruction(instrCounter, blocks);

        if (previous != null) {
            previous.addSuccessor(currentLine, EdgeType.REGULAR, previousMetadata);
            currentLine.addRegularPredecessor(previous);
            previousMetadata = null;
        }

        IBlock nextPrevious = currentLine;
        switch (instruction.getType()) {

        case AbstractInsnNode.LOOKUPSWITCH_INSN:
            LookupSwitchInsnNode lookup = (LookupSwitchInsnNode) instruction;

            // add edge for default handler
            if (lookup.dflt != null) {
                final IBlock target = getBlockForInstruction(lookup.dflt, mn, blocks);
                target.addRegularPredecessor(currentLine);
                currentLine.addRegularSuccessor(target);
            }

            @SuppressWarnings("cast")
            final Iterator<Integer> keys = (Iterator<Integer>) lookup.keys.iterator();

            for (LabelNode ln : (List<LabelNode>) lookup.labels) {
                final IBlock target = getBlockForInstruction(ln, mn, blocks);
                final Integer key = keys.next();

                target.addPredecessor(currentLine, EdgeType.LOOKUP_SWITCH, key);
                currentLine.addSuccessor(target, EdgeType.LOOKUP_SWITCH, key);
            }
            nextPrevious = null;
            break;

        case AbstractInsnNode.TABLESWITCH_INSN:

            TableSwitchInsnNode tblSwitch = (TableSwitchInsnNode) instruction;

            // add edge for default handler
            if (tblSwitch.dflt != null) {
                final IBlock target = getBlockForInstruction(tblSwitch.dflt, mn, blocks);
                target.addRegularPredecessor(currentLine);
                currentLine.addRegularSuccessor(target);
            }
            int currentKey = tblSwitch.min;

            for (LabelNode ln : (List<LabelNode>) tblSwitch.labels) {
                final IBlock target = getBlockForInstruction(ln, mn, blocks);

                target.addPredecessor(currentLine, EdgeType.TABLE_SWITCH, currentKey);
                currentLine.addSuccessor(target, EdgeType.TABLE_SWITCH, currentKey);

                currentKey++;
            }
            nextPrevious = null;
            break;

        case AbstractInsnNode.INSN:

            if (instruction.getOpcode() == Opcodes.RETURN
                    || instruction.getOpcode() == Opcodes.IRETURN) /* method exit */
            {
                currentLine.addRegularSuccessor(methodExit);
                methodExit.addRegularPredecessor(currentLine);
                nextPrevious = null;
            } else if (instruction.getOpcode() == Opcodes.ATHROW || instruction.getOpcode() == Opcodes.RET) {
                nextPrevious = null;
            }
            break;

        case AbstractInsnNode.JUMP_INSN: /* jump */

            final JumpInsnNode jmp = (JumpInsnNode) instruction;
            final LabelNode label = jmp.label;
            final int target = mn.instructions.indexOf(label);

            final boolean isConditional = ASMUtil.isConditionalJump(instruction);

            if (isConditional) { // label edges of conditional jump instructions with "true" and "false
                previousMetadata = "false";
            }

            final IBlock targetBlock = getBlockForInstruction(target, blocks);
            targetBlock.addRegularPredecessor(currentLine);

            // create edge from current block to jump target 
            currentLine.addSuccessor(targetBlock, EdgeType.REGULAR, isConditional ? "true" : null);

            if (instruction.getOpcode() == Opcodes.GOTO) {
                nextPrevious = null;
            }
            break;
        }

        // link last instruction with method_exit block
        if (!it.hasNext()) {
            currentLine.addRegularSuccessor(methodExit);
            methodExit.addRegularPredecessor(currentLine);
        }
        previous = nextPrevious;
    }
    // try/catch blocks need special treatment because
    // they are not represented as opcodes
    for (TryCatchBlockNode node : (List<TryCatchBlockNode>) mn.tryCatchBlocks) {
        final LabelNode startLabel = node.start;
        final int startTarget = mn.instructions.indexOf(startLabel);

        final LabelNode endLabel = node.end;
        final int endTarget = mn.instructions.indexOf(endLabel);

        final int handlerTarget = mn.instructions.indexOf(node.handler);
        IBlock handler = getBlockForInstruction(node.handler, mn, blocks);

        for (int i = startTarget; i <= endTarget; i++) {
            if (i != handlerTarget) {
                getBlockForInstruction(i, blocks).addExceptionHandler(handler, node.type);
            }
        }
    }

    // merge adjacent instructions
    final Set<Integer> linesBeforeMerge = new HashSet<>();
    for (IBlock block : blocks.values()) {
        linesBeforeMerge.addAll(block.getInstructionNums());
    }

    final List<IBlock> result = mergeBlocks(blocks, mn);

    if (debug) {
        System.out.println("################ Control-blocks merged ################");
    }
    // sanity check
    final Set<Integer> linesAfterMerge = new HashSet<>();
    for (IBlock block : result) {
        linesAfterMerge.addAll(block.getInstructionNums());
        if (debug) {
            System.out.println("-----");
            System.out.println(block + " has " + block.getByteCodeInstructionCount(mn) + " instructions.");
            System.out.println(block.disassemble(mn, false, true));
        }
        for (Edge e : block.getEdges()) {
            if (!result.contains(e.src) && e.src != methodExit) {
                throw new RuntimeException(e + " has src that is not in result list?");
            }
            if (!result.contains(e.dst) && e.dst != methodExit) {
                throw new RuntimeException(e + " has destination that is not in result list?");
            }
        }
    }

    if (!linesBeforeMerge.equals(linesAfterMerge)) {
        throw new RuntimeException("Internal error, line count mismatch before/after control block merge: \n\n"
                + linesBeforeMerge + "\n\n" + linesAfterMerge);
    }

    // add starting block and link it with block that contains the lowest instruction number
    MethodEntry methodEntry = new MethodEntry();
    int lowest = Integer.MAX_VALUE;
    for (Integer i : blocks.keySet()) {
        if (i < lowest) {
            lowest = i;
        }
    }

    final IBlock firstBlock = blocks.get(lowest);
    if (firstBlock.hasRegularPredecessor()) {
        throw new IllegalStateException(firstBlock + " that constrains first instruction has a predecessor?");
    }

    methodEntry.addRegularSuccessor(firstBlock);
    firstBlock.addRegularPredecessor(methodEntry);
    result.add(0, methodEntry);

    // add end block to results
    result.add(methodExit);//owner+"#"+
    ControlFlowGraph cfg = new ControlFlowGraph(mn, result);
    System.out.println("CFGMAP:" + formatname(owner) + "#" + cfg.getMethod().name);
    graphmap.put(formatname(owner) + "#" + cfg.getMethod().name, cfg);
    return cfg;
}