Browse Source

Improvements in the handling of signals

Added 'volatile' to 'l_signalT' variables plus some minor changes.
pull/24/head
Roberto Ierusalimschy 5 years ago
parent
commit
17dbaa8639
  1. 20
      ldebug.c
  2. 10
      ldo.c
  3. 9
      lstate.c
  4. 4
      lstate.h
  5. 3
      lua.c

20
ldebug.c

@ -107,13 +107,15 @@ static int getcurrentline (CallInfo *ci) {
/* /*
** This function can be called asynchronously (e.g. during a signal), ** Set 'trap' for all active Lua frames.
** under "reasonable" assumptions. A new 'ci' is completely linked ** This function can be called during a signal, under "reasonable"
** in the list before it becomes part of the "active" list, and ** assumptions. A new 'ci' is completely linked in the list before it
** we assume that pointers are atomic (see comment in next function). ** becomes part of the "active" list, and we assume that pointers are
** (If we traverse one more item, there is no problem. If we traverse ** atomic; see comment in next function.
** one less item, the worst that can happen is that the signal will ** (A compiler doing interprocedural optimizations could, theoretically,
** not interrupt the script.) ** reorder memory writes in such a way that the list could be
** temporarily broken while inserting a new element. We simply assume it
** has no good reasons to do that.)
*/ */
static void settraps (CallInfo *ci) { static void settraps (CallInfo *ci) {
for (; ci != NULL; ci = ci->previous) for (; ci != NULL; ci = ci->previous)
@ -123,8 +125,8 @@ static void settraps (CallInfo *ci) {
/* /*
** This function can be called asynchronously (e.g. during a signal), ** This function can be called during a signal, under "reasonable"
** under "reasonable" assumptions. ** assumptions.
** Fields 'oldpc', 'basehookcount', and 'hookcount' (set by ** Fields 'oldpc', 'basehookcount', and 'hookcount' (set by
** 'resethookcount') are for debug only, and it is no problem if they ** 'resethookcount') are for debug only, and it is no problem if they
** get arbitrary values (causes at most one wrong hook call). 'hookmask' ** get arbitrary values (causes at most one wrong hook call). 'hookmask'

10
ldo.c

@ -422,7 +422,7 @@ void luaD_poscall (lua_State *L, CallInfo *ci, int nres) {
#define next_ci(L) (L->ci = (L->ci->next ? L->ci->next : luaE_extendCI(L))) #define next_ci(L) (L->ci->next ? L->ci->next : luaE_extendCI(L))
/* /*
@ -466,13 +466,13 @@ void luaD_call (lua_State *L, StkId func, int nresults) {
f = fvalue(s2v(func)); f = fvalue(s2v(func));
Cfunc: { Cfunc: {
int n; /* number of returns */ int n; /* number of returns */
CallInfo *ci; CallInfo *ci = next_ci(L);
checkstackp(L, LUA_MINSTACK, func); /* ensure minimum stack size */ checkstackp(L, LUA_MINSTACK, func); /* ensure minimum stack size */
ci = next_ci(L);
ci->nresults = nresults; ci->nresults = nresults;
ci->callstatus = CIST_C; ci->callstatus = CIST_C;
ci->top = L->top + LUA_MINSTACK; ci->top = L->top + LUA_MINSTACK;
ci->func = func; ci->func = func;
L->ci = ci;
lua_assert(ci->top <= L->stack_last); lua_assert(ci->top <= L->stack_last);
if (L->hookmask & LUA_MASKCALL) { if (L->hookmask & LUA_MASKCALL) {
int narg = cast_int(L->top - func) - 1; int narg = cast_int(L->top - func) - 1;
@ -486,18 +486,18 @@ void luaD_call (lua_State *L, StkId func, int nresults) {
break; break;
} }
case LUA_VLCL: { /* Lua function */ case LUA_VLCL: { /* Lua function */
CallInfo *ci; CallInfo *ci = next_ci(L);
Proto *p = clLvalue(s2v(func))->p; Proto *p = clLvalue(s2v(func))->p;
int narg = cast_int(L->top - func) - 1; /* number of real arguments */ int narg = cast_int(L->top - func) - 1; /* number of real arguments */
int nfixparams = p->numparams; int nfixparams = p->numparams;
int fsize = p->maxstacksize; /* frame size */ int fsize = p->maxstacksize; /* frame size */
checkstackp(L, fsize, func); checkstackp(L, fsize, func);
ci = next_ci(L);
ci->nresults = nresults; ci->nresults = nresults;
ci->u.l.savedpc = p->code; /* starting point */ ci->u.l.savedpc = p->code; /* starting point */
ci->callstatus = 0; ci->callstatus = 0;
ci->top = func + 1 + fsize; ci->top = func + 1 + fsize;
ci->func = func; ci->func = func;
L->ci = ci;
for (; narg < nfixparams; narg++) for (; narg < nfixparams; narg++)
setnilvalue(s2v(L->top++)); /* complete missing arguments */ setnilvalue(s2v(L->top++)); /* complete missing arguments */
lua_assert(ci->top <= L->stack_last); lua_assert(ci->top <= L->stack_last);

9
lstate.c

@ -190,14 +190,15 @@ void luaE_freeCI (lua_State *L) {
*/ */
void luaE_shrinkCI (lua_State *L) { void luaE_shrinkCI (lua_State *L) {
CallInfo *ci = L->ci; CallInfo *ci = L->ci;
CallInfo *next;
CallInfo *next2; /* next's next */ CallInfo *next2; /* next's next */
L->nCcalls += L->nci; /* add removed elements back to 'nCcalls' */ L->nCcalls += L->nci; /* add removed elements back to 'nCcalls' */
/* while there are two nexts */ /* while there are two nexts */
while (ci->next != NULL && (next2 = ci->next->next) != NULL) { while ((next = ci->next) != NULL && (next2 = next->next) != NULL) {
luaM_free(L, ci->next); /* free next */ ci->next = next2; /* remove next from the list */
L->nci--;
ci->next = next2; /* remove 'next' from the list */
next2->previous = ci; next2->previous = ci;
luaM_free(L, next); /* free next */
L->nci--;
ci = next2; /* keep next's next */ ci = next2; /* keep next's next */
} }
L->nCcalls -= L->nci; /* adjust result */ L->nCcalls -= L->nci; /* adjust result */

4
lstate.h

@ -173,7 +173,7 @@ typedef struct CallInfo {
union { union {
struct { /* only for Lua functions */ struct { /* only for Lua functions */
const Instruction *savedpc; const Instruction *savedpc;
l_signalT trap; volatile l_signalT trap;
int nextraargs; /* # of extra arguments in vararg functions */ int nextraargs; /* # of extra arguments in vararg functions */
} l; } l;
struct { /* only for C functions */ struct { /* only for C functions */
@ -300,7 +300,7 @@ struct lua_State {
int stacksize; int stacksize;
int basehookcount; int basehookcount;
int hookcount; int hookcount;
l_signalT hookmask; volatile l_signalT hookmask;
}; };

3
lua.c

@ -54,8 +54,9 @@ static void lstop (lua_State *L, lua_Debug *ar) {
** interpreter. ** interpreter.
*/ */
static void laction (int i) { static void laction (int i) {
int flag = LUA_MASKCALL | LUA_MASKRET | LUA_MASKLINE | LUA_MASKCOUNT;
signal(i, SIG_DFL); /* if another SIGINT happens, terminate process */ signal(i, SIG_DFL); /* if another SIGINT happens, terminate process */
lua_sethook(globalL, lstop, LUA_MASKCALL | LUA_MASKRET | LUA_MASKCOUNT, 1); lua_sethook(globalL, lstop, flag, 1);
} }

Loading…
Cancel
Save