aboutsummaryrefslogtreecommitdiff
path: root/lparser.c
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--lparser.c321
1 files changed, 234 insertions, 87 deletions
diff --git a/lparser.c b/lparser.c
index 380e45f5..dde0b6d5 100644
--- a/lparser.c
+++ b/lparser.c
@@ -30,8 +30,8 @@
30 30
31 31
32 32
33/* maximum number of local variables per function (must be smaller 33/* maximum number of variable declarations per function (must be
34 than 250, due to the bytecode format) */ 34 smaller than 250, due to the bytecode format) */
35#define MAXVARS 200 35#define MAXVARS 200
36 36
37 37
@@ -50,7 +50,7 @@ typedef struct BlockCnt {
50 struct BlockCnt *previous; /* chain */ 50 struct BlockCnt *previous; /* chain */
51 int firstlabel; /* index of first label in this block */ 51 int firstlabel; /* index of first label in this block */
52 int firstgoto; /* index of first pending goto in this block */ 52 int firstgoto; /* index of first pending goto in this block */
53 lu_byte nactvar; /* # active locals outside the block */ 53 short nactvar; /* number of active declarations at block entry */
54 lu_byte upval; /* true if some variable in the block is an upvalue */ 54 lu_byte upval; /* true if some variable in the block is an upvalue */
55 lu_byte isloop; /* 1 if 'block' is a loop; 2 if it has pending breaks */ 55 lu_byte isloop; /* 1 if 'block' is a loop; 2 if it has pending breaks */
56 lu_byte insidetbc; /* true if inside the scope of a to-be-closed var. */ 56 lu_byte insidetbc; /* true if inside the scope of a to-be-closed var. */
@@ -188,18 +188,16 @@ static short registerlocalvar (LexState *ls, FuncState *fs,
188 188
189 189
190/* 190/*
191** Create a new local variable with the given 'name' and given 'kind'. 191** Create a new variable with the given 'name' and given 'kind'.
192** Return its index in the function. 192** Return its index in the function.
193*/ 193*/
194static int new_localvarkind (LexState *ls, TString *name, lu_byte kind) { 194static int new_varkind (LexState *ls, TString *name, lu_byte kind) {
195 lua_State *L = ls->L; 195 lua_State *L = ls->L;
196 FuncState *fs = ls->fs; 196 FuncState *fs = ls->fs;
197 Dyndata *dyd = ls->dyd; 197 Dyndata *dyd = ls->dyd;
198 Vardesc *var; 198 Vardesc *var;
199 luaY_checklimit(fs, dyd->actvar.n + 1 - fs->firstlocal,
200 MAXVARS, "local variables");
201 luaM_growvector(L, dyd->actvar.arr, dyd->actvar.n + 1, 199 luaM_growvector(L, dyd->actvar.arr, dyd->actvar.n + 1,
202 dyd->actvar.size, Vardesc, SHRT_MAX, "local variables"); 200 dyd->actvar.size, Vardesc, SHRT_MAX, "variable declarations");
203 var = &dyd->actvar.arr[dyd->actvar.n++]; 201 var = &dyd->actvar.arr[dyd->actvar.n++];
204 var->vd.kind = kind; /* default */ 202 var->vd.kind = kind; /* default */
205 var->vd.name = name; 203 var->vd.name = name;
@@ -211,7 +209,7 @@ static int new_localvarkind (LexState *ls, TString *name, lu_byte kind) {
211** Create a new local variable with the given 'name' and regular kind. 209** Create a new local variable with the given 'name' and regular kind.
212*/ 210*/
213static int new_localvar (LexState *ls, TString *name) { 211static int new_localvar (LexState *ls, TString *name) {
214 return new_localvarkind(ls, name, VDKREG); 212 return new_varkind(ls, name, VDKREG);
215} 213}
216 214
217#define new_localvarliteral(ls,v) \ 215#define new_localvarliteral(ls,v) \
@@ -238,7 +236,7 @@ static Vardesc *getlocalvardesc (FuncState *fs, int vidx) {
238static lu_byte reglevel (FuncState *fs, int nvar) { 236static lu_byte reglevel (FuncState *fs, int nvar) {
239 while (nvar-- > 0) { 237 while (nvar-- > 0) {
240 Vardesc *vd = getlocalvardesc(fs, nvar); /* get previous variable */ 238 Vardesc *vd = getlocalvardesc(fs, nvar); /* get previous variable */
241 if (vd->vd.kind != RDKCTC) /* is in a register? */ 239 if (varinreg(vd)) /* is in a register? */
242 return cast_byte(vd->vd.ridx + 1); 240 return cast_byte(vd->vd.ridx + 1);
243 } 241 }
244 return 0; /* no variables in registers */ 242 return 0; /* no variables in registers */
@@ -259,7 +257,7 @@ lu_byte luaY_nvarstack (FuncState *fs) {
259*/ 257*/
260static LocVar *localdebuginfo (FuncState *fs, int vidx) { 258static LocVar *localdebuginfo (FuncState *fs, int vidx) {
261 Vardesc *vd = getlocalvardesc(fs, vidx); 259 Vardesc *vd = getlocalvardesc(fs, vidx);
262 if (vd->vd.kind == RDKCTC) 260 if (!varinreg(vd))
263 return NULL; /* no debug info. for constants */ 261 return NULL; /* no debug info. for constants */
264 else { 262 else {
265 int idx = vd->vd.pidx; 263 int idx = vd->vd.pidx;
@@ -275,7 +273,7 @@ static LocVar *localdebuginfo (FuncState *fs, int vidx) {
275static void init_var (FuncState *fs, expdesc *e, int vidx) { 273static void init_var (FuncState *fs, expdesc *e, int vidx) {
276 e->f = e->t = NO_JUMP; 274 e->f = e->t = NO_JUMP;
277 e->k = VLOCAL; 275 e->k = VLOCAL;
278 e->u.var.vidx = cast(unsigned short, vidx); 276 e->u.var.vidx = cast_short(vidx);
279 e->u.var.ridx = getlocalvardesc(fs, vidx)->vd.ridx; 277 e->u.var.ridx = getlocalvardesc(fs, vidx)->vd.ridx;
280} 278}
281 279
@@ -303,14 +301,18 @@ static void check_readonly (LexState *ls, expdesc *e) {
303 varname = up->name; 301 varname = up->name;
304 break; 302 break;
305 } 303 }
304 case VINDEXUP: case VINDEXSTR: case VINDEXED: { /* global variable */
305 if (e->u.ind.ro) /* read-only? */
306 varname = tsvalue(&fs->f->k[e->u.ind.keystr]);
307 break;
308 }
306 default: 309 default:
307 return; /* other cases cannot be read-only */ 310 lua_assert(e->k == VINDEXI); /* this one doesn't need any check */
308 } 311 return; /* integer index cannot be read-only */
309 if (varname) {
310 const char *msg = luaO_pushfstring(ls->L,
311 "attempt to assign to const variable '%s'", getstr(varname));
312 luaK_semerror(ls, msg); /* error */
313 } 312 }
313 if (varname)
314 luaK_semerror(ls, "attempt to assign to const variable '%s'",
315 getstr(varname));
314} 316}
315 317
316 318
@@ -326,6 +328,7 @@ static void adjustlocalvars (LexState *ls, int nvars) {
326 Vardesc *var = getlocalvardesc(fs, vidx); 328 Vardesc *var = getlocalvardesc(fs, vidx);
327 var->vd.ridx = cast_byte(reglevel++); 329 var->vd.ridx = cast_byte(reglevel++);
328 var->vd.pidx = registerlocalvar(ls, fs, var->vd.name); 330 var->vd.pidx = registerlocalvar(ls, fs, var->vd.name);
331 luaY_checklimit(fs, reglevel, MAXVARS, "local variables");
329 } 332 }
330} 333}
331 334
@@ -392,18 +395,38 @@ static int newupvalue (FuncState *fs, TString *name, expdesc *v) {
392 395
393 396
394/* 397/*
395** Look for an active local variable with the name 'n' in the 398** Look for an active variable with the name 'n' in the
396** function 'fs'. If found, initialize 'var' with it and return 399** function 'fs'. If found, initialize 'var' with it and return
397** its expression kind; otherwise return -1. 400** its expression kind; otherwise return -1. While searching,
401** var->u.info==-1 means that the preambular global declaration is
402** active (the default while there is no other global declaration);
403** var->u.info==-2 means there is no active collective declaration
404** (some previous global declaration but no collective declaration);
405** and var->u.info>=0 points to the inner-most (the first one found)
406** collective declaration, if there is one.
398*/ 407*/
399static int searchvar (FuncState *fs, TString *n, expdesc *var) { 408static int searchvar (FuncState *fs, TString *n, expdesc *var) {
400 int i; 409 int i;
401 for (i = cast_int(fs->nactvar) - 1; i >= 0; i--) { 410 for (i = cast_int(fs->nactvar) - 1; i >= 0; i--) {
402 Vardesc *vd = getlocalvardesc(fs, i); 411 Vardesc *vd = getlocalvardesc(fs, i);
403 if (eqstr(n, vd->vd.name)) { /* found? */ 412 if (varglobal(vd)) { /* global declaration? */
413 if (vd->vd.name == NULL) { /* collective declaration? */
414 if (var->u.info < 0) /* no previous collective declaration? */
415 var->u.info = fs->firstlocal + i; /* this is the first one */
416 }
417 else { /* global name */
418 if (eqstr(n, vd->vd.name)) { /* found? */
419 init_exp(var, VGLOBAL, fs->firstlocal + i);
420 return VGLOBAL;
421 }
422 else if (var->u.info == -1) /* active preambular declaration? */
423 var->u.info = -2; /* invalidate preambular declaration */
424 }
425 }
426 else if (eqstr(n, vd->vd.name)) { /* found? */
404 if (vd->vd.kind == RDKCTC) /* compile-time constant? */ 427 if (vd->vd.kind == RDKCTC) /* compile-time constant? */
405 init_exp(var, VCONST, fs->firstlocal + i); 428 init_exp(var, VCONST, fs->firstlocal + i);
406 else /* real variable */ 429 else /* local variable */
407 init_var(fs, var, i); 430 init_var(fs, var, i);
408 return cast_int(var->k); 431 return cast_int(var->k);
409 } 432 }
@@ -442,48 +465,67 @@ static void marktobeclosed (FuncState *fs) {
442** 'var' as 'void' as a flag. 465** 'var' as 'void' as a flag.
443*/ 466*/
444static void singlevaraux (FuncState *fs, TString *n, expdesc *var, int base) { 467static void singlevaraux (FuncState *fs, TString *n, expdesc *var, int base) {
445 if (fs == NULL) /* no more levels? */ 468 int v = searchvar(fs, n, var); /* look up variables at current level */
446 init_exp(var, VVOID, 0); /* default is global */ 469 if (v >= 0) { /* found? */
447 else { 470 if (v == VLOCAL && !base)
448 int v = searchvar(fs, n, var); /* look up locals at current level */ 471 markupval(fs, var->u.var.vidx); /* local will be used as an upval */
449 if (v >= 0) { /* found? */ 472 }
450 if (v == VLOCAL && !base) 473 else { /* not found at current level; try upvalues */
451 markupval(fs, var->u.var.vidx); /* local will be used as an upval */ 474 int idx = searchupvalue(fs, n); /* try existing upvalues */
452 } 475 if (idx < 0) { /* not found? */
453 else { /* not found as local at current level; try upvalues */ 476 if (fs->prev != NULL) /* more levels? */
454 int idx = searchupvalue(fs, n); /* try existing upvalues */
455 if (idx < 0) { /* not found? */
456 singlevaraux(fs->prev, n, var, 0); /* try upper levels */ 477 singlevaraux(fs->prev, n, var, 0); /* try upper levels */
457 if (var->k == VLOCAL || var->k == VUPVAL) /* local or upvalue? */ 478 if (var->k == VLOCAL || var->k == VUPVAL) /* local or upvalue? */
458 idx = newupvalue(fs, n, var); /* will be a new upvalue */ 479 idx = newupvalue(fs, n, var); /* will be a new upvalue */
459 else /* it is a global or a constant */ 480 else /* it is a global or a constant */
460 return; /* don't need to do anything at this level */ 481 return; /* don't need to do anything at this level */
461 }
462 init_exp(var, VUPVAL, idx); /* new or old upvalue */
463 } 482 }
483 init_exp(var, VUPVAL, idx); /* new or old upvalue */
464 } 484 }
465} 485}
466 486
467 487
488static void buildglobal (LexState *ls, TString *varname, expdesc *var) {
489 FuncState *fs = ls->fs;
490 expdesc key;
491 init_exp(var, VGLOBAL, -1); /* global by default */
492 singlevaraux(fs, ls->envn, var, 1); /* get environment variable */
493 if (var->k == VGLOBAL)
494 luaK_semerror(ls, "_ENV is global when accessing variable '%s'",
495 getstr(varname));
496 luaK_exp2anyregup(fs, var); /* _ENV could be a constant */
497 codestring(&key, varname); /* key is variable name */
498 luaK_indexed(fs, var, &key); /* 'var' represents _ENV[varname] */
499}
500
501
468/* 502/*
469** Find a variable with the given name 'n', handling global variables 503** Find a variable with the given name 'n', handling global variables
470** too. 504** too.
471*/ 505*/
472static void singlevar (LexState *ls, expdesc *var) { 506static void buildvar (LexState *ls, TString *varname, expdesc *var) {
473 TString *varname = str_checkname(ls);
474 FuncState *fs = ls->fs; 507 FuncState *fs = ls->fs;
508 init_exp(var, VGLOBAL, -1); /* global by default */
475 singlevaraux(fs, varname, var, 1); 509 singlevaraux(fs, varname, var, 1);
476 if (var->k == VVOID) { /* global name? */ 510 if (var->k == VGLOBAL) { /* global name? */
477 expdesc key; 511 int info = var->u.info;
478 singlevaraux(fs, ls->envn, var, 1); /* get environment variable */ 512 /* global by default in the scope of a global declaration? */
479 lua_assert(var->k != VVOID); /* this one must exist */ 513 if (info == -2)
480 luaK_exp2anyregup(fs, var); /* but could be a constant */ 514 luaK_semerror(ls, "variable '%s' not declared", getstr(varname));
481 codestring(&key, varname); /* key is variable name */ 515 buildglobal(ls, varname, var);
482 luaK_indexed(fs, var, &key); /* env[varname] */ 516 if (info != -1 && ls->dyd->actvar.arr[info].vd.kind == GDKCONST)
517 var->u.ind.ro = 1; /* mark variable as read-only */
518 else /* anyway must be a global */
519 lua_assert(info == -1 || ls->dyd->actvar.arr[info].vd.kind == GDKREG);
483 } 520 }
484} 521}
485 522
486 523
524static void singlevar (LexState *ls, expdesc *var) {
525 buildvar(ls, str_checkname(ls), var);
526}
527
528
487/* 529/*
488** Adjust the number of results from an expression list 'e' with 'nexps' 530** Adjust the number of results from an expression list 'e' with 'nexps'
489** expressions to 'nvars' values. 531** expressions to 'nvars' values.
@@ -518,14 +560,14 @@ static void adjust_assign (LexState *ls, int nvars, int nexps, expdesc *e) {
518 560
519/* 561/*
520** Generates an error that a goto jumps into the scope of some 562** Generates an error that a goto jumps into the scope of some
521** local variable. 563** variable declaration.
522*/ 564*/
523static l_noret jumpscopeerror (LexState *ls, Labeldesc *gt) { 565static l_noret jumpscopeerror (LexState *ls, Labeldesc *gt) {
524 TString *tsname = getlocalvardesc(ls->fs, gt->nactvar)->vd.name; 566 TString *tsname = getlocalvardesc(ls->fs, gt->nactvar)->vd.name;
525 const char *varname = getstr(tsname); 567 const char *varname = (tsname != NULL) ? getstr(tsname) : "*";
526 const char *msg = "<goto %s> at line %d jumps into the scope of local '%s'"; 568 luaK_semerror(ls,
527 msg = luaO_pushfstring(ls->L, msg, getstr(gt->name), gt->line, varname); 569 "<goto %s> at line %d jumps into the scope of '%s'",
528 luaK_semerror(ls, msg); /* raise the error */ 570 getstr(gt->name), gt->line, varname); /* raise the error */
529} 571}
530 572
531 573
@@ -563,7 +605,7 @@ static void closegoto (LexState *ls, int g, Labeldesc *label, int bup) {
563 605
564/* 606/*
565** Search for an active label with the given name, starting at 607** Search for an active label with the given name, starting at
566** index 'ilb' (so that it can searh for all labels in current block 608** index 'ilb' (so that it can search for all labels in current block
567** or all labels in current function). 609** or all labels in current function).
568*/ 610*/
569static Labeldesc *findlabel (LexState *ls, TString *name, int ilb) { 611static Labeldesc *findlabel (LexState *ls, TString *name, int ilb) {
@@ -630,7 +672,7 @@ static void createlabel (LexState *ls, TString *name, int line, int last) {
630 672
631 673
632/* 674/*
633** Traverse the pending goto's of the finishing block checking whether 675** Traverse the pending gotos of the finishing block checking whether
634** each match some label of that block. Those that do not match are 676** each match some label of that block. Those that do not match are
635** "exported" to the outer block, to be solved there. In particular, 677** "exported" to the outer block, to be solved there. In particular,
636** its 'nactvar' is updated with the level of the inner block, 678** its 'nactvar' is updated with the level of the inner block,
@@ -666,8 +708,9 @@ static void enterblock (FuncState *fs, BlockCnt *bl, lu_byte isloop) {
666 bl->firstlabel = fs->ls->dyd->label.n; 708 bl->firstlabel = fs->ls->dyd->label.n;
667 bl->firstgoto = fs->ls->dyd->gt.n; 709 bl->firstgoto = fs->ls->dyd->gt.n;
668 bl->upval = 0; 710 bl->upval = 0;
711 /* inherit 'insidetbc' from enclosing block */
669 bl->insidetbc = (fs->bl != NULL && fs->bl->insidetbc); 712 bl->insidetbc = (fs->bl != NULL && fs->bl->insidetbc);
670 bl->previous = fs->bl; 713 bl->previous = fs->bl; /* link block in function's block list */
671 fs->bl = bl; 714 fs->bl = bl;
672 lua_assert(fs->freereg == luaY_nvarstack(fs)); 715 lua_assert(fs->freereg == luaY_nvarstack(fs));
673} 716}
@@ -677,11 +720,10 @@ static void enterblock (FuncState *fs, BlockCnt *bl, lu_byte isloop) {
677** generates an error for an undefined 'goto'. 720** generates an error for an undefined 'goto'.
678*/ 721*/
679static l_noret undefgoto (LexState *ls, Labeldesc *gt) { 722static l_noret undefgoto (LexState *ls, Labeldesc *gt) {
680 const char *msg = "no visible label '%s' for <goto> at line %d";
681 msg = luaO_pushfstring(ls->L, msg, getstr(gt->name), gt->line);
682 /* breaks are checked when created, cannot be undefined */ 723 /* breaks are checked when created, cannot be undefined */
683 lua_assert(!eqstr(gt->name, luaS_newliteral(ls->L, "break"))); 724 lua_assert(!eqstr(gt->name, ls->brkn));
684 luaK_semerror(ls, msg); 725 luaK_semerror(ls, "no visible label '%s' for <goto> at line %d",
726 getstr(gt->name), gt->line);
685} 727}
686 728
687 729
@@ -695,7 +737,7 @@ static void leaveblock (FuncState *fs) {
695 removevars(fs, bl->nactvar); /* remove block locals */ 737 removevars(fs, bl->nactvar); /* remove block locals */
696 lua_assert(bl->nactvar == fs->nactvar); /* back to level on entry */ 738 lua_assert(bl->nactvar == fs->nactvar); /* back to level on entry */
697 if (bl->isloop == 2) /* has to fix pending breaks? */ 739 if (bl->isloop == 2) /* has to fix pending breaks? */
698 createlabel(ls, luaS_newliteral(ls->L, "break"), 0, 0); 740 createlabel(ls, ls->brkn, 0, 0);
699 solvegotos(fs, bl); 741 solvegotos(fs, bl);
700 if (bl->previous == NULL) { /* was it the last block? */ 742 if (bl->previous == NULL) { /* was it the last block? */
701 if (bl->firstgoto < ls->dyd->gt.n) /* still pending gotos? */ 743 if (bl->firstgoto < ls->dyd->gt.n) /* still pending gotos? */
@@ -868,10 +910,8 @@ static void recfield (LexState *ls, ConsControl *cc) {
868 FuncState *fs = ls->fs; 910 FuncState *fs = ls->fs;
869 lu_byte reg = ls->fs->freereg; 911 lu_byte reg = ls->fs->freereg;
870 expdesc tab, key, val; 912 expdesc tab, key, val;
871 if (ls->t.token == TK_NAME) { 913 if (ls->t.token == TK_NAME)
872 luaY_checklimit(fs, cc->nh, INT_MAX / 2, "items in a constructor");
873 codename(ls, &key); 914 codename(ls, &key);
874 }
875 else /* ls->t.token == '[' */ 915 else /* ls->t.token == '[' */
876 yindex(ls, &key); 916 yindex(ls, &key);
877 cc->nh++; 917 cc->nh++;
@@ -1402,6 +1442,15 @@ static void check_conflict (LexState *ls, struct LHS_assign *lh, expdesc *v) {
1402 } 1442 }
1403} 1443}
1404 1444
1445
1446/* Create code to store the "top" register in 'var' */
1447static void storevartop (FuncState *fs, expdesc *var) {
1448 expdesc e;
1449 init_exp(&e, VNONRELOC, fs->freereg - 1);
1450 luaK_storevar(fs, var, &e); /* will also free the top register */
1451}
1452
1453
1405/* 1454/*
1406** Parse and compile a multiple assignment. The first "variable" 1455** Parse and compile a multiple assignment. The first "variable"
1407** (a 'suffixedexp') was already read by the caller. 1456** (a 'suffixedexp') was already read by the caller.
@@ -1435,8 +1484,7 @@ static void restassign (LexState *ls, struct LHS_assign *lh, int nvars) {
1435 return; /* avoid default */ 1484 return; /* avoid default */
1436 } 1485 }
1437 } 1486 }
1438 init_exp(&e, VNONRELOC, ls->fs->freereg-1); /* default assignment */ 1487 storevartop(ls->fs, &lh->v); /* default assignment */
1439 luaK_storevar(ls->fs, &lh->v, &e);
1440} 1488}
1441 1489
1442 1490
@@ -1469,7 +1517,7 @@ static void breakstat (LexState *ls, int line) {
1469 ok: 1517 ok:
1470 bl->isloop = 2; /* signal that block has pending breaks */ 1518 bl->isloop = 2; /* signal that block has pending breaks */
1471 luaX_next(ls); /* skip break */ 1519 luaX_next(ls); /* skip break */
1472 newgotoentry(ls, luaS_newliteral(ls->L, "break"), line); 1520 newgotoentry(ls, ls->brkn, line);
1473} 1521}
1474 1522
1475 1523
@@ -1479,11 +1527,9 @@ static void breakstat (LexState *ls, int line) {
1479*/ 1527*/
1480static void checkrepeated (LexState *ls, TString *name) { 1528static void checkrepeated (LexState *ls, TString *name) {
1481 Labeldesc *lb = findlabel(ls, name, ls->fs->firstlabel); 1529 Labeldesc *lb = findlabel(ls, name, ls->fs->firstlabel);
1482 if (l_unlikely(lb != NULL)) { /* already defined? */ 1530 if (l_unlikely(lb != NULL)) /* already defined? */
1483 const char *msg = "label '%s' already defined on line %d"; 1531 luaK_semerror(ls, "label '%s' already defined on line %d",
1484 msg = luaO_pushfstring(ls->L, msg, getstr(name), lb->line); 1532 getstr(name), lb->line); /* error */
1485 luaK_semerror(ls, msg); /* error */
1486 }
1487} 1533}
1488 1534
1489 1535
@@ -1605,7 +1651,7 @@ static void fornum (LexState *ls, TString *varname, int line) {
1605 int base = fs->freereg; 1651 int base = fs->freereg;
1606 new_localvarliteral(ls, "(for state)"); 1652 new_localvarliteral(ls, "(for state)");
1607 new_localvarliteral(ls, "(for state)"); 1653 new_localvarliteral(ls, "(for state)");
1608 new_localvarkind(ls, varname, RDKCONST); /* control variable */ 1654 new_varkind(ls, varname, RDKCONST); /* control variable */
1609 checknext(ls, '='); 1655 checknext(ls, '=');
1610 exp1(ls); /* initial value */ 1656 exp1(ls); /* initial value */
1611 checknext(ls, ','); 1657 checknext(ls, ',');
@@ -1632,7 +1678,7 @@ static void forlist (LexState *ls, TString *indexname) {
1632 new_localvarliteral(ls, "(for state)"); /* iterator function */ 1678 new_localvarliteral(ls, "(for state)"); /* iterator function */
1633 new_localvarliteral(ls, "(for state)"); /* state */ 1679 new_localvarliteral(ls, "(for state)"); /* state */
1634 new_localvarliteral(ls, "(for state)"); /* closing var. (after swap) */ 1680 new_localvarliteral(ls, "(for state)"); /* closing var. (after swap) */
1635 new_localvarkind(ls, indexname, RDKCONST); /* control variable */ 1681 new_varkind(ls, indexname, RDKCONST); /* control variable */
1636 /* other declared variables */ 1682 /* other declared variables */
1637 while (testnext(ls, ',')) { 1683 while (testnext(ls, ',')) {
1638 new_localvar(ls, str_checkname(ls)); 1684 new_localvar(ls, str_checkname(ls));
@@ -1707,8 +1753,8 @@ static void localfunc (LexState *ls) {
1707} 1753}
1708 1754
1709 1755
1710static lu_byte getlocalattribute (LexState *ls) { 1756static lu_byte getvarattribute (LexState *ls, lu_byte df) {
1711 /* ATTRIB -> ['<' Name '>'] */ 1757 /* attrib -> ['<' NAME '>'] */
1712 if (testnext(ls, '<')) { 1758 if (testnext(ls, '<')) {
1713 TString *ts = str_checkname(ls); 1759 TString *ts = str_checkname(ls);
1714 const char *attr = getstr(ts); 1760 const char *attr = getstr(ts);
@@ -1718,10 +1764,9 @@ static lu_byte getlocalattribute (LexState *ls) {
1718 else if (strcmp(attr, "close") == 0) 1764 else if (strcmp(attr, "close") == 0)
1719 return RDKTOCLOSE; /* to-be-closed variable */ 1765 return RDKTOCLOSE; /* to-be-closed variable */
1720 else 1766 else
1721 luaK_semerror(ls, 1767 luaK_semerror(ls, "unknown attribute '%s'", attr);
1722 luaO_pushfstring(ls->L, "unknown attribute '%s'", attr));
1723 } 1768 }
1724 return VDKREG; /* regular variable */ 1769 return df; /* return default value */
1725} 1770}
1726 1771
1727 1772
@@ -1734,7 +1779,7 @@ static void checktoclose (FuncState *fs, int level) {
1734 1779
1735 1780
1736static void localstat (LexState *ls) { 1781static void localstat (LexState *ls) {
1737 /* stat -> LOCAL NAME ATTRIB { ',' NAME ATTRIB } ['=' explist] */ 1782 /* stat -> LOCAL NAME attrib { ',' NAME attrib } ['=' explist] */
1738 FuncState *fs = ls->fs; 1783 FuncState *fs = ls->fs;
1739 int toclose = -1; /* index of to-be-closed variable (if any) */ 1784 int toclose = -1; /* index of to-be-closed variable (if any) */
1740 Vardesc *var; /* last variable */ 1785 Vardesc *var; /* last variable */
@@ -1742,10 +1787,12 @@ static void localstat (LexState *ls) {
1742 int nvars = 0; 1787 int nvars = 0;
1743 int nexps; 1788 int nexps;
1744 expdesc e; 1789 expdesc e;
1745 do { 1790 /* get prefixed attribute (if any); default is regular local variable */
1746 TString *vname = str_checkname(ls); 1791 lu_byte defkind = getvarattribute(ls, VDKREG);
1747 lu_byte kind = getlocalattribute(ls); 1792 do { /* for each variable */
1748 vidx = new_localvarkind(ls, vname, kind); 1793 TString *vname = str_checkname(ls); /* get its name */
1794 lu_byte kind = getvarattribute(ls, defkind); /* postfixed attribute */
1795 vidx = new_varkind(ls, vname, kind); /* predeclare it */
1749 if (kind == RDKTOCLOSE) { /* to-be-closed? */ 1796 if (kind == RDKTOCLOSE) { /* to-be-closed? */
1750 if (toclose != -1) /* one already present? */ 1797 if (toclose != -1) /* one already present? */
1751 luaK_semerror(ls, "multiple to-be-closed variables in local list"); 1798 luaK_semerror(ls, "multiple to-be-closed variables in local list");
@@ -1753,13 +1800,13 @@ static void localstat (LexState *ls) {
1753 } 1800 }
1754 nvars++; 1801 nvars++;
1755 } while (testnext(ls, ',')); 1802 } while (testnext(ls, ','));
1756 if (testnext(ls, '=')) 1803 if (testnext(ls, '=')) /* initialization? */
1757 nexps = explist(ls, &e); 1804 nexps = explist(ls, &e);
1758 else { 1805 else {
1759 e.k = VVOID; 1806 e.k = VVOID;
1760 nexps = 0; 1807 nexps = 0;
1761 } 1808 }
1762 var = getlocalvardesc(fs, vidx); /* get last variable */ 1809 var = getlocalvardesc(fs, vidx); /* retrieve last variable */
1763 if (nvars == nexps && /* no adjustments? */ 1810 if (nvars == nexps && /* no adjustments? */
1764 var->vd.kind == RDKCONST && /* last variable is const? */ 1811 var->vd.kind == RDKCONST && /* last variable is const? */
1765 luaK_exp2const(fs, &e, &var->k)) { /* compile-time constant? */ 1812 luaK_exp2const(fs, &e, &var->k)) { /* compile-time constant? */
@@ -1775,6 +1822,86 @@ static void localstat (LexState *ls) {
1775} 1822}
1776 1823
1777 1824
1825static lu_byte getglobalattribute (LexState *ls, lu_byte df) {
1826 lu_byte kind = getvarattribute(ls, df);
1827 switch (kind) {
1828 case RDKTOCLOSE:
1829 luaK_semerror(ls, "global variables cannot be to-be-closed");
1830 break; /* to avoid warnings */
1831 case RDKCONST:
1832 return GDKCONST; /* adjust kind for global variable */
1833 default:
1834 return kind;
1835 }
1836}
1837
1838
1839static void globalnames (LexState *ls, lu_byte defkind) {
1840 FuncState *fs = ls->fs;
1841 int nvars = 0;
1842 int lastidx; /* index of last registered variable */
1843 do { /* for each name */
1844 TString *vname = str_checkname(ls);
1845 lu_byte kind = getglobalattribute(ls, defkind);
1846 lastidx = new_varkind(ls, vname, kind);
1847 nvars++;
1848 } while (testnext(ls, ','));
1849 if (testnext(ls, '=')) { /* initialization? */
1850 expdesc e;
1851 int i;
1852 int nexps = explist(ls, &e); /* read list of expressions */
1853 adjust_assign(ls, nvars, nexps, &e);
1854 for (i = 0; i < nvars; i++) { /* for each variable */
1855 expdesc var;
1856 TString *varname = getlocalvardesc(fs, lastidx - i)->vd.name;
1857 buildglobal(ls, varname, &var); /* create global variable in 'var' */
1858 storevartop(fs, &var);
1859 }
1860 }
1861 fs->nactvar = cast_short(fs->nactvar + nvars); /* activate declaration */
1862}
1863
1864
1865static void globalstat (LexState *ls) {
1866 /* globalstat -> (GLOBAL) attrib '*'
1867 globalstat -> (GLOBAL) attrib NAME attrib {',' NAME attrib} */
1868 FuncState *fs = ls->fs;
1869 /* get prefixed attribute (if any); default is regular global variable */
1870 lu_byte defkind = getglobalattribute(ls, GDKREG);
1871 if (!testnext(ls, '*'))
1872 globalnames(ls, defkind);
1873 else {
1874 /* use NULL as name to represent '*' entries */
1875 new_varkind(ls, NULL, defkind);
1876 fs->nactvar++; /* activate declaration */
1877 }
1878}
1879
1880
1881static void globalfunc (LexState *ls, int line) {
1882 /* globalfunc -> (GLOBAL FUNCTION) NAME body */
1883 expdesc var, b;
1884 FuncState *fs = ls->fs;
1885 TString *fname = str_checkname(ls);
1886 new_varkind(ls, fname, GDKREG); /* declare global variable */
1887 fs->nactvar++; /* enter its scope */
1888 buildglobal(ls, fname, &var);
1889 body(ls, &b, 0, ls->linenumber); /* compile and return closure in 'b' */
1890 luaK_storevar(fs, &var, &b);
1891 luaK_fixline(fs, line); /* definition "happens" in the first line */
1892}
1893
1894
1895static void globalstatfunc (LexState *ls, int line) {
1896 /* stat -> GLOBAL globalfunc | GLOBAL globalstat */
1897 luaX_next(ls); /* skip 'global' */
1898 if (testnext(ls, TK_FUNCTION))
1899 globalfunc(ls, line);
1900 else
1901 globalstat(ls);
1902}
1903
1904
1778static int funcname (LexState *ls, expdesc *v) { 1905static int funcname (LexState *ls, expdesc *v) {
1779 /* funcname -> NAME {fieldsel} [':' NAME] */ 1906 /* funcname -> NAME {fieldsel} [':' NAME] */
1780 int ismethod = 0; 1907 int ismethod = 0;
@@ -1795,8 +1922,8 @@ static void funcstat (LexState *ls, int line) {
1795 expdesc v, b; 1922 expdesc v, b;
1796 luaX_next(ls); /* skip FUNCTION */ 1923 luaX_next(ls); /* skip FUNCTION */
1797 ismethod = funcname(ls, &v); 1924 ismethod = funcname(ls, &v);
1798 body(ls, &b, ismethod, line);
1799 check_readonly(ls, &v); 1925 check_readonly(ls, &v);
1926 body(ls, &b, ismethod, line);
1800 luaK_storevar(ls->fs, &v, &b); 1927 luaK_storevar(ls->fs, &v, &b);
1801 luaK_fixline(ls->fs, line); /* definition "happens" in the first line */ 1928 luaK_fixline(ls->fs, line); /* definition "happens" in the first line */
1802} 1929}
@@ -1894,6 +2021,10 @@ static void statement (LexState *ls) {
1894 localstat(ls); 2021 localstat(ls);
1895 break; 2022 break;
1896 } 2023 }
2024 case TK_GLOBAL: { /* stat -> globalstatfunc */
2025 globalstatfunc(ls, line);
2026 break;
2027 }
1897 case TK_DBCOLON: { /* stat -> label */ 2028 case TK_DBCOLON: { /* stat -> label */
1898 luaX_next(ls); /* skip double colon */ 2029 luaX_next(ls); /* skip double colon */
1899 labelstat(ls, str_checkname(ls), line); 2030 labelstat(ls, str_checkname(ls), line);
@@ -1913,6 +2044,22 @@ static void statement (LexState *ls) {
1913 gotostat(ls, line); 2044 gotostat(ls, line);
1914 break; 2045 break;
1915 } 2046 }
2047#if defined(LUA_COMPAT_GLOBAL)
2048 case TK_NAME: {
2049 /* compatibility code to parse global keyword when "global"
2050 is not reserved */
2051 if (ls->t.seminfo.ts == ls->glbn) { /* current = "global"? */
2052 int lk = luaX_lookahead(ls);
2053 if (lk == '<' || lk == TK_NAME || lk == '*' || lk == TK_FUNCTION) {
2054 /* 'global <attrib>' or 'global name' or 'global *' or
2055 'global function' */
2056 globalstatfunc(ls, line);
2057 break;
2058 }
2059 } /* else... */
2060 }
2061#endif
2062 /* FALLTHROUGH */
1916 default: { /* stat -> func | assignment */ 2063 default: { /* stat -> func | assignment */
1917 exprstat(ls); 2064 exprstat(ls);
1918 break; 2065 break;