diff options
| author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 1997-11-19 15:29:23 -0200 |
|---|---|---|
| committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 1997-11-19 15:29:23 -0200 |
| commit | 592a3f289b428e3ee5cc595a266607ad7f5d94ff (patch) | |
| tree | 19a371157be240f7e0f579117d04d466e911afcd /lua.stx | |
| parent | 9cdeb275e7c93007b2ece6f81aaeafe530076805 (diff) | |
| download | lua-592a3f289b428e3ee5cc595a266607ad7f5d94ff.tar.gz lua-592a3f289b428e3ee5cc595a266607ad7f5d94ff.tar.bz2 lua-592a3f289b428e3ee5cc595a266607ad7f5d94ff.zip | |
first implementation of centralized global state.
Diffstat (limited to 'lua.stx')
| -rw-r--r-- | lua.stx | 245 |
1 files changed, 123 insertions, 122 deletions
| @@ -1,6 +1,6 @@ | |||
| 1 | %{ | 1 | %{ |
| 2 | /* | 2 | /* |
| 3 | ** $Id: lua.stx,v 1.16 1997/10/30 18:47:19 roberto Exp roberto $ | 3 | ** $Id: lua.stx,v 1.17 1997/11/07 15:09:49 roberto Exp roberto $ |
| 4 | ** Syntax analizer and code generator | 4 | ** Syntax analizer and code generator |
| 5 | ** See Copyright Notice in lua.h | 5 | ** See Copyright Notice in lua.h |
| 6 | */ | 6 | */ |
| @@ -16,13 +16,13 @@ | |||
| 16 | #include "lmem.h" | 16 | #include "lmem.h" |
| 17 | #include "lopcodes.h" | 17 | #include "lopcodes.h" |
| 18 | #include "lparser.h" | 18 | #include "lparser.h" |
| 19 | #include "lstate.h" | ||
| 19 | #include "lstring.h" | 20 | #include "lstring.h" |
| 20 | #include "lua.h" | 21 | #include "lua.h" |
| 21 | #include "luadebug.h" | 22 | #include "luadebug.h" |
| 22 | #include "lzio.h" | 23 | #include "lzio.h" |
| 23 | 24 | ||
| 24 | 25 | ||
| 25 | /* to avoid warnings generated by yacc */ | ||
| 26 | int luaY_parse (void); | 26 | int luaY_parse (void); |
| 27 | 27 | ||
| 28 | 28 | ||
| @@ -61,7 +61,7 @@ typedef long vardesc; | |||
| 61 | #define dotindex(v) ((-(v))-1) | 61 | #define dotindex(v) ((-(v))-1) |
| 62 | 62 | ||
| 63 | /* state needed to generate code for a given function */ | 63 | /* state needed to generate code for a given function */ |
| 64 | typedef struct State { | 64 | typedef struct FuncState { |
| 65 | TProtoFunc *f; /* current function header */ | 65 | TProtoFunc *f; /* current function header */ |
| 66 | int pc; /* next position to code */ | 66 | int pc; /* next position to code */ |
| 67 | TaggedString *localvar[MAXLOCALS]; /* store local variable names */ | 67 | TaggedString *localvar[MAXLOCALS]; /* store local variable names */ |
| @@ -75,11 +75,11 @@ typedef struct State { | |||
| 75 | int maxconsts; /* size of f->consts */ | 75 | int maxconsts; /* size of f->consts */ |
| 76 | vardesc varbuffer[MAXVAR]; /* variables in an assignment list */ | 76 | vardesc varbuffer[MAXVAR]; /* variables in an assignment list */ |
| 77 | vardesc upvalues[MAXUPVALUES]; /* upvalues */ | 77 | vardesc upvalues[MAXUPVALUES]; /* upvalues */ |
| 78 | } State; | 78 | } FuncState; |
| 79 | 79 | ||
| 80 | static State *mainState, *currState; | ||
| 81 | 80 | ||
| 82 | 81 | ||
| 82 | #define YYPURE 1 | ||
| 83 | 83 | ||
| 84 | 84 | ||
| 85 | void luaY_syntaxerror (char *s, char *token) | 85 | void luaY_syntaxerror (char *s, char *token) |
| @@ -87,7 +87,7 @@ void luaY_syntaxerror (char *s, char *token) | |||
| 87 | if (token[0] == 0) | 87 | if (token[0] == 0) |
| 88 | token = "<eof>"; | 88 | token = "<eof>"; |
| 89 | luaL_verror("%.100s;\n> last token read: \"%.50s\" at line %d in file %.50s", | 89 | luaL_verror("%.100s;\n> last token read: \"%.50s\" at line %d in file %.50s", |
| 90 | s, token, luaX_linenumber, mainState->f->fileName->str); | 90 | s, token, L->lexstate->linenumber, L->mainState->f->fileName->str); |
| 91 | } | 91 | } |
| 92 | 92 | ||
| 93 | 93 | ||
| @@ -99,16 +99,16 @@ void luaY_error (char *s) | |||
| 99 | 99 | ||
| 100 | static void check_pc (int n) | 100 | static void check_pc (int n) |
| 101 | { | 101 | { |
| 102 | if (currState->pc+n > currState->maxcode) | 102 | if (L->currState->pc+n > L->currState->maxcode) |
| 103 | currState->maxcode = luaM_growvector(&currState->f->code, | 103 | L->currState->maxcode = luaM_growvector(&L->currState->f->code, |
| 104 | currState->maxcode, Byte, codeEM, MAX_INT); | 104 | L->currState->maxcode, Byte, codeEM, MAX_INT); |
| 105 | } | 105 | } |
| 106 | 106 | ||
| 107 | 107 | ||
| 108 | static void movecode_up (int d, int s, int n) | 108 | static void movecode_up (int d, int s, int n) |
| 109 | { | 109 | { |
| 110 | while (n--) | 110 | while (n--) |
| 111 | currState->f->code[d+n] = currState->f->code[s+n]; | 111 | L->currState->f->code[d+n] = L->currState->f->code[s+n]; |
| 112 | } | 112 | } |
| 113 | 113 | ||
| 114 | 114 | ||
| @@ -116,24 +116,24 @@ static void movecode_down (int d, int s, int n) | |||
| 116 | { | 116 | { |
| 117 | int i; | 117 | int i; |
| 118 | for (i=0; i<n; i++) | 118 | for (i=0; i<n; i++) |
| 119 | currState->f->code[d+i] = currState->f->code[s+i]; | 119 | L->currState->f->code[d+i] = L->currState->f->code[s+i]; |
| 120 | } | 120 | } |
| 121 | 121 | ||
| 122 | 122 | ||
| 123 | static void code_byte (Byte c) | 123 | static void code_byte (Byte c) |
| 124 | { | 124 | { |
| 125 | check_pc(1); | 125 | check_pc(1); |
| 126 | currState->f->code[currState->pc++] = c; | 126 | L->currState->f->code[L->currState->pc++] = c; |
| 127 | } | 127 | } |
| 128 | 128 | ||
| 129 | 129 | ||
| 130 | static void deltastack (int delta) | 130 | static void deltastack (int delta) |
| 131 | { | 131 | { |
| 132 | currState->stacksize += delta; | 132 | L->currState->stacksize += delta; |
| 133 | if (currState->stacksize > currState->maxstacksize) { | 133 | if (L->currState->stacksize > L->currState->maxstacksize) { |
| 134 | if (currState->stacksize > 255) | 134 | if (L->currState->stacksize > 255) |
| 135 | luaY_error("function/expression too complex (limit 256)"); | 135 | luaY_error("function/expression too complex (limit 256)"); |
| 136 | currState->maxstacksize = currState->stacksize; | 136 | L->currState->maxstacksize = L->currState->stacksize; |
| 137 | } | 137 | } |
| 138 | } | 138 | } |
| 139 | 139 | ||
| @@ -142,18 +142,18 @@ static int code_oparg_at (int pc, OpCode op, int builtin, int arg, int delta) | |||
| 142 | { | 142 | { |
| 143 | deltastack(delta); | 143 | deltastack(delta); |
| 144 | if (arg < builtin) { | 144 | if (arg < builtin) { |
| 145 | currState->f->code[pc] = op+1+arg; | 145 | L->currState->f->code[pc] = op+1+arg; |
| 146 | return 1; | 146 | return 1; |
| 147 | } | 147 | } |
| 148 | else if (arg <= 255) { | 148 | else if (arg <= 255) { |
| 149 | currState->f->code[pc] = op; | 149 | L->currState->f->code[pc] = op; |
| 150 | currState->f->code[pc+1] = arg; | 150 | L->currState->f->code[pc+1] = arg; |
| 151 | return 2; | 151 | return 2; |
| 152 | } | 152 | } |
| 153 | else if (arg <= MAX_WORD) { | 153 | else if (arg <= MAX_WORD) { |
| 154 | currState->f->code[pc] = op+1+builtin; | 154 | L->currState->f->code[pc] = op+1+builtin; |
| 155 | currState->f->code[pc+1] = arg&0xFF; | 155 | L->currState->f->code[pc+1] = arg&0xFF; |
| 156 | currState->f->code[pc+2] = arg>>8; | 156 | L->currState->f->code[pc+2] = arg>>8; |
| 157 | return 3; | 157 | return 3; |
| 158 | } | 158 | } |
| 159 | else luaY_error("code too long (limit 64K)"); | 159 | else luaY_error("code too long (limit 64K)"); |
| @@ -164,13 +164,13 @@ static int code_oparg_at (int pc, OpCode op, int builtin, int arg, int delta) | |||
| 164 | static int fix_opcode (int pc, OpCode op, int builtin, int arg) | 164 | static int fix_opcode (int pc, OpCode op, int builtin, int arg) |
| 165 | { | 165 | { |
| 166 | if (arg < builtin) { /* close space */ | 166 | if (arg < builtin) { /* close space */ |
| 167 | movecode_down(pc+1, pc+2, currState->pc-(pc+2)); | 167 | movecode_down(pc+1, pc+2, L->currState->pc-(pc+2)); |
| 168 | currState->pc--; | 168 | L->currState->pc--; |
| 169 | } | 169 | } |
| 170 | else if (arg > 255) { /* open space */ | 170 | else if (arg > 255) { /* open space */ |
| 171 | check_pc(1); | 171 | check_pc(1); |
| 172 | movecode_up(pc+1, pc, currState->pc-pc); | 172 | movecode_up(pc+1, pc, L->currState->pc-pc); |
| 173 | currState->pc++; | 173 | L->currState->pc++; |
| 174 | } | 174 | } |
| 175 | return code_oparg_at(pc, op, builtin, arg, 0) - 2; | 175 | return code_oparg_at(pc, op, builtin, arg, 0) - 2; |
| 176 | } | 176 | } |
| @@ -179,7 +179,7 @@ static int fix_opcode (int pc, OpCode op, int builtin, int arg) | |||
| 179 | static void code_oparg (OpCode op, int builtin, int arg, int delta) | 179 | static void code_oparg (OpCode op, int builtin, int arg, int delta) |
| 180 | { | 180 | { |
| 181 | check_pc(3); /* maximum code size */ | 181 | check_pc(3); /* maximum code size */ |
| 182 | currState->pc += code_oparg_at(currState->pc, op, builtin, arg, delta); | 182 | L->currState->pc += code_oparg_at(L->currState->pc, op, builtin, arg, delta); |
| 183 | } | 183 | } |
| 184 | 184 | ||
| 185 | 185 | ||
| @@ -214,7 +214,7 @@ static void code_constant (int c) | |||
| 214 | } | 214 | } |
| 215 | 215 | ||
| 216 | 216 | ||
| 217 | static int next_constant (State *cs) | 217 | static int next_constant (FuncState *cs) |
| 218 | { | 218 | { |
| 219 | TProtoFunc *f = cs->f; | 219 | TProtoFunc *f = cs->f; |
| 220 | if (f->nconsts >= cs->maxconsts) { | 220 | if (f->nconsts >= cs->maxconsts) { |
| @@ -225,7 +225,7 @@ static int next_constant (State *cs) | |||
| 225 | } | 225 | } |
| 226 | 226 | ||
| 227 | 227 | ||
| 228 | static int string_constant (TaggedString *s, State *cs) | 228 | static int string_constant (TaggedString *s, FuncState *cs) |
| 229 | { | 229 | { |
| 230 | TProtoFunc *f = cs->f; | 230 | TProtoFunc *f = cs->f; |
| 231 | int c = s->constindex; | 231 | int c = s->constindex; |
| @@ -242,7 +242,7 @@ static int string_constant (TaggedString *s, State *cs) | |||
| 242 | 242 | ||
| 243 | static void code_string (TaggedString *s) | 243 | static void code_string (TaggedString *s) |
| 244 | { | 244 | { |
| 245 | code_constant(string_constant(s, currState)); | 245 | code_constant(string_constant(s, L->currState)); |
| 246 | } | 246 | } |
| 247 | 247 | ||
| 248 | 248 | ||
| @@ -250,16 +250,16 @@ static void code_string (TaggedString *s) | |||
| 250 | static int real_constant (real r) | 250 | static int real_constant (real r) |
| 251 | { | 251 | { |
| 252 | /* check whether 'r' has appeared within the last LIM entries */ | 252 | /* check whether 'r' has appeared within the last LIM entries */ |
| 253 | TObject *cnt = currState->f->consts; | 253 | TObject *cnt = L->currState->f->consts; |
| 254 | int c = currState->f->nconsts; | 254 | int c = L->currState->f->nconsts; |
| 255 | int lim = c < LIM ? 0 : c-LIM; | 255 | int lim = c < LIM ? 0 : c-LIM; |
| 256 | while (--c >= lim) { | 256 | while (--c >= lim) { |
| 257 | if (ttype(&cnt[c]) == LUA_T_NUMBER && nvalue(&cnt[c]) == r) | 257 | if (ttype(&cnt[c]) == LUA_T_NUMBER && nvalue(&cnt[c]) == r) |
| 258 | return c; | 258 | return c; |
| 259 | } | 259 | } |
| 260 | /* not found; create a luaM_new entry */ | 260 | /* not found; create a luaM_new entry */ |
| 261 | c = next_constant(currState); | 261 | c = next_constant(L->currState); |
| 262 | cnt = currState->f->consts; /* 'next_constant' may reallocate this vector */ | 262 | cnt = L->currState->f->consts; /* 'next_constant' may reallocate this vector */ |
| 263 | ttype(&cnt[c]) = LUA_T_NUMBER; | 263 | ttype(&cnt[c]) = LUA_T_NUMBER; |
| 264 | nvalue(&cnt[c]) = r; | 264 | nvalue(&cnt[c]) = r; |
| 265 | return c; | 265 | return c; |
| @@ -292,13 +292,13 @@ static void flush_list (int m, int n) | |||
| 292 | 292 | ||
| 293 | static void luaI_registerlocalvar (TaggedString *varname, int line) | 293 | static void luaI_registerlocalvar (TaggedString *varname, int line) |
| 294 | { | 294 | { |
| 295 | if (currState->maxvars != -1) { /* debug information? */ | 295 | if (L->currState->maxvars != -1) { /* debug information? */ |
| 296 | if (currState->nvars >= currState->maxvars) | 296 | if (L->currState->nvars >= L->currState->maxvars) |
| 297 | currState->maxvars = luaM_growvector(&currState->f->locvars, | 297 | L->currState->maxvars = luaM_growvector(&L->currState->f->locvars, |
| 298 | currState->maxvars, LocVar, "", MAX_WORD); | 298 | L->currState->maxvars, LocVar, "", MAX_WORD); |
| 299 | currState->f->locvars[currState->nvars].varname = varname; | 299 | L->currState->f->locvars[L->currState->nvars].varname = varname; |
| 300 | currState->f->locvars[currState->nvars].line = line; | 300 | L->currState->f->locvars[L->currState->nvars].line = line; |
| 301 | currState->nvars++; | 301 | L->currState->nvars++; |
| 302 | } | 302 | } |
| 303 | } | 303 | } |
| 304 | 304 | ||
| @@ -311,17 +311,17 @@ static void luaI_unregisterlocalvar (int line) | |||
| 311 | 311 | ||
| 312 | static void store_localvar (TaggedString *name, int n) | 312 | static void store_localvar (TaggedString *name, int n) |
| 313 | { | 313 | { |
| 314 | if (currState->nlocalvar+n < MAXLOCALS) | 314 | if (L->currState->nlocalvar+n < MAXLOCALS) |
| 315 | currState->localvar[currState->nlocalvar+n] = name; | 315 | L->currState->localvar[L->currState->nlocalvar+n] = name; |
| 316 | else | 316 | else |
| 317 | luaY_error("too many local variables (limit 32)"); | 317 | luaY_error("too many local variables (limit 32)"); |
| 318 | luaI_registerlocalvar(name, luaX_linenumber); | 318 | luaI_registerlocalvar(name, L->lexstate->linenumber); |
| 319 | } | 319 | } |
| 320 | 320 | ||
| 321 | static void add_localvar (TaggedString *name) | 321 | static void add_localvar (TaggedString *name) |
| 322 | { | 322 | { |
| 323 | store_localvar(name, 0); | 323 | store_localvar(name, 0); |
| 324 | currState->nlocalvar++; | 324 | L->currState->nlocalvar++; |
| 325 | } | 325 | } |
| 326 | 326 | ||
| 327 | 327 | ||
| @@ -342,11 +342,11 @@ static void add_varbuffer (vardesc var, int n) | |||
| 342 | { | 342 | { |
| 343 | if (n >= MAXVAR) | 343 | if (n >= MAXVAR) |
| 344 | luaY_error("variable buffer overflow (limit 32)"); | 344 | luaY_error("variable buffer overflow (limit 32)"); |
| 345 | currState->varbuffer[n] = var2store(var); | 345 | L->currState->varbuffer[n] = var2store(var); |
| 346 | } | 346 | } |
| 347 | 347 | ||
| 348 | 348 | ||
| 349 | static int aux_localname (TaggedString *n, State *st) | 349 | static int aux_localname (TaggedString *n, FuncState *st) |
| 350 | { | 350 | { |
| 351 | int i; | 351 | int i; |
| 352 | for (i=st->nlocalvar-1; i >= 0; i--) | 352 | for (i=st->nlocalvar-1; i >= 0; i--) |
| @@ -355,12 +355,12 @@ static int aux_localname (TaggedString *n, State *st) | |||
| 355 | } | 355 | } |
| 356 | 356 | ||
| 357 | 357 | ||
| 358 | static vardesc singlevar (TaggedString *n, State *st) | 358 | static vardesc singlevar (TaggedString *n, FuncState *st) |
| 359 | { | 359 | { |
| 360 | int i = aux_localname(n, st); | 360 | int i = aux_localname(n, st); |
| 361 | if (i == -1) { /* check shadowing */ | 361 | if (i == -1) { /* check shadowing */ |
| 362 | int l; | 362 | int l; |
| 363 | for (l=1; l<=(st-mainState); l++) | 363 | for (l=1; l<=(st-L->mainState); l++) |
| 364 | if (aux_localname(n, st-l) >= 0) | 364 | if (aux_localname(n, st-l) >= 0) |
| 365 | luaY_syntaxerror("cannot access a variable in outer scope", n->str); | 365 | luaY_syntaxerror("cannot access a variable in outer scope", n->str); |
| 366 | return string_constant(n, st)+MINGLOBAL; /* global value */ | 366 | return string_constant(n, st)+MINGLOBAL; /* global value */ |
| @@ -371,16 +371,16 @@ static vardesc singlevar (TaggedString *n, State *st) | |||
| 371 | 371 | ||
| 372 | static int indexupvalue (TaggedString *n) | 372 | static int indexupvalue (TaggedString *n) |
| 373 | { | 373 | { |
| 374 | vardesc v = singlevar(n, currState-1); | 374 | vardesc v = singlevar(n, L->currState-1); |
| 375 | int i; | 375 | int i; |
| 376 | for (i=0; i<currState->nupvalues; i++) { | 376 | for (i=0; i<L->currState->nupvalues; i++) { |
| 377 | if (currState->upvalues[i] == v) | 377 | if (L->currState->upvalues[i] == v) |
| 378 | return i; | 378 | return i; |
| 379 | } | 379 | } |
| 380 | /* new one */ | 380 | /* new one */ |
| 381 | if (++(currState->nupvalues) > MAXUPVALUES) | 381 | if (++(L->currState->nupvalues) > MAXUPVALUES) |
| 382 | luaY_error("too many upvalues in a single function (limit 16)"); | 382 | luaY_error("too many upvalues in a single function (limit 16)"); |
| 383 | currState->upvalues[i] = v; /* i = currState->nupvalues - 1 */ | 383 | L->currState->upvalues[i] = v; /* i = L->currState->nupvalues - 1 */ |
| 384 | return i; | 384 | return i; |
| 385 | } | 385 | } |
| 386 | 386 | ||
| @@ -388,9 +388,9 @@ static int indexupvalue (TaggedString *n) | |||
| 388 | static void pushupvalue (TaggedString *n) | 388 | static void pushupvalue (TaggedString *n) |
| 389 | { | 389 | { |
| 390 | int i; | 390 | int i; |
| 391 | if (currState == mainState) | 391 | if (L->currState == L->mainState) |
| 392 | luaY_error("cannot access upvalue in main"); | 392 | luaY_error("cannot access upvalue in main"); |
| 393 | if (aux_localname(n, currState) >= 0) | 393 | if (aux_localname(n, L->currState) >= 0) |
| 394 | luaY_syntaxerror("cannot access an upvalue in current scope", n->str); | 394 | luaY_syntaxerror("cannot access an upvalue in current scope", n->str); |
| 395 | i = indexupvalue(n); | 395 | i = indexupvalue(n); |
| 396 | code_oparg(PUSHUPVALUE, 2, i, 1); | 396 | code_oparg(PUSHUPVALUE, 2, i, 1); |
| @@ -399,10 +399,9 @@ static void pushupvalue (TaggedString *n) | |||
| 399 | 399 | ||
| 400 | void luaY_codedebugline (int line) | 400 | void luaY_codedebugline (int line) |
| 401 | { | 401 | { |
| 402 | static int lastline = 0; | 402 | if (lua_debug && line != L->lexstate->lastline) { |
| 403 | if (lua_debug && line != lastline) { | ||
| 404 | code_oparg(SETLINE, 0, line, 0); | 403 | code_oparg(SETLINE, 0, line, 0); |
| 405 | lastline = line; | 404 | L->lexstate->lastline = line; |
| 406 | } | 405 | } |
| 407 | } | 406 | } |
| 408 | 407 | ||
| @@ -421,10 +420,10 @@ static long adjust_functioncall (long exp, int nresults) | |||
| 421 | if (exp <= 0) | 420 | if (exp <= 0) |
| 422 | return -exp; /* exp is -list length */ | 421 | return -exp; /* exp is -list length */ |
| 423 | else { | 422 | else { |
| 424 | int temp = currState->f->code[exp]; | 423 | int temp = L->currState->f->code[exp]; |
| 425 | int nparams = currState->f->code[exp-1]; | 424 | int nparams = L->currState->f->code[exp-1]; |
| 426 | exp += fix_opcode(exp-2, CALLFUNC, 2, nresults); | 425 | exp += fix_opcode(exp-2, CALLFUNC, 2, nresults); |
| 427 | currState->f->code[exp] = nparams; | 426 | L->currState->f->code[exp] = nparams; |
| 428 | if (nresults != MULT_RET) | 427 | if (nresults != MULT_RET) |
| 429 | deltastack(nresults); | 428 | deltastack(nresults); |
| 430 | deltastack(-(nparams+1)); | 429 | deltastack(-(nparams+1)); |
| @@ -436,7 +435,7 @@ static long adjust_functioncall (long exp, int nresults) | |||
| 436 | static void adjust_mult_assign (int vars, long exps) | 435 | static void adjust_mult_assign (int vars, long exps) |
| 437 | { | 436 | { |
| 438 | if (exps > 0) { /* must correct function call */ | 437 | if (exps > 0) { /* must correct function call */ |
| 439 | int diff = currState->f->code[exps] - vars; | 438 | int diff = L->currState->f->code[exps] - vars; |
| 440 | if (diff < 0) | 439 | if (diff < 0) |
| 441 | adjust_functioncall(exps, -diff); | 440 | adjust_functioncall(exps, -diff); |
| 442 | else { | 441 | else { |
| @@ -450,11 +449,11 @@ static void adjust_mult_assign (int vars, long exps) | |||
| 450 | 449 | ||
| 451 | static void code_args (int nparams, int dots) | 450 | static void code_args (int nparams, int dots) |
| 452 | { | 451 | { |
| 453 | currState->nlocalvar += nparams; | 452 | L->currState->nlocalvar += nparams; |
| 454 | if (!dots) | 453 | if (!dots) |
| 455 | code_oparg(ARGS, 0, currState->nlocalvar, currState->nlocalvar); | 454 | code_oparg(ARGS, 0, L->currState->nlocalvar, L->currState->nlocalvar); |
| 456 | else { | 455 | else { |
| 457 | code_oparg(VARARGS, 0, currState->nlocalvar, currState->nlocalvar+1); | 456 | code_oparg(VARARGS, 0, L->currState->nlocalvar, L->currState->nlocalvar+1); |
| 458 | add_localvar(luaS_new("arg")); | 457 | add_localvar(luaS_new("arg")); |
| 459 | } | 458 | } |
| 460 | } | 459 | } |
| @@ -487,9 +486,9 @@ static void storevar (vardesc var) | |||
| 487 | /* returns how many elements are left as 'garbage' on the stack */ | 486 | /* returns how many elements are left as 'garbage' on the stack */ |
| 488 | static int lua_codestore (int i, int left) | 487 | static int lua_codestore (int i, int left) |
| 489 | { | 488 | { |
| 490 | if (currState->varbuffer[i] != 0 || /* global or local var or */ | 489 | if (L->currState->varbuffer[i] != 0 || /* global or local var or */ |
| 491 | left+i == 0) { /* indexed var without values in between */ | 490 | left+i == 0) { /* indexed var without values in between */ |
| 492 | storevar(currState->varbuffer[i]); | 491 | storevar(L->currState->varbuffer[i]); |
| 493 | return left; | 492 | return left; |
| 494 | } | 493 | } |
| 495 | else { /* indexed var with values in between*/ | 494 | else { /* indexed var with values in between*/ |
| @@ -508,7 +507,7 @@ static int fix_jump (int pc, OpCode op, int n) | |||
| 508 | 507 | ||
| 509 | static void fix_upjmp (OpCode op, int pos) | 508 | static void fix_upjmp (OpCode op, int pos) |
| 510 | { | 509 | { |
| 511 | int delta = currState->pc+JMPSIZE - pos; /* jump is relative */ | 510 | int delta = L->currState->pc+JMPSIZE - pos; /* jump is relative */ |
| 512 | if (delta > 255) delta++; | 511 | if (delta > 255) delta++; |
| 513 | code_oparg(op, 0, delta, 0); | 512 | code_oparg(op, 0, delta, 0); |
| 514 | } | 513 | } |
| @@ -517,38 +516,38 @@ static void fix_upjmp (OpCode op, int pos) | |||
| 517 | static void codeIf (int thenAdd, int elseAdd) | 516 | static void codeIf (int thenAdd, int elseAdd) |
| 518 | { | 517 | { |
| 519 | int elseinit = elseAdd+JMPSIZE; | 518 | int elseinit = elseAdd+JMPSIZE; |
| 520 | if (currState->pc == elseinit) { /* no else part */ | 519 | if (L->currState->pc == elseinit) { /* no else part */ |
| 521 | currState->pc -= JMPSIZE; | 520 | L->currState->pc -= JMPSIZE; |
| 522 | elseinit = currState->pc; | 521 | elseinit = L->currState->pc; |
| 523 | } | 522 | } |
| 524 | else | 523 | else |
| 525 | elseinit += fix_jump(elseAdd, JMP, currState->pc); | 524 | elseinit += fix_jump(elseAdd, JMP, L->currState->pc); |
| 526 | fix_jump(thenAdd, IFFJMP, elseinit); | 525 | fix_jump(thenAdd, IFFJMP, elseinit); |
| 527 | } | 526 | } |
| 528 | 527 | ||
| 529 | 528 | ||
| 530 | static void code_shortcircuit (int pc, OpCode op) | 529 | static void code_shortcircuit (int pc, OpCode op) |
| 531 | { | 530 | { |
| 532 | fix_jump(pc, op, currState->pc); | 531 | fix_jump(pc, op, L->currState->pc); |
| 533 | } | 532 | } |
| 534 | 533 | ||
| 535 | 534 | ||
| 536 | static void codereturn (void) | 535 | static void codereturn (void) |
| 537 | { | 536 | { |
| 538 | code_oparg(RETCODE, 0, currState->nlocalvar, 0); | 537 | code_oparg(RETCODE, 0, L->currState->nlocalvar, 0); |
| 539 | currState->stacksize = currState->nlocalvar; | 538 | L->currState->stacksize = L->currState->nlocalvar; |
| 540 | } | 539 | } |
| 541 | 540 | ||
| 542 | 541 | ||
| 543 | static void func_onstack (TProtoFunc *f) | 542 | static void func_onstack (TProtoFunc *f) |
| 544 | { | 543 | { |
| 545 | int i; | 544 | int i; |
| 546 | int nupvalues = (currState+1)->nupvalues; | 545 | int nupvalues = (L->currState+1)->nupvalues; |
| 547 | int c = next_constant(currState); | 546 | int c = next_constant(L->currState); |
| 548 | ttype(&currState->f->consts[c]) = LUA_T_PROTO; | 547 | ttype(&L->currState->f->consts[c]) = LUA_T_PROTO; |
| 549 | currState->f->consts[c].value.tf = (currState+1)->f; | 548 | L->currState->f->consts[c].value.tf = (L->currState+1)->f; |
| 550 | for (i=0; i<nupvalues; i++) | 549 | for (i=0; i<nupvalues; i++) |
| 551 | lua_pushvar((currState+1)->upvalues[i]); | 550 | lua_pushvar((L->currState+1)->upvalues[i]); |
| 552 | code_constant(c); | 551 | code_constant(c); |
| 553 | code_oparg(CLOSURE, 2, nupvalues, -nupvalues); | 552 | code_oparg(CLOSURE, 2, nupvalues, -nupvalues); |
| 554 | } | 553 | } |
| @@ -557,48 +556,48 @@ static void func_onstack (TProtoFunc *f) | |||
| 557 | static void init_state (TaggedString *filename) | 556 | static void init_state (TaggedString *filename) |
| 558 | { | 557 | { |
| 559 | TProtoFunc *f = luaF_newproto(); | 558 | TProtoFunc *f = luaF_newproto(); |
| 560 | currState->stacksize = 0; | 559 | L->currState->stacksize = 0; |
| 561 | currState->maxstacksize = 0; | 560 | L->currState->maxstacksize = 0; |
| 562 | currState->nlocalvar = 0; | 561 | L->currState->nlocalvar = 0; |
| 563 | currState->nupvalues = 0; | 562 | L->currState->nupvalues = 0; |
| 564 | currState->f = f; | 563 | L->currState->f = f; |
| 565 | f->fileName = filename; | 564 | f->fileName = filename; |
| 566 | currState->pc = 0; | 565 | L->currState->pc = 0; |
| 567 | currState->maxcode = 0; | 566 | L->currState->maxcode = 0; |
| 568 | f->code = NULL; | 567 | f->code = NULL; |
| 569 | currState->maxconsts = 0; | 568 | L->currState->maxconsts = 0; |
| 570 | if (lua_debug) { | 569 | if (lua_debug) { |
| 571 | currState->nvars = 0; | 570 | L->currState->nvars = 0; |
| 572 | currState->maxvars = 0; | 571 | L->currState->maxvars = 0; |
| 573 | } | 572 | } |
| 574 | else | 573 | else |
| 575 | currState->maxvars = -1; /* flag no debug information */ | 574 | L->currState->maxvars = -1; /* flag no debug information */ |
| 576 | code_byte(0); /* to be filled with stacksize */ | 575 | code_byte(0); /* to be filled with stacksize */ |
| 577 | } | 576 | } |
| 578 | 577 | ||
| 579 | 578 | ||
| 580 | static void init_func (void) | 579 | static void init_func (void) |
| 581 | { | 580 | { |
| 582 | if (currState-mainState >= MAXSTATES-1) | 581 | if (L->currState-L->mainState >= MAXSTATES-1) |
| 583 | luaY_error("too many nested functions (limit 6)"); | 582 | luaY_error("too many nested functions (limit 6)"); |
| 584 | currState++; | 583 | L->currState++; |
| 585 | init_state(mainState->f->fileName); | 584 | init_state(L->mainState->f->fileName); |
| 586 | luaY_codedebugline(luaX_linenumber); | 585 | luaY_codedebugline(L->lexstate->linenumber); |
| 587 | currState->f->lineDefined = luaX_linenumber; | 586 | L->currState->f->lineDefined = L->lexstate->linenumber; |
| 588 | } | 587 | } |
| 589 | 588 | ||
| 590 | static TProtoFunc *close_func (void) | 589 | static TProtoFunc *close_func (void) |
| 591 | { | 590 | { |
| 592 | TProtoFunc *f = currState->f; | 591 | TProtoFunc *f = L->currState->f; |
| 593 | code_neutralop(ENDCODE); | 592 | code_neutralop(ENDCODE); |
| 594 | f->code[0] = currState->maxstacksize; | 593 | f->code[0] = L->currState->maxstacksize; |
| 595 | f->code = luaM_reallocvector(f->code, currState->pc, Byte); | 594 | f->code = luaM_reallocvector(f->code, L->currState->pc, Byte); |
| 596 | f->consts = luaM_reallocvector(f->consts, f->nconsts, TObject); | 595 | f->consts = luaM_reallocvector(f->consts, f->nconsts, TObject); |
| 597 | if (currState->maxvars != -1) { /* debug information? */ | 596 | if (L->currState->maxvars != -1) { /* debug information? */ |
| 598 | luaI_registerlocalvar(NULL, -1); /* flag end of vector */ | 597 | luaI_registerlocalvar(NULL, -1); /* flag end of vector */ |
| 599 | f->locvars = luaM_reallocvector(f->locvars, currState->nvars, LocVar); | 598 | f->locvars = luaM_reallocvector(f->locvars, L->currState->nvars, LocVar); |
| 600 | } | 599 | } |
| 601 | currState--; | 600 | L->currState--; |
| 602 | return f; | 601 | return f; |
| 603 | } | 602 | } |
| 604 | 603 | ||
| @@ -608,8 +607,10 @@ static TProtoFunc *close_func (void) | |||
| 608 | */ | 607 | */ |
| 609 | TProtoFunc *luaY_parser (ZIO *z, char *chunkname) | 608 | TProtoFunc *luaY_parser (ZIO *z, char *chunkname) |
| 610 | { | 609 | { |
| 611 | State state[MAXSTATES]; | 610 | struct LexState lexstate; |
| 612 | currState = mainState = &state[0]; | 611 | FuncState state[MAXSTATES]; |
| 612 | L->currState = L->mainState = &state[0]; | ||
| 613 | L->lexstate = &lexstate; | ||
| 613 | luaX_setinput(z); | 614 | luaX_setinput(z); |
| 614 | init_state(luaS_new(chunkname)); | 615 | init_state(luaS_new(chunkname)); |
| 615 | if (luaY_parse ()) lua_error("parse error"); | 616 | if (luaY_parse ()) lua_error("parse error"); |
| @@ -685,10 +686,10 @@ stat : IF cond THEN block SaveWord elsepart END { codeIf($2, $5); } | |||
| 685 | int expsize = $3-$2; | 686 | int expsize = $3-$2; |
| 686 | int newpos = $2+JMPSIZE; | 687 | int newpos = $2+JMPSIZE; |
| 687 | check_pc(expsize); | 688 | check_pc(expsize); |
| 688 | memcpy(&currState->f->code[currState->pc], | 689 | memcpy(&L->currState->f->code[L->currState->pc], |
| 689 | &currState->f->code[$2], expsize); | 690 | &L->currState->f->code[$2], expsize); |
| 690 | movecode_down($2, $3, currState->pc-$2); | 691 | movecode_down($2, $3, L->currState->pc-$2); |
| 691 | newpos += fix_jump($2, JMP, currState->pc-expsize); | 692 | newpos += fix_jump($2, JMP, L->currState->pc-expsize); |
| 692 | fix_upjmp(IFTUPJMP, newpos); | 693 | fix_upjmp(IFTUPJMP, newpos); |
| 693 | }} | 694 | }} |
| 694 | 695 | ||
| @@ -712,18 +713,18 @@ stat : IF cond THEN block SaveWord elsepart END { codeIf($2, $5); } | |||
| 712 | 713 | ||
| 713 | | LOCAL localnamelist decinit | 714 | | LOCAL localnamelist decinit |
| 714 | { | 715 | { |
| 715 | currState->nlocalvar += $2; | 716 | L->currState->nlocalvar += $2; |
| 716 | adjust_mult_assign($2, $3); | 717 | adjust_mult_assign($2, $3); |
| 717 | } | 718 | } |
| 718 | 719 | ||
| 719 | | FUNCTION funcname body { func_onstack($3); storevar($2); } | 720 | | FUNCTION funcname body { func_onstack($3); storevar($2); } |
| 720 | ; | 721 | ; |
| 721 | 722 | ||
| 722 | block : {$<vInt>$ = currState->nlocalvar;} chunk | 723 | block : {$<vInt>$ = L->currState->nlocalvar;} chunk |
| 723 | { | 724 | { |
| 724 | adjuststack(currState->nlocalvar - $<vInt>1); | 725 | adjuststack(L->currState->nlocalvar - $<vInt>1); |
| 725 | for (; currState->nlocalvar > $<vInt>1; currState->nlocalvar--) | 726 | for (; L->currState->nlocalvar > $<vInt>1; L->currState->nlocalvar--) |
| 726 | luaI_unregisterlocalvar(luaX_linenumber); | 727 | luaI_unregisterlocalvar(L->lexstate->linenumber); |
| 727 | } | 728 | } |
| 728 | ; | 729 | ; |
| 729 | 730 | ||
| @@ -753,13 +754,13 @@ ret : /* empty */ | |||
| 753 | } | 754 | } |
| 754 | ; | 755 | ; |
| 755 | 756 | ||
| 756 | GetPC : /* empty */ { $$ = currState->pc; } | 757 | GetPC : /* empty */ { $$ = L->currState->pc; } |
| 757 | ; | 758 | ; |
| 758 | 759 | ||
| 759 | SaveWord : /* empty */ | 760 | SaveWord : /* empty */ |
| 760 | { $$ = currState->pc; | 761 | { $$ = L->currState->pc; |
| 761 | check_pc(JMPSIZE); | 762 | check_pc(JMPSIZE); |
| 762 | currState->pc += JMPSIZE; /* open space */ | 763 | L->currState->pc += JMPSIZE; /* open space */ |
| 763 | } | 764 | } |
| 764 | ; | 765 | ; |
| 765 | 766 | ||
| @@ -808,7 +809,7 @@ functioncall : funcvalue funcParams | |||
| 808 | { | 809 | { |
| 809 | code_byte(0); /* save space for opcode */ | 810 | code_byte(0); /* save space for opcode */ |
| 810 | code_byte($1+$2); /* number of parameters */ | 811 | code_byte($1+$2); /* number of parameters */ |
| 811 | $$ = currState->pc; | 812 | $$ = L->currState->pc; |
| 812 | code_byte(0); /* must be adjusted by other rules */ | 813 | code_byte(0); /* must be adjusted by other rules */ |
| 813 | } | 814 | } |
| 814 | ; | 815 | ; |
| @@ -816,7 +817,7 @@ functioncall : funcvalue funcParams | |||
| 816 | funcvalue : varexp { $$ = 0; } | 817 | funcvalue : varexp { $$ = 0; } |
| 817 | | varexp ':' NAME | 818 | | varexp ':' NAME |
| 818 | { | 819 | { |
| 819 | code_oparg(PUSHSELF, 0, string_constant($3, currState), 1); | 820 | code_oparg(PUSHSELF, 0, string_constant($3, L->currState), 1); |
| 820 | $$ = 1; | 821 | $$ = 1; |
| 821 | } | 822 | } |
| 822 | ; | 823 | ; |
| @@ -834,7 +835,7 @@ exprlist1 : expr { if ($1 != 0) $$ = $1; else $$ = -1; } | |||
| 834 | { | 835 | { |
| 835 | if ($4 == 0) $$ = -($<vLong>3 + 1); /* -length */ | 836 | if ($4 == 0) $$ = -($<vLong>3 + 1); /* -length */ |
| 836 | else { | 837 | else { |
| 837 | currState->f->code[$4] = $<vLong>3; /* store list length */ | 838 | L->currState->f->code[$4] = $<vLong>3; /* store list length */ |
| 838 | $$ = $4; | 839 | $$ = $4; |
| 839 | } | 840 | } |
| 840 | } | 841 | } |
| @@ -899,9 +900,9 @@ varlist1 : var { $$ = 1; add_varbuffer($1, 0); } | |||
| 899 | | varlist1 ',' var { add_varbuffer($3, $1); $$ = $1+1; } | 900 | | varlist1 ',' var { add_varbuffer($3, $1); $$ = $1+1; } |
| 900 | ; | 901 | ; |
| 901 | 902 | ||
| 902 | var : NAME { $$ = singlevar($1, currState); } | 903 | var : NAME { $$ = singlevar($1, L->currState); } |
| 903 | | varexp '[' expr1 ']' { $$ = 0; } /* indexed variable */ | 904 | | varexp '[' expr1 ']' { $$ = 0; } /* indexed variable */ |
| 904 | | varexp '.' NAME { $$ = (-string_constant($3, currState))-1; } | 905 | | varexp '.' NAME { $$ = (-string_constant($3, L->currState))-1; } |
| 905 | ; | 906 | ; |
| 906 | 907 | ||
| 907 | varexp : var { lua_pushvar($1); } | 908 | varexp : var { lua_pushvar($1); } |
