2812
|
1 |
/*
|
|
2 |
** $Id: lparser.c,v 2.42.1.3 2007/12/28 15:32:23 roberto Exp $
|
|
3 |
** Lua Parser
|
|
4 |
** See Copyright Notice in lua.h
|
|
5 |
*/
|
|
6 |
|
|
7 |
|
|
8 |
#include <string.h>
|
|
9 |
|
|
10 |
#define lparser_c
|
|
11 |
#define LUA_CORE
|
|
12 |
|
|
13 |
#include "lua.h"
|
|
14 |
|
|
15 |
#include "lcode.h"
|
|
16 |
#include "ldebug.h"
|
|
17 |
#include "ldo.h"
|
|
18 |
#include "lfunc.h"
|
|
19 |
#include "llex.h"
|
|
20 |
#include "lmem.h"
|
|
21 |
#include "lobject.h"
|
|
22 |
#include "lopcodes.h"
|
|
23 |
#include "lparser.h"
|
|
24 |
#include "lstate.h"
|
|
25 |
#include "lstring.h"
|
|
26 |
#include "ltable.h"
|
|
27 |
|
|
28 |
|
|
29 |
|
10017
|
30 |
#define hasmultret(k) ((k) == VCALL || (k) == VVARARG)
|
2812
|
31 |
|
10017
|
32 |
#define getlocvar(fs, i) ((fs)->f->locvars[(fs)->actvar[i]])
|
2812
|
33 |
|
10017
|
34 |
#define luaY_checklimit(fs,v,l,m) if ((v)>(l)) errorlimit(fs,l,m)
|
2812
|
35 |
|
|
36 |
|
|
37 |
/*
|
|
38 |
** nodes for block list (list of active blocks)
|
|
39 |
*/
|
|
40 |
typedef struct BlockCnt {
|
|
41 |
struct BlockCnt *previous; /* chain */
|
|
42 |
int breaklist; /* list of jumps out of this loop */
|
|
43 |
lu_byte nactvar; /* # active locals outside the breakable structure */
|
|
44 |
lu_byte upval; /* true if some variable in the block is an upvalue */
|
|
45 |
lu_byte isbreakable; /* true if `block' is a loop */
|
|
46 |
} BlockCnt;
|
|
47 |
|
|
48 |
|
|
49 |
|
|
50 |
/*
|
|
51 |
** prototypes for recursive non-terminal functions
|
|
52 |
*/
|
|
53 |
static void chunk (LexState *ls);
|
|
54 |
static void expr (LexState *ls, expdesc *v);
|
|
55 |
|
|
56 |
|
|
57 |
static void anchor_token (LexState *ls) {
|
|
58 |
if (ls->t.token == TK_NAME || ls->t.token == TK_STRING) {
|
|
59 |
TString *ts = ls->t.seminfo.ts;
|
|
60 |
luaX_newstring(ls, getstr(ts), ts->tsv.len);
|
|
61 |
}
|
|
62 |
}
|
|
63 |
|
|
64 |
|
|
65 |
static void error_expected (LexState *ls, int token) {
|
|
66 |
luaX_syntaxerror(ls,
|
|
67 |
luaO_pushfstring(ls->L, LUA_QS " expected", luaX_token2str(ls, token)));
|
|
68 |
}
|
|
69 |
|
|
70 |
|
|
71 |
static void errorlimit (FuncState *fs, int limit, const char *what) {
|
|
72 |
const char *msg = (fs->f->linedefined == 0) ?
|
|
73 |
luaO_pushfstring(fs->L, "main function has more than %d %s", limit, what) :
|
|
74 |
luaO_pushfstring(fs->L, "function at line %d has more than %d %s",
|
|
75 |
fs->f->linedefined, limit, what);
|
|
76 |
luaX_lexerror(fs->ls, msg, 0);
|
|
77 |
}
|
|
78 |
|
|
79 |
|
|
80 |
static int testnext (LexState *ls, int c) {
|
|
81 |
if (ls->t.token == c) {
|
|
82 |
luaX_next(ls);
|
|
83 |
return 1;
|
|
84 |
}
|
|
85 |
else return 0;
|
|
86 |
}
|
|
87 |
|
|
88 |
|
|
89 |
static void check (LexState *ls, int c) {
|
|
90 |
if (ls->t.token != c)
|
|
91 |
error_expected(ls, c);
|
|
92 |
}
|
|
93 |
|
|
94 |
static void checknext (LexState *ls, int c) {
|
|
95 |
check(ls, c);
|
|
96 |
luaX_next(ls);
|
|
97 |
}
|
|
98 |
|
|
99 |
|
10017
|
100 |
#define check_condition(ls,c,msg) { if (!(c)) luaX_syntaxerror(ls, msg); }
|
2812
|
101 |
|
|
102 |
|
|
103 |
|
|
104 |
static void check_match (LexState *ls, int what, int who, int where) {
|
|
105 |
if (!testnext(ls, what)) {
|
|
106 |
if (where == ls->linenumber)
|
|
107 |
error_expected(ls, what);
|
|
108 |
else {
|
|
109 |
luaX_syntaxerror(ls, luaO_pushfstring(ls->L,
|
|
110 |
LUA_QS " expected (to close " LUA_QS " at line %d)",
|
|
111 |
luaX_token2str(ls, what), luaX_token2str(ls, who), where));
|
|
112 |
}
|
|
113 |
}
|
|
114 |
}
|
|
115 |
|
|
116 |
|
|
117 |
static TString *str_checkname (LexState *ls) {
|
|
118 |
TString *ts;
|
|
119 |
check(ls, TK_NAME);
|
|
120 |
ts = ls->t.seminfo.ts;
|
|
121 |
luaX_next(ls);
|
|
122 |
return ts;
|
|
123 |
}
|
|
124 |
|
|
125 |
|
|
126 |
static void init_exp (expdesc *e, expkind k, int i) {
|
|
127 |
e->f = e->t = NO_JUMP;
|
|
128 |
e->k = k;
|
|
129 |
e->u.s.info = i;
|
|
130 |
}
|
|
131 |
|
|
132 |
|
|
133 |
static void codestring (LexState *ls, expdesc *e, TString *s) {
|
|
134 |
init_exp(e, VK, luaK_stringK(ls->fs, s));
|
|
135 |
}
|
|
136 |
|
|
137 |
|
|
138 |
static void checkname(LexState *ls, expdesc *e) {
|
|
139 |
codestring(ls, e, str_checkname(ls));
|
|
140 |
}
|
|
141 |
|
|
142 |
|
|
143 |
static int registerlocalvar (LexState *ls, TString *varname) {
|
|
144 |
FuncState *fs = ls->fs;
|
|
145 |
Proto *f = fs->f;
|
|
146 |
int oldsize = f->sizelocvars;
|
|
147 |
luaM_growvector(ls->L, f->locvars, fs->nlocvars, f->sizelocvars,
|
|
148 |
LocVar, SHRT_MAX, "too many local variables");
|
|
149 |
while (oldsize < f->sizelocvars) f->locvars[oldsize++].varname = NULL;
|
|
150 |
f->locvars[fs->nlocvars].varname = varname;
|
|
151 |
luaC_objbarrier(ls->L, f, varname);
|
|
152 |
return fs->nlocvars++;
|
|
153 |
}
|
|
154 |
|
|
155 |
|
|
156 |
#define new_localvarliteral(ls,v,n) \
|
|
157 |
new_localvar(ls, luaX_newstring(ls, "" v, (sizeof(v)/sizeof(char))-1), n)
|
|
158 |
|
|
159 |
|
|
160 |
static void new_localvar (LexState *ls, TString *name, int n) {
|
|
161 |
FuncState *fs = ls->fs;
|
|
162 |
luaY_checklimit(fs, fs->nactvar+n+1, LUAI_MAXVARS, "local variables");
|
|
163 |
fs->actvar[fs->nactvar+n] = cast(unsigned short, registerlocalvar(ls, name));
|
|
164 |
}
|
|
165 |
|
|
166 |
|
|
167 |
static void adjustlocalvars (LexState *ls, int nvars) {
|
|
168 |
FuncState *fs = ls->fs;
|
|
169 |
fs->nactvar = cast_byte(fs->nactvar + nvars);
|
|
170 |
for (; nvars; nvars--) {
|
|
171 |
getlocvar(fs, fs->nactvar - nvars).startpc = fs->pc;
|
|
172 |
}
|
|
173 |
}
|
|
174 |
|
|
175 |
|
|
176 |
static void removevars (LexState *ls, int tolevel) {
|
|
177 |
FuncState *fs = ls->fs;
|
|
178 |
while (fs->nactvar > tolevel)
|
|
179 |
getlocvar(fs, --fs->nactvar).endpc = fs->pc;
|
|
180 |
}
|
|
181 |
|
|
182 |
|
|
183 |
static int indexupvalue (FuncState *fs, TString *name, expdesc *v) {
|
|
184 |
int i;
|
|
185 |
Proto *f = fs->f;
|
|
186 |
int oldsize = f->sizeupvalues;
|
|
187 |
for (i=0; i<f->nups; i++) {
|
|
188 |
if (fs->upvalues[i].k == v->k && fs->upvalues[i].info == v->u.s.info) {
|
|
189 |
lua_assert(f->upvalues[i] == name);
|
|
190 |
return i;
|
|
191 |
}
|
|
192 |
}
|
|
193 |
/* new one */
|
|
194 |
luaY_checklimit(fs, f->nups + 1, LUAI_MAXUPVALUES, "upvalues");
|
|
195 |
luaM_growvector(fs->L, f->upvalues, f->nups, f->sizeupvalues,
|
|
196 |
TString *, MAX_INT, "");
|
|
197 |
while (oldsize < f->sizeupvalues) f->upvalues[oldsize++] = NULL;
|
|
198 |
f->upvalues[f->nups] = name;
|
|
199 |
luaC_objbarrier(fs->L, f, name);
|
|
200 |
lua_assert(v->k == VLOCAL || v->k == VUPVAL);
|
|
201 |
fs->upvalues[f->nups].k = cast_byte(v->k);
|
|
202 |
fs->upvalues[f->nups].info = cast_byte(v->u.s.info);
|
|
203 |
return f->nups++;
|
|
204 |
}
|
|
205 |
|
|
206 |
|
|
207 |
static int searchvar (FuncState *fs, TString *n) {
|
|
208 |
int i;
|
|
209 |
for (i=fs->nactvar-1; i >= 0; i--) {
|
|
210 |
if (n == getlocvar(fs, i).varname)
|
|
211 |
return i;
|
|
212 |
}
|
|
213 |
return -1; /* not found */
|
|
214 |
}
|
|
215 |
|
|
216 |
|
|
217 |
static void markupval (FuncState *fs, int level) {
|
|
218 |
BlockCnt *bl = fs->bl;
|
|
219 |
while (bl && bl->nactvar > level) bl = bl->previous;
|
|
220 |
if (bl) bl->upval = 1;
|
|
221 |
}
|
|
222 |
|
|
223 |
|
|
224 |
static int singlevaraux (FuncState *fs, TString *n, expdesc *var, int base) {
|
|
225 |
if (fs == NULL) { /* no more levels? */
|
|
226 |
init_exp(var, VGLOBAL, NO_REG); /* default is global variable */
|
|
227 |
return VGLOBAL;
|
|
228 |
}
|
|
229 |
else {
|
|
230 |
int v = searchvar(fs, n); /* look up at current level */
|
|
231 |
if (v >= 0) {
|
|
232 |
init_exp(var, VLOCAL, v);
|
|
233 |
if (!base)
|
|
234 |
markupval(fs, v); /* local will be used as an upval */
|
|
235 |
return VLOCAL;
|
|
236 |
}
|
|
237 |
else { /* not found at current level; try upper one */
|
|
238 |
if (singlevaraux(fs->prev, n, var, 0) == VGLOBAL)
|
|
239 |
return VGLOBAL;
|
|
240 |
var->u.s.info = indexupvalue(fs, n, var); /* else was LOCAL or UPVAL */
|
|
241 |
var->k = VUPVAL; /* upvalue in this level */
|
|
242 |
return VUPVAL;
|
|
243 |
}
|
|
244 |
}
|
|
245 |
}
|
|
246 |
|
|
247 |
|
|
248 |
static void singlevar (LexState *ls, expdesc *var) {
|
|
249 |
TString *varname = str_checkname(ls);
|
|
250 |
FuncState *fs = ls->fs;
|
|
251 |
if (singlevaraux(fs, varname, var, 1) == VGLOBAL)
|
|
252 |
var->u.s.info = luaK_stringK(fs, varname); /* info points to global name */
|
|
253 |
}
|
|
254 |
|
|
255 |
|
|
256 |
static void adjust_assign (LexState *ls, int nvars, int nexps, expdesc *e) {
|
|
257 |
FuncState *fs = ls->fs;
|
|
258 |
int extra = nvars - nexps;
|
|
259 |
if (hasmultret(e->k)) {
|
|
260 |
extra++; /* includes call itself */
|
|
261 |
if (extra < 0) extra = 0;
|
|
262 |
luaK_setreturns(fs, e, extra); /* last exp. provides the difference */
|
|
263 |
if (extra > 1) luaK_reserveregs(fs, extra-1);
|
|
264 |
}
|
|
265 |
else {
|
|
266 |
if (e->k != VVOID) luaK_exp2nextreg(fs, e); /* close last expression */
|
|
267 |
if (extra > 0) {
|
|
268 |
int reg = fs->freereg;
|
|
269 |
luaK_reserveregs(fs, extra);
|
|
270 |
luaK_nil(fs, reg, extra);
|
|
271 |
}
|
|
272 |
}
|
|
273 |
}
|
|
274 |
|
|
275 |
|
|
276 |
static void enterlevel (LexState *ls) {
|
|
277 |
if (++ls->L->nCcalls > LUAI_MAXCCALLS)
|
10017
|
278 |
luaX_lexerror(ls, "chunk has too many syntax levels", 0);
|
2812
|
279 |
}
|
|
280 |
|
|
281 |
|
10017
|
282 |
#define leavelevel(ls) ((ls)->L->nCcalls--)
|
2812
|
283 |
|
|
284 |
|
|
285 |
static void enterblock (FuncState *fs, BlockCnt *bl, lu_byte isbreakable) {
|
|
286 |
bl->breaklist = NO_JUMP;
|
|
287 |
bl->isbreakable = isbreakable;
|
|
288 |
bl->nactvar = fs->nactvar;
|
|
289 |
bl->upval = 0;
|
|
290 |
bl->previous = fs->bl;
|
|
291 |
fs->bl = bl;
|
|
292 |
lua_assert(fs->freereg == fs->nactvar);
|
|
293 |
}
|
|
294 |
|
|
295 |
|
|
296 |
static void leaveblock (FuncState *fs) {
|
|
297 |
BlockCnt *bl = fs->bl;
|
|
298 |
fs->bl = bl->previous;
|
|
299 |
removevars(fs->ls, bl->nactvar);
|
|
300 |
if (bl->upval)
|
|
301 |
luaK_codeABC(fs, OP_CLOSE, bl->nactvar, 0, 0);
|
|
302 |
/* a block either controls scope or breaks (never both) */
|
|
303 |
lua_assert(!bl->isbreakable || !bl->upval);
|
|
304 |
lua_assert(bl->nactvar == fs->nactvar);
|
|
305 |
fs->freereg = fs->nactvar; /* free registers */
|
|
306 |
luaK_patchtohere(fs, bl->breaklist);
|
|
307 |
}
|
|
308 |
|
|
309 |
|
|
310 |
static void pushclosure (LexState *ls, FuncState *func, expdesc *v) {
|
|
311 |
FuncState *fs = ls->fs;
|
|
312 |
Proto *f = fs->f;
|
|
313 |
int oldsize = f->sizep;
|
|
314 |
int i;
|
|
315 |
luaM_growvector(ls->L, f->p, fs->np, f->sizep, Proto *,
|
|
316 |
MAXARG_Bx, "constant table overflow");
|
|
317 |
while (oldsize < f->sizep) f->p[oldsize++] = NULL;
|
|
318 |
f->p[fs->np++] = func->f;
|
|
319 |
luaC_objbarrier(ls->L, f, func->f);
|
|
320 |
init_exp(v, VRELOCABLE, luaK_codeABx(fs, OP_CLOSURE, 0, fs->np-1));
|
|
321 |
for (i=0; i<func->f->nups; i++) {
|
|
322 |
OpCode o = (func->upvalues[i].k == VLOCAL) ? OP_MOVE : OP_GETUPVAL;
|
|
323 |
luaK_codeABC(fs, o, 0, func->upvalues[i].info, 0);
|
|
324 |
}
|
|
325 |
}
|
|
326 |
|
|
327 |
|
|
328 |
static void open_func (LexState *ls, FuncState *fs) {
|
|
329 |
lua_State *L = ls->L;
|
|
330 |
Proto *f = luaF_newproto(L);
|
|
331 |
fs->f = f;
|
|
332 |
fs->prev = ls->fs; /* linked list of funcstates */
|
|
333 |
fs->ls = ls;
|
|
334 |
fs->L = L;
|
|
335 |
ls->fs = fs;
|
|
336 |
fs->pc = 0;
|
|
337 |
fs->lasttarget = -1;
|
|
338 |
fs->jpc = NO_JUMP;
|
|
339 |
fs->freereg = 0;
|
|
340 |
fs->nk = 0;
|
|
341 |
fs->np = 0;
|
|
342 |
fs->nlocvars = 0;
|
|
343 |
fs->nactvar = 0;
|
|
344 |
fs->bl = NULL;
|
|
345 |
f->source = ls->source;
|
|
346 |
f->maxstacksize = 2; /* registers 0/1 are always valid */
|
|
347 |
fs->h = luaH_new(L, 0, 0);
|
|
348 |
/* anchor table of constants and prototype (to avoid being collected) */
|
|
349 |
sethvalue2s(L, L->top, fs->h);
|
|
350 |
incr_top(L);
|
|
351 |
setptvalue2s(L, L->top, f);
|
|
352 |
incr_top(L);
|
|
353 |
}
|
|
354 |
|
|
355 |
|
|
356 |
static void close_func (LexState *ls) {
|
|
357 |
lua_State *L = ls->L;
|
|
358 |
FuncState *fs = ls->fs;
|
|
359 |
Proto *f = fs->f;
|
|
360 |
removevars(ls, 0);
|
|
361 |
luaK_ret(fs, 0, 0); /* final return */
|
|
362 |
luaM_reallocvector(L, f->code, f->sizecode, fs->pc, Instruction);
|
|
363 |
f->sizecode = fs->pc;
|
|
364 |
luaM_reallocvector(L, f->lineinfo, f->sizelineinfo, fs->pc, int);
|
|
365 |
f->sizelineinfo = fs->pc;
|
|
366 |
luaM_reallocvector(L, f->k, f->sizek, fs->nk, TValue);
|
|
367 |
f->sizek = fs->nk;
|
|
368 |
luaM_reallocvector(L, f->p, f->sizep, fs->np, Proto *);
|
|
369 |
f->sizep = fs->np;
|
|
370 |
luaM_reallocvector(L, f->locvars, f->sizelocvars, fs->nlocvars, LocVar);
|
|
371 |
f->sizelocvars = fs->nlocvars;
|
|
372 |
luaM_reallocvector(L, f->upvalues, f->sizeupvalues, f->nups, TString *);
|
|
373 |
f->sizeupvalues = f->nups;
|
|
374 |
lua_assert(luaG_checkcode(f));
|
|
375 |
lua_assert(fs->bl == NULL);
|
|
376 |
ls->fs = fs->prev;
|
|
377 |
L->top -= 2; /* remove table and prototype from the stack */
|
|
378 |
/* last token read was anchored in defunct function; must reanchor it */
|
|
379 |
if (fs) anchor_token(ls);
|
|
380 |
}
|
|
381 |
|
|
382 |
|
|
383 |
Proto *luaY_parser (lua_State *L, ZIO *z, Mbuffer *buff, const char *name) {
|
|
384 |
struct LexState lexstate;
|
|
385 |
struct FuncState funcstate;
|
|
386 |
lexstate.buff = buff;
|
|
387 |
luaX_setinput(L, &lexstate, z, luaS_new(L, name));
|
|
388 |
open_func(&lexstate, &funcstate);
|
|
389 |
funcstate.f->is_vararg = VARARG_ISVARARG; /* main func. is always vararg */
|
|
390 |
luaX_next(&lexstate); /* read first token */
|
|
391 |
chunk(&lexstate);
|
|
392 |
check(&lexstate, TK_EOS);
|
|
393 |
close_func(&lexstate);
|
|
394 |
lua_assert(funcstate.prev == NULL);
|
|
395 |
lua_assert(funcstate.f->nups == 0);
|
|
396 |
lua_assert(lexstate.fs == NULL);
|
|
397 |
return funcstate.f;
|
|
398 |
}
|
|
399 |
|
|
400 |
|
|
401 |
|
|
402 |
/*============================================================*/
|
|
403 |
/* GRAMMAR RULES */
|
|
404 |
/*============================================================*/
|
|
405 |
|
|
406 |
|
|
407 |
static void field (LexState *ls, expdesc *v) {
|
|
408 |
/* field -> ['.' | ':'] NAME */
|
|
409 |
FuncState *fs = ls->fs;
|
|
410 |
expdesc key;
|
|
411 |
luaK_exp2anyreg(fs, v);
|
|
412 |
luaX_next(ls); /* skip the dot or colon */
|
|
413 |
checkname(ls, &key);
|
|
414 |
luaK_indexed(fs, v, &key);
|
|
415 |
}
|
|
416 |
|
|
417 |
|
|
418 |
static void yindex (LexState *ls, expdesc *v) {
|
|
419 |
/* index -> '[' expr ']' */
|
|
420 |
luaX_next(ls); /* skip the '[' */
|
|
421 |
expr(ls, v);
|
|
422 |
luaK_exp2val(ls->fs, v);
|
|
423 |
checknext(ls, ']');
|
|
424 |
}
|
|
425 |
|
|
426 |
|
|
427 |
/*
|
|
428 |
** {======================================================================
|
|
429 |
** Rules for Constructors
|
|
430 |
** =======================================================================
|
|
431 |
*/
|
|
432 |
|
|
433 |
|
|
434 |
struct ConsControl {
|
|
435 |
expdesc v; /* last list item read */
|
|
436 |
expdesc *t; /* table descriptor */
|
|
437 |
int nh; /* total number of `record' elements */
|
|
438 |
int na; /* total number of array elements */
|
|
439 |
int tostore; /* number of array elements pending to be stored */
|
|
440 |
};
|
|
441 |
|
|
442 |
|
|
443 |
static void recfield (LexState *ls, struct ConsControl *cc) {
|
|
444 |
/* recfield -> (NAME | `['exp1`]') = exp1 */
|
|
445 |
FuncState *fs = ls->fs;
|
|
446 |
int reg = ls->fs->freereg;
|
|
447 |
expdesc key, val;
|
|
448 |
int rkkey;
|
|
449 |
if (ls->t.token == TK_NAME) {
|
|
450 |
luaY_checklimit(fs, cc->nh, MAX_INT, "items in a constructor");
|
|
451 |
checkname(ls, &key);
|
|
452 |
}
|
|
453 |
else /* ls->t.token == '[' */
|
|
454 |
yindex(ls, &key);
|
|
455 |
cc->nh++;
|
|
456 |
checknext(ls, '=');
|
|
457 |
rkkey = luaK_exp2RK(fs, &key);
|
|
458 |
expr(ls, &val);
|
|
459 |
luaK_codeABC(fs, OP_SETTABLE, cc->t->u.s.info, rkkey, luaK_exp2RK(fs, &val));
|
|
460 |
fs->freereg = reg; /* free registers */
|
|
461 |
}
|
|
462 |
|
|
463 |
|
|
464 |
static void closelistfield (FuncState *fs, struct ConsControl *cc) {
|
|
465 |
if (cc->v.k == VVOID) return; /* there is no list item */
|
|
466 |
luaK_exp2nextreg(fs, &cc->v);
|
|
467 |
cc->v.k = VVOID;
|
|
468 |
if (cc->tostore == LFIELDS_PER_FLUSH) {
|
|
469 |
luaK_setlist(fs, cc->t->u.s.info, cc->na, cc->tostore); /* flush */
|
|
470 |
cc->tostore = 0; /* no more items pending */
|
|
471 |
}
|
|
472 |
}
|
|
473 |
|
|
474 |
|
|
475 |
static void lastlistfield (FuncState *fs, struct ConsControl *cc) {
|
|
476 |
if (cc->tostore == 0) return;
|
|
477 |
if (hasmultret(cc->v.k)) {
|
|
478 |
luaK_setmultret(fs, &cc->v);
|
|
479 |
luaK_setlist(fs, cc->t->u.s.info, cc->na, LUA_MULTRET);
|
|
480 |
cc->na--; /* do not count last expression (unknown number of elements) */
|
|
481 |
}
|
|
482 |
else {
|
|
483 |
if (cc->v.k != VVOID)
|
|
484 |
luaK_exp2nextreg(fs, &cc->v);
|
|
485 |
luaK_setlist(fs, cc->t->u.s.info, cc->na, cc->tostore);
|
|
486 |
}
|
|
487 |
}
|
|
488 |
|
|
489 |
|
|
490 |
static void listfield (LexState *ls, struct ConsControl *cc) {
|
|
491 |
expr(ls, &cc->v);
|
|
492 |
luaY_checklimit(ls->fs, cc->na, MAX_INT, "items in a constructor");
|
|
493 |
cc->na++;
|
|
494 |
cc->tostore++;
|
|
495 |
}
|
|
496 |
|
|
497 |
|
|
498 |
static void constructor (LexState *ls, expdesc *t) {
|
|
499 |
/* constructor -> ?? */
|
|
500 |
FuncState *fs = ls->fs;
|
|
501 |
int line = ls->linenumber;
|
|
502 |
int pc = luaK_codeABC(fs, OP_NEWTABLE, 0, 0, 0);
|
|
503 |
struct ConsControl cc;
|
|
504 |
cc.na = cc.nh = cc.tostore = 0;
|
|
505 |
cc.t = t;
|
|
506 |
init_exp(t, VRELOCABLE, pc);
|
|
507 |
init_exp(&cc.v, VVOID, 0); /* no value (yet) */
|
|
508 |
luaK_exp2nextreg(ls->fs, t); /* fix it at stack top (for gc) */
|
|
509 |
checknext(ls, '{');
|
|
510 |
do {
|
|
511 |
lua_assert(cc.v.k == VVOID || cc.tostore > 0);
|
|
512 |
if (ls->t.token == '}') break;
|
|
513 |
closelistfield(fs, &cc);
|
|
514 |
switch(ls->t.token) {
|
|
515 |
case TK_NAME: { /* may be listfields or recfields */
|
|
516 |
luaX_lookahead(ls);
|
|
517 |
if (ls->lookahead.token != '=') /* expression? */
|
|
518 |
listfield(ls, &cc);
|
|
519 |
else
|
|
520 |
recfield(ls, &cc);
|
|
521 |
break;
|
|
522 |
}
|
|
523 |
case '[': { /* constructor_item -> recfield */
|
|
524 |
recfield(ls, &cc);
|
|
525 |
break;
|
|
526 |
}
|
|
527 |
default: { /* constructor_part -> listfield */
|
|
528 |
listfield(ls, &cc);
|
|
529 |
break;
|
|
530 |
}
|
|
531 |
}
|
|
532 |
} while (testnext(ls, ',') || testnext(ls, ';'));
|
|
533 |
check_match(ls, '}', '{', line);
|
|
534 |
lastlistfield(fs, &cc);
|
|
535 |
SETARG_B(fs->f->code[pc], luaO_int2fb(cc.na)); /* set initial array size */
|
|
536 |
SETARG_C(fs->f->code[pc], luaO_int2fb(cc.nh)); /* set initial table size */
|
|
537 |
}
|
|
538 |
|
|
539 |
/* }====================================================================== */
|
|
540 |
|
|
541 |
|
|
542 |
|
|
543 |
static void parlist (LexState *ls) {
|
|
544 |
/* parlist -> [ param { `,' param } ] */
|
|
545 |
FuncState *fs = ls->fs;
|
|
546 |
Proto *f = fs->f;
|
|
547 |
int nparams = 0;
|
|
548 |
f->is_vararg = 0;
|
|
549 |
if (ls->t.token != ')') { /* is `parlist' not empty? */
|
|
550 |
do {
|
|
551 |
switch (ls->t.token) {
|
|
552 |
case TK_NAME: { /* param -> NAME */
|
|
553 |
new_localvar(ls, str_checkname(ls), nparams++);
|
|
554 |
break;
|
|
555 |
}
|
|
556 |
case TK_DOTS: { /* param -> `...' */
|
|
557 |
luaX_next(ls);
|
|
558 |
#if defined(LUA_COMPAT_VARARG)
|
|
559 |
/* use `arg' as default name */
|
|
560 |
new_localvarliteral(ls, "arg", nparams++);
|
|
561 |
f->is_vararg = VARARG_HASARG | VARARG_NEEDSARG;
|
|
562 |
#endif
|
|
563 |
f->is_vararg |= VARARG_ISVARARG;
|
|
564 |
break;
|
|
565 |
}
|
|
566 |
default: luaX_syntaxerror(ls, "<name> or " LUA_QL("...") " expected");
|
|
567 |
}
|
|
568 |
} while (!f->is_vararg && testnext(ls, ','));
|
|
569 |
}
|
|
570 |
adjustlocalvars(ls, nparams);
|
|
571 |
f->numparams = cast_byte(fs->nactvar - (f->is_vararg & VARARG_HASARG));
|
|
572 |
luaK_reserveregs(fs, fs->nactvar); /* reserve register for parameters */
|
|
573 |
}
|
|
574 |
|
|
575 |
|
|
576 |
static void body (LexState *ls, expdesc *e, int needself, int line) {
|
|
577 |
/* body -> `(' parlist `)' chunk END */
|
|
578 |
FuncState new_fs;
|
|
579 |
open_func(ls, &new_fs);
|
|
580 |
new_fs.f->linedefined = line;
|
|
581 |
checknext(ls, '(');
|
|
582 |
if (needself) {
|
|
583 |
new_localvarliteral(ls, "self", 0);
|
|
584 |
adjustlocalvars(ls, 1);
|
|
585 |
}
|
|
586 |
parlist(ls);
|
|
587 |
checknext(ls, ')');
|
|
588 |
chunk(ls);
|
|
589 |
new_fs.f->lastlinedefined = ls->linenumber;
|
|
590 |
check_match(ls, TK_END, TK_FUNCTION, line);
|
|
591 |
close_func(ls);
|
|
592 |
pushclosure(ls, &new_fs, e);
|
|
593 |
}
|
|
594 |
|
|
595 |
|
|
596 |
static int explist1 (LexState *ls, expdesc *v) {
|
|
597 |
/* explist1 -> expr { `,' expr } */
|
|
598 |
int n = 1; /* at least one expression */
|
|
599 |
expr(ls, v);
|
|
600 |
while (testnext(ls, ',')) {
|
|
601 |
luaK_exp2nextreg(ls->fs, v);
|
|
602 |
expr(ls, v);
|
|
603 |
n++;
|
|
604 |
}
|
|
605 |
return n;
|
|
606 |
}
|
|
607 |
|
|
608 |
|
|
609 |
static void funcargs (LexState *ls, expdesc *f) {
|
|
610 |
FuncState *fs = ls->fs;
|
|
611 |
expdesc args;
|
|
612 |
int base, nparams;
|
|
613 |
int line = ls->linenumber;
|
|
614 |
switch (ls->t.token) {
|
|
615 |
case '(': { /* funcargs -> `(' [ explist1 ] `)' */
|
|
616 |
if (line != ls->lastline)
|
|
617 |
luaX_syntaxerror(ls,"ambiguous syntax (function call x new statement)");
|
|
618 |
luaX_next(ls);
|
|
619 |
if (ls->t.token == ')') /* arg list is empty? */
|
|
620 |
args.k = VVOID;
|
|
621 |
else {
|
|
622 |
explist1(ls, &args);
|
|
623 |
luaK_setmultret(fs, &args);
|
|
624 |
}
|
|
625 |
check_match(ls, ')', '(', line);
|
|
626 |
break;
|
|
627 |
}
|
|
628 |
case '{': { /* funcargs -> constructor */
|
|
629 |
constructor(ls, &args);
|
|
630 |
break;
|
|
631 |
}
|
|
632 |
case TK_STRING: { /* funcargs -> STRING */
|
|
633 |
codestring(ls, &args, ls->t.seminfo.ts);
|
|
634 |
luaX_next(ls); /* must use `seminfo' before `next' */
|
|
635 |
break;
|
|
636 |
}
|
|
637 |
default: {
|
|
638 |
luaX_syntaxerror(ls, "function arguments expected");
|
|
639 |
return;
|
|
640 |
}
|
|
641 |
}
|
|
642 |
lua_assert(f->k == VNONRELOC);
|
|
643 |
base = f->u.s.info; /* base register for call */
|
|
644 |
if (hasmultret(args.k))
|
|
645 |
nparams = LUA_MULTRET; /* open call */
|
|
646 |
else {
|
|
647 |
if (args.k != VVOID)
|
|
648 |
luaK_exp2nextreg(fs, &args); /* close last argument */
|
|
649 |
nparams = fs->freereg - (base+1);
|
|
650 |
}
|
|
651 |
init_exp(f, VCALL, luaK_codeABC(fs, OP_CALL, base, nparams+1, 2));
|
|
652 |
luaK_fixline(fs, line);
|
|
653 |
fs->freereg = base+1; /* call remove function and arguments and leaves
|
|
654 |
(unless changed) one result */
|
|
655 |
}
|
|
656 |
|
|
657 |
|
|
658 |
|
|
659 |
|
|
660 |
/*
|
|
661 |
** {======================================================================
|
|
662 |
** Expression parsing
|
|
663 |
** =======================================================================
|
|
664 |
*/
|
|
665 |
|
|
666 |
|
|
667 |
static void prefixexp (LexState *ls, expdesc *v) {
|
|
668 |
/* prefixexp -> NAME | '(' expr ')' */
|
|
669 |
switch (ls->t.token) {
|
|
670 |
case '(': {
|
|
671 |
int line = ls->linenumber;
|
|
672 |
luaX_next(ls);
|
|
673 |
expr(ls, v);
|
|
674 |
check_match(ls, ')', '(', line);
|
|
675 |
luaK_dischargevars(ls->fs, v);
|
|
676 |
return;
|
|
677 |
}
|
|
678 |
case TK_NAME: {
|
|
679 |
singlevar(ls, v);
|
|
680 |
return;
|
|
681 |
}
|
|
682 |
default: {
|
|
683 |
luaX_syntaxerror(ls, "unexpected symbol");
|
|
684 |
return;
|
|
685 |
}
|
|
686 |
}
|
|
687 |
}
|
|
688 |
|
|
689 |
|
|
690 |
static void primaryexp (LexState *ls, expdesc *v) {
|
|
691 |
/* primaryexp ->
|
|
692 |
prefixexp { `.' NAME | `[' exp `]' | `:' NAME funcargs | funcargs } */
|
|
693 |
FuncState *fs = ls->fs;
|
|
694 |
prefixexp(ls, v);
|
|
695 |
for (;;) {
|
|
696 |
switch (ls->t.token) {
|
|
697 |
case '.': { /* field */
|
|
698 |
field(ls, v);
|
|
699 |
break;
|
|
700 |
}
|
|
701 |
case '[': { /* `[' exp1 `]' */
|
|
702 |
expdesc key;
|
|
703 |
luaK_exp2anyreg(fs, v);
|
|
704 |
yindex(ls, &key);
|
|
705 |
luaK_indexed(fs, v, &key);
|
|
706 |
break;
|
|
707 |
}
|
|
708 |
case ':': { /* `:' NAME funcargs */
|
|
709 |
expdesc key;
|
|
710 |
luaX_next(ls);
|
|
711 |
checkname(ls, &key);
|
|
712 |
luaK_self(fs, v, &key);
|
|
713 |
funcargs(ls, v);
|
|
714 |
break;
|
|
715 |
}
|
|
716 |
case '(': case TK_STRING: case '{': { /* funcargs */
|
|
717 |
luaK_exp2nextreg(fs, v);
|
|
718 |
funcargs(ls, v);
|
|
719 |
break;
|
|
720 |
}
|
|
721 |
default: return;
|
|
722 |
}
|
|
723 |
}
|
|
724 |
}
|
|
725 |
|
|
726 |
|
|
727 |
static void simpleexp (LexState *ls, expdesc *v) {
|
|
728 |
/* simpleexp -> NUMBER | STRING | NIL | true | false | ... |
|
|
729 |
constructor | FUNCTION body | primaryexp */
|
|
730 |
switch (ls->t.token) {
|
|
731 |
case TK_NUMBER: {
|
|
732 |
init_exp(v, VKNUM, 0);
|
|
733 |
v->u.nval = ls->t.seminfo.r;
|
|
734 |
break;
|
|
735 |
}
|
|
736 |
case TK_STRING: {
|
|
737 |
codestring(ls, v, ls->t.seminfo.ts);
|
|
738 |
break;
|
|
739 |
}
|
|
740 |
case TK_NIL: {
|
|
741 |
init_exp(v, VNIL, 0);
|
|
742 |
break;
|
|
743 |
}
|
|
744 |
case TK_TRUE: {
|
|
745 |
init_exp(v, VTRUE, 0);
|
|
746 |
break;
|
|
747 |
}
|
|
748 |
case TK_FALSE: {
|
|
749 |
init_exp(v, VFALSE, 0);
|
|
750 |
break;
|
|
751 |
}
|
|
752 |
case TK_DOTS: { /* vararg */
|
|
753 |
FuncState *fs = ls->fs;
|
|
754 |
check_condition(ls, fs->f->is_vararg,
|
|
755 |
"cannot use " LUA_QL("...") " outside a vararg function");
|
|
756 |
fs->f->is_vararg &= ~VARARG_NEEDSARG; /* don't need 'arg' */
|
|
757 |
init_exp(v, VVARARG, luaK_codeABC(fs, OP_VARARG, 0, 1, 0));
|
|
758 |
break;
|
|
759 |
}
|
|
760 |
case '{': { /* constructor */
|
|
761 |
constructor(ls, v);
|
|
762 |
return;
|
|
763 |
}
|
|
764 |
case TK_FUNCTION: {
|
|
765 |
luaX_next(ls);
|
|
766 |
body(ls, v, 0, ls->linenumber);
|
|
767 |
return;
|
|
768 |
}
|
|
769 |
default: {
|
|
770 |
primaryexp(ls, v);
|
|
771 |
return;
|
|
772 |
}
|
|
773 |
}
|
|
774 |
luaX_next(ls);
|
|
775 |
}
|
|
776 |
|
|
777 |
|
|
778 |
static UnOpr getunopr (int op) {
|
|
779 |
switch (op) {
|
|
780 |
case TK_NOT: return OPR_NOT;
|
|
781 |
case '-': return OPR_MINUS;
|
|
782 |
case '#': return OPR_LEN;
|
|
783 |
default: return OPR_NOUNOPR;
|
|
784 |
}
|
|
785 |
}
|
|
786 |
|
|
787 |
|
|
788 |
static BinOpr getbinopr (int op) {
|
|
789 |
switch (op) {
|
|
790 |
case '+': return OPR_ADD;
|
|
791 |
case '-': return OPR_SUB;
|
|
792 |
case '*': return OPR_MUL;
|
|
793 |
case '/': return OPR_DIV;
|
|
794 |
case '%': return OPR_MOD;
|
|
795 |
case '^': return OPR_POW;
|
|
796 |
case TK_CONCAT: return OPR_CONCAT;
|
|
797 |
case TK_NE: return OPR_NE;
|
|
798 |
case TK_EQ: return OPR_EQ;
|
|
799 |
case '<': return OPR_LT;
|
|
800 |
case TK_LE: return OPR_LE;
|
|
801 |
case '>': return OPR_GT;
|
|
802 |
case TK_GE: return OPR_GE;
|
|
803 |
case TK_AND: return OPR_AND;
|
|
804 |
case TK_OR: return OPR_OR;
|
|
805 |
default: return OPR_NOBINOPR;
|
|
806 |
}
|
|
807 |
}
|
|
808 |
|
|
809 |
|
|
810 |
static const struct {
|
|
811 |
lu_byte left; /* left priority for each binary operator */
|
|
812 |
lu_byte right; /* right priority */
|
|
813 |
} priority[] = { /* ORDER OPR */
|
|
814 |
{6, 6}, {6, 6}, {7, 7}, {7, 7}, {7, 7}, /* `+' `-' `/' `%' */
|
|
815 |
{10, 9}, {5, 4}, /* power and concat (right associative) */
|
|
816 |
{3, 3}, {3, 3}, /* equality and inequality */
|
|
817 |
{3, 3}, {3, 3}, {3, 3}, {3, 3}, /* order */
|
|
818 |
{2, 2}, {1, 1} /* logical (and/or) */
|
|
819 |
};
|
|
820 |
|
10017
|
821 |
#define UNARY_PRIORITY 8 /* priority for unary operators */
|
2812
|
822 |
|
|
823 |
|
|
824 |
/*
|
|
825 |
** subexpr -> (simpleexp | unop subexpr) { binop subexpr }
|
|
826 |
** where `binop' is any binary operator with a priority higher than `limit'
|
|
827 |
*/
|
|
828 |
static BinOpr subexpr (LexState *ls, expdesc *v, unsigned int limit) {
|
|
829 |
BinOpr op;
|
|
830 |
UnOpr uop;
|
|
831 |
enterlevel(ls);
|
|
832 |
uop = getunopr(ls->t.token);
|
|
833 |
if (uop != OPR_NOUNOPR) {
|
|
834 |
luaX_next(ls);
|
|
835 |
subexpr(ls, v, UNARY_PRIORITY);
|
|
836 |
luaK_prefix(ls->fs, uop, v);
|
|
837 |
}
|
|
838 |
else simpleexp(ls, v);
|
|
839 |
/* expand while operators have priorities higher than `limit' */
|
|
840 |
op = getbinopr(ls->t.token);
|
|
841 |
while (op != OPR_NOBINOPR && priority[op].left > limit) {
|
|
842 |
expdesc v2;
|
|
843 |
BinOpr nextop;
|
|
844 |
luaX_next(ls);
|
|
845 |
luaK_infix(ls->fs, op, v);
|
|
846 |
/* read sub-expression with higher priority */
|
|
847 |
nextop = subexpr(ls, &v2, priority[op].right);
|
|
848 |
luaK_posfix(ls->fs, op, v, &v2);
|
|
849 |
op = nextop;
|
|
850 |
}
|
|
851 |
leavelevel(ls);
|
|
852 |
return op; /* return first untreated operator */
|
|
853 |
}
|
|
854 |
|
|
855 |
|
|
856 |
static void expr (LexState *ls, expdesc *v) {
|
|
857 |
subexpr(ls, v, 0);
|
|
858 |
}
|
|
859 |
|
|
860 |
/* }==================================================================== */
|
|
861 |
|
|
862 |
|
|
863 |
|
|
864 |
/*
|
|
865 |
** {======================================================================
|
|
866 |
** Rules for Statements
|
|
867 |
** =======================================================================
|
|
868 |
*/
|
|
869 |
|
|
870 |
|
|
871 |
static int block_follow (int token) {
|
|
872 |
switch (token) {
|
|
873 |
case TK_ELSE: case TK_ELSEIF: case TK_END:
|
|
874 |
case TK_UNTIL: case TK_EOS:
|
|
875 |
return 1;
|
|
876 |
default: return 0;
|
|
877 |
}
|
|
878 |
}
|
|
879 |
|
|
880 |
|
|
881 |
static void block (LexState *ls) {
|
|
882 |
/* block -> chunk */
|
|
883 |
FuncState *fs = ls->fs;
|
|
884 |
BlockCnt bl;
|
|
885 |
enterblock(fs, &bl, 0);
|
|
886 |
chunk(ls);
|
|
887 |
lua_assert(bl.breaklist == NO_JUMP);
|
|
888 |
leaveblock(fs);
|
|
889 |
}
|
|
890 |
|
|
891 |
|
|
892 |
/*
|
|
893 |
** structure to chain all variables in the left-hand side of an
|
|
894 |
** assignment
|
|
895 |
*/
|
|
896 |
struct LHS_assign {
|
|
897 |
struct LHS_assign *prev;
|
|
898 |
expdesc v; /* variable (global, local, upvalue, or indexed) */
|
|
899 |
};
|
|
900 |
|
|
901 |
|
|
902 |
/*
|
|
903 |
** check whether, in an assignment to a local variable, the local variable
|
|
904 |
** is needed in a previous assignment (to a table). If so, save original
|
|
905 |
** local value in a safe place and use this safe copy in the previous
|
|
906 |
** assignment.
|
|
907 |
*/
|
|
908 |
static void check_conflict (LexState *ls, struct LHS_assign *lh, expdesc *v) {
|
|
909 |
FuncState *fs = ls->fs;
|
|
910 |
int extra = fs->freereg; /* eventual position to save local variable */
|
|
911 |
int conflict = 0;
|
|
912 |
for (; lh; lh = lh->prev) {
|
|
913 |
if (lh->v.k == VINDEXED) {
|
|
914 |
if (lh->v.u.s.info == v->u.s.info) { /* conflict? */
|
|
915 |
conflict = 1;
|
|
916 |
lh->v.u.s.info = extra; /* previous assignment will use safe copy */
|
|
917 |
}
|
|
918 |
if (lh->v.u.s.aux == v->u.s.info) { /* conflict? */
|
|
919 |
conflict = 1;
|
|
920 |
lh->v.u.s.aux = extra; /* previous assignment will use safe copy */
|
|
921 |
}
|
|
922 |
}
|
|
923 |
}
|
|
924 |
if (conflict) {
|
|
925 |
luaK_codeABC(fs, OP_MOVE, fs->freereg, v->u.s.info, 0); /* make copy */
|
|
926 |
luaK_reserveregs(fs, 1);
|
|
927 |
}
|
|
928 |
}
|
|
929 |
|
|
930 |
|
|
931 |
static void assignment (LexState *ls, struct LHS_assign *lh, int nvars) {
|
|
932 |
expdesc e;
|
|
933 |
check_condition(ls, VLOCAL <= lh->v.k && lh->v.k <= VINDEXED,
|
|
934 |
"syntax error");
|
|
935 |
if (testnext(ls, ',')) { /* assignment -> `,' primaryexp assignment */
|
|
936 |
struct LHS_assign nv;
|
|
937 |
nv.prev = lh;
|
|
938 |
primaryexp(ls, &nv.v);
|
|
939 |
if (nv.v.k == VLOCAL)
|
|
940 |
check_conflict(ls, lh, &nv.v);
|
|
941 |
luaY_checklimit(ls->fs, nvars, LUAI_MAXCCALLS - ls->L->nCcalls,
|
|
942 |
"variables in assignment");
|
|
943 |
assignment(ls, &nv, nvars+1);
|
|
944 |
}
|
|
945 |
else { /* assignment -> `=' explist1 */
|
|
946 |
int nexps;
|
|
947 |
checknext(ls, '=');
|
|
948 |
nexps = explist1(ls, &e);
|
|
949 |
if (nexps != nvars) {
|
|
950 |
adjust_assign(ls, nvars, nexps, &e);
|
|
951 |
if (nexps > nvars)
|
|
952 |
ls->fs->freereg -= nexps - nvars; /* remove extra values */
|
|
953 |
}
|
|
954 |
else {
|
|
955 |
luaK_setoneret(ls->fs, &e); /* close last expression */
|
|
956 |
luaK_storevar(ls->fs, &lh->v, &e);
|
|
957 |
return; /* avoid default */
|
|
958 |
}
|
|
959 |
}
|
|
960 |
init_exp(&e, VNONRELOC, ls->fs->freereg-1); /* default assignment */
|
|
961 |
luaK_storevar(ls->fs, &lh->v, &e);
|
|
962 |
}
|
|
963 |
|
|
964 |
|
|
965 |
static int cond (LexState *ls) {
|
|
966 |
/* cond -> exp */
|
|
967 |
expdesc v;
|
|
968 |
expr(ls, &v); /* read condition */
|
|
969 |
if (v.k == VNIL) v.k = VFALSE; /* `falses' are all equal here */
|
|
970 |
luaK_goiftrue(ls->fs, &v);
|
|
971 |
return v.f;
|
|
972 |
}
|
|
973 |
|
|
974 |
|
|
975 |
static void breakstat (LexState *ls) {
|
|
976 |
FuncState *fs = ls->fs;
|
|
977 |
BlockCnt *bl = fs->bl;
|
|
978 |
int upval = 0;
|
|
979 |
while (bl && !bl->isbreakable) {
|
|
980 |
upval |= bl->upval;
|
|
981 |
bl = bl->previous;
|
|
982 |
}
|
|
983 |
if (!bl)
|
|
984 |
luaX_syntaxerror(ls, "no loop to break");
|
|
985 |
if (upval)
|
|
986 |
luaK_codeABC(fs, OP_CLOSE, bl->nactvar, 0, 0);
|
|
987 |
luaK_concat(fs, &bl->breaklist, luaK_jump(fs));
|
|
988 |
}
|
|
989 |
|
|
990 |
|
|
991 |
static void whilestat (LexState *ls, int line) {
|
|
992 |
/* whilestat -> WHILE cond DO block END */
|
|
993 |
FuncState *fs = ls->fs;
|
|
994 |
int whileinit;
|
|
995 |
int condexit;
|
|
996 |
BlockCnt bl;
|
|
997 |
luaX_next(ls); /* skip WHILE */
|
|
998 |
whileinit = luaK_getlabel(fs);
|
|
999 |
condexit = cond(ls);
|
|
1000 |
enterblock(fs, &bl, 1);
|
|
1001 |
checknext(ls, TK_DO);
|
|
1002 |
block(ls);
|
|
1003 |
luaK_patchlist(fs, luaK_jump(fs), whileinit);
|
|
1004 |
check_match(ls, TK_END, TK_WHILE, line);
|
|
1005 |
leaveblock(fs);
|
|
1006 |
luaK_patchtohere(fs, condexit); /* false conditions finish the loop */
|
|
1007 |
}
|
|
1008 |
|
|
1009 |
|
|
1010 |
static void repeatstat (LexState *ls, int line) {
|
|
1011 |
/* repeatstat -> REPEAT block UNTIL cond */
|
|
1012 |
int condexit;
|
|
1013 |
FuncState *fs = ls->fs;
|
|
1014 |
int repeat_init = luaK_getlabel(fs);
|
|
1015 |
BlockCnt bl1, bl2;
|
|
1016 |
enterblock(fs, &bl1, 1); /* loop block */
|
|
1017 |
enterblock(fs, &bl2, 0); /* scope block */
|
|
1018 |
luaX_next(ls); /* skip REPEAT */
|
|
1019 |
chunk(ls);
|
|
1020 |
check_match(ls, TK_UNTIL, TK_REPEAT, line);
|
|
1021 |
condexit = cond(ls); /* read condition (inside scope block) */
|
|
1022 |
if (!bl2.upval) { /* no upvalues? */
|
|
1023 |
leaveblock(fs); /* finish scope */
|
|
1024 |
luaK_patchlist(ls->fs, condexit, repeat_init); /* close the loop */
|
|
1025 |
}
|
|
1026 |
else { /* complete semantics when there are upvalues */
|
|
1027 |
breakstat(ls); /* if condition then break */
|
|
1028 |
luaK_patchtohere(ls->fs, condexit); /* else... */
|
|
1029 |
leaveblock(fs); /* finish scope... */
|
|
1030 |
luaK_patchlist(ls->fs, luaK_jump(fs), repeat_init); /* and repeat */
|
|
1031 |
}
|
|
1032 |
leaveblock(fs); /* finish loop */
|
|
1033 |
}
|
|
1034 |
|
|
1035 |
|
|
1036 |
static int exp1 (LexState *ls) {
|
|
1037 |
expdesc e;
|
|
1038 |
int k;
|
|
1039 |
expr(ls, &e);
|
|
1040 |
k = e.k;
|
|
1041 |
luaK_exp2nextreg(ls->fs, &e);
|
|
1042 |
return k;
|
|
1043 |
}
|
|
1044 |
|
|
1045 |
|
|
1046 |
static void forbody (LexState *ls, int base, int line, int nvars, int isnum) {
|
|
1047 |
/* forbody -> DO block */
|
|
1048 |
BlockCnt bl;
|
|
1049 |
FuncState *fs = ls->fs;
|
|
1050 |
int prep, endfor;
|
|
1051 |
adjustlocalvars(ls, 3); /* control variables */
|
|
1052 |
checknext(ls, TK_DO);
|
|
1053 |
prep = isnum ? luaK_codeAsBx(fs, OP_FORPREP, base, NO_JUMP) : luaK_jump(fs);
|
|
1054 |
enterblock(fs, &bl, 0); /* scope for declared variables */
|
|
1055 |
adjustlocalvars(ls, nvars);
|
|
1056 |
luaK_reserveregs(fs, nvars);
|
|
1057 |
block(ls);
|
|
1058 |
leaveblock(fs); /* end of scope for declared variables */
|
|
1059 |
luaK_patchtohere(fs, prep);
|
|
1060 |
endfor = (isnum) ? luaK_codeAsBx(fs, OP_FORLOOP, base, NO_JUMP) :
|
|
1061 |
luaK_codeABC(fs, OP_TFORLOOP, base, 0, nvars);
|
|
1062 |
luaK_fixline(fs, line); /* pretend that `OP_FOR' starts the loop */
|
|
1063 |
luaK_patchlist(fs, (isnum ? endfor : luaK_jump(fs)), prep + 1);
|
|
1064 |
}
|
|
1065 |
|
|
1066 |
|
|
1067 |
static void fornum (LexState *ls, TString *varname, int line) {
|
|
1068 |
/* fornum -> NAME = exp1,exp1[,exp1] forbody */
|
|
1069 |
FuncState *fs = ls->fs;
|
|
1070 |
int base = fs->freereg;
|
|
1071 |
new_localvarliteral(ls, "(for index)", 0);
|
|
1072 |
new_localvarliteral(ls, "(for limit)", 1);
|
|
1073 |
new_localvarliteral(ls, "(for step)", 2);
|
|
1074 |
new_localvar(ls, varname, 3);
|
|
1075 |
checknext(ls, '=');
|
|
1076 |
exp1(ls); /* initial value */
|
|
1077 |
checknext(ls, ',');
|
|
1078 |
exp1(ls); /* limit */
|
|
1079 |
if (testnext(ls, ','))
|
|
1080 |
exp1(ls); /* optional step */
|
|
1081 |
else { /* default step = 1 */
|
|
1082 |
luaK_codeABx(fs, OP_LOADK, fs->freereg, luaK_numberK(fs, 1));
|
|
1083 |
luaK_reserveregs(fs, 1);
|
|
1084 |
}
|
|
1085 |
forbody(ls, base, line, 1, 1);
|
|
1086 |
}
|
|
1087 |
|
|
1088 |
|
|
1089 |
static void forlist (LexState *ls, TString *indexname) {
|
|
1090 |
/* forlist -> NAME {,NAME} IN explist1 forbody */
|
|
1091 |
FuncState *fs = ls->fs;
|
|
1092 |
expdesc e;
|
|
1093 |
int nvars = 0;
|
|
1094 |
int line;
|
|
1095 |
int base = fs->freereg;
|
|
1096 |
/* create control variables */
|
|
1097 |
new_localvarliteral(ls, "(for generator)", nvars++);
|
|
1098 |
new_localvarliteral(ls, "(for state)", nvars++);
|
|
1099 |
new_localvarliteral(ls, "(for control)", nvars++);
|
|
1100 |
/* create declared variables */
|
|
1101 |
new_localvar(ls, indexname, nvars++);
|
|
1102 |
while (testnext(ls, ','))
|
|
1103 |
new_localvar(ls, str_checkname(ls), nvars++);
|
|
1104 |
checknext(ls, TK_IN);
|
|
1105 |
line = ls->linenumber;
|
|
1106 |
adjust_assign(ls, 3, explist1(ls, &e), &e);
|
|
1107 |
luaK_checkstack(fs, 3); /* extra space to call generator */
|
|
1108 |
forbody(ls, base, line, nvars - 3, 0);
|
|
1109 |
}
|
|
1110 |
|
|
1111 |
|
|
1112 |
static void forstat (LexState *ls, int line) {
|
|
1113 |
/* forstat -> FOR (fornum | forlist) END */
|
|
1114 |
FuncState *fs = ls->fs;
|
|
1115 |
TString *varname;
|
|
1116 |
BlockCnt bl;
|
|
1117 |
enterblock(fs, &bl, 1); /* scope for loop and control variables */
|
|
1118 |
luaX_next(ls); /* skip `for' */
|
|
1119 |
varname = str_checkname(ls); /* first variable name */
|
|
1120 |
switch (ls->t.token) {
|
|
1121 |
case '=': fornum(ls, varname, line); break;
|
|
1122 |
case ',': case TK_IN: forlist(ls, varname); break;
|
|
1123 |
default: luaX_syntaxerror(ls, LUA_QL("=") " or " LUA_QL("in") " expected");
|
|
1124 |
}
|
|
1125 |
check_match(ls, TK_END, TK_FOR, line);
|
|
1126 |
leaveblock(fs); /* loop scope (`break' jumps to this point) */
|
|
1127 |
}
|
|
1128 |
|
|
1129 |
|
|
1130 |
static int test_then_block (LexState *ls) {
|
|
1131 |
/* test_then_block -> [IF | ELSEIF] cond THEN block */
|
|
1132 |
int condexit;
|
|
1133 |
luaX_next(ls); /* skip IF or ELSEIF */
|
|
1134 |
condexit = cond(ls);
|
|
1135 |
checknext(ls, TK_THEN);
|
|
1136 |
block(ls); /* `then' part */
|
|
1137 |
return condexit;
|
|
1138 |
}
|
|
1139 |
|
|
1140 |
|
|
1141 |
static void ifstat (LexState *ls, int line) {
|
|
1142 |
/* ifstat -> IF cond THEN block {ELSEIF cond THEN block} [ELSE block] END */
|
|
1143 |
FuncState *fs = ls->fs;
|
|
1144 |
int flist;
|
|
1145 |
int escapelist = NO_JUMP;
|
|
1146 |
flist = test_then_block(ls); /* IF cond THEN block */
|
|
1147 |
while (ls->t.token == TK_ELSEIF) {
|
|
1148 |
luaK_concat(fs, &escapelist, luaK_jump(fs));
|
|
1149 |
luaK_patchtohere(fs, flist);
|
|
1150 |
flist = test_then_block(ls); /* ELSEIF cond THEN block */
|
|
1151 |
}
|
|
1152 |
if (ls->t.token == TK_ELSE) {
|
|
1153 |
luaK_concat(fs, &escapelist, luaK_jump(fs));
|
|
1154 |
luaK_patchtohere(fs, flist);
|
|
1155 |
luaX_next(ls); /* skip ELSE (after patch, for correct line info) */
|
|
1156 |
block(ls); /* `else' part */
|
|
1157 |
}
|
|
1158 |
else
|
|
1159 |
luaK_concat(fs, &escapelist, flist);
|
|
1160 |
luaK_patchtohere(fs, escapelist);
|
|
1161 |
check_match(ls, TK_END, TK_IF, line);
|
|
1162 |
}
|
|
1163 |
|
|
1164 |
|
|
1165 |
static void localfunc (LexState *ls) {
|
|
1166 |
expdesc v, b;
|
|
1167 |
FuncState *fs = ls->fs;
|
|
1168 |
new_localvar(ls, str_checkname(ls), 0);
|
|
1169 |
init_exp(&v, VLOCAL, fs->freereg);
|
|
1170 |
luaK_reserveregs(fs, 1);
|
|
1171 |
adjustlocalvars(ls, 1);
|
|
1172 |
body(ls, &b, 0, ls->linenumber);
|
|
1173 |
luaK_storevar(fs, &v, &b);
|
|
1174 |
/* debug information will only see the variable after this point! */
|
|
1175 |
getlocvar(fs, fs->nactvar - 1).startpc = fs->pc;
|
|
1176 |
}
|
|
1177 |
|
|
1178 |
|
|
1179 |
static void localstat (LexState *ls) {
|
|
1180 |
/* stat -> LOCAL NAME {`,' NAME} [`=' explist1] */
|
|
1181 |
int nvars = 0;
|
|
1182 |
int nexps;
|
|
1183 |
expdesc e;
|
|
1184 |
do {
|
|
1185 |
new_localvar(ls, str_checkname(ls), nvars++);
|
|
1186 |
} while (testnext(ls, ','));
|
|
1187 |
if (testnext(ls, '='))
|
|
1188 |
nexps = explist1(ls, &e);
|
|
1189 |
else {
|
|
1190 |
e.k = VVOID;
|
|
1191 |
nexps = 0;
|
|
1192 |
}
|
|
1193 |
adjust_assign(ls, nvars, nexps, &e);
|
|
1194 |
adjustlocalvars(ls, nvars);
|
|
1195 |
}
|
|
1196 |
|
|
1197 |
|
|
1198 |
static int funcname (LexState *ls, expdesc *v) {
|
|
1199 |
/* funcname -> NAME {field} [`:' NAME] */
|
|
1200 |
int needself = 0;
|
|
1201 |
singlevar(ls, v);
|
|
1202 |
while (ls->t.token == '.')
|
|
1203 |
field(ls, v);
|
|
1204 |
if (ls->t.token == ':') {
|
|
1205 |
needself = 1;
|
|
1206 |
field(ls, v);
|
|
1207 |
}
|
|
1208 |
return needself;
|
|
1209 |
}
|
|
1210 |
|
|
1211 |
|
|
1212 |
static void funcstat (LexState *ls, int line) {
|
|
1213 |
/* funcstat -> FUNCTION funcname body */
|
|
1214 |
int needself;
|
|
1215 |
expdesc v, b;
|
|
1216 |
luaX_next(ls); /* skip FUNCTION */
|
|
1217 |
needself = funcname(ls, &v);
|
|
1218 |
body(ls, &b, needself, line);
|
|
1219 |
luaK_storevar(ls->fs, &v, &b);
|
|
1220 |
luaK_fixline(ls->fs, line); /* definition `happens' in the first line */
|
|
1221 |
}
|
|
1222 |
|
|
1223 |
|
|
1224 |
static void exprstat (LexState *ls) {
|
|
1225 |
/* stat -> func | assignment */
|
|
1226 |
FuncState *fs = ls->fs;
|
|
1227 |
struct LHS_assign v;
|
|
1228 |
primaryexp(ls, &v.v);
|
|
1229 |
if (v.v.k == VCALL) /* stat -> func */
|
|
1230 |
SETARG_C(getcode(fs, &v.v), 1); /* call statement uses no results */
|
|
1231 |
else { /* stat -> assignment */
|
|
1232 |
v.prev = NULL;
|
|
1233 |
assignment(ls, &v, 1);
|
|
1234 |
}
|
|
1235 |
}
|
|
1236 |
|
|
1237 |
|
|
1238 |
static void retstat (LexState *ls) {
|
|
1239 |
/* stat -> RETURN explist */
|
|
1240 |
FuncState *fs = ls->fs;
|
|
1241 |
expdesc e;
|
|
1242 |
int first, nret; /* registers with returned values */
|
|
1243 |
luaX_next(ls); /* skip RETURN */
|
|
1244 |
if (block_follow(ls->t.token) || ls->t.token == ';')
|
|
1245 |
first = nret = 0; /* return no values */
|
|
1246 |
else {
|
|
1247 |
nret = explist1(ls, &e); /* optional return values */
|
|
1248 |
if (hasmultret(e.k)) {
|
|
1249 |
luaK_setmultret(fs, &e);
|
|
1250 |
if (e.k == VCALL && nret == 1) { /* tail call? */
|
|
1251 |
SET_OPCODE(getcode(fs,&e), OP_TAILCALL);
|
|
1252 |
lua_assert(GETARG_A(getcode(fs,&e)) == fs->nactvar);
|
|
1253 |
}
|
|
1254 |
first = fs->nactvar;
|
|
1255 |
nret = LUA_MULTRET; /* return all values */
|
|
1256 |
}
|
|
1257 |
else {
|
|
1258 |
if (nret == 1) /* only one single value? */
|
|
1259 |
first = luaK_exp2anyreg(fs, &e);
|
|
1260 |
else {
|
|
1261 |
luaK_exp2nextreg(fs, &e); /* values must go to the `stack' */
|
|
1262 |
first = fs->nactvar; /* return all `active' values */
|
|
1263 |
lua_assert(nret == fs->freereg - first);
|
|
1264 |
}
|
|
1265 |
}
|
|
1266 |
}
|
|
1267 |
luaK_ret(fs, first, nret);
|
|
1268 |
}
|
|
1269 |
|
|
1270 |
|
|
1271 |
static int statement (LexState *ls) {
|
|
1272 |
int line = ls->linenumber; /* may be needed for error messages */
|
|
1273 |
switch (ls->t.token) {
|
|
1274 |
case TK_IF: { /* stat -> ifstat */
|
|
1275 |
ifstat(ls, line);
|
|
1276 |
return 0;
|
|
1277 |
}
|
|
1278 |
case TK_WHILE: { /* stat -> whilestat */
|
|
1279 |
whilestat(ls, line);
|
|
1280 |
return 0;
|
|
1281 |
}
|
|
1282 |
case TK_DO: { /* stat -> DO block END */
|
|
1283 |
luaX_next(ls); /* skip DO */
|
|
1284 |
block(ls);
|
|
1285 |
check_match(ls, TK_END, TK_DO, line);
|
|
1286 |
return 0;
|
|
1287 |
}
|
|
1288 |
case TK_FOR: { /* stat -> forstat */
|
|
1289 |
forstat(ls, line);
|
|
1290 |
return 0;
|
|
1291 |
}
|
|
1292 |
case TK_REPEAT: { /* stat -> repeatstat */
|
|
1293 |
repeatstat(ls, line);
|
|
1294 |
return 0;
|
|
1295 |
}
|
|
1296 |
case TK_FUNCTION: {
|
|
1297 |
funcstat(ls, line); /* stat -> funcstat */
|
|
1298 |
return 0;
|
|
1299 |
}
|
|
1300 |
case TK_LOCAL: { /* stat -> localstat */
|
|
1301 |
luaX_next(ls); /* skip LOCAL */
|
|
1302 |
if (testnext(ls, TK_FUNCTION)) /* local function? */
|
|
1303 |
localfunc(ls);
|
|
1304 |
else
|
|
1305 |
localstat(ls);
|
|
1306 |
return 0;
|
|
1307 |
}
|
|
1308 |
case TK_RETURN: { /* stat -> retstat */
|
|
1309 |
retstat(ls);
|
|
1310 |
return 1; /* must be last statement */
|
|
1311 |
}
|
|
1312 |
case TK_BREAK: { /* stat -> breakstat */
|
|
1313 |
luaX_next(ls); /* skip BREAK */
|
|
1314 |
breakstat(ls);
|
|
1315 |
return 1; /* must be last statement */
|
|
1316 |
}
|
|
1317 |
default: {
|
|
1318 |
exprstat(ls);
|
|
1319 |
return 0; /* to avoid warnings */
|
|
1320 |
}
|
|
1321 |
}
|
|
1322 |
}
|
|
1323 |
|
|
1324 |
|
|
1325 |
static void chunk (LexState *ls) {
|
|
1326 |
/* chunk -> { stat [`;'] } */
|
|
1327 |
int islast = 0;
|
|
1328 |
enterlevel(ls);
|
|
1329 |
while (!islast && !block_follow(ls->t.token)) {
|
|
1330 |
islast = statement(ls);
|
|
1331 |
testnext(ls, ';');
|
|
1332 |
lua_assert(ls->fs->f->maxstacksize >= ls->fs->freereg &&
|
|
1333 |
ls->fs->freereg >= ls->fs->nactvar);
|
|
1334 |
ls->fs->freereg = ls->fs->nactvar; /* free registers */
|
|
1335 |
}
|
|
1336 |
leavelevel(ls);
|
|
1337 |
}
|
|
1338 |
|
|
1339 |
/* }====================================================================== */
|