diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/lj_dispatch.c | 5 | ||||
| -rw-r--r-- | src/lj_snap.c | 6 | ||||
| -rw-r--r-- | src/lj_snap.h | 2 | ||||
| -rw-r--r-- | src/lj_trace.c | 55 | ||||
| -rw-r--r-- | src/lj_trace.h | 2 |
5 files changed, 33 insertions, 37 deletions
diff --git a/src/lj_dispatch.c b/src/lj_dispatch.c index b83912c5..f1579c8d 100644 --- a/src/lj_dispatch.c +++ b/src/lj_dispatch.c | |||
| @@ -359,10 +359,7 @@ void LJ_FASTCALL lj_dispatch_ins(lua_State *L, const BCIns *pc) | |||
| 359 | jit_State *J = G2J(g); | 359 | jit_State *J = G2J(g); |
| 360 | if (J->state != LJ_TRACE_IDLE) { | 360 | if (J->state != LJ_TRACE_IDLE) { |
| 361 | J->L = L; | 361 | J->L = L; |
| 362 | J->pc = pc-1; | 362 | lj_trace_ins(J, pc-1); /* The interpreter bytecode PC is offset by 1. */ |
| 363 | J->fn = fn; | ||
| 364 | J->pt = pt; | ||
| 365 | lj_trace_ins(J); | ||
| 366 | } | 363 | } |
| 367 | } | 364 | } |
| 368 | #endif | 365 | #endif |
diff --git a/src/lj_snap.c b/src/lj_snap.c index 547b2089..04b9a7f6 100644 --- a/src/lj_snap.c +++ b/src/lj_snap.c | |||
| @@ -179,7 +179,7 @@ void lj_snap_regspmap(uint16_t *rsmap, Trace *T, SnapNo snapno) | |||
| 179 | } | 179 | } |
| 180 | 180 | ||
| 181 | /* Restore interpreter state from exit state with the help of a snapshot. */ | 181 | /* Restore interpreter state from exit state with the help of a snapshot. */ |
| 182 | void lj_snap_restore(jit_State *J, void *exptr) | 182 | const BCIns *lj_snap_restore(jit_State *J, void *exptr) |
| 183 | { | 183 | { |
| 184 | ExitState *ex = (ExitState *)exptr; | 184 | ExitState *ex = (ExitState *)exptr; |
| 185 | SnapNo snapno = J->exitno; /* For now, snapno == exitno. */ | 185 | SnapNo snapno = J->exitno; /* For now, snapno == exitno. */ |
| @@ -187,7 +187,7 @@ void lj_snap_restore(jit_State *J, void *exptr) | |||
| 187 | SnapShot *snap = &T->snap[snapno]; | 187 | SnapShot *snap = &T->snap[snapno]; |
| 188 | MSize n, nent = snap->nent; | 188 | MSize n, nent = snap->nent; |
| 189 | SnapEntry *map = &T->snapmap[snap->mapofs]; | 189 | SnapEntry *map = &T->snapmap[snap->mapofs]; |
| 190 | SnapEntry *flinks = map + nent; | 190 | SnapEntry *flinks = map + nent + 1; |
| 191 | int32_t ftsz0; | 191 | int32_t ftsz0; |
| 192 | BCReg nslots = snap->nslots; | 192 | BCReg nslots = snap->nslots; |
| 193 | TValue *frame; | 193 | TValue *frame; |
| @@ -201,7 +201,6 @@ void lj_snap_restore(jit_State *J, void *exptr) | |||
| 201 | } | 201 | } |
| 202 | 202 | ||
| 203 | /* Fill stack slots with data from the registers and spill slots. */ | 203 | /* Fill stack slots with data from the registers and spill slots. */ |
| 204 | J->pc = snap_pc(*flinks++); | ||
| 205 | frame = L->base-1; | 204 | frame = L->base-1; |
| 206 | ftsz0 = frame_ftsz(frame); /* Preserve link to previous frame in slot #0. */ | 205 | ftsz0 = frame_ftsz(frame); /* Preserve link to previous frame in slot #0. */ |
| 207 | for (n = 0; n < nent; n++) { | 206 | for (n = 0; n < nent; n++) { |
| @@ -266,6 +265,7 @@ void lj_snap_restore(jit_State *J, void *exptr) | |||
| 266 | } | 265 | } |
| 267 | L->top = curr_topL(L); | 266 | L->top = curr_topL(L); |
| 268 | lua_assert(map + nent + 1 + snap->depth == flinks); | 267 | lua_assert(map + nent + 1 + snap->depth == flinks); |
| 268 | return snap_pc(map[nent]); | ||
| 269 | } | 269 | } |
| 270 | 270 | ||
| 271 | #undef IR | 271 | #undef IR |
diff --git a/src/lj_snap.h b/src/lj_snap.h index ed7d98a1..80be33b7 100644 --- a/src/lj_snap.h +++ b/src/lj_snap.h | |||
| @@ -13,7 +13,7 @@ | |||
| 13 | LJ_FUNC void lj_snap_add(jit_State *J); | 13 | LJ_FUNC void lj_snap_add(jit_State *J); |
| 14 | LJ_FUNC void lj_snap_shrink(jit_State *J); | 14 | LJ_FUNC void lj_snap_shrink(jit_State *J); |
| 15 | LJ_FUNC void lj_snap_regspmap(uint16_t *rsmap, Trace *T, SnapNo snapno); | 15 | LJ_FUNC void lj_snap_regspmap(uint16_t *rsmap, Trace *T, SnapNo snapno); |
| 16 | LJ_FUNC void lj_snap_restore(jit_State *J, void *exptr); | 16 | LJ_FUNC const BCIns *lj_snap_restore(jit_State *J, void *exptr); |
| 17 | LJ_FUNC void lj_snap_grow_buf_(jit_State *J, MSize need); | 17 | LJ_FUNC void lj_snap_grow_buf_(jit_State *J, MSize need); |
| 18 | LJ_FUNC void lj_snap_grow_map_(jit_State *J, MSize need); | 18 | LJ_FUNC void lj_snap_grow_map_(jit_State *J, MSize need); |
| 19 | 19 | ||
diff --git a/src/lj_trace.c b/src/lj_trace.c index 0a973d51..b5946346 100644 --- a/src/lj_trace.c +++ b/src/lj_trace.c | |||
| @@ -532,46 +532,52 @@ static TValue *trace_state(lua_State *L, lua_CFunction dummy, void *ud) | |||
| 532 | /* -- Event handling ------------------------------------------------------ */ | 532 | /* -- Event handling ------------------------------------------------------ */ |
| 533 | 533 | ||
| 534 | /* A bytecode instruction is about to be executed. Record it. */ | 534 | /* A bytecode instruction is about to be executed. Record it. */ |
| 535 | void lj_trace_ins(jit_State *J) | 535 | void lj_trace_ins(jit_State *J, const BCIns *pc) |
| 536 | { | 536 | { |
| 537 | while (lj_vm_cpcall(J->L, NULL, (void *)J, trace_state) != 0) | 537 | /* Note: J->L must already be set. pc is the true bytecode PC here. */ |
| 538 | J->state = LJ_TRACE_ERR; | 538 | J->pc = pc; |
| 539 | } | ||
| 540 | |||
| 541 | /* Start recording a new trace. */ | ||
| 542 | static void trace_new(jit_State *J) | ||
| 543 | { | ||
| 544 | lua_assert(J->state == LJ_TRACE_IDLE); | ||
| 545 | J->state = LJ_TRACE_START; | ||
| 546 | J->fn = curr_func(J->L); | 539 | J->fn = curr_func(J->L); |
| 547 | J->pt = funcproto(J->fn); | 540 | J->pt = funcproto(J->fn); |
| 548 | lj_trace_ins(J); | 541 | while (lj_vm_cpcall(J->L, NULL, (void *)J, trace_state) != 0) |
| 542 | J->state = LJ_TRACE_ERR; | ||
| 549 | } | 543 | } |
| 550 | 544 | ||
| 551 | /* A hotcount triggered. Start recording a root trace. */ | 545 | /* A hotcount triggered. Start recording a root trace. */ |
| 552 | void LJ_FASTCALL lj_trace_hot(jit_State *J, const BCIns *pc) | 546 | void LJ_FASTCALL lj_trace_hot(jit_State *J, const BCIns *pc) |
| 553 | { | 547 | { |
| 548 | /* Note: pc is the interpreter bytecode PC here. It's offset by 1. */ | ||
| 554 | hotcount_set(J2GG(J), pc, J->param[JIT_P_hotloop]+1); /* Reset hotcount. */ | 549 | hotcount_set(J2GG(J), pc, J->param[JIT_P_hotloop]+1); /* Reset hotcount. */ |
| 555 | /* Only start a new trace if not recording or inside __gc call or vmevent. */ | 550 | /* Only start a new trace if not recording or inside __gc call or vmevent. */ |
| 556 | if (J->state == LJ_TRACE_IDLE && | 551 | if (J->state == LJ_TRACE_IDLE && |
| 557 | !(J2G(J)->hookmask & (HOOK_GC|HOOK_VMEVENT))) { | 552 | !(J2G(J)->hookmask & (HOOK_GC|HOOK_VMEVENT))) { |
| 558 | J->parent = 0; /* Root trace. */ | 553 | J->parent = 0; /* Root trace. */ |
| 559 | J->exitno = 0; | 554 | J->exitno = 0; |
| 560 | J->pc = pc-1; /* The interpreter bytecode PC is offset by 1. */ | 555 | J->state = LJ_TRACE_START; |
| 561 | trace_new(J); | 556 | lj_trace_ins(J, pc-1); |
| 562 | } | 557 | } |
| 563 | } | 558 | } |
| 564 | 559 | ||
| 565 | /* A trace exited. Restore interpreter state and check for hot exits. */ | 560 | /* Check for a hot side exit. If yes, start recording a side trace. */ |
| 561 | static void trace_hotside(jit_State *J, const BCIns *pc) | ||
| 562 | { | ||
| 563 | SnapShot *snap = &J->trace[J->parent]->snap[J->exitno]; | ||
| 564 | if (!(J2G(J)->hookmask & (HOOK_GC|HOOK_VMEVENT)) && | ||
| 565 | snap->count != SNAPCOUNT_DONE && | ||
| 566 | ++snap->count >= J->param[JIT_P_hotexit]) { | ||
| 567 | lua_assert(J->state == LJ_TRACE_IDLE); | ||
| 568 | /* J->parent is non-zero for a side trace. */ | ||
| 569 | J->state = LJ_TRACE_START; | ||
| 570 | lj_trace_ins(J, pc); | ||
| 571 | } | ||
| 572 | } | ||
| 573 | |||
| 574 | /* A trace exited. Restore interpreter state. */ | ||
| 566 | void * LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr) | 575 | void * LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr) |
| 567 | { | 576 | { |
| 577 | const BCIns *pc = lj_snap_restore(J, exptr); | ||
| 568 | lua_State *L = J->L; | 578 | lua_State *L = J->L; |
| 569 | void *cf; | 579 | void *cf = cframe_raw(L->cframe); |
| 570 | 580 | setcframe_pc(cf, pc); /* Restart interpreter at this PC. */ | |
| 571 | /* Restore interpreter state. */ | ||
| 572 | lj_snap_restore(J, exptr); | ||
| 573 | cf = cframe_raw(L->cframe); | ||
| 574 | setcframe_pc(cf, J->pc); | ||
| 575 | 581 | ||
| 576 | lj_vmevent_send(L, TEXIT, | 582 | lj_vmevent_send(L, TEXIT, |
| 577 | ExitState *ex = (ExitState *)exptr; | 583 | ExitState *ex = (ExitState *)exptr; |
| @@ -591,14 +597,7 @@ void * LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr) | |||
| 591 | } | 597 | } |
| 592 | ); | 598 | ); |
| 593 | 599 | ||
| 594 | { /* Check for a hot exit. */ | 600 | trace_hotside(J, pc); |
| 595 | SnapShot *snap = &J->trace[J->parent]->snap[J->exitno]; | ||
| 596 | if (!(J2G(J)->hookmask & (HOOK_GC|HOOK_VMEVENT)) && | ||
| 597 | snap->count != SNAPCOUNT_DONE && | ||
| 598 | ++snap->count >= J->param[JIT_P_hotexit]) | ||
| 599 | trace_new(J); /* Start recording a side trace. */ | ||
| 600 | } | ||
| 601 | |||
| 602 | return cf; /* Return the interpreter C frame. */ | 601 | return cf; /* Return the interpreter C frame. */ |
| 603 | } | 602 | } |
| 604 | 603 | ||
diff --git a/src/lj_trace.h b/src/lj_trace.h index 0d4e30e0..a8e45974 100644 --- a/src/lj_trace.h +++ b/src/lj_trace.h | |||
| @@ -31,7 +31,7 @@ LJ_FUNC int lj_trace_flushall(lua_State *L); | |||
| 31 | LJ_FUNC void lj_trace_freestate(global_State *g); | 31 | LJ_FUNC void lj_trace_freestate(global_State *g); |
| 32 | 32 | ||
| 33 | /* Event handling. */ | 33 | /* Event handling. */ |
| 34 | LJ_FUNC void lj_trace_ins(jit_State *J); | 34 | LJ_FUNC void lj_trace_ins(jit_State *J, const BCIns *pc); |
| 35 | LJ_FUNCA void LJ_FASTCALL lj_trace_hot(jit_State *J, const BCIns *pc); | 35 | LJ_FUNCA void LJ_FASTCALL lj_trace_hot(jit_State *J, const BCIns *pc); |
| 36 | LJ_FUNCA void * LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr); | 36 | LJ_FUNCA void * LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr); |
| 37 | 37 | ||
