📄 interp.c
字号:
Operand operand; WITH_OPCODE_CHANGE_CP_DINDEX(OPC_INVOKEINTERFACE, idx, cache); frame->last_pc = pc; new_mb = resolveInterfaceMethod(mb->class, idx); if(exceptionOccured0(ee)) goto throwException; if(CLASS_CB(new_mb->class)->access_flags & ACC_INTERFACE) { operand.uu.u1 = idx; operand.uu.u2 = 0; OPCODE_REWRITE(OPC_INVOKEINTERFACE_QUICK, cache, operand); } else { operand.uu.u1 = new_mb->args_count; operand.uu.u2 = new_mb->method_table_index; OPCODE_REWRITE(OPC_INVOKEVIRTUAL_QUICK, cache, operand); } REDISPATCH });) DEF_OPC_RW(OPC_MULTIANEWARRAY, ({ int idx = pc->operand.uui.u1; int cache = pc->operand.uui.i; frame->last_pc = pc; resolveClass(mb->class, idx, FALSE); if(exceptionOccured0(ee)) goto throwException; OPCODE_REWRITE(OPC_MULTIANEWARRAY_QUICK, cache, pc->operand); REDISPATCH });) DEF_OPC_RW_4(OPC_NEW, OPC_ANEWARRAY, OPC_CHECKCAST, OPC_INSTANCEOF, ({ int idx = pc->operand.uui.u1; int opcode = pc->operand.uui.u2; int cache = pc->operand.uui.i; Class *class; frame->last_pc = pc; class = resolveClass(mb->class, idx, opcode == OPC_NEW); if(exceptionOccured0(ee)) goto throwException; if(opcode == OPC_NEW) { ClassBlock *cb = CLASS_CB(class); if(cb->access_flags & (ACC_INTERFACE | ACC_ABSTRACT)) { signalException("java/lang/InstantiationError", cb->name); goto throwException; } } OPCODE_REWRITE((opcode + OPC_NEW_QUICK-OPC_NEW), cache, pc->operand); REDISPATCH });)#else /* DIRECT */ DEF_OPC_210(OPC_LDC, { frame->last_pc = pc; resolveSingleConstant(mb->class, SINGLE_INDEX(pc)); if(exceptionOccured0(ee)) goto throwException; OPCODE_REWRITE(OPC_LDC_QUICK); DISPATCH(0, 0); }) DEF_OPC_210(OPC_LDC_W, { frame->last_pc = pc; resolveSingleConstant(mb->class, DOUBLE_INDEX(pc)); if(exceptionOccured0(ee)) goto throwException; OPCODE_REWRITE(OPC_LDC_W_QUICK); DISPATCH(0, 0); }) DEF_OPC_210(OPC_ALOAD_0, { if(mb->access_flags & ACC_STATIC) OPCODE_REWRITE(OPC_ILOAD_0); else OPCODE_REWRITE(OPC_ALOAD_THIS); DISPATCH(0, 0); }) DEF_OPC_210(OPC_TABLESWITCH, { int *aligned_pc = (int*)((uintptr_t)(pc + 4) & ~0x3); int deflt = ntohl(aligned_pc[0]); int low = ntohl(aligned_pc[1]); int high = ntohl(aligned_pc[2]); int index = *--ostack; DISPATCH(0, (index < low || index > high) ? deflt : ntohl(aligned_pc[index - low + 3])); }) DEF_OPC_210(OPC_LOOKUPSWITCH, { int *aligned_pc = (int*)((uintptr_t)(pc + 4) & ~0x3); int deflt = ntohl(aligned_pc[0]); int npairs = ntohl(aligned_pc[1]); int key = *--ostack; int i; for(i = 2; (i < npairs*2+2) && (key != ntohl(aligned_pc[i])); i += 2); DISPATCH(0, i == npairs*2+2 ? deflt : ntohl(aligned_pc[i+1])); }) DEF_OPC_210(OPC_GETSTATIC, { FieldBlock *fb; frame->last_pc = pc; fb = resolveField(mb->class, DOUBLE_INDEX(pc)); if(exceptionOccured0(ee)) goto throwException; if((*fb->type == 'J') || (*fb->type == 'D')) OPCODE_REWRITE(OPC_GETSTATIC2_QUICK); else OPCODE_REWRITE(OPC_GETSTATIC_QUICK); DISPATCH(0, 0); }) DEF_OPC_210(OPC_PUTSTATIC, { FieldBlock *fb; frame->last_pc = pc; fb = resolveField(mb->class, DOUBLE_INDEX(pc)); if(exceptionOccured0(ee)) goto throwException; if((*fb->type == 'J') || (*fb->type == 'D')) OPCODE_REWRITE(OPC_PUTSTATIC2_QUICK); else OPCODE_REWRITE(OPC_PUTSTATIC_QUICK); DISPATCH(0, 0); }) DEF_OPC_210(OPC_GETFIELD, { int idx; FieldBlock *fb; WITH_OPCODE_CHANGE_CP_DINDEX(OPC_GETFIELD, idx); frame->last_pc = pc; fb = resolveField(mb->class, idx); if(exceptionOccured0(ee)) goto throwException; if(fb->offset > 255) OPCODE_REWRITE(OPC_GETFIELD_QUICK_W); else OPCODE_REWRITE_OPERAND1(((*fb->type == 'J') || (*fb->type == 'D') ? OPC_GETFIELD2_QUICK : OPC_GETFIELD_QUICK), fb->offset); DISPATCH(0, 0); }) DEF_OPC_210(OPC_PUTFIELD, { int idx; FieldBlock *fb; WITH_OPCODE_CHANGE_CP_DINDEX(OPC_PUTFIELD, idx); frame->last_pc = pc; fb = resolveField(mb->class, idx); if(exceptionOccured0(ee)) goto throwException; if(fb->offset > 255) OPCODE_REWRITE(OPC_PUTFIELD_QUICK_W); else OPCODE_REWRITE_OPERAND1(((*fb->type == 'J') || (*fb->type == 'D') ? OPC_PUTFIELD2_QUICK : OPC_PUTFIELD_QUICK), fb->offset); DISPATCH(0, 0); }) DEF_OPC_210(OPC_GETFIELD_QUICK_W, { FieldBlock *fb = RESOLVED_FIELD(pc); Object *obj = (Object *)*--ostack; uintptr_t *addr; NULL_POINTER_CHECK(obj); addr = &(INST_DATA(obj)[fb->offset]); if((*fb->type == 'J') || (*fb->type == 'D')) { PUSH_LONG(*(u8*)addr, 3); } else { PUSH_0(*addr, 3); } })#ifdef USE_CACHE DEF_OPC_012(OPC_PUTFIELD_QUICK_W, { FieldBlock *fb = RESOLVED_FIELD(pc); if((*fb->type == 'J') || (*fb->type == 'D')) { Object *obj = (Object *)*--ostack; NULL_POINTER_CHECK(obj); *(u8*)(&(INST_DATA(obj)[fb->offset])) = cache.l; } else { Object *obj = (Object *)cache.i.v1; NULL_POINTER_CHECK(obj); INST_DATA(obj)[fb->offset] = cache.i.v2; } DISPATCH(0, 3); })#else DEF_OPC_012(OPC_PUTFIELD_QUICK_W, { FieldBlock *fb = RESOLVED_FIELD(pc); if((*fb->type == 'J') || (*fb->type == 'D')) { Object *obj = (Object *)ostack[-3]; ostack -= 3; NULL_POINTER_CHECK(obj); *(u8*)(&(INST_DATA(obj)[fb->offset])) = *(u8*)&ostack[1]; } else { Object *obj = (Object *)ostack[-2]; ostack -= 2; NULL_POINTER_CHECK(obj); INST_DATA(obj)[fb->offset] = ostack[1]; } DISPATCH(0, 3); })#endif DEF_OPC_210(OPC_INVOKEVIRTUAL, { int idx; WITH_OPCODE_CHANGE_CP_DINDEX(OPC_INVOKEVIRTUAL, idx); frame->last_pc = pc; new_mb = resolveMethod(mb->class, idx); if(exceptionOccured0(ee)) goto throwException; if((new_mb->args_count < 256) && (new_mb->method_table_index < 256)) { OPCODE_REWRITE_OPERAND2(OPC_INVOKEVIRTUAL_QUICK, new_mb->method_table_index, new_mb->args_count); } else OPCODE_REWRITE(OPC_INVOKEVIRTUAL_QUICK_W); DISPATCH(0, 0); }) DEF_OPC_210(OPC_INVOKEVIRTUAL_QUICK_W, { new_mb = RESOLVED_METHOD(pc); arg1 = ostack - (new_mb->args_count); NULL_POINTER_CHECK(*arg1); new_class = (*(Object **)arg1)->class; new_mb = CLASS_CB(new_class)->method_table[new_mb->method_table_index]; goto invokeMethod; }) DEF_OPC_210(OPC_INVOKESPECIAL, { int idx; WITH_OPCODE_CHANGE_CP_DINDEX(OPC_INVOKESPECIAL, idx); frame->last_pc = pc; new_mb = resolveMethod(mb->class, idx); if(exceptionOccured0(ee)) goto throwException; /* Check if invoking a super method... */ if((CLASS_CB(mb->class)->access_flags & ACC_SUPER) && ((new_mb->access_flags & ACC_PRIVATE) == 0) && (new_mb->name[0] != '<')) { OPCODE_REWRITE_OPERAND2(OPC_INVOKESUPER_QUICK, new_mb->method_table_index >> 8, new_mb->method_table_index & 0xff); } else OPCODE_REWRITE(OPC_INVOKENONVIRTUAL_QUICK); DISPATCH(0, 0); }) DEF_OPC_210(OPC_INVOKESTATIC, { frame->last_pc = pc; new_mb = resolveMethod(mb->class, DOUBLE_INDEX(pc)); if(exceptionOccured0(ee)) goto throwException; OPCODE_REWRITE(OPC_INVOKESTATIC_QUICK); DISPATCH(0, 0); }) DEF_OPC_210(OPC_INVOKEINTERFACE, { frame->last_pc = pc; new_mb = resolveInterfaceMethod(mb->class, DOUBLE_INDEX(pc)); if(exceptionOccured0(ee)) goto throwException; if(CLASS_CB(new_mb->class)->access_flags & ACC_INTERFACE) OPCODE_REWRITE(OPC_INVOKEINTERFACE_QUICK); else { pc[3] = pc[4] = OPC_NOP; OPCODE_REWRITE(OPC_INVOKEVIRTUAL); } DISPATCH(0, 0); })#define REWRITE_RESOLVE_CLASS(opcode) \ DEF_OPC_210(opcode, { \ frame->last_pc = pc; \ resolveClass(mb->class, DOUBLE_INDEX(pc), FALSE); \ \ if(exceptionOccured0(ee)) \ goto throwException; \ \ OPCODE_REWRITE((opcode + OPC_ANEWARRAY_QUICK-OPC_ANEWARRAY)); \ DISPATCH(0, 0); \ }) REWRITE_RESOLVE_CLASS(OPC_ANEWARRAY) REWRITE_RESOLVE_CLASS(OPC_CHECKCAST) REWRITE_RESOLVE_CLASS(OPC_INSTANCEOF) REWRITE_RESOLVE_CLASS(OPC_MULTIANEWARRAY) DEF_OPC_210(OPC_NEW, { Class *class; ClassBlock *cb; frame->last_pc = pc; class = resolveClass(mb->class, DOUBLE_INDEX(pc), TRUE); if(exceptionOccured0(ee)) goto throwException; cb = CLASS_CB(class); if(cb->access_flags & (ACC_INTERFACE | ACC_ABSTRACT)) { signalException("java/lang/InstantiationError", cb->name); goto throwException; } OPCODE_REWRITE(OPC_NEW_QUICK); DISPATCH(0, 0); }) DEF_OPC_210(OPC_WIDE, { int opcode = pc[1]; switch(opcode) { case OPC_ILOAD: case OPC_FLOAD: case OPC_ALOAD: *ostack++ = lvars[DOUBLE_INDEX(pc+1)]; pc += 4; break; case OPC_LLOAD: case OPC_DLOAD: *(u8*)ostack = *(u8*)(&lvars[DOUBLE_INDEX(pc+1)]); ostack += 2; pc += 4; break; case OPC_ISTORE: case OPC_FSTORE: case OPC_ASTORE: lvars[DOUBLE_INDEX(pc+1)] = *--ostack; pc += 4; break; case OPC_LSTORE: case OPC_DSTORE: ostack -= 2; *(u8*)(&lvars[DOUBLE_INDEX(pc+1)]) = *(u8*)ostack; pc += 4; break; case OPC_RET: pc = (unsigned char*)lvars[DOUBLE_INDEX((pc+1))]; break; case OPC_IINC:
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -