/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You 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 org.apache.bcel.verifier.structurals;
import org.apache.bcel.Const;
import org.apache.bcel.classfile.Constant;
import org.apache.bcel.classfile.ConstantClass;
import org.apache.bcel.classfile.ConstantDouble;
import org.apache.bcel.classfile.ConstantFloat;
import org.apache.bcel.classfile.ConstantInteger;
import org.apache.bcel.classfile.ConstantLong;
import org.apache.bcel.classfile.ConstantString;
// CHECKSTYLE:OFF (there are lots of references!)
import org.apache.bcel.generic.*;
//CHECKSTYLE:ON
This Visitor class may be used for a type-based Java Virtual Machine
simulation.
It does not check for correct types on the OperandStack or in the
LocalVariables; nor does it check their sizes are sufficiently big.
Thus, to use this Visitor for bytecode verifying, you have to make sure
externally that the type constraints of the Java Virtual Machine instructions
are satisfied. An InstConstraintVisitor may be used for this.
Anyway, this Visitor does not mandate it. For example, when you
visitIADD(IADD o), then there are two stack slots popped and one
stack slot containing a Type.INT is pushed (where you could also
pop only one slot if you know there are two Type.INT on top of the
stack). Monitor-specific behavior is not simulated.
Conventions:
Type.VOID will never be pushed onto the stack. Type.DOUBLE and Type.LONG
that would normally take up two stack slots (like Double_HIGH and
Double_LOW) are represented by a simple single Type.DOUBLE or Type.LONG
object on the stack here.
If a two-slot type is stored into a local variable, the next variable
is given the type Type.UNKNOWN.
See Also: - visitDSTORE(DSTORE o)
- InstConstraintVisitor
/**
* This Visitor class may be used for a type-based Java Virtual Machine
* simulation.
*
* <p>It does not check for correct types on the OperandStack or in the
* LocalVariables; nor does it check their sizes are sufficiently big.
* Thus, to use this Visitor for bytecode verifying, you have to make sure
* externally that the type constraints of the Java Virtual Machine instructions
* are satisfied. An InstConstraintVisitor may be used for this.
* Anyway, this Visitor does not mandate it. For example, when you
* visitIADD(IADD o), then there are two stack slots popped and one
* stack slot containing a Type.INT is pushed (where you could also
* pop only one slot if you know there are two Type.INT on top of the
* stack). Monitor-specific behavior is not simulated.</p>
*
* <b>Conventions:</b>
*
* <p>Type.VOID will never be pushed onto the stack. Type.DOUBLE and Type.LONG
* that would normally take up two stack slots (like Double_HIGH and
* Double_LOW) are represented by a simple single Type.DOUBLE or Type.LONG
* object on the stack here.</p>
*
* <p>If a two-slot type is stored into a local variable, the next variable
* is given the type Type.UNKNOWN.</p>
*
* @see #visitDSTORE(DSTORE o)
* @see InstConstraintVisitor
*/
public class ExecutionVisitor extends EmptyVisitor{
The executionframe we're operating on.
/**
* The executionframe we're operating on.
*/
private Frame frame = null;
The ConstantPoolGen we're working with.
See Also: - setConstantPoolGen(ConstantPoolGen)
/**
* The ConstantPoolGen we're working with.
* @see #setConstantPoolGen(ConstantPoolGen)
*/
private ConstantPoolGen cpg = null;
Constructor. Constructs a new instance of this class.
/**
* Constructor. Constructs a new instance of this class.
*/
public ExecutionVisitor() {}
The OperandStack from the current Frame we're operating on.
See Also: - setFrame(Frame)
/**
* The OperandStack from the current Frame we're operating on.
* @see #setFrame(Frame)
*/
private OperandStack stack() {
return frame.getStack();
}
The LocalVariables from the current Frame we're operating on.
See Also: - setFrame(Frame)
/**
* The LocalVariables from the current Frame we're operating on.
* @see #setFrame(Frame)
*/
private LocalVariables locals() {
return frame.getLocals();
}
Sets the ConstantPoolGen needed for symbolic execution.
/**
* Sets the ConstantPoolGen needed for symbolic execution.
*/
public void setConstantPoolGen(final ConstantPoolGen cpg) { // TODO could be package-protected?
this.cpg = cpg;
}
The only method granting access to the single instance of
the ExecutionVisitor class. Before actively using this
instance, SET THE ConstantPoolGen FIRST.
See Also: - setConstantPoolGen(ConstantPoolGen)
/**
* The only method granting access to the single instance of
* the ExecutionVisitor class. Before actively using this
* instance, <B>SET THE ConstantPoolGen FIRST</B>.
* @see #setConstantPoolGen(ConstantPoolGen)
*/
public void setFrame(final Frame f) { // TODO could be package-protected?
this.frame = f;
}
///** Symbolically executes the corresponding Java Virtual Machine instruction. */
//public void visitWIDE(WIDE o) {
// The WIDE instruction is modelled as a flag
// of the embedded instructions in BCEL.
// Therefore BCEL checks for possible errors
// when parsing in the .class file: We don't
// have even the possibilty to care for WIDE
// here.
//}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitAALOAD(final AALOAD o) {
stack().pop(); // pop the index int
//System.out.print(stack().peek());
final Type t = stack().pop(); // Pop Array type
if (t == Type.NULL) {
stack().push(Type.NULL);
} // Do nothing stackwise --- a NullPointerException is thrown at Run-Time
else{
final ArrayType at = (ArrayType) t;
stack().push(at.getElementType());
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitAASTORE(final AASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitACONST_NULL(final ACONST_NULL o) {
stack().push(Type.NULL);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitALOAD(final ALOAD o) {
stack().push(locals().get(o.getIndex()));
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitANEWARRAY(final ANEWARRAY o) {
stack().pop(); //count
stack().push( new ArrayType(o.getType(cpg), 1) );
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitARETURN(final ARETURN o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitARRAYLENGTH(final ARRAYLENGTH o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitASTORE(final ASTORE o) {
locals().set(o.getIndex(), stack().pop());
//System.err.println("TODO-DEBUG: set LV '"+o.getIndex()+"' to '"+locals().get(o.getIndex())+"'.");
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitATHROW(final ATHROW o) {
final Type t = stack().pop();
stack().clear();
if (t.equals(Type.NULL)) {
stack().push(Type.getType("Ljava/lang/NullPointerException;"));
} else {
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitBALOAD(final BALOAD o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitBASTORE(final BASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitBIPUSH(final BIPUSH o) {
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitCALOAD(final CALOAD o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitCASTORE(final CASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitCHECKCAST(final CHECKCAST o) {
// It's possibly wrong to do so, but SUN's
// ByteCode verifier seems to do (only) this, too.
// TODO: One could use a sophisticated analysis here to check
// if a type cannot possibly be cated to another and by
// so doing predict the ClassCastException at run-time.
stack().pop();
stack().push(o.getType(cpg));
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitD2F(final D2F o) {
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitD2I(final D2I o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitD2L(final D2L o) {
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDADD(final DADD o) {
stack().pop();
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDALOAD(final DALOAD o) {
stack().pop();
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDASTORE(final DASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDCMPG(final DCMPG o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDCMPL(final DCMPL o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDCONST(final DCONST o) {
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDDIV(final DDIV o) {
stack().pop();
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDLOAD(final DLOAD o) {
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDMUL(final DMUL o) {
stack().pop();
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDNEG(final DNEG o) {
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDREM(final DREM o) {
stack().pop();
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDRETURN(final DRETURN o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDSTORE(final DSTORE o) {
locals().set(o.getIndex(), stack().pop());
locals().set(o.getIndex()+1, Type.UNKNOWN);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDSUB(final DSUB o) {
stack().pop();
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDUP(final DUP o) {
final Type t = stack().pop();
stack().push(t);
stack().push(t);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDUP_X1(final DUP_X1 o) {
final Type w1 = stack().pop();
final Type w2 = stack().pop();
stack().push(w1);
stack().push(w2);
stack().push(w1);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDUP_X2(final DUP_X2 o) {
final Type w1 = stack().pop();
final Type w2 = stack().pop();
if (w2.getSize() == 2) {
stack().push(w1);
stack().push(w2);
stack().push(w1);
}
else{
final Type w3 = stack().pop();
stack().push(w1);
stack().push(w3);
stack().push(w2);
stack().push(w1);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDUP2(final DUP2 o) {
final Type t = stack().pop();
if (t.getSize() == 2) {
stack().push(t);
stack().push(t);
}
else{ // t.getSize() is 1
final Type u = stack().pop();
stack().push(u);
stack().push(t);
stack().push(u);
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDUP2_X1(final DUP2_X1 o) {
final Type t = stack().pop();
if (t.getSize() == 2) {
final Type u = stack().pop();
stack().push(t);
stack().push(u);
stack().push(t);
}
else{ //t.getSize() is1
final Type u = stack().pop();
final Type v = stack().pop();
stack().push(u);
stack().push(t);
stack().push(v);
stack().push(u);
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitDUP2_X2(final DUP2_X2 o) {
final Type t = stack().pop();
if (t.getSize() == 2) {
final Type u = stack().pop();
if (u.getSize() == 2) {
stack().push(t);
stack().push(u);
stack().push(t);
}else{
final Type v = stack().pop();
stack().push(t);
stack().push(v);
stack().push(u);
stack().push(t);
}
}
else{ //t.getSize() is 1
final Type u = stack().pop();
final Type v = stack().pop();
if (v.getSize() == 2) {
stack().push(u);
stack().push(t);
stack().push(v);
stack().push(u);
stack().push(t);
}else{
final Type w = stack().pop();
stack().push(u);
stack().push(t);
stack().push(w);
stack().push(v);
stack().push(u);
stack().push(t);
}
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitF2D(final F2D o) {
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitF2I(final F2I o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitF2L(final F2L o) {
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFADD(final FADD o) {
stack().pop();
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFALOAD(final FALOAD o) {
stack().pop();
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFASTORE(final FASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFCMPG(final FCMPG o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFCMPL(final FCMPL o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFCONST(final FCONST o) {
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFDIV(final FDIV o) {
stack().pop();
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFLOAD(final FLOAD o) {
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFMUL(final FMUL o) {
stack().pop();
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFNEG(final FNEG o) {
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFREM(final FREM o) {
stack().pop();
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFRETURN(final FRETURN o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFSTORE(final FSTORE o) {
locals().set(o.getIndex(), stack().pop());
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitFSUB(final FSUB o) {
stack().pop();
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitGETFIELD(final GETFIELD o) {
stack().pop();
Type t = o.getFieldType(cpg);
if ( t.equals(Type.BOOLEAN) ||
t.equals(Type.CHAR) ||
t.equals(Type.BYTE) ||
t.equals(Type.SHORT) ) {
t = Type.INT;
}
stack().push(t);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitGETSTATIC(final GETSTATIC o) {
Type t = o.getFieldType(cpg);
if ( t.equals(Type.BOOLEAN) ||
t.equals(Type.CHAR) ||
t.equals(Type.BYTE) ||
t.equals(Type.SHORT) ) {
t = Type.INT;
}
stack().push(t);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitGOTO(final GOTO o) {
// no stack changes.
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitGOTO_W(final GOTO_W o) {
// no stack changes.
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitI2B(final I2B o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitI2C(final I2C o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitI2D(final I2D o) {
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitI2F(final I2F o) {
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitI2L(final I2L o) {
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitI2S(final I2S o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIADD(final IADD o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIALOAD(final IALOAD o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIAND(final IAND o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIASTORE(final IASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitICONST(final ICONST o) {
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIDIV(final IDIV o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ACMPEQ(final IF_ACMPEQ o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ACMPNE(final IF_ACMPNE o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ICMPEQ(final IF_ICMPEQ o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ICMPGE(final IF_ICMPGE o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ICMPGT(final IF_ICMPGT o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ICMPLE(final IF_ICMPLE o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ICMPLT(final IF_ICMPLT o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIF_ICMPNE(final IF_ICMPNE o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFEQ(final IFEQ o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFGE(final IFGE o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFGT(final IFGT o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFLE(final IFLE o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFLT(final IFLT o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFNE(final IFNE o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFNONNULL(final IFNONNULL o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIFNULL(final IFNULL o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIINC(final IINC o) {
// stack is not changed.
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitILOAD(final ILOAD o) {
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIMUL(final IMUL o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitINEG(final INEG o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitINSTANCEOF(final INSTANCEOF o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction.
Since: 6.0
/**
* Symbolically executes the corresponding Java Virtual Machine instruction.
* @since 6.0
*/
@Override
public void visitINVOKEDYNAMIC(final INVOKEDYNAMIC o) {
for (int i=0; i<o.getArgumentTypes(cpg).length; i++) {
stack().pop();
}
// We are sure the invoked method will xRETURN eventually
// We simulate xRETURNs functionality here because we
// don't really "jump into" and simulate the invoked
// method.
if (o.getReturnType(cpg) != Type.VOID) {
Type t = o.getReturnType(cpg);
if ( t.equals(Type.BOOLEAN) ||
t.equals(Type.CHAR) ||
t.equals(Type.BYTE) ||
t.equals(Type.SHORT) ) {
t = Type.INT;
}
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitINVOKEINTERFACE(final INVOKEINTERFACE o) {
stack().pop(); //objectref
for (int i=0; i<o.getArgumentTypes(cpg).length; i++) {
stack().pop();
}
// We are sure the invoked method will xRETURN eventually
// We simulate xRETURNs functionality here because we
// don't really "jump into" and simulate the invoked
// method.
if (o.getReturnType(cpg) != Type.VOID) {
Type t = o.getReturnType(cpg);
if ( t.equals(Type.BOOLEAN) ||
t.equals(Type.CHAR) ||
t.equals(Type.BYTE) ||
t.equals(Type.SHORT) ) {
t = Type.INT;
}
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitINVOKESPECIAL(final INVOKESPECIAL o) {
if (o.getMethodName(cpg).equals(Const.CONSTRUCTOR_NAME)) {
final UninitializedObjectType t = (UninitializedObjectType) stack().peek(o.getArgumentTypes(cpg).length);
if (t == Frame.getThis()) {
Frame.setThis(null);
}
stack().initializeObject(t);
locals().initializeObject(t);
}
stack().pop(); //objectref
for (int i=0; i<o.getArgumentTypes(cpg).length; i++) {
stack().pop();
}
// We are sure the invoked method will xRETURN eventually
// We simulate xRETURNs functionality here because we
// don't really "jump into" and simulate the invoked
// method.
if (o.getReturnType(cpg) != Type.VOID) {
Type t = o.getReturnType(cpg);
if ( t.equals(Type.BOOLEAN) ||
t.equals(Type.CHAR) ||
t.equals(Type.BYTE) ||
t.equals(Type.SHORT) ) {
t = Type.INT;
}
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitINVOKESTATIC(final INVOKESTATIC o) {
for (int i=0; i<o.getArgumentTypes(cpg).length; i++) {
stack().pop();
}
// We are sure the invoked method will xRETURN eventually
// We simulate xRETURNs functionality here because we
// don't really "jump into" and simulate the invoked
// method.
if (o.getReturnType(cpg) != Type.VOID) {
Type t = o.getReturnType(cpg);
if ( t.equals(Type.BOOLEAN) ||
t.equals(Type.CHAR) ||
t.equals(Type.BYTE) ||
t.equals(Type.SHORT) ) {
t = Type.INT;
}
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitINVOKEVIRTUAL(final INVOKEVIRTUAL o) {
stack().pop(); //objectref
for (int i=0; i<o.getArgumentTypes(cpg).length; i++) {
stack().pop();
}
// We are sure the invoked method will xRETURN eventually
// We simulate xRETURNs functionality here because we
// don't really "jump into" and simulate the invoked
// method.
if (o.getReturnType(cpg) != Type.VOID) {
Type t = o.getReturnType(cpg);
if ( t.equals(Type.BOOLEAN) ||
t.equals(Type.CHAR) ||
t.equals(Type.BYTE) ||
t.equals(Type.SHORT) ) {
t = Type.INT;
}
stack().push(t);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIOR(final IOR o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIREM(final IREM o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIRETURN(final IRETURN o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitISHL(final ISHL o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitISHR(final ISHR o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitISTORE(final ISTORE o) {
locals().set(o.getIndex(), stack().pop());
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitISUB(final ISUB o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIUSHR(final IUSHR o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitIXOR(final IXOR o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitJSR(final JSR o) {
stack().push(new ReturnaddressType(o.physicalSuccessor()));
//System.err.println("TODO-----------:"+o.physicalSuccessor());
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitJSR_W(final JSR_W o) {
stack().push(new ReturnaddressType(o.physicalSuccessor()));
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitL2D(final L2D o) {
stack().pop();
stack().push(Type.DOUBLE);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitL2F(final L2F o) {
stack().pop();
stack().push(Type.FLOAT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitL2I(final L2I o) {
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLADD(final LADD o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLALOAD(final LALOAD o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLAND(final LAND o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLASTORE(final LASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLCMP(final LCMP o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLCONST(final LCONST o) {
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLDC(final LDC o) {
final Constant c = cpg.getConstant(o.getIndex());
if (c instanceof ConstantInteger) {
stack().push(Type.INT);
}
if (c instanceof ConstantFloat) {
stack().push(Type.FLOAT);
}
if (c instanceof ConstantString) {
stack().push(Type.STRING);
}
if (c instanceof ConstantClass) {
stack().push(Type.CLASS);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
public void visitLDC_W(final LDC_W o) {
final Constant c = cpg.getConstant(o.getIndex());
if (c instanceof ConstantInteger) {
stack().push(Type.INT);
}
if (c instanceof ConstantFloat) {
stack().push(Type.FLOAT);
}
if (c instanceof ConstantString) {
stack().push(Type.STRING);
}
if (c instanceof ConstantClass) {
stack().push(Type.CLASS);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLDC2_W(final LDC2_W o) {
final Constant c = cpg.getConstant(o.getIndex());
if (c instanceof ConstantLong) {
stack().push(Type.LONG);
}
if (c instanceof ConstantDouble) {
stack().push(Type.DOUBLE);
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLDIV(final LDIV o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLLOAD(final LLOAD o) {
stack().push(locals().get(o.getIndex()));
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLMUL(final LMUL o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLNEG(final LNEG o) {
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLOOKUPSWITCH(final LOOKUPSWITCH o) {
stack().pop(); //key
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLOR(final LOR o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLREM(final LREM o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLRETURN(final LRETURN o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLSHL(final LSHL o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLSHR(final LSHR o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLSTORE(final LSTORE o) {
locals().set(o.getIndex(), stack().pop());
locals().set(o.getIndex()+1, Type.UNKNOWN);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLSUB(final LSUB o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLUSHR(final LUSHR o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitLXOR(final LXOR o) {
stack().pop();
stack().pop();
stack().push(Type.LONG);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitMONITORENTER(final MONITORENTER o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitMONITOREXIT(final MONITOREXIT o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitMULTIANEWARRAY(final MULTIANEWARRAY o) {
for (int i=0; i<o.getDimensions(); i++) {
stack().pop();
}
stack().push(o.getType(cpg));
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitNEW(final NEW o) {
stack().push(new UninitializedObjectType((ObjectType) (o.getType(cpg))));
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitNEWARRAY(final NEWARRAY o) {
stack().pop();
stack().push(o.getType());
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitNOP(final NOP o) {
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitPOP(final POP o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitPOP2(final POP2 o) {
final Type t = stack().pop();
if (t.getSize() == 1) {
stack().pop();
}
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitPUTFIELD(final PUTFIELD o) {
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitPUTSTATIC(final PUTSTATIC o) {
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitRET(final RET o) {
// do nothing, return address
// is in in the local variables.
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitRETURN(final RETURN o) {
// do nothing.
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitSALOAD(final SALOAD o) {
stack().pop();
stack().pop();
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitSASTORE(final SASTORE o) {
stack().pop();
stack().pop();
stack().pop();
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitSIPUSH(final SIPUSH o) {
stack().push(Type.INT);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitSWAP(final SWAP o) {
final Type t = stack().pop();
final Type u = stack().pop();
stack().push(t);
stack().push(u);
}
Symbolically executes the corresponding Java Virtual Machine instruction. /** Symbolically executes the corresponding Java Virtual Machine instruction. */
@Override
public void visitTABLESWITCH(final TABLESWITCH o) {
stack().pop();
}
}