mirror of
https://github.com/lua/lua.git
synced 2026-09-14 06:18:10 +00:00
New conceptual model for vararg
Conceptually, all functions get their vararg arguments in a vararg table. The storing of vararg arguments in the stack is always treated as an optimization.
This commit is contained in:
24
lparser.c
24
lparser.c
@@ -1056,9 +1056,8 @@ static void constructor (LexState *ls, expdesc *t) {
|
||||
/* }====================================================================== */
|
||||
|
||||
|
||||
static void setvararg (FuncState *fs, int kind) {
|
||||
lua_assert(kind & PF_ISVARARG);
|
||||
fs->f->flag |= cast_byte(kind);
|
||||
static void setvararg (FuncState *fs) {
|
||||
fs->f->flag |= PF_ISVARARG;
|
||||
luaK_codeABC(fs, OP_VARARGPREP, 0, 0, 0);
|
||||
}
|
||||
|
||||
@@ -1078,12 +1077,12 @@ static void parlist (LexState *ls) {
|
||||
break;
|
||||
}
|
||||
case TK_DOTS: {
|
||||
varargk |= PF_ISVARARG;
|
||||
varargk = 1;
|
||||
luaX_next(ls); /* skip '...' */
|
||||
if (ls->t.token == TK_NAME) {
|
||||
if (ls->t.token == TK_NAME)
|
||||
new_varkind(ls, str_checkname(ls), RDKVAVAR);
|
||||
varargk |= PF_VAVAR;
|
||||
}
|
||||
else
|
||||
new_localvarliteral(ls, "(vararg table)");
|
||||
break;
|
||||
}
|
||||
default: luaX_syntaxerror(ls, "<name> or '...' expected");
|
||||
@@ -1092,10 +1091,9 @@ static void parlist (LexState *ls) {
|
||||
}
|
||||
adjustlocalvars(ls, nparams);
|
||||
f->numparams = cast_byte(fs->nactvar);
|
||||
if (varargk != 0) {
|
||||
setvararg(fs, varargk); /* declared vararg */
|
||||
if (varargk & PF_VAVAR)
|
||||
adjustlocalvars(ls, 1); /* vararg parameter */
|
||||
if (varargk) {
|
||||
setvararg(fs); /* declared vararg */
|
||||
adjustlocalvars(ls, 1); /* vararg parameter */
|
||||
}
|
||||
/* reserve registers for parameters (plus vararg parameter, if present) */
|
||||
luaK_reserveregs(fs, fs->nactvar);
|
||||
@@ -1287,7 +1285,7 @@ static void simpleexp (LexState *ls, expdesc *v) {
|
||||
FuncState *fs = ls->fs;
|
||||
check_condition(ls, fs->f->flag & PF_ISVARARG,
|
||||
"cannot use '...' outside a vararg function");
|
||||
init_exp(v, VVARARG, luaK_codeABC(fs, OP_VARARG, 0, 0, 1));
|
||||
init_exp(v, VVARARG, luaK_codeABC(fs, OP_VARARG, 0, fs->f->numparams, 1));
|
||||
break;
|
||||
}
|
||||
case '{' /*}*/: { /* constructor */
|
||||
@@ -2153,7 +2151,7 @@ static void mainfunc (LexState *ls, FuncState *fs) {
|
||||
BlockCnt bl;
|
||||
Upvaldesc *env;
|
||||
open_func(ls, fs, &bl);
|
||||
setvararg(fs, PF_ISVARARG); /* main function is always vararg */
|
||||
setvararg(fs); /* main function is always vararg */
|
||||
env = allocupvalue(fs); /* ...set environment upvalue */
|
||||
env->instack = 1;
|
||||
env->idx = 0;
|
||||
|
||||
Reference in New Issue
Block a user