36 #if defined(ENABLE_GC_CACAO)
53 #if defined(ENABLE_RT_TIMING)
71 #define REPLACE_PATCH_DYNAMIC_CALL
83 #define DOLOG(code) do{ if (opt_TraceReplacement > 1) { code; } } while(0)
84 #define DOLOG_SHORT(code) do{ if (opt_TraceReplacement > 0) { code; } } while(0)
87 #define DOLOG_SHORT(code)
93 #define REPLACE_STATISTICS
95 #if defined(REPLACE_STATISTICS)
118 #define REPLACE_COUNT(cnt) (cnt)++
119 #define REPLACE_COUNT_IF(cnt, cond) do{ if(cond) (cnt)++; } while(0)
120 #define REPLACE_COUNT_INC(cnt, inc) ((cnt) += (inc))
122 #define REPLACE_COUNT_DIST(array, val) \
124 int limit = (sizeof(array) / sizeof(int)) - 1; \
125 if ((val) < (limit)) (array)[val]++; \
126 else (array)[limit]++; \
133 #define REPLACE_COUNT(cnt)
134 #define REPLACE_COUNT_IF(cnt, cond)
135 #define REPLACE_COUNT_INC(cnt, inc)
136 #define REPLACE_COUNT_DIST(array, val)
143 #define TOP_IS_NORMAL 0
144 #define TOP_IS_ON_STACK 1
145 #define TOP_IS_IN_ITMP1 2
146 #define TOP_IS_VOID 3
195 rp->method = (iinfo) ? iinfo->
method : jd->
m;
204 rp->parent = (iinfo) ? iinfo->rp : NULL;
209 for (i = 0; i < rp->method->maxlocals; ++
i) {
210 index = javalocals[
i];
232 for (i = 0; i < stackdepth; ++
i) {
233 v =
VAR(stackvars[i]);
235 ra->index = (i < paramcount) ? RPLALLOC_PARAM : RPLALLOC_STACK;
249 rp->regalloccount = ra - rp->regalloc;
284 calleeinfo = iptr->
sx.
s23.s3.inlineinfo;
289 rplpoint::TYPE_INLINE, iptr, pra,
296 ra->index = RPLALLOC_SYNC;
329 #define CLEAR_javalocals(array, method) \
331 for (i=0; i<(method)->maxlocals; ++i) \
332 (array)[i] = jitdata::UNUSED; \
335 #define COPY_OR_CLEAR_javalocals(dest, array, method) \
337 if ((array) != NULL) \
338 MCOPY((dest), (array), s4, (method)->maxlocals); \
340 CLEAR_javalocals((dest), (method)); \
343 #define COUNT_javalocals(array, method, counter) \
345 for (i=0; i<(method)->maxlocals; ++i) \
346 if ((array)[i] != jitdata::UNUSED) \
371 #if defined(REPLACE_PATCH_DYNAMIC_CALL)
386 assert(code->rplpoints == NULL);
387 assert(code->rplpointcount == 0);
388 assert(code->regalloc == NULL);
389 assert(code->regalloccount == 0);
390 assert(code->globalcount == 0);
396 #if defined(REPLACE_PATCH_DYNAMIC_CALL)
432 iend = iptr + bptr->
icount;
436 for (; iptr != iend; ++iptr) {
438 #if defined(ENABLE_GC_CACAO)
440 md = iptr->
sx.
s23.s3.bte->md;
481 iinfo = iptr->
sx.
s23.s3.inlineinfo;
495 assert(iinfo == iptr->
sx.
s23.s3.inlineinfo);
508 assert(iinfo == iptr->
sx.
s23.s3.inlineinfo ||
509 iinfo == iptr->
sx.
s23.s3.inlineinfo->parent);
510 iinfo = iptr->
sx.
s23.s3.inlineinfo;
529 #if defined(REPLACE_PATCH_DYNAMIC_CALL)
530 int test = (needentry && bptr == jd->
basicblocks) ? firstcount : count;
534 if (test > startcount) {
540 alloccount += bptr->indepth;
541 if (bptr->inlineinfo)
542 alloccount -= bptr->inlineinfo->throughcount;
557 rplpoints =
MNEW(rplpoint, count);
558 regalloc =
MNEW(rplalloc, alloccount);
592 rp[-1].flags |= rplpoint::FLAG_COUNTDOWN;
598 iend = iptr + bptr->
icount;
600 for (; iptr != iend; ++iptr) {
602 #if defined(ENABLE_GC_CACAO)
604 md = iptr->
sx.
s23.s3.bte->md;
608 rplpoint::TYPE_CALL, iptr, &ra,
609 javalocals, iptr->
sx.
s23.s2.args,
623 rplpoint::TYPE_CALL, iptr, &ra,
624 javalocals, iptr->
sx.
s23.s2.args,
643 rplpoint::TYPE_RETURN, iptr, &ra,
649 rplpoint::TYPE_RETURN, iptr, &ra,
655 jd, rp++, iptr, &ra, javalocals);
662 assert(iinfo == iptr->
sx.
s23.s3.inlineinfo);
672 rplpoint::TYPE_BODY, iptr, &ra,
674 rp[-1].flags |= rplpoint::FLAG_NOTRAP;
678 assert(iinfo == iptr->
sx.
s23.s3.inlineinfo ||
679 iinfo == iptr->
sx.
s23.s3.inlineinfo->parent);
680 iinfo = iptr->
sx.
s23.s3.inlineinfo;
692 assert((rp - rplpoints) == count);
693 assert((ra - regalloc) == alloccount);
697 code->rplpoints = rplpoints;
698 code->rplpointcount = count;
700 code->regalloccount = alloccount;
701 code->globalcount = 0;
702 code->memuse = rd->
memuse;
727 MFREE(code->rplpoints,rplpoint,code->rplpointcount);
730 MFREE(code->regalloc,rplalloc,code->regalloccount);
732 code->rplpoints = NULL;
733 code->rplpointcount = 0;
734 code->regalloc = NULL;
735 code->regalloccount = 0;
736 code->globalcount = 0;
766 assert(code->savedmcode == NULL);
771 i = code->rplpointcount;
772 rp = code->rplpoints;
774 if (rp->flags & rplpoint::FLAG_NOTRAP)
777 if (mappable && (rp->type == rplpoint::TYPE_RETURN))
786 code->savedmcode = savedmcode;
792 i = code->rplpointcount;
793 rp = code->rplpoints +
i;
795 assert(!(rp->flags & rplpoint::FLAG_ACTIVE));
797 if (rp->flags & rplpoint::FLAG_NOTRAP)
800 if (mappable && (rp->type == rplpoint::TYPE_RETURN))
808 #if defined(ENABLE_JIT)
809 # if defined(ENABLE_DISASSEMBLER)
814 md_patch_replacement_point(rp->pc, savedmcode,
false);
816 # if defined(ENABLE_DISASSEMBLER)
822 rp->flags |= rplpoint::FLAG_ACTIVE;
825 assert(savedmcode == code->savedmcode);
847 if (code->savedmcode == NULL) {
850 i = code->rplpointcount;
851 rp = code->rplpoints;
853 if ((rp->flags & (rplpoint::FLAG_ACTIVE | rplpoint::FLAG_COUNTDOWN))
854 == rplpoint::FLAG_COUNTDOWN)
857 *(
s4*) (rp->pc + 9) = 0;
864 assert(code->savedmcode != NULL);
865 savedmcode = code->savedmcode;
869 i = code->rplpointcount;
870 rp = code->rplpoints;
873 if (!(rp->flags & rplpoint::FLAG_ACTIVE))
881 #if defined(ENABLE_JIT)
882 # if defined(ENABLE_DISASSEMBLER)
887 md_patch_replacement_point(rp->pc, savedmcode,
true);
889 # if defined(ENABLE_DISASSEMBLER)
895 rp->flags &= ~rplpoint::FLAG_ACTIVE;
904 MFREE(code->savedmcode,
u1, count * REPLACEMENT_PATCH_SIZE);
905 code->savedmcode = NULL;
930 replace_val_t *javaval)
934 #ifdef HAS_4BYTE_STACKSLOT
936 javaval->l = *(
u8*)(es->
sp + ra->regoff);
940 javaval->p = *(
ptrint*)(es->
sp + ra->regoff);
941 #ifdef HAS_4BYTE_STACKSLOT
948 javaval->d = es->
fltregs[ra->regoff];
951 javaval->f = javaval->d;
954 #if defined(SUPPORT_COMBINE_INTEGER_REGISTERS)
961 javaval->p = es->
intregs[ra->regoff];
980 replace_val_t *javaval)
984 #ifdef HAS_4BYTE_STACKSLOT
986 *(
u8*)(es->
sp + ra->regoff) = javaval->l;
990 *(
ptrint*)(es->
sp + ra->regoff) = javaval->p;
991 #ifdef HAS_4BYTE_STACKSLOT
999 es->
fltregs[ra->regoff] = (double) javaval->f;
1002 es->
fltregs[ra->regoff] = javaval->d;
1011 es->
intregs[ra->regoff] = javaval->p;
1034 sourceframe_t *frame;
1037 MZERO(frame, sourceframe_t, 1);
1039 frame->down = ss->frames;
1069 rplpoint::TYPE_CALL,
1070 rplpoint::TYPE_CALL,
1071 rplpoint::TYPE_RETURN,
1086 sourceframe_t *frame;
1089 #if defined(__I386__)
1103 if (rp->type == rplpoint::TYPE_EXH) {
1109 #if defined(__I386__)
1116 frame->method = rp->method;
1121 frame->fromcode = code;
1126 frame->javalocalcount = count;
1131 for (i=0; i<count; ++
i) {
1132 #if !defined(NDEBUG)
1133 frame->javalocals[
i].l = (
u8) 0x00dead0000dead00ULL;
1140 #if !defined(NDEBUG)
1149 count = rp->regalloccount;
1152 while (count && (i = ra->index) >= 0) {
1153 assert(i < m->maxlocals);
1154 frame->javalocaltype[
i] = ra->type;
1156 frame->javalocals[
i].i = ra->regoff;
1165 #if defined(REPLACE_PATCH_DYNAMIC_CALL)
1166 if (topframe && !(rp->method->flags &
ACC_STATIC) && rp == code->rplpoints) {
1170 if (frame->javalocaltype[0] ==
TYPE_ADR)
1171 frame->instance = frame->javalocals[0];
1176 md = rp->method->parseddesc;
1191 #if defined(__I386__)
1192 else if (!(rp->method->flags &
ACC_STATIC)) {
1201 frame->javastackdepth = count;
1205 #if !defined(NDEBUG)
1207 for (i=0; i<count; ++
i) {
1208 frame->javastack[
i].l = (
u8) 0x00dead0000dead00ULL;
1220 assert(ra->index == RPLALLOC_STACK);
1222 frame->javastack[
i].p = sp[-1];
1231 assert(ra->index == RPLALLOC_STACK);
1242 assert(ra->index == RPLALLOC_STACK);
1243 frame->javastack[
i].l = 0;
1252 for (; count--; ra++) {
1253 if (ra->index == RPLALLOC_SYNC) {
1254 assert(rp->type == rplpoint::TYPE_INLINE);
1259 sourceframe_t *calleeframe = frame->down;
1260 assert(calleeframe);
1261 assert(calleeframe->syncslotcount == 0);
1262 assert(calleeframe->syncslots == NULL);
1264 calleeframe->syncslotcount = 1;
1269 frame->javastackdepth--;
1273 assert(ra->index == RPLALLOC_STACK || ra->index == RPLALLOC_PARAM);
1277 if (!topframe && ra->index == RPLALLOC_PARAM) {
1278 frame->javastackdepth--;
1282 frame->javastack[
i].i = ra->regoff;
1285 frame->javastacktype[
i] = ra->type;
1320 sourceframe_t *frame;
1333 ss->frames = frame->down;
1343 if (rp->type == rplpoint::TYPE_EXH) {
1350 count = rp->regalloccount;
1352 while (count && (i = ra->index) >= 0) {
1353 assert(i < m->maxlocals);
1354 assert(i < frame->javalocalcount);
1355 assert(ra->type == frame->javalocaltype[i]);
1374 assert(ra->index == RPLALLOC_STACK);
1375 assert(i < frame->javastackdepth);
1376 assert(frame->javastacktype[i] ==
TYPE_ADR);
1377 sp[-1] = frame->javastack[
i].p;
1385 assert(ra->index == RPLALLOC_STACK);
1386 assert(i < frame->javastackdepth);
1387 assert(frame->javastacktype[i] ==
TYPE_ADR);
1396 assert(ra->index == RPLALLOC_STACK);
1397 assert(i < frame->javastackdepth);
1398 assert(frame->javastacktype[i] ==
TYPE_VOID);
1406 for (; count--; ra++) {
1407 if (ra->index == RPLALLOC_SYNC) {
1408 assert(rp->type == rplpoint::TYPE_INLINE);
1413 assert(frame->down);
1414 assert(frame->down->syncslotcount == 1);
1415 assert(frame->down->syncslots != NULL);
1422 assert(ra->index == RPLALLOC_STACK || ra->index == RPLALLOC_PARAM);
1426 if (!topframe && ra->index == RPLALLOC_PARAM) {
1436 assert(i < frame->javastackdepth);
1437 assert(ra->type == frame->javastacktype[i]);
1485 #if STACKFRAME_RA_BETWEEN_FRAMES
1486 es->
sp -= SIZEOF_VOID_P;
1487 *((
void **)es->
sp) = (
void *) ra;
1496 DOLOG(
printf(
"building stackframe of %d words at %p\n",
1509 #if !defined(NDEBUG) && 0
1510 for (i=0; i< (basesp -
sp) && i < 1; ++
i) {
1511 sp[
i] = 0xdeaddeadU;
1515 #if defined(__I386__)
1518 if ((basesp - sp) > 0) {
1525 #if STACKFRAME_RA_TOP_OF_FRAME
1526 # if STACKFRAME_LEAFMETHODS_RA_REGISTER
1532 #if STACKFRAME_RA_LINKAGE_AREA
1533 # if STACKFRAME_LEAFMETHODS_RA_REGISTER
1536 *((uint8_t**) ((intptr_t) basesp +
LA_LR_OFFSET)) = ra;
1546 *((uintptr_t*) basesp) = es->
intregs[reg];
1549 #if !defined(NDEBUG) && 0
1562 *((
double*) basesp) = es->
fltregs[reg];
1565 #if !defined(NDEBUG) && 0
1566 *(
u8*)&(es->
fltregs[reg]) = 0x44dead4444dead44ULL;
1592 sourceframe_t *frame)
1606 assert(frame->syncslotcount == 0);
1607 assert(frame->syncslots == NULL);
1608 count = code_get_sync_slot_count(es->
code);
1609 frame->syncslotcount = count;
1611 for (i=0; i<count; ++
i) {
1612 frame->syncslots[
i].p = *((intptr_t*) (sp + es->
code->memuse + i));
1638 es->
pv = (uint8_t*) pv;
1641 return (code) ? ra : NULL;
1661 #if !defined(NDEBUG)
1666 DOLOG(
printf(
"patch method pointer from: %p to %p\n",
1667 (
void*) *mpp, (
void*)entrypoint); );
1669 #if !defined(NDEBUG)
1675 printf(
"\t with %p ", (
void*) newcode);
1678 assert(oldcode->m == newcode->
m);
1716 assert(oldentrypoint);
1721 for (; mpp != mppend; ++mpp)
1722 if (*mpp == oldentrypoint) {
1791 sourceframe_t *callerframe,
1792 sourceframe_t *calleeframe)
1797 #if !defined(__I386__)
1807 assert(callerframe->down == calleeframe);
1811 calleecode = calleeframe->tocode;
1814 calleem = calleeframe->method;
1815 assert(calleem == calleecode->
m);
1821 #
if !defined(__I386__)
1822 atentry = (calleeframe->down == NULL)
1824 && (calleeframe->fromrp->id == 0);
1829 pv = callerframe->fromcode->entrypoint;
1832 if (patchpos == NULL) {
1837 #if !defined(__I386__)
1845 oldentrypoint = calleeframe->fromcode->entrypoint;
1849 if (!calleeframe->instance.a) {
1857 obj = calleeframe->instance.a;
1869 #if defined(__I386__)
1871 if (*(
u2 *)(patchpos - 1) == 0x0b0f) {
1900 sourceframe_t *callerframe,
1901 sourceframe_t *calleeframe)
1910 assert(!rpcall || callerframe);
1911 assert(!rpcall || rpcall->type == rplpoint::TYPE_CALL);
1912 assert(!rpcall || rpcall == callerframe->torp);
1913 assert(calleeframe);
1914 assert(!callerframe || calleeframe == callerframe->down);
1918 calleecode = calleeframe->tocode;
1924 ra = rpcall->pc + rpcall->callsize;
1934 es->
code = calleecode;
1941 count = code_get_sync_slot_count(calleecode);
1942 assert(count == calleeframe->syncslotcount);
1943 for (i=0; i<count; ++
i) {
1944 *((intptr_t*) (sp + calleecode->memuse + i)) = calleeframe->syncslots[i].p;
1949 if (callerframe && rpcall) {
1950 #if defined(REPLACE_PATCH_ALL)
1951 if (rpcall->type == callerframe->fromrp->type)
1953 if (rpcall == callerframe->fromrp)
1976 sourceframe_t *frame,
1989 DOLOG(
printf(
"searching replacement point for:\n");
1996 rp = code->rplpoints;
1997 i = code->rplpointcount;
1999 if (rp->id == frame->id && rp->method == frame->method
2000 && rp->parent == parent
2009 for (j = rp->regalloccount; j--; ++ra) {
2011 if (ra->index == RPLALLOC_STACK) {
2012 assert(stacki < frame->javastackdepth);
2013 if (frame->javastack[stacki].i != ra->regoff)
2018 assert(ra->index >= 0 && ra->index < frame->javalocalcount);
2019 if (frame->javalocals[ra->index].i != ra->regoff)
2032 #if !defined(NDEBUG)
2033 printf(
"candidate replacement points were:\n");
2034 rp = code->rplpoints;
2035 i = code->rplpointcount;
2041 vm_abort(
"no matching replacement point found");
2068 DOLOG(
printf(
"searching for rp at pc:%p in %p ", (
void*)pc, (
void*)code);
2073 rp = code->rplpoints;
2074 for (i=0; i<code->rplpointcount; ++
i, ++rp) {
2076 if (rp->pc <= pc && rp->pc + rp->callsize >= pc) {
2077 if (desired_flags) {
2078 if (rp->flags & desired_flags) {
2110 sourceframe_t *frame;
2122 frame->nativepc = es->
pc;
2123 frame->nativeframesize = (es->
sp != 0) ? (((uintptr_t) sfi->
sp) - ((uintptr_t) es->
sp)) : 0;
2124 assert(frame->nativeframesize >= 0);
2131 frame->nativesavint[j++] = es->
intregs[
i];
2137 frame->nativesavflt[j++] = es->
fltregs[
i];
2142 #if defined(ENABLE_GC_CACAO)
2146 es->
intregs[
i] = sfi->intregs[j++];
2171 #if STACKFRAME_RA_BETWEEN_FRAMES
2172 es->
sp += SIZEOF_VOID_P;
2175 es->
pc = (uint8_t*) (((uintptr_t) ((sfi->
xpc) ? sfi->
xpc : sfi->
ra)) - 1);
2201 sourceframe_t *frame;
2213 assert(REPLACE_IS_NATIVE_FRAME(frame));
2215 ss->frames = frame->down;
2220 #if STACKFRAME_RA_BETWEEN_FRAMES
2221 es->
sp -= SIZEOF_VOID_P;
2226 assert(es->
sp == frame->sfi->sp);
2230 #if defined(ENABLE_GC_CACAO)
2234 frame->sfi->intregs[j++] = es->
intregs[
i];
2245 es->
intregs[
i] = frame->nativesavint[j++];
2251 es->
fltregs[
i] = frame->nativesavflt[j++];
2256 es->
sp -= frame->nativeframesize;
2260 es->
pc = frame->nativepc;
2286 #if defined(REPLACE_STATISTICS)
2313 if (es->
code == NULL)
2316 goto after_machine_frame;
2322 (ss->frames == NULL) ?
" TOPFRAME" :
"");
2327 #if defined(REPLACE_STATISTICS)
2336 ss->frames->torp = ss->frames->fromrp;
2337 ss->frames->tocode = ss->frames->fromcode;
2349 assert(rp->type == rplpoint::TYPE_INLINE);
2363 #if !defined(ENABLE_GC_CACAO)
2371 after_machine_frame:
2375 vm_abort(
"could not find replacement point while unrolling call");
2380 assert(rp->type == rplpoint::TYPE_CALL);
2412 sourceframe_t *frame;
2416 #if defined(REPLACE_STATISTICS)
2425 for (frame = ss->frames; frame != NULL; frame = frame->down) {
2429 if (REPLACE_IS_NATIVE_FRAME(frame)) {
2436 if (frame->tocode) {
2437 code = frame->tocode;
2442 assert(frame->torp == NULL);
2444 if (parent == NULL) {
2447 #if defined(REPLACE_STATISTICS)
2448 oldcode = frame->method->code;
2452 if (frame->method->hitcountdown < 0
2453 || (frame->down && frame->down->method->hitcountdown < 0))
2470 frame->tocode = code;
2474 if (rp->type == rplpoint::TYPE_CALL) {
2502 #if defined(ENABLE_GC_CACAO)
2503 static void replace_map_source_state_identity(sourcestate_t *ss)
2505 sourceframe_t *frame;
2509 for (frame = ss->frames; frame != NULL; frame = frame->down) {
2513 if (REPLACE_IS_NATIVE_FRAME(frame)) {
2519 if (frame->tocode) {
2520 assert(frame->tocode == frame->fromcode);
2521 assert(frame->torp == frame->fromrp);
2523 assert(frame->tocode == NULL);
2524 assert(frame->torp == NULL);
2525 frame->tocode = frame->fromcode;
2526 frame->torp = frame->fromrp;
2555 sourceframe_t *prevframe;
2562 while (ss->frames) {
2564 if (REPLACE_IS_NATIVE_FRAME(ss->frames)) {
2565 prevframe = ss->frames;
2572 if (parent == NULL) {
2575 DOLOG(
printf(
"pushing activation record for:\n");
2577 else printf(
"\tfirst frame\n"); );
2584 rp = ss->frames->torp;
2587 DOLOG(
printf(
"creating execution state for%s:\n",
2588 (ss->frames->down == NULL) ?
" TOPFRAME" :
"");
2592 es->
code = ss->frames->tocode;
2593 prevframe = ss->frames;
2599 if (rp->type == rplpoint::TYPE_CALL) {
2630 #if defined(ENABLE_THREADS) && defined(ENABLE_GC_CACAO)
2634 origcode = es->
code;
2637 #if defined(ENABLE_TLH)
2663 #if defined(ENABLE_THREADS) && defined(ENABLE_GC_CACAO)
2674 replace_map_source_state_identity(ss);
2696 vm_abort(
"exception during method replacement");
2702 #if !defined(NDEBUG)
2705 if (!opt_TestReplacement) {
2706 sourceframe_t *frame = ss->frames;
2708 frame = frame->down;
2710 if (frame->torp == origrp) {
2712 printf(
"WARNING: identity replacement, turning off rps to avoid infinite loop\n");
2719 #if defined(ENABLE_THREADS) && defined(ENABLE_GC_CACAO)
2727 #if !defined(NDEBUG)
2730 if (opt_TestReplacement)
2774 if ((rp != NULL) && (rp->pc == pc)
2775 && (rp->flags & (rplpoint::FLAG_ACTIVE | rplpoint::FLAG_COUNTDOWN))) {
2789 DOLOG(
printf(
"JUMPING IN!\n"); fflush(stdout); );
2801 #if defined(ENABLE_GC_CACAO)
2825 replace_map_source_state_identity(ss);
2833 #if defined(ENABLE_GC_CACAO)
2856 #if defined(REPLACE_STATISTICS)
2862 for (i=0; i<limit; ++
i)
2864 sum += array[limit];
2865 for (i=0; i<limit; ++
i) {
2867 fprintf(file,
" %3d: %8d (cum %3d%%)\n",
2868 i, array[i], (sum) ? ((100*cum)/sum) : 0);
2870 fprintf(file,
" >=%3d: %8d\n",limit,array[limit]);
2875 #if defined(REPLACE_STATISTICS)
2877 #define REPLACE_PRINT_DIST(name, array) \
2878 printf(" " name " distribution:\n"); \
2879 print_freq(stdout, (array), sizeof(array)/sizeof(int) - 1);
2883 printf(
"replacement statistics:\n");
2913 #if defined(REPLACE_STATISTICS)
2923 for (i=0; i<frame->javalocalcount; ++
i) {
2924 switch (frame->javalocaltype[i]) {
2938 adr = ret = prim = n = 0;
2939 for (i=0; i<frame->javastackdepth; ++
i) {
2940 switch (frame->javastacktype[i]) {
2966 #if !defined(NDEBUG)
2968 #define TYPECHAR(t) (((t) >= 0 && (t) <= TYPE_RET) ? show_jit_type_letters[t] : '?')
2986 printf(
"(rplpoint *)NULL\n");
2990 for (j=0; j<
depth; ++j)
2993 printf(
"rplpoint (id %d) %p pc:%p+%d type:%s",
2994 rp->id, (
void*)rp,rp->pc,rp->callsize,
2995 replace_type_str[rp->type]);
2996 if (rp->flags & rplpoint::FLAG_NOTRAP)
2998 if (rp->flags & rplpoint::FLAG_COUNTDOWN)
3000 if (rp->flags & rplpoint::FLAG_ACTIVE)
3002 printf(
" parent:%p\n", (
void*)rp->parent);
3003 for (j=0; j<
depth; ++j)
3005 printf(
"ra:%d = [", rp->regalloccount);
3007 for (j=0; j<rp->regalloccount; ++j) {
3010 index = rp->regalloc[j].index;
3012 case RPLALLOC_STACK:
printf(
"S");
break;
3013 case RPLALLOC_PARAM:
printf(
"P");
break;
3014 case RPLALLOC_SYNC :
printf(
"Y");
break;
3015 default:
printf(
"%d", index);
3018 if (rp->regalloc[j].type ==
TYPE_RET) {
3019 printf(
"ret(L%03d)", rp->regalloc[j].regoff);
3022 show_allocation(rp->regalloc[j].type, rp->regalloc[j].flags, rp->regalloc[j].regoff);
3027 for (j=0; j<
depth; ++j)
3046 #if !defined(NDEBUG)
3055 printf(
"(codeinfo *)NULL\n");
3059 printf(
"\treplacement points: %d\n",code->rplpointcount);
3061 printf(
"\ttotal allocations : %d\n",code->regalloccount);
3064 printf(
"\tmemuse : %d\n",code->memuse);
3068 for (i=0; i<code->rplpointcount; ++
i) {
3069 rp = code->rplpoints +
i;
3072 parent = rp->parent;
3075 parent = parent->parent;
3083 #if !defined(NDEBUG)
3089 printf(
"%016llx",(
unsigned long long) value.l);
3092 printf(
" <INVALID TYPE:%d>", type);
3096 if (type ==
TYPE_ADR && value.a != NULL) {
3109 printf(
" %ld", (
long) value.i);
3112 printf(
" %lld", (
long long) value.l);
3124 #if !defined(NDEBUG)
3130 if (REPLACE_IS_NATIVE_FRAME(frame)) {
3133 printf(
"\tnativepc: %p\n", frame->nativepc);
3134 printf(
"\tframesize: %d\n", frame->nativeframesize);
3145 printf(
"\tF%02d = %f\n", i, frame->nativesavflt[j++]);
3154 printf(
"\tid: %d\n", frame->id);
3155 printf(
"\ttype: %s\n", replace_type_str[frame->type]);
3158 if (frame->instance.a) {
3164 if (frame->javalocalcount) {
3165 printf(
"\tlocals (%d):\n",frame->javalocalcount);
3166 for (i=0; i<frame->javalocalcount; ++
i) {
3167 t = frame->javalocaltype[
i];
3169 printf(
"\tlocal[ %2d] = void\n",i);
3180 if (frame->javastackdepth) {
3181 printf(
"\tstack (depth %d):\n",frame->javastackdepth);
3182 for (i=0; i<frame->javastackdepth; ++
i) {
3183 t = frame->javastacktype[
i];
3185 printf(
"\tstack[%2d] = void", i);
3188 printf(
"\tstack[%2d] = ",i);
3196 if (frame->syncslotcount) {
3197 printf(
"\tsynchronization slots (%d):\n",frame->syncslotcount);
3198 for (i=0; i<frame->syncslotcount; ++
i) {
3199 printf(
"\tslot[%2d] = %016llx\n",i,(
unsigned long long) frame->syncslots[i].p);
3204 if (frame->fromcode) {
3205 printf(
"\tfrom %p ", (
void*)frame->fromcode);
3208 if (frame->tocode) {
3209 printf(
"\tto %p ", (
void*)frame->tocode);
3213 if (frame->fromrp) {
3214 printf(
"\tfrom replacement point:\n");
3218 printf(
"\tto replacement point:\n");
3236 #if !defined(NDEBUG)
3240 sourceframe_t *frame;
3243 printf(
"(sourcestate_t *)NULL\n");
3247 printf(
"sourcestate_t:\n");
3249 for (i=0, frame = ss->frames; frame != NULL; frame = frame->down, ++i) {
3250 printf(
" frame %d:\n", i);
3266 #if !defined(NDEBUG)
3269 sourceframe_t *frame;
3271 for (frame = ss->frames; frame != NULL; frame = frame->down) {
3274 if (REPLACE_IS_NATIVE_FRAME(frame)) {
3275 printf(
"NATIVE (pc %p size %d) ",
3276 (
void*)frame->nativepc, frame->nativeframesize);
3282 printf(
"%c", (frame->torp == frame->fromrp) ?
'=' :
'+');
3285 printf(
"%s", replace_type_str[frame->fromrp->type]);
3287 if (frame->torp && frame->torp->type != frame->fromrp->type)
3288 printf(
"->%s", replace_type_str[frame->torp->type]);
3290 if (frame->tocode != frame->fromcode)
3292 (
void*) frame->fromcode, (
void*) frame->tocode,
3295 printf(
" (%p/%d) ", (
void*) frame->fromcode, frame->fromrp->id);
3302 #if !defined(NDEBUG)
3305 printf(
"prev=%p pv=%p sp=%p ra=%p xpc=%p method=",
3306 (
void*)sfi->
prev, (
void*)sfi->
pv, (
void*)sfi->
sp,
3307 (
void*)sfi->
ra, (
void*)sfi->
xpc);
methodptr * interfacetable[1]
static void replace_push_native_frame(executionstate_t *es, sourcestate_t *ss)
#define REPLACE_COUNT_IF(cnt, cond)
codeinfo * jit_get_current_code(methodinfo *m)
void replace_replacement_point_println(rplpoint *rp, int depth)
void replace_show_replacement_points(codeinfo *code)
void replace_free_replacement_points(codeinfo *code)
static int stat_dist_locals_prim[10]
void method_print(methodinfo *m)
void executionstate_pop_stackframe(executionstate_t *es)
Restore callee-saved registers (including the RA register), set the stack pointer to the next stackfr...
static struct stackframeinfo_t * threads_get_current_stackframeinfo(void)
u1 * disassinstr(u1 *code)
methodinfo * code_get_methodinfo_for_pv(void *pv)
static int stat_dist_frames[20]
void replace_activate_replacement_points(codeinfo *code, bool mappable)
Utf8String to_utf8() const
static int stat_dist_stack_prim[10]
#define SUPPORT_COMBINE_INTEGER_REGISTERS
static int stat_dist_locals[20]
sourcestate_t * replace_recover_source_state(rplpoint *rp, stackframeinfo_t *sfi, executionstate_t *es)
static sourceframe_t * replace_new_sourceframe(sourcestate_t *ss)
void utf_display_printable_ascii_classname(Utf8String u)
static int stat_dist_method_rplpoints[20]
insinfo_inline * inlineinfo
void replace_deactivate_replacement_points(codeinfo *code)
static int stat_staticpatch
static s4 replace_normalize_type_map[]
#define REPLACE_COUNT_DIST(array, val)
static void replace_pop_native_frame(executionstate_t *es, sourcestate_t *ss, stackframeinfo_t *sfi)
bool replace_create_replacement_points(jitdata *jd)
static void replace_write_executionstate(rplpoint *rp, executionstate_t *es, sourcestate_t *ss, bool topframe)
void replace_patch_future_calls(u1 *ra, sourceframe_t *callerframe, sourceframe_t *calleeframe)
static int stat_replacements
void replace_patch_callback(classinfo *c, struct replace_patch_data_t *pd)
static int stat_unroll_inline
void replace_sourcestate_println_short(sourcestate_t *ss)
#define COUNT_javalocals(array, method, counter)
static void replace_build_execution_state(sourcestate_t *ss, executionstate_t *es)
#define BBFLAG_REPLACEMENT
#define REPLACE_COUNT(cnt)
s4 * interfacevftbllength
void(* classcache_foreach_functionptr_t)(classinfo *, void *)
#define JITDATA_HAS_FLAG_COUNTDOWN(jd)
static int stat_recompile
void replace_sourcestate_println(sourcestate_t *ss)
rplpoint * replace_find_replacement_point(codeinfo *code, sourceframe_t *frame, rplpoint *parent)
void jit_request_optimization(methodinfo *m)
static int code_is_leafmethod(codeinfo *code)
void replace_patch_class_hierarchy(methodinfo *m, u1 *oldentrypoint, u1 *entrypoint)
static void replace_read_value(executionstate_t *es, rplalloc *ra, replace_val_t *javaval)
#define MZERO(ptr, type, num)
void vm_abort(const char *text,...)
#define IS_2_WORD_TYPE(a)
static void replace_write_value(executionstate_t *es, rplalloc *ra, replace_val_t *javaval)
static void replace_read_executionstate(rplpoint *rp, executionstate_t *es, sourcestate_t *ss, bool topframe)
jlong jlong jlong jlong jint depth
codeinfo * code_find_codeinfo_for_pc(void *pc)
void executionstate_println(executionstate_t *es)
#define REPLACE_COUNT_INC(cnt, inc)
static void print_freq(FILE *file, int *array, int limit)
static int stat_dist_locals_ret[10]
void replace_source_frame_println(sourceframe_t *frame)
void method_println(methodinfo *m)
void replace_patch_class(vftbl_t *vftbl, methodinfo *m, u1 *oldentrypoint, u1 *entrypoint)
void class_println(classinfo *c)
static codeinfo * code_get_codeinfo_for_pv(void *pv)
const char * show_jit_type_names[]
#define IS_FLT_DBL_TYPE(a)
Type
Types used internally by JITTED code.
static int stat_regallocs
#define RETADDR_FROM_JAVALOCAL(jl)
static void replace_create_replacement_point(jitdata *jd, insinfo_inline *iinfo, rplpoint *rp, rplpoint::Type type, instruction *iptr, rplalloc **pra, s4 *javalocals, s4 *stackvars, s4 stackdepth, s4 paramcount)
#define SIZE_OF_STACKSLOT
int32_t * javalocals_start
void threads_suspend_ack()
static void * md_codegen_get_pv_from_pc(void *ra)
void md_push_stackframe(executionstate_t *es, codeinfo *calleecode, u1 *ra)
union instruction::@12 sx
static void java_value_print(s4 type, replace_val_t value)
#define STACK_SLOTS_PER_FLOAT
void stack_javalocals_store(instruction *iptr, s4 *javalocals)
u1 * replace_pop_activation_record(executionstate_t *es, sourceframe_t *frame)
const char * abi_registers_integer_name[]
#define INSTRUCTION_GET_METHODDESC(iptr, md)
This file contains the real-time timing utilities.
void utf_display_printable_ascii(Utf8String u)
void replace_push_activation_record(executionstate_t *es, rplpoint *rpcall, sourceframe_t *callerframe, sourceframe_t *calleeframe)
static int stat_dist_stack_ret[10]
static insinfo_inline * replace_create_inline_start_replacement_point(jitdata *jd, rplpoint *rp, instruction *iptr, rplalloc **pra, s4 *javalocals)
void * md_jit_method_patch_address(void *pv, void *ra, void *mptr)
bool regalloc(jitdata *jd)
#define REPLACEMENT_PATCH_SIZE
classinfo * class_java_lang_String
static int stat_unroll_call
void replace_print_statistics(void)
void show_allocation(s4 type, s4 flags, s4 regoff)
static int stat_dist_locals_void[10]
bool replace_handler(u1 *pc, executionstate_t *es)
rplpoint * replace_find_replacement_point_for_pc(codeinfo *code, u1 *pc, unsigned desired_flags)
static void replace_stackframeinfo_println(stackframeinfo_t *sfi)
static void * allocate(size_t size)
static void replace_patch_method_pointer(methodptr *mpp, methodptr entrypoint, const char *kind)
void classcache_foreach_loaded_class(classcache_foreach_functionptr_t func, void *data)
struct instruction::@12::@13 s23
uintptr_t intregs[INT_REG_CNT]
#define REPLACE_PRINT_DIST(name, array)
#define GC_EXECUTIONSTATE
#define DOLOG_SHORT(code)
static int stat_dist_stack_adr[10]
#define MCOPY(dest, src, type, num)
static void replace_me(rplpoint *rp, executionstate_t *es)
#define COPY_OR_CLEAR_javalocals(dest, array, method)
double fltregs[FLT_REG_CNT]
static int stat_dist_stack[10]
static int stat_dist_locals_adr[10]
#define MFREE(ptr, type, num)
static void replace_statistics_source_frame(sourceframe_t *frame)
static bool replace_map_source_state(sourcestate_t *ss)
static int32_t md_stacktrace_get_framesize(codeinfo *code)
Returns the size (in bytes) of the current stackframe, specified by the passed codeinfo structure...
#define asm_abstractmethoderror
static const char * replace_type_str[]
#define INS_FLAG_ID_SHIFT