mirror of https://github.com/lua/lua
new opcode TAILCALL
This commit is contained in:
parent
78edc241e9
commit
0870a2d1d8
12
lopcodes.h
12
lopcodes.h
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
** $Id: lopcodes.h,v 1.29 1999/02/26 15:19:54 roberto Exp roberto $
|
||||
** $Id: lopcodes.h,v 1.30 1999/03/04 21:15:50 roberto Exp roberto $
|
||||
** Opcodes for Lua virtual machine
|
||||
** See Copyright Notice in lua.h
|
||||
*/
|
||||
|
@ -17,8 +17,12 @@
|
|||
typedef enum {
|
||||
/* name parm before after side effect
|
||||
-----------------------------------------------------------------------------*/
|
||||
ENDCODE,/* - - - */
|
||||
RETCODE,/* b - - */
|
||||
ENDCODE,/* - - (return) */
|
||||
RETCODE,/* b - (return) */
|
||||
|
||||
CALL,/* b c v_c...v_1 f r_b...r_1 f(v1,...,v_c) */
|
||||
|
||||
TAILCALL,/* b c v_c...v_1 f (return) f(v1,...,v_c) */
|
||||
|
||||
PUSHNIL,/* b - nil_0...nil_b */
|
||||
POP,/* b a_b...a_1 - */
|
||||
|
@ -101,8 +105,6 @@ IFFUPJMP,/* b x - (x==nil)? PC-=b */
|
|||
CLOSUREW,/* w c v_c...v_1 closure(CNST[w], v_c...v_1) */
|
||||
CLOSURE,/* b c v_c...v_1 closure(CNST[b], v_c...v_1) */
|
||||
|
||||
CALL,/* b c v_c...v_1 f r_b...r_1 f(v1,...,v_c) */
|
||||
|
||||
SETLINEW,/* w - - LINE=w */
|
||||
SETLINE,/* b - - LINE=b */
|
||||
|
||||
|
|
17
lparser.c
17
lparser.c
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
** $Id: lparser.c,v 1.25 1999/02/26 15:48:55 roberto Exp roberto $
|
||||
** $Id: lparser.c,v 1.26 1999/03/04 21:17:26 roberto Exp roberto $
|
||||
** LL(1) Parser and code generator for Lua
|
||||
** See Copyright Notice in lua.h
|
||||
*/
|
||||
|
@ -387,15 +387,13 @@ static void adjuststack (LexState *ls, int n) {
|
|||
|
||||
|
||||
static void close_exp (LexState *ls, int pc, int nresults) {
|
||||
if (pc > 0) { /* expression is an open function call */
|
||||
if (pc > 0) { /* expression is an open function call? */
|
||||
Byte *code = ls->fs->f->code;
|
||||
code[pc-1] = (Byte)nresults; /* set nresults */
|
||||
if (nresults != MULT_RET)
|
||||
deltastack(ls, nresults); /* push results */
|
||||
deltastack(ls, -(code[pc]+1)); /* pop params (at code[pc]) and function */
|
||||
/* push results, pop params (at code[pc]) and function */
|
||||
deltastack(ls, nresults-(code[pc]+1));
|
||||
}
|
||||
#ifdef DEBUG
|
||||
if (nresults != MULT_RET)
|
||||
code_oparg(ls, CHECKSTACK, ls->fs->stacksize, 0);
|
||||
#endif
|
||||
}
|
||||
|
@ -879,7 +877,12 @@ static void ret (LexState *ls) {
|
|||
if (optional(ls, RETURN)) {
|
||||
listdesc e;
|
||||
explist(ls, &e);
|
||||
close_exp(ls, e.pc, MULT_RET);
|
||||
if (e.pc > 0) { /* expression is an open function call? */
|
||||
Byte *code = ls->fs->f->code;
|
||||
code[e.pc-2] = TAILCALL; /* instead of a conventional CALL */
|
||||
code[e.pc-1] = (Byte)ls->fs->nlocalvar;
|
||||
}
|
||||
else
|
||||
code_oparg(ls, RETCODE, ls->fs->nlocalvar, 0);
|
||||
ls->fs->stacksize = ls->fs->nlocalvar; /* removes all temp values */
|
||||
optional(ls, ';');
|
||||
|
|
32
lvm.c
32
lvm.c
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
** $Id: lvm.c,v 1.51 1999/02/24 17:55:51 roberto Exp roberto $
|
||||
** $Id: lvm.c,v 1.52 1999/03/04 21:15:50 roberto Exp roberto $
|
||||
** Lua virtual machine
|
||||
** See Copyright Notice in lua.h
|
||||
*/
|
||||
|
@ -329,13 +329,22 @@ StkId luaV_execute (Closure *cl, TProtoFunc *tf, StkId base) {
|
|||
switchentry:
|
||||
switch ((OpCode)*pc++) {
|
||||
|
||||
case ENDCODE: aux = 1;
|
||||
case ENDCODE:
|
||||
S->top = S->stack + base;
|
||||
/* goes through */
|
||||
goto ret;
|
||||
|
||||
case RETCODE:
|
||||
if (L->callhook)
|
||||
luaD_callHook(base, NULL, 1);
|
||||
return base + (aux ? 0 : *pc);
|
||||
base += *pc++;
|
||||
goto ret;
|
||||
|
||||
case CALL: aux = *pc++;
|
||||
luaD_call((S->top-S->stack)-(*pc++), aux);
|
||||
break;
|
||||
|
||||
case TAILCALL: aux = *pc++;
|
||||
luaD_call((S->top-S->stack)-(*pc++), MULT_RET);
|
||||
base += aux;
|
||||
goto ret;
|
||||
|
||||
case PUSHNIL: aux = *pc++;
|
||||
do {
|
||||
|
@ -619,12 +628,6 @@ StkId luaV_execute (Closure *cl, TProtoFunc *tf, StkId base) {
|
|||
luaC_checkGC();
|
||||
break;
|
||||
|
||||
case CALL: aux = *pc++; {
|
||||
StkId newBase = (S->top-S->stack)-(*pc++);
|
||||
luaD_call(newBase, aux);
|
||||
break;
|
||||
}
|
||||
|
||||
case SETLINEW: aux += highbyte(*pc++);
|
||||
case SETLINE: aux += *pc++;
|
||||
if ((S->stack+base-1)->ttype != LUA_T_LINE) {
|
||||
|
@ -648,6 +651,9 @@ StkId luaV_execute (Closure *cl, TProtoFunc *tf, StkId base) {
|
|||
break;
|
||||
|
||||
}
|
||||
}
|
||||
} ret:
|
||||
if (L->callhook)
|
||||
luaD_callHook(0, NULL, 1);
|
||||
return base;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue