in src/main/java/com/amazon/corretto/hotpatch/org/objectweb/asm/Frame.java [680:1108]
void execute(
final int opcode, final int arg, final Symbol argSymbol, final SymbolTable symbolTable) {
// Abstract types popped from the stack or read from local variables.
int abstractType1;
int abstractType2;
int abstractType3;
int abstractType4;
switch (opcode) {
case Opcodes.NOP:
case Opcodes.INEG:
case Opcodes.LNEG:
case Opcodes.FNEG:
case Opcodes.DNEG:
case Opcodes.I2B:
case Opcodes.I2C:
case Opcodes.I2S:
case Opcodes.GOTO:
case Opcodes.RETURN:
break;
case Opcodes.ACONST_NULL:
push(NULL);
break;
case Opcodes.ICONST_M1:
case Opcodes.ICONST_0:
case Opcodes.ICONST_1:
case Opcodes.ICONST_2:
case Opcodes.ICONST_3:
case Opcodes.ICONST_4:
case Opcodes.ICONST_5:
case Opcodes.BIPUSH:
case Opcodes.SIPUSH:
case Opcodes.ILOAD:
push(INTEGER);
break;
case Opcodes.LCONST_0:
case Opcodes.LCONST_1:
case Opcodes.LLOAD:
push(LONG);
push(TOP);
break;
case Opcodes.FCONST_0:
case Opcodes.FCONST_1:
case Opcodes.FCONST_2:
case Opcodes.FLOAD:
push(FLOAT);
break;
case Opcodes.DCONST_0:
case Opcodes.DCONST_1:
case Opcodes.DLOAD:
push(DOUBLE);
push(TOP);
break;
case Opcodes.LDC:
switch (argSymbol.tag) {
case Symbol.CONSTANT_INTEGER_TAG:
push(INTEGER);
break;
case Symbol.CONSTANT_LONG_TAG:
push(LONG);
push(TOP);
break;
case Symbol.CONSTANT_FLOAT_TAG:
push(FLOAT);
break;
case Symbol.CONSTANT_DOUBLE_TAG:
push(DOUBLE);
push(TOP);
break;
case Symbol.CONSTANT_CLASS_TAG:
push(REFERENCE_KIND | symbolTable.addType("java/lang/Class"));
break;
case Symbol.CONSTANT_STRING_TAG:
push(REFERENCE_KIND | symbolTable.addType("java/lang/String"));
break;
case Symbol.CONSTANT_METHOD_TYPE_TAG:
push(REFERENCE_KIND | symbolTable.addType("java/lang/invoke/MethodType"));
break;
case Symbol.CONSTANT_METHOD_HANDLE_TAG:
push(REFERENCE_KIND | symbolTable.addType("java/lang/invoke/MethodHandle"));
break;
case Symbol.CONSTANT_DYNAMIC_TAG:
push(symbolTable, argSymbol.value);
break;
default:
throw new AssertionError();
}
break;
case Opcodes.ALOAD:
push(getLocal(arg));
break;
case Opcodes.LALOAD:
case Opcodes.D2L:
pop(2);
push(LONG);
push(TOP);
break;
case Opcodes.DALOAD:
case Opcodes.L2D:
pop(2);
push(DOUBLE);
push(TOP);
break;
case Opcodes.AALOAD:
pop(1);
abstractType1 = pop();
push(abstractType1 == NULL ? abstractType1 : ELEMENT_OF + abstractType1);
break;
case Opcodes.ISTORE:
case Opcodes.FSTORE:
case Opcodes.ASTORE:
abstractType1 = pop();
setLocal(arg, abstractType1);
if (arg > 0) {
int previousLocalType = getLocal(arg - 1);
if (previousLocalType == LONG || previousLocalType == DOUBLE) {
setLocal(arg - 1, TOP);
} else if ((previousLocalType & KIND_MASK) == LOCAL_KIND
|| (previousLocalType & KIND_MASK) == STACK_KIND) {
// The type of the previous local variable is not known yet, but if it later appears
// to be LONG or DOUBLE, we should then use TOP instead.
setLocal(arg - 1, previousLocalType | TOP_IF_LONG_OR_DOUBLE_FLAG);
}
}
break;
case Opcodes.LSTORE:
case Opcodes.DSTORE:
pop(1);
abstractType1 = pop();
setLocal(arg, abstractType1);
setLocal(arg + 1, TOP);
if (arg > 0) {
int previousLocalType = getLocal(arg - 1);
if (previousLocalType == LONG || previousLocalType == DOUBLE) {
setLocal(arg - 1, TOP);
} else if ((previousLocalType & KIND_MASK) == LOCAL_KIND
|| (previousLocalType & KIND_MASK) == STACK_KIND) {
// The type of the previous local variable is not known yet, but if it later appears
// to be LONG or DOUBLE, we should then use TOP instead.
setLocal(arg - 1, previousLocalType | TOP_IF_LONG_OR_DOUBLE_FLAG);
}
}
break;
case Opcodes.IASTORE:
case Opcodes.BASTORE:
case Opcodes.CASTORE:
case Opcodes.SASTORE:
case Opcodes.FASTORE:
case Opcodes.AASTORE:
pop(3);
break;
case Opcodes.LASTORE:
case Opcodes.DASTORE:
pop(4);
break;
case Opcodes.POP:
case Opcodes.IFEQ:
case Opcodes.IFNE:
case Opcodes.IFLT:
case Opcodes.IFGE:
case Opcodes.IFGT:
case Opcodes.IFLE:
case Opcodes.IRETURN:
case Opcodes.FRETURN:
case Opcodes.ARETURN:
case Opcodes.TABLESWITCH:
case Opcodes.LOOKUPSWITCH:
case Opcodes.ATHROW:
case Opcodes.MONITORENTER:
case Opcodes.MONITOREXIT:
case Opcodes.IFNULL:
case Opcodes.IFNONNULL:
pop(1);
break;
case Opcodes.POP2:
case Opcodes.IF_ICMPEQ:
case Opcodes.IF_ICMPNE:
case Opcodes.IF_ICMPLT:
case Opcodes.IF_ICMPGE:
case Opcodes.IF_ICMPGT:
case Opcodes.IF_ICMPLE:
case Opcodes.IF_ACMPEQ:
case Opcodes.IF_ACMPNE:
case Opcodes.LRETURN:
case Opcodes.DRETURN:
pop(2);
break;
case Opcodes.DUP:
abstractType1 = pop();
push(abstractType1);
push(abstractType1);
break;
case Opcodes.DUP_X1:
abstractType1 = pop();
abstractType2 = pop();
push(abstractType1);
push(abstractType2);
push(abstractType1);
break;
case Opcodes.DUP_X2:
abstractType1 = pop();
abstractType2 = pop();
abstractType3 = pop();
push(abstractType1);
push(abstractType3);
push(abstractType2);
push(abstractType1);
break;
case Opcodes.DUP2:
abstractType1 = pop();
abstractType2 = pop();
push(abstractType2);
push(abstractType1);
push(abstractType2);
push(abstractType1);
break;
case Opcodes.DUP2_X1:
abstractType1 = pop();
abstractType2 = pop();
abstractType3 = pop();
push(abstractType2);
push(abstractType1);
push(abstractType3);
push(abstractType2);
push(abstractType1);
break;
case Opcodes.DUP2_X2:
abstractType1 = pop();
abstractType2 = pop();
abstractType3 = pop();
abstractType4 = pop();
push(abstractType2);
push(abstractType1);
push(abstractType4);
push(abstractType3);
push(abstractType2);
push(abstractType1);
break;
case Opcodes.SWAP:
abstractType1 = pop();
abstractType2 = pop();
push(abstractType1);
push(abstractType2);
break;
case Opcodes.IALOAD:
case Opcodes.BALOAD:
case Opcodes.CALOAD:
case Opcodes.SALOAD:
case Opcodes.IADD:
case Opcodes.ISUB:
case Opcodes.IMUL:
case Opcodes.IDIV:
case Opcodes.IREM:
case Opcodes.IAND:
case Opcodes.IOR:
case Opcodes.IXOR:
case Opcodes.ISHL:
case Opcodes.ISHR:
case Opcodes.IUSHR:
case Opcodes.L2I:
case Opcodes.D2I:
case Opcodes.FCMPL:
case Opcodes.FCMPG:
pop(2);
push(INTEGER);
break;
case Opcodes.LADD:
case Opcodes.LSUB:
case Opcodes.LMUL:
case Opcodes.LDIV:
case Opcodes.LREM:
case Opcodes.LAND:
case Opcodes.LOR:
case Opcodes.LXOR:
pop(4);
push(LONG);
push(TOP);
break;
case Opcodes.FALOAD:
case Opcodes.FADD:
case Opcodes.FSUB:
case Opcodes.FMUL:
case Opcodes.FDIV:
case Opcodes.FREM:
case Opcodes.L2F:
case Opcodes.D2F:
pop(2);
push(FLOAT);
break;
case Opcodes.DADD:
case Opcodes.DSUB:
case Opcodes.DMUL:
case Opcodes.DDIV:
case Opcodes.DREM:
pop(4);
push(DOUBLE);
push(TOP);
break;
case Opcodes.LSHL:
case Opcodes.LSHR:
case Opcodes.LUSHR:
pop(3);
push(LONG);
push(TOP);
break;
case Opcodes.IINC:
setLocal(arg, INTEGER);
break;
case Opcodes.I2L:
case Opcodes.F2L:
pop(1);
push(LONG);
push(TOP);
break;
case Opcodes.I2F:
pop(1);
push(FLOAT);
break;
case Opcodes.I2D:
case Opcodes.F2D:
pop(1);
push(DOUBLE);
push(TOP);
break;
case Opcodes.F2I:
case Opcodes.ARRAYLENGTH:
case Opcodes.INSTANCEOF:
pop(1);
push(INTEGER);
break;
case Opcodes.LCMP:
case Opcodes.DCMPL:
case Opcodes.DCMPG:
pop(4);
push(INTEGER);
break;
case Opcodes.JSR:
case Opcodes.RET:
throw new IllegalArgumentException("JSR/RET are not supported with computeFrames option");
case Opcodes.GETSTATIC:
push(symbolTable, argSymbol.value);
break;
case Opcodes.PUTSTATIC:
pop(argSymbol.value);
break;
case Opcodes.GETFIELD:
pop(1);
push(symbolTable, argSymbol.value);
break;
case Opcodes.PUTFIELD:
pop(argSymbol.value);
pop();
break;
case Opcodes.INVOKEVIRTUAL:
case Opcodes.INVOKESPECIAL:
case Opcodes.INVOKESTATIC:
case Opcodes.INVOKEINTERFACE:
pop(argSymbol.value);
if (opcode != Opcodes.INVOKESTATIC) {
abstractType1 = pop();
if (opcode == Opcodes.INVOKESPECIAL && argSymbol.name.charAt(0) == '<') {
addInitializedType(abstractType1);
}
}
push(symbolTable, argSymbol.value);
break;
case Opcodes.INVOKEDYNAMIC:
pop(argSymbol.value);
push(symbolTable, argSymbol.value);
break;
case Opcodes.NEW:
push(UNINITIALIZED_KIND | symbolTable.addUninitializedType(argSymbol.value, arg));
break;
case Opcodes.NEWARRAY:
pop();
switch (arg) {
case Opcodes.T_BOOLEAN:
push(ARRAY_OF | BOOLEAN);
break;
case Opcodes.T_CHAR:
push(ARRAY_OF | CHAR);
break;
case Opcodes.T_BYTE:
push(ARRAY_OF | BYTE);
break;
case Opcodes.T_SHORT:
push(ARRAY_OF | SHORT);
break;
case Opcodes.T_INT:
push(ARRAY_OF | INTEGER);
break;
case Opcodes.T_FLOAT:
push(ARRAY_OF | FLOAT);
break;
case Opcodes.T_DOUBLE:
push(ARRAY_OF | DOUBLE);
break;
case Opcodes.T_LONG:
push(ARRAY_OF | LONG);
break;
default:
throw new IllegalArgumentException();
}
break;
case Opcodes.ANEWARRAY:
String arrayElementType = argSymbol.value;
pop();
if (arrayElementType.charAt(0) == '[') {
push(symbolTable, '[' + arrayElementType);
} else {
push(ARRAY_OF | REFERENCE_KIND | symbolTable.addType(arrayElementType));
}
break;
case Opcodes.CHECKCAST:
String castType = argSymbol.value;
pop();
if (castType.charAt(0) == '[') {
push(symbolTable, castType);
} else {
push(REFERENCE_KIND | symbolTable.addType(castType));
}
break;
case Opcodes.MULTIANEWARRAY:
pop(arg);
push(symbolTable, argSymbol.value);
break;
default:
throw new IllegalArgumentException();
}
}