/** * evaluates an instruction and determines if it will result in true or false on TOS. * * @param i is an instruction to analyze * @return whether TOS is true, false, or not known */ private static ConstantBoolean isTrueInstructionInfo(InstructionInfo i) { ConstantBoolean ret = ConstantBoolean.DONT_KNOW; switch (i.getOpcode()) { case OP_pushtrue: ret = ConstantBoolean.TRUE; break; case OP_pushfalse: ret = ConstantBoolean.FALSE; break; case OP_pushbyte: { int value = i.getImmediate(); assert value >= 0; ret = ECMASupport.toBoolean(value) ? ConstantBoolean.TRUE : ConstantBoolean.FALSE; break; } case OP_pushint: { int value = (Integer) i.getOperand(0); ret = ECMASupport.toBoolean(value) ? ConstantBoolean.TRUE : ConstantBoolean.FALSE; break; } case OP_pushuint: { long value = (Long) i.getOperand(0); ret = ECMASupport.toBoolean(value) ? ConstantBoolean.TRUE : ConstantBoolean.FALSE; break; } case OP_pushstring: { String value = i.getOperand(0).toString(); ret = ECMASupport.toBoolean(value) ? ConstantBoolean.TRUE : ConstantBoolean.FALSE; break; } case OP_pushnull: ret = ConstantBoolean.FALSE; break; } return ret; }
/** * Optimizations for OP_convert_d: convert_d, convert_d -> convert_d pushbyte n, convert_d -> * pushdouble n pushint n, convert_d -> pushdouble n pushuint n, convert_d -> pushdouble n * pushdouble n, convert_d -> pushdouble n pushnan, convert_d -> pushnan lf32, convert_d -> lf32 * lf64, convert_d -> lf64 * * @param i The convert_d instruction */ private void op_convert_d(InstructionInfo i) { InstructionInfo prev = previous(1); switch (prev.getOpcode()) { case OP_pushbyte: { // replace pushbyte, convert d with pushdouble - should be faster replace( 1, InstructionFactory.getInstruction( OP_pushdouble, new Double(convertByteImmediateToDouble(prev.getImmediate())))); break; } case OP_pushint: case OP_pushuint: { // replace pushint , convert d with pushdouble - should be faster replace( 1, InstructionFactory.getInstruction( OP_pushdouble, new Double(((Number) prev.getOperand(0)).doubleValue()))); break; } case OP_pushdouble: case OP_pushnan: case OP_lf32: case OP_lf64: case OP_convert_d: { // result is already a double, just erase the op_convert_d delete(0); break; } default: { // nothing to do - instruction has already been added } } }