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

📄 inlinejsr.c

📁 已经移植好的java虚拟机
💻 C
📖 第 1 页 / 共 2 页
字号:
#if MYDEBUG    printf("Creating code of length %d\n", pc);#endif    for (codeRef = context->codeRef; codeRef < codeRefEnd; codeRef++) {        if (codeRef->flags != CRF_SKIP) {             instruction_data_type *this_idata = &idata[codeRef->inumber];            opcode_type opcode = this_idata->opcode;            int pc = codeRef->offset;            unsigned char *source = &oldCode[this_idata->offset];            unsigned char *target = &newCode[pc];            #if MYDEBUG            printf("\t%d:\t%d\tpc=%d\t%s (%d) \n",                    (codeRef - context->codeRef),                    (this_idata - vcontext->instruction_data),                    pc,                    (this_idata->opcode == 256                          ? "invokeinit" : opnames[this_idata->opcode]),                   this_idata->offset                   );#endif                        switch(opcode) {                 case opc_ifeq: case opc_ifne: case opc_iflt:                 case opc_ifge: case opc_ifgt: case opc_ifle:                case opc_ifnull: case opc_ifnonnull:                case opc_if_icmpeq: case opc_if_icmpne: case opc_if_icmplt:                 case opc_if_icmpge: case opc_if_icmpgt: case opc_if_icmple:                case opc_if_acmpeq: case opc_if_acmpne:                 case opc_goto: case opc_goto_w:                    target[0] = source[0];                    updateTarget(context, this_idata->operand.i,                                  codeRef->subroutine,                                  target + 1, pc, this_idata->length - 1);                    break;                                case opc_jsr: case opc_jsr_w:                     target[0] = opc_goto;                    if (codeRef->flags == CRF_JSR_SIMPLE_GOTO) {                         updateTarget(context, this_idata->operand.i,                                      codeRef->subroutine,                                      target + 1, pc, this_idata->length - 1);                    } else if (codeRef->flags == CRF_JSR_TARGETED_GOTO) {                         updateTarget(context, this_idata->operand.i,                                      codeRef[1].subroutine,                                      target + 1, pc, this_idata->length - 1);                    } else {                         panic("Shouldn't have anything referring to jsr");                    }                    break;                case opc_ret:                    if (codeRef->flags & CRF_RET_SIMPLE_GOTO) {                         int gotoTarget =                             codeRef->subroutine->nextInstruction->offset;                        target[0] = opc_goto;                        target[1] = (gotoTarget - pc) >> 8;                        target[2] = (gotoTarget - pc);                    } else {                         panic("Shouldn't have anything referring to ret");                    }                    break;                default:                    memcpy(target, source, this_idata->length);                    break;                case opc_tableswitch:                 case opc_lookupswitch: {                    int *successors = this_idata->operand.ip;                    int keys = successors[0] - 1; /* don't include default */                    SubrContext *subroutine = codeRef->subroutine;                    int i;                                        long *targetPtr, *sourcePtr;                    target[0] = source[0];                    target[1] = target[2] = target[3] = 0; /* clear alignment */                                        targetPtr = (long *)UCALIGN(target + 1);                    sourcePtr = (long *)UCALIGN(source + 1);                                        /* Update the default target */                    updateTarget(context, successors[1], subroutine,                                  targetPtr, pc, 4);                    if (opcode == opc_tableswitch) {                         targetPtr[1] = sourcePtr[1]; /* low */                        targetPtr[2] = sourcePtr[2]; /* high */                        for (i = 0; i < keys; i++) {                             updateTarget(context, successors[2 + i], subroutine,                                         &targetPtr[3 + i], pc, 4);                        }                    } else {                         targetPtr[1] = sourcePtr[1]; /* pairs */                         for (i = 0; i < keys; i++) {                             targetPtr[2 + (i << 1)] = sourcePtr[2 + (i << 1)];                            updateTarget(context, successors[2 + i], subroutine,                                         &targetPtr[3 + (i << 1)], pc, 4);                        }                    }                    break;                }            }        }    }    mb->code = newCode;    mb->code_length = newCodeLength;}static void fixupExceptionHandlers(JsrContext *context) {     const int catchFrameSize = sizeof(struct CatchFrame);    context_type *vcontext = context->vcontext;    struct methodblock *mb = vcontext->mb;    short *code_data = vcontext->code_data; /* maps offset to inumber */        CodeRef *codeRefEnd = context->codeRefEnd;            /* Structure to hold new catch frames */    struct CatchFrame *catchFrames = malloc(catchFrameSize * MAX_CODE_SIZE);    struct CatchFrame *currentCatchFrame = catchFrames;    CodeRef *hRef, *instRef;    unsigned long i;    /* Look at each exception handler */    for (i = 0; i < mb->exception_table_length; i++) {         struct CatchFrame *this_handler = &mb->exception_table[i];        int start_inumber   = code_data[this_handler->start_pc];        int end_inumber     = code_data[this_handler->end_pc];        int handler_inumber = code_data[this_handler->handler_pc];                    /* First instruction that maps to the specified handler */        for (hRef = context->mapping[handler_inumber]                   ; hRef != NULL; hRef = hRef->next) {            /* Find all instructions that go to this handler. */            bool_t wasMatch = FALSE;            for (instRef = context->codeRef; instRef < codeRefEnd; instRef++) {                if (instRef->flags != CRF_SKIP) {                     bool_t thisMatch = instRef->inumber >= start_inumber                                    && instRef->inumber < end_inumber                                    && subroutineGoto(context,                                                       instRef->subroutine,                                                      hRef->subroutine);                    if (thisMatch && !wasMatch) {                         /* Start a new catch frame */                        memcpy(currentCatchFrame, this_handler, catchFrameSize);                        currentCatchFrame->handler_pc = hRef->offset;                        currentCatchFrame->start_pc = instRef->offset;                        wasMatch = TRUE;                    } else if (wasMatch && !thisMatch) {                         currentCatchFrame->end_pc = instRef->offset;                        currentCatchFrame++;                        wasMatch = FALSE;                    }                }            }            if (wasMatch) {                 /* We end the code still in the catch frame */                currentCatchFrame->end_pc = mb->code_length;                currentCatchFrame++;            }        }    }    /* free(mb->exception_table); */    mb->exception_table_length = currentCatchFrame - catchFrames;    mb->exception_table = realloc(catchFrames,                              (char *)currentCatchFrame - (char *)catchFrames);}static void fixupLineNumberTable(JsrContext *context) {    context_type *vcontext = context->vcontext;    struct methodblock *mb = vcontext->mb;    int tableLength = mb->line_number_table_length;    instruction_data_type *idata = vcontext->instruction_data;    instruction_data_type *last_idata = &idata[vcontext->instruction_count - 1];    int oldCodeLength = last_idata->offset + last_idata->length;    struct lineno *lineTable = malloc(sizeof(struct lineno) * MAX_CODE_SIZE);    struct lineno *currentLineTableEntry = lineTable;    unsigned long *mapTable = calloc(sizeof(short *), oldCodeLength);    CodeRef *codeRefEnd = context->codeRefEnd;    CodeRef *codeRef;    int i, currentLineNumber;    {         unsigned long startPC, endPC, line, pc;        for (i = 0; i < tableLength - 1; i++) {             startPC = mb->line_number_table[i].pc;            endPC   = mb->line_number_table[i + 1].pc;            line    = mb->line_number_table[i].line_number;            for (pc = startPC; pc < endPC; pc++) {                 mapTable[pc] = line;            }        }        startPC = mb->line_number_table[tableLength - 1].pc;        endPC = oldCodeLength;        line = mb->line_number_table[tableLength - 1].line_number;        for (pc = startPC; pc < endPC; pc++) {             mapTable[pc] = line;        }    }    currentLineNumber = -1;    for (codeRef = context->codeRef; codeRef < codeRefEnd; codeRef++) {        if (codeRef->flags != CRF_SKIP) {             instruction_data_type *this_idata = &idata[codeRef->inumber];            int thisLineNumber = mapTable[this_idata->offset];            if (thisLineNumber != currentLineNumber) {                 currentLineTableEntry->line_number = thisLineNumber;                currentLineTableEntry->pc = codeRef->offset;                currentLineTableEntry++;                currentLineNumber = thisLineNumber;            }        }    }        free(mapTable);    mb->line_number_table = realloc(lineTable,                                     (char *)currentLineTableEntry -                                     (char *)lineTable);    mb->line_number_table_length = currentLineTableEntry - lineTable;}static void fixupVariableTable(JsrContext *context) {     context_type *vcontext = context->vcontext;    struct methodblock *mb = context->vcontext->mb;    instruction_data_type *idata = vcontext->instruction_data;    CodeRef *codeRefEnd = context->codeRefEnd;    CodeRef *codeRef;    unsigned long i;    struct localvar *localVars =         malloc(sizeof(struct localvar) * MAX_CODE_SIZE);    struct localvar *currentLocalVar = localVars;    for (i = 0; i < mb->localvar_table_length; i++) {         struct localvar *oldEntry = &mb->localvar_table[i];        int startPC = oldEntry->pc0;        int endPC = startPC + oldEntry->length; /* inclusive! */                    bool_t was_matching = FALSE;        for (codeRef = context->codeRef; codeRef < codeRefEnd; codeRef++) {            if (codeRef->flags != CRF_SKIP) {                 instruction_data_type *this_idata = &idata[codeRef->inumber];                bool_t is_matching = this_idata->offset >= startPC                                   && this_idata->offset <= endPC;                if (!was_matching && is_matching) {                     memcpy(currentLocalVar, oldEntry, sizeof(struct localvar));                    currentLocalVar->pc0 = codeRef->offset;                    was_matching = TRUE;                } else if (was_matching && !is_matching) {                     currentLocalVar->length =                         codeRef[-1].offset - currentLocalVar->pc0;                    currentLocalVar++;                    was_matching = FALSE;                }            }        }        if (was_matching) {             currentLocalVar->length =                 codeRefEnd[-1].offset - currentLocalVar->pc0;            currentLocalVar++;        }    }                    /* free(mb->localvar_table); */    mb->localvar_table_length = currentLocalVar - localVars;    mb->localvar_table = realloc(localVars,                                  (char *)currentLocalVar - (char *)localVars);}static voidupdateTarget(JsrContext *context, int inumber,              SubrContext* subroutine, void* target, int offset, int size){    CodeRef *codeRef;    for (codeRef = context->mapping[inumber];             codeRef != NULL;             codeRef = codeRef->next) {         if (subroutineGoto(context, subroutine, codeRef->subroutine)) {             int value = codeRef->offset - offset;            unsigned char *t = target;            if (size == 2) {                 t[0] = value >> 8;                t[1] = value;            } else if (size == 4) {                 t[0] = value >> 24;                t[1] = value >> 16;                t[2] = value >> 8;                t[3] = value;            } else {                 panic("Bad value passed for size");            }            return;        }    }    panic("Cannot find value for updateTarget");}static bool_t subroutineGoto(JsrContext *context, SubrContext *from, SubrContext *to){     if (to == NULL || to == from) {         return TRUE;    } else if (from == NULL || to->depth >= from->depth) {        return FALSE;    } else {         do { from = from->parent; } while (from->depth > to->depth);        return from == to;    }}static bool_t matchSubroutine(JsrContext *context,                 instruction_data_type *this_idata,                 SubrContext *subroutine){    int depth = subroutine->depth;    int i;        for (i = depth - 1; i >= 0; --i) {         if (this_idata->register_info.masks[i].entry != subroutine->target) {             return FALSE;        }        subroutine = subroutine->parent;    }    return TRUE;}

⌨️ 快捷键说明

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