⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 stackmap.c

📁 This is a java virtual machine implement in c
💻 C
📖 第 1 页 / 共 3 页
字号:
/*0290*/                BIT_SET(stackSize);
/*0291*/                stackSize--;
/*0292*/                goto pushDouble;
/*0293*/
/*0294*/                /* These pop two items off the stack */
/*0295*/            case IF_ICMPEQ: case IF_ICMPNE: case IF_ICMPLT: case IF_ICMPGE:
/*0296*/            case IF_ICMPGT: case IF_ICMPLE: case IF_ACMPEQ: case IF_ACMPNE:
/*0297*/            case PUTFIELD_FAST:
/*0298*/            case PUTSTATIC2_FAST:
/*0299*/                thisIP += 2;
/*0300*/            case POP2:
/*0301*/            case LADD: case DADD: case LSUB: case DSUB: case LMUL: case DMUL:
/*0302*/            case LDIV: case DDIV: case LREM: case DREM:
/*0303*/            case LAND: case LOR: case LXOR:
/*0304*/                stackSize -= 2;
/*0305*/                break;
/*0306*/
/*0307*/                /* These pop two items off, and then push non-pointer */
/*0308*/            case IALOAD: case FALOAD: case BALOAD: case CALOAD: case SALOAD:
/*0309*/                stackSize -= 2;
/*0310*/                goto pushInt;
/*0311*/
/*0312*/                /* These pop two items off, and then push two non pointers */
/*0313*/            case DALOAD: case LALOAD:
/*0314*/                stackSize -= 2;
/*0315*/                goto pushDouble;
/*0316*/
/*0317*/                /* These pop three items off the stack. */
/*0318*/            case PUTFIELD2_FAST:
/*0319*/                thisIP += 2;
/*0320*/            case IASTORE: case FASTORE: case AASTORE: case BASTORE:
/*0321*/            case CASTORE: case SASTORE:
/*0322*/            case LCMP:    case DCMPL:   case DCMPG:
/*0323*/                stackSize -= 3;
/*0324*/                break;
/*0325*/
/*0326*/                /* These pop four items off the stack. */
/*0327*/            case LASTORE:
/*0328*/            case DASTORE:
/*0329*/                stackSize -= 4;
/*0330*/                break;
/*0331*/
/*0332*/                /* These either load a pointer or an integer */
/*0333*/            case LDC:
/*0334*/                index = *thisIP++;
/*0335*/                goto handleLoadConstant;
/*0336*/            case LDC_W:
/*0337*/                index = getUShort(thisIP);
/*0338*/                thisIP += 2;
/*0339*/            handleLoadConstant:
/*0340*/                if (CONSTANTPOOL_TAG(cp, index) == CONSTANT_String) {
/*0341*/                    goto pushPointer;
/*0342*/                } else {
/*0343*/                    goto pushInt;
/*0344*/                }
/*0345*/
/*0346*/                /* These involve doing bit twiddling */
/*0347*/            case DUP:
/*0348*/                getBits(map, stackSize - 1, 1, dupValues);
/*0349*/                if (dupValues[0]) {
/*0350*/                    goto pushPointer;
/*0351*/                } else {
/*0352*/                    goto pushInt;
/*0353*/                }
/*0354*/
/*0355*/            case DUP_X1:
/*0356*/                getBits(map, stackSize - 2, 2, dupValues + 1);
/*0357*/                dupValues[0] = dupValues[2];
/*0358*/                setBits(map, stackSize - 2, 3, dupValues);
/*0359*/                stackSize++;
/*0360*/                break;
/*0361*/
/*0362*/            case DUP_X2:
/*0363*/                getBits(map, stackSize - 3, 3, dupValues + 1);
/*0364*/                dupValues[0] = dupValues[3];
/*0365*/                setBits(map, stackSize - 3, 4, dupValues);
/*0366*/                stackSize++;
/*0367*/                break;
/*0368*/
/*0369*/
/*0370*/            case DUP2:
/*0371*/                getBits(map, stackSize - 2, 2, dupValues);
/*0372*/                setBits(map, stackSize, 2, dupValues);
/*0373*/                stackSize += 2;
/*0374*/                break;
/*0375*/
/*0376*/
/*0377*/            case DUP2_X1:
/*0378*/                getBits(map, stackSize - 3, 3, dupValues + 2);
/*0379*/                dupValues[0] = dupValues[3];
/*0380*/                dupValues[1] = dupValues[4];
/*0381*/                setBits(map, stackSize - 3, 5, dupValues);
/*0382*/                stackSize  += 2;
/*0383*/                break;
/*0384*/
/*0385*/
/*0386*/            case DUP2_X2:
/*0387*/                getBits(map, stackSize - 4, 4, dupValues + 2);
/*0388*/                dupValues[0] = dupValues[4];
/*0389*/                dupValues[1] = dupValues[5];
/*0390*/                setBits(map, stackSize - 4, 6, dupValues);
/*0391*/                stackSize += 2;
/*0392*/                break;
/*0393*/
/*0394*/            case SWAP:
/*0395*/                getBits(map, stackSize - 2, 2, dupValues + 1);
/*0396*/                dupValues[0] = dupValues[2];
/*0397*/                setBits(map, stackSize - 2, 2, dupValues);
/*0398*/                break;
/*0399*/
/*0400*/                /* Get a field.  We don't know what type of object we
/*0401./                 * are getting.
/*0402./                 */
/*0403*/            case GETFIELD:
/*0404*/                /* Remove the pointer to the object */
/*0405*/                stackSize -= 1;
/*0406*/            case GETSTATIC:
/*0407*/                index = getUShort(thisIP);
/*0408*/                thisIP += 2;
/*0409*/                field = (FIELD)cp->entries[index].cache;
/*0422*/                /* Determine what needs to be pushed onto the stack,
/*0423./                 * on the basis of the flags in the field */
/*0424*/                if (field->accessFlags & ACC_POINTER) {
/*0425*/                    goto pushPointer;
/*0426*/                } else if (field->accessFlags & ACC_DOUBLE) {
/*0427*/                    goto pushDouble;
/*0428*/                } else {
/*0429*/                    goto pushInt;
/*0430*/                }
/*0431*/
/*0432*/                /* Set a field value from the stack */
/*0433*/            case PUTFIELD:
/*0434*/                /* Remove the pointer to the object */
/*0435*/                stackSize -= 1;
/*0436*/            case PUTSTATIC:
/*0437*/                index = getUShort(thisIP);
/*0438*/                thisIP += 2;
/*0439*/                field = (FIELD)cp->entries[index].cache;
/*0451*/                /* We are either removing a single word or two words.  We
/*0452./                 * don't care if it is a pointer or not.
/*0453./                 */
/*0454*/                stackSize -= (field->accessFlags & ACC_DOUBLE) ? 2 : 1;
/*0455*/                break;
/*0456*/
/*0457*/
/*0458*/                /* We remove thisIP[2] dimensions, and then we push
/*0459./                 * the result */
/*0460*/            case MULTIANEWARRAY:
/*0461*/            case MULTIANEWARRAY_FAST:
/*0462*/                stackSize -= thisIP[2];
/*0463*/                thisIP += 3;
/*0464*/                goto pushPointer;
/*0465*/
/*0466*/            case WIDE:
/*0467*/                token = *thisIP++;
/*0468*/                index = getUShort(thisIP); thisIP += 2;
/*0469*/                switch (token) {
/*0470*/                    case ILOAD: case FLOAD:
/*0471*/                        goto pushInt;
/*0472*/                    case LLOAD: case DLOAD:
/*0473*/                        goto pushDouble;
/*0474*/                    case ALOAD:
/*0475*/                        goto pushPointer;
/*0476*/                    case LSTORE: case DSTORE:
/*0477*/                        goto storeDouble;
/*0478*/                    case ISTORE: case FSTORE:
/*0479*/                        goto storeInt;
/*0480*/                    case ASTORE:
/*0481*/                        goto storePointer;
/*0482*/                    case IINC:
/*0483*/                        thisIP += 2; break;
/*0484*/                    default:    /* RET shouldn't happen! */
/*0485*/                        fatalError(KVM_MSG_UNEXPECTED_BYTECODE);
/*0486*/                        break;
/*0487*/                }
/*0488*/                break;
/*0489*/
/*0490*/#if ENABLEFASTBYTECODES
/*0491*/            case INVOKEVIRTUAL_FAST:
/*0492*/            case INVOKEINTERFACE_FAST:
/*0493*/            {
/*0494*/                unsigned int iCacheIndex = getUShort(thisIP);
/*0495*/                ICACHE thisICache = getInlineCache(iCacheIndex);
/*0496*/                method = (METHOD)thisICache->contents;
/*0497*/                thisIP += (token == INVOKEINTERFACE_FAST) ? 4 : 2;
/*0498*/                goto handleMethodCall;
/*0499*/            }
/*0500*/#endif
/*0501*/
/*0502*/#if ENABLEFASTBYTECODES
/*0503*/            case INVOKESPECIAL_FAST:
/*0504*/            case INVOKESTATIC_FAST:
/*0505*/#endif
/*0506*/            case INVOKEVIRTUAL:
/*0507*/            case INVOKESPECIAL:
/*0508*/            case INVOKESTATIC:
/*0509*/            case INVOKEINTERFACE: {
/*0510*/                unsigned int cpIndex = getUShort(thisIP);
/*0511*/                CONSTANTPOOL_ENTRY thisEntry = &cp->entries[cpIndex];
/*0512*/                thisIP += (token == INVOKEINTERFACE) ? 4 : 2;
/*0517*/                method = ((METHOD) thisEntry->cache);
/*0518*/            }
/*0519*/
/*0520*/#if ENABLEFASTBYTECODES
/*0521*/            handleMethodCall:
/*0522*/#endif
/*0529*/                /* Remove the arguments. */
/*0530*/                stackSize -= method->argCount;
/*0534*/                /* Push the return result */
/*0535*/                switch (method->accessFlags & (ACC_POINTER | ACC_DOUBLE)) {
/*0536*/                    case ACC_DOUBLE:
/*0537*/                        goto pushDouble;
/*0538*/                    case 0:     /* int */
/*0539*/                        goto pushInt;
/*0540*/                    case ACC_POINTER | ACC_DOUBLE:   /* void */
/*0541*/                        break;
/*0542*/                    case ACC_POINTER:
/*0543*/                        goto pushPointer;
/*0544*/                }
/*0545*/                break;
/*0546*/
/*0553*/            default:
/*0554*/                fatalError(KVM_MSG_UNEXPECTED_BYTECODE);
/*0555*/        }
/*0556*/
/*0557*/        if (stackSize < localsCount) {
/*0558*/            fatalError(KVM_MSG_ILLEGAL_STACK_SIZE);
/*0559*/        }
/*0560*/
/*0570*/    } /* end of while */
/*0571*/
/*0572*/    if (thisIP > targetIP) {
/*0573*/        fatalError(KVM_MSG_STRANGE_VALUE_OF_THISIP);
/*0574*/    }
/*0575*/
/*0576*/    return stackSize - localsCount;
/*0577*/}
/*0578*/
/*0579*//*=========================================================================
/*0580./ * FUNCTION:      getInitialRegisterMask
/*0581./ * TYPE:          Important GC function
/*0582./ * OVERVIEW:      Returns a bitmap indicating the live size of the stack
/*0583./ * INTERFACE:
/*0584./ *   parameters:  thisMethod:    The current method
/*0585./ *                targetOffsetP: Pointer to offset into the method for which
/*0586./ *                               we want a stack map
/*0587./ *                map            Map to fill in with the stack map information.
/*0588./ *
/*0589./ *   returns:     The stack size.  It also fills in *map and *targetOffsetP.
/*0590./ *
/*0591./ * This function will determine a stack map either for *targetOffsetP or for
/*0592./ * some offset before *targetOffsetP.  It will update *targetOffsetP with the
/*0593./ * offset that it actually knows about.
/*0594./ *
/*0595./ * This function has two sources of knowing a stack map for a particular
/*0596./ * location.
/*0597./ *      the method's stackmap field.
/*0598./ *      the method's signature, if there is no stackmap, or all stackmaps
/*0599./ *                 are for an address after the current one.
/*0600./ *=======================================================================*/

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -