aboutsummaryrefslogtreecommitdiff
path: root/lvm.c
diff options
context:
space:
mode:
Diffstat (limited to 'lvm.c')
-rw-r--r--lvm.c227
1 files changed, 100 insertions, 127 deletions
diff --git a/lvm.c b/lvm.c
index a25f02cd..55a9e433 100644
--- a/lvm.c
+++ b/lvm.c
@@ -1,10 +1,11 @@
1/* 1/*
2** $Id: lvm.c,v 1.164 2001/02/02 15:13:05 roberto Exp roberto $ 2** $Id: lvm.c,v 1.165 2001/02/06 16:01:29 roberto Exp roberto $
3** Lua virtual machine 3** Lua virtual machine
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
6 6
7 7
8#include <stdarg.h>
8#include <stdio.h> 9#include <stdio.h>
9#include <stdlib.h> 10#include <stdlib.h>
10#include <string.h> 11#include <string.h>
@@ -26,14 +27,6 @@
26 27
27 28
28 29
29/*
30** Extra stack size to run a function:
31** TAG_LINE(1), NAME(1), TM calls(3) (plus some extra...)
32*/
33#define EXTRA_FSTACK 8
34
35
36
37int luaV_tonumber (TObject *obj) { 30int luaV_tonumber (TObject *obj) {
38 if (ttype(obj) != LUA_TSTRING) 31 if (ttype(obj) != LUA_TSTRING)
39 return 1; 32 return 1;
@@ -58,7 +51,7 @@ int luaV_tostring (lua_State *L, TObject *obj) { /* LUA_NUMBER */
58} 51}
59 52
60 53
61static void traceexec (lua_State *L, StkId base, StkId top, lua_Hook linehook) { 54static void traceexec (lua_State *L, StkId base, lua_Hook linehook) {
62 CallInfo *ci = infovalue(base-1); 55 CallInfo *ci = infovalue(base-1);
63 int *lineinfo = ci->func->f.l->lineinfo; 56 int *lineinfo = ci->func->f.l->lineinfo;
64 int pc = (*ci->pc - ci->func->f.l->code) - 1; 57 int pc = (*ci->pc - ci->func->f.l->code) - 1;
@@ -72,7 +65,6 @@ static void traceexec (lua_State *L, StkId base, StkId top, lua_Hook linehook) {
72 /* calls linehook when enters a new line or jumps back (loop) */ 65 /* calls linehook when enters a new line or jumps back (loop) */
73 if (newline != ci->line || pc <= ci->lastpc) { 66 if (newline != ci->line || pc <= ci->lastpc) {
74 ci->line = newline; 67 ci->line = newline;
75 L->top = top;
76 luaD_lineHook(L, base-2, newline, linehook); 68 luaD_lineHook(L, base-2, newline, linehook);
77 } 69 }
78 ci->lastpc = pc; 70 ci->lastpc = pc;
@@ -104,19 +96,52 @@ void luaV_Lclosure (lua_State *L, Proto *l, int nelems) {
104} 96}
105 97
106 98
99static void callTM (lua_State *L, const char *fmt, ...) {
100 va_list argp;
101 StkId base = L->top;
102 int has_result = 0;
103 va_start(argp, fmt);
104 for (;;) {
105 switch (*fmt++) {
106 case 'c':
107 setclvalue(L->top, va_arg(argp, Closure *));
108 break;
109 case 'o':
110 setobj(L->top, va_arg(argp, TObject *));
111 break;
112 case 's':
113 setsvalue(L->top, va_arg(argp, TString *));
114 break;
115 case 'r':
116 has_result = 1;
117 /* go through */
118 default:
119 goto endloop;
120 }
121 incr_top;
122 } endloop:
123 luaD_call(L, base, has_result);
124 if (has_result) {
125 L->top--;
126 setobj(va_arg(argp, TObject *), L->top);
127 }
128 va_end(argp);
129}
130
131
107/* 132/*
108** Function to index a table. 133** Function to index a table.
109** Receives the table at `t' and the key at the top (`top'-1), 134** Receives the table at `t' and the key at the `key'.
110** leaves the result at `res'. 135** leaves the result at `res'.
111*/ 136*/
112void luaV_gettable (lua_State *L, StkId t, StkId top, StkId res) { 137void luaV_gettable (lua_State *L, StkId t, TObject *key, StkId res) {
113 Closure *tm; 138 Closure *tm;
114 int tg; 139 int tg;
115 if (ttype(t) == LUA_TTABLE && /* `t' is a table? */ 140 if (ttype(t) == LUA_TTABLE && /* `t' is a table? */
116 ((tg = hvalue(t)->htag) == LUA_TTABLE || /* with default tag? */ 141 ((tg = hvalue(t)->htag) == LUA_TTABLE || /* with default tag? */
117 luaT_gettm(G(L), tg, TM_GETTABLE) == NULL)) { /* or no TM? */ 142 luaT_gettm(G(L), tg, TM_GETTABLE) == NULL)) { /* or no TM? */
118 /* do a primitive get */ 143 /* do a primitive get */
119 const TObject *h = luaH_get(hvalue(t), top-1); 144 const TObject *h = luaH_get(hvalue(t), key);
120 /* result is no nil or there is no `index' tag method? */ 145 /* result is no nil or there is no `index' tag method? */
121 if (ttype(h) != LUA_TNIL || ((tm=luaT_gettm(G(L), tg, TM_INDEX)) == NULL)) { 146 if (ttype(h) != LUA_TNIL || ((tm=luaT_gettm(G(L), tg, TM_INDEX)) == NULL)) {
122 setobj(res, h); 147 setobj(res, h);
@@ -127,116 +152,79 @@ void luaV_gettable (lua_State *L, StkId t, StkId top, StkId res) {
127 else { /* try a `gettable' tag method */ 152 else { /* try a `gettable' tag method */
128 tm = luaT_gettmbyObj(G(L), t, TM_GETTABLE); 153 tm = luaT_gettmbyObj(G(L), t, TM_GETTABLE);
129 } 154 }
130 L->top = top;
131 if (tm == NULL) /* no tag method? */ 155 if (tm == NULL) /* no tag method? */
132 luaG_typeerror(L, t, "index"); 156 luaG_typeerror(L, t, "index");
133 else { /* call tag method */ 157 else
134 luaD_checkstack(L, 2); 158 callTM(L, "coor", tm, t, key, res);
135 setobj(res+2, top-1); /* key */
136 setobj(res+1, t); /* table */
137 setclvalue(res, tm); /* tag method */
138 L->top = res+3;
139 luaD_call(L, res, 1);
140 L->top = top; /* will be decremented by the callee */
141 }
142} 159}
143 160
144 161
162
145/* 163/*
146** Receives table at `t', key at `key' and value at top. 164** Receives table at `t', key at `key' and value at `val'.
147*/ 165*/
148void luaV_settable (lua_State *L, StkId t, StkId key, StkId top) { 166void luaV_settable (lua_State *L, StkId t, StkId key, StkId val) {
149 int tg; 167 int tg;
150 if (ttype(t) == LUA_TTABLE && /* `t' is a table? */ 168 if (ttype(t) == LUA_TTABLE && /* `t' is a table? */
151 ((tg = hvalue(t)->htag) == LUA_TTABLE || /* with default tag? */ 169 ((tg = hvalue(t)->htag) == LUA_TTABLE || /* with default tag? */
152 luaT_gettm(G(L), tg, TM_SETTABLE) == NULL)) { /* or no TM? */ 170 luaT_gettm(G(L), tg, TM_SETTABLE) == NULL)) { /* or no TM? */
153 setobj(luaH_set(L, hvalue(t), key), top-1); /* do a primitive set */ 171 setobj(luaH_set(L, hvalue(t), key), val); /* do a primitive set */
154 } 172 }
155 else { /* try a `settable' tag method */ 173 else { /* try a `settable' tag method */
156 Closure *tm = luaT_gettmbyObj(G(L), t, TM_SETTABLE); 174 Closure *tm = luaT_gettmbyObj(G(L), t, TM_SETTABLE);
157 lua_assert(L->top == top);
158 if (tm == NULL) /* no tag method? */ 175 if (tm == NULL) /* no tag method? */
159 luaG_typeerror(L, t, "index"); 176 luaG_typeerror(L, t, "index");
160 else { 177 else
161 luaD_checkstack(L, 3); 178 callTM(L, "cooo", tm, t, key, val);
162 setobj(top+2, top-1);
163 setobj(top+1, key);
164 setobj(top, t);
165 setclvalue(top-1, tm);
166 L->top = top+3;
167 luaD_call(L, top-1, 0); /* call `settable' tag method */
168 lua_assert(L->top == top-1);
169 L->top = top; /* will be decremented by the callee */
170 }
171 } 179 }
172} 180}
173 181
174 182
175void luaV_getglobal (lua_State *L, TString *s, StkId top) { 183void luaV_getglobal (lua_State *L, TString *name, StkId res) {
176 const TObject *value = luaH_getstr(L->gt, s); 184 const TObject *value = luaH_getstr(L->gt, name);
177 Closure *tm; 185 Closure *tm;
178 if (!HAS_TM_GETGLOBAL(L, ttype(value)) || /* is there a tag method? */ 186 if (!HAS_TM_GETGLOBAL(L, ttype(value)) || /* is there a tag method? */
179 (tm = luaT_gettmbyObj(G(L), value, TM_GETGLOBAL)) == NULL) { 187 (tm = luaT_gettmbyObj(G(L), value, TM_GETGLOBAL)) == NULL) {
180 setobj(top, value); /* default behavior */ 188 setobj(res, value); /* default behavior */
181 }
182 else { /* call tag method */
183 L->top = top;
184 luaD_checkstack(L, 3);
185 setclvalue(top, tm);
186 setsvalue(top+1, s); /* global name */
187 setobj(top+2, value);
188 L->top = top+3;
189 luaD_call(L, top, 1);
190 lua_assert(L->top == top+1);
191 L->top = top; /* will be incremented by the callee */
192 } 189 }
190 else
191 callTM(L, "csor", tm, name, value, res);
193} 192}
194 193
195 194
196void luaV_setglobal (lua_State *L, TString *s, StkId top) { 195void luaV_setglobal (lua_State *L, TString *name, StkId val) {
197 TObject *oldvalue = luaH_setstr(L, L->gt, s); 196 TObject *oldvalue = luaH_setstr(L, L->gt, name);
198 Closure *tm; 197 Closure *tm;
199 if (!HAS_TM_SETGLOBAL(L, ttype(oldvalue)) || /* no tag methods? */ 198 if (!HAS_TM_SETGLOBAL(L, ttype(oldvalue)) || /* no tag methods? */
200 (tm = luaT_gettmbyObj(G(L), oldvalue, TM_SETGLOBAL)) == NULL) { 199 (tm = luaT_gettmbyObj(G(L), oldvalue, TM_SETGLOBAL)) == NULL) {
201 setobj(oldvalue, top-1); /* raw set */ 200 setobj(oldvalue, val); /* raw set */
202 }
203 else { /* call tag method */
204 lua_assert(L->top == top);
205 luaD_checkstack(L, 3);
206 setobj(top+2, top-1); /* new value */
207 setobj(top+1, oldvalue); /* old value */
208 setsvalue(top, s); /* var name */
209 setclvalue(top-1, tm); /* tag method */
210 L->top = top+3;
211 luaD_call(L, top-1, 0);
212 lua_assert(L->top == top-1);
213 L->top = top; /* will be decremented by the callee */
214 } 201 }
202 else
203 callTM(L, "csoo", tm, name, oldvalue, val);
215} 204}
216 205
217 206
218static int call_binTM (lua_State *L, StkId top, TMS event) { 207static int call_binTM (lua_State *L, const TObject *p1, const TObject *p2,
219 /* try first operand */ 208 TObject *res, TMS event) {
220 Closure *tm = luaT_gettmbyObj(G(L), top-2, event); 209 TString *opname;
221 L->top = top; 210 Closure *tm = luaT_gettmbyObj(G(L), p1, event); /* try first operand */
222 if (tm == NULL) { 211 if (tm == NULL) {
223 tm = luaT_gettmbyObj(G(L), top-1, event); /* try second operand */ 212 tm = luaT_gettmbyObj(G(L), p2, event); /* try second operand */
224 if (tm == NULL) { 213 if (tm == NULL) {
225 tm = luaT_gettm(G(L), 0, event); /* try a `global' method */ 214 tm = luaT_gettm(G(L), 0, event); /* try a `global' method */
226 if (tm == NULL) 215 if (tm == NULL)
227 return 0; /* error */ 216 return 0; /* no tag method */
228 } 217 }
229 } 218 }
230 setsvalue(L->top, luaS_new(L, luaT_eventname[event])); 219 opname = luaS_new(L, luaT_eventname[event]);
231 incr_top; 220 callTM(L, "coosr", tm, p1, p2, opname, res);
232 luaD_callTM(L, tm, 3, 1);
233 return 1; 221 return 1;
234} 222}
235 223
236 224
237static void call_arith (lua_State *L, StkId top, TMS event) { 225static void call_arith (lua_State *L, StkId p1, TMS event) {
238 if (!call_binTM(L, top, event)) 226 if (!call_binTM(L, p1, p1+1, p1, event))
239 luaG_binerror(L, top-2, LUA_TNUMBER, "perform arithmetic on"); 227 luaG_binerror(L, p1, LUA_TNUMBER, "perform arithmetic on");
240} 228}
241 229
242 230
@@ -262,19 +250,14 @@ static int luaV_strlessthan (const TString *ls, const TString *rs) {
262} 250}
263 251
264 252
265int luaV_lessthan (lua_State *L, const TObject *l, const TObject *r, StkId top) { 253int luaV_lessthan (lua_State *L, const TObject *l, const TObject *r) {
266 if (ttype(l) == LUA_TNUMBER && ttype(r) == LUA_TNUMBER) 254 if (ttype(l) == LUA_TNUMBER && ttype(r) == LUA_TNUMBER)
267 return (nvalue(l) < nvalue(r)); 255 return (nvalue(l) < nvalue(r));
268 else if (ttype(l) == LUA_TSTRING && ttype(r) == LUA_TSTRING) 256 else if (ttype(l) == LUA_TSTRING && ttype(r) == LUA_TSTRING)
269 return luaV_strlessthan(tsvalue(l), tsvalue(r)); 257 return luaV_strlessthan(tsvalue(l), tsvalue(r));
270 else { /* call TM */ 258 else { /* try TM */
271 L->top = top; 259 if (!call_binTM(L, l, r, L->top, TM_LT))
272 luaD_checkstack(L, 2); 260 luaG_ordererror(L, l, r);
273 setobj(top++, l);
274 setobj(top++, r);
275 if (!call_binTM(L, top, TM_LT))
276 luaG_ordererror(L, top);
277 L->top--;
278 return (ttype(L->top) != LUA_TNIL); 261 return (ttype(L->top) != LUA_TNIL);
279 } 262 }
280} 263}
@@ -284,7 +267,7 @@ void luaV_strconc (lua_State *L, int total, StkId top) {
284 do { 267 do {
285 int n = 2; /* number of elements handled in this pass (at least 2) */ 268 int n = 2; /* number of elements handled in this pass (at least 2) */
286 if (tostring(L, top-2) || tostring(L, top-1)) { 269 if (tostring(L, top-2) || tostring(L, top-1)) {
287 if (!call_binTM(L, top, TM_CONCAT)) 270 if (!call_binTM(L, top-2, top-1, top-2, TM_CONCAT))
288 luaG_binerror(L, top-2, LUA_TSTRING, "concat"); 271 luaG_binerror(L, top-2, LUA_TSTRING, "concat");
289 } 272 }
290 else if (tsvalue(top-1)->len > 0) { /* if len=0, do nothing */ 273 else if (tsvalue(top-1)->len > 0) { /* if len=0, do nothing */
@@ -350,17 +333,16 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
350 TString **const kstr = tf->kstr; 333 TString **const kstr = tf->kstr;
351 const lua_Hook linehook = L->linehook; 334 const lua_Hook linehook = L->linehook;
352 infovalue(base-1)->pc = &pc; 335 infovalue(base-1)->pc = &pc;
353 luaD_checkstack(L, tf->maxstacksize+EXTRA_FSTACK);
354 if (tf->is_vararg) /* varargs? */ 336 if (tf->is_vararg) /* varargs? */
355 adjust_varargs(L, base, tf->numparams); 337 adjust_varargs(L, base, tf->numparams);
356 else 338 luaD_adjusttop(L, base, tf->maxstacksize);
357 luaD_adjusttop(L, base, tf->numparams); 339 top = base+tf->numparams+tf->is_vararg;
358 top = L->top;
359 /* main loop of interpreter */ 340 /* main loop of interpreter */
360 for (;;) { 341 for (;;) {
361 const Instruction i = *pc++; 342 const Instruction i = *pc++;
343 lua_assert(L->top == base+tf->maxstacksize);
362 if (linehook) 344 if (linehook)
363 traceexec(L, base, top, linehook); 345 traceexec(L, base, linehook);
364 switch (GET_OPCODE(i)) { 346 switch (GET_OPCODE(i)) {
365 case OP_RETURN: { 347 case OP_RETURN: {
366 L->top = top; 348 L->top = top;
@@ -372,6 +354,7 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
372 L->top = top; 354 L->top = top;
373 luaD_call(L, base+GETARG_A(i), nres); 355 luaD_call(L, base+GETARG_A(i), nres);
374 top = L->top; 356 top = L->top;
357 L->top = base+tf->maxstacksize;
375 break; 358 break;
376 } 359 }
377 case OP_TAILCALL: { 360 case OP_TAILCALL: {
@@ -425,31 +408,27 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
425 break; 408 break;
426 } 409 }
427 case OP_GETTABLE: { 410 case OP_GETTABLE: {
428 luaV_gettable(L, top-2, top, top-2);
429 top--; 411 top--;
412 luaV_gettable(L, top-1, top, top-1);
430 break; 413 break;
431 } 414 }
432 case OP_GETDOTTED: { 415 case OP_GETDOTTED: {
433 setsvalue(top, kstr[GETARG_U(i)]); 416 setsvalue(top, kstr[GETARG_U(i)]);
434 luaV_gettable(L, top-1, top+1, top-1); 417 luaV_gettable(L, top-1, top, top-1);
435 break; 418 break;
436 } 419 }
437 case OP_GETINDEXED: { 420 case OP_GETINDEXED: {
438 setobj(top, base+GETARG_U(i)); 421 luaV_gettable(L, top-1, base+GETARG_U(i), top-1);
439 luaV_gettable(L, top-1, top+1, top-1);
440 break; 422 break;
441 } 423 }
442 case OP_PUSHSELF: { 424 case OP_PUSHSELF: {
443 TObject receiver; 425 setobj(top, top-1);
444 setobj(&receiver, top-1); 426 setsvalue(top+1, kstr[GETARG_U(i)]);
445 setsvalue(top, kstr[GETARG_U(i)]); 427 luaV_gettable(L, top-1, top+1, top-1);
446 top++; 428 top++;
447 luaV_gettable(L, top-2, top, top-2);
448 setobj(top-1, &receiver);
449 break; 429 break;
450 } 430 }
451 case OP_CREATETABLE: { 431 case OP_CREATETABLE: {
452 L->top = top;
453 luaC_checkGC(L); 432 luaC_checkGC(L);
454 sethvalue(top, luaH_new(L, GETARG_U(i))); 433 sethvalue(top, luaH_new(L, GETARG_U(i)));
455 top++; 434 top++;
@@ -460,15 +439,13 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
460 break; 439 break;
461 } 440 }
462 case OP_SETGLOBAL: { 441 case OP_SETGLOBAL: {
463 L->top = top; /* primitive set may generate an error */
464 luaV_setglobal(L, kstr[GETARG_U(i)], top);
465 top--; 442 top--;
443 luaV_setglobal(L, kstr[GETARG_U(i)], top);
466 break; 444 break;
467 } 445 }
468 case OP_SETTABLE: { 446 case OP_SETTABLE: {
469 StkId t = top-GETARG_A(i); 447 StkId t = top-GETARG_A(i);
470 L->top = top; /* primitive set may generate an error */ 448 luaV_settable(L, t, t+1, top-1);
471 luaV_settable(L, t, t+1, top);
472 top -= GETARG_B(i); /* pop values */ 449 top -= GETARG_B(i); /* pop values */
473 break; 450 break;
474 } 451 }
@@ -476,16 +453,13 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
476 int aux = GETARG_A(i) * LFIELDS_PER_FLUSH; 453 int aux = GETARG_A(i) * LFIELDS_PER_FLUSH;
477 int n = GETARG_B(i); 454 int n = GETARG_B(i);
478 Hash *arr = hvalue(top-n-1); 455 Hash *arr = hvalue(top-n-1);
479 L->top = top-n;
480 for (; n; n--) 456 for (; n; n--)
481 setobj(luaH_setnum(L, arr, n+aux), --top); 457 setobj(luaH_setnum(L, arr, n+aux), --top);
482 break; 458 break;
483 } 459 }
484 case OP_SETMAP: { 460 case OP_SETMAP: {
485 int n = GETARG_U(i); 461 int n = GETARG_U(i);
486 StkId finaltop = top-2*n; 462 Hash *arr = hvalue((top-2*n)-1);
487 Hash *arr = hvalue(finaltop-1);
488 L->top = finaltop;
489 for (; n; n--) { 463 for (; n; n--) {
490 top-=2; 464 top-=2;
491 setobj(luaH_set(L, arr, top), top+1); 465 setobj(luaH_set(L, arr, top), top+1);
@@ -494,7 +468,7 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
494 } 468 }
495 case OP_ADD: { 469 case OP_ADD: {
496 if (tonumber(top-2) || tonumber(top-1)) 470 if (tonumber(top-2) || tonumber(top-1))
497 call_arith(L, top, TM_ADD); 471 call_arith(L, top-2, TM_ADD);
498 else 472 else
499 nvalue(top-2) += nvalue(top-1); 473 nvalue(top-2) += nvalue(top-1);
500 top--; 474 top--;
@@ -503,7 +477,7 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
503 case OP_ADDI: { 477 case OP_ADDI: {
504 if (tonumber(top-1)) { 478 if (tonumber(top-1)) {
505 setnvalue(top, (lua_Number)GETARG_S(i)); 479 setnvalue(top, (lua_Number)GETARG_S(i));
506 call_arith(L, top+1, TM_ADD); 480 call_arith(L, top-1, TM_ADD);
507 } 481 }
508 else 482 else
509 nvalue(top-1) += (lua_Number)GETARG_S(i); 483 nvalue(top-1) += (lua_Number)GETARG_S(i);
@@ -511,7 +485,7 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
511 } 485 }
512 case OP_SUB: { 486 case OP_SUB: {
513 if (tonumber(top-2) || tonumber(top-1)) 487 if (tonumber(top-2) || tonumber(top-1))
514 call_arith(L, top, TM_SUB); 488 call_arith(L, top-2, TM_SUB);
515 else 489 else
516 nvalue(top-2) -= nvalue(top-1); 490 nvalue(top-2) -= nvalue(top-1);
517 top--; 491 top--;
@@ -519,7 +493,7 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
519 } 493 }
520 case OP_MULT: { 494 case OP_MULT: {
521 if (tonumber(top-2) || tonumber(top-1)) 495 if (tonumber(top-2) || tonumber(top-1))
522 call_arith(L, top, TM_MUL); 496 call_arith(L, top-2, TM_MUL);
523 else 497 else
524 nvalue(top-2) *= nvalue(top-1); 498 nvalue(top-2) *= nvalue(top-1);
525 top--; 499 top--;
@@ -527,14 +501,14 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
527 } 501 }
528 case OP_DIV: { 502 case OP_DIV: {
529 if (tonumber(top-2) || tonumber(top-1)) 503 if (tonumber(top-2) || tonumber(top-1))
530 call_arith(L, top, TM_DIV); 504 call_arith(L, top-2, TM_DIV);
531 else 505 else
532 nvalue(top-2) /= nvalue(top-1); 506 nvalue(top-2) /= nvalue(top-1);
533 top--; 507 top--;
534 break; 508 break;
535 } 509 }
536 case OP_POW: { 510 case OP_POW: {
537 if (!call_binTM(L, top, TM_POW)) 511 if (!call_binTM(L, top-2, top-1, top-2, TM_POW))
538 luaD_error(L, "undefined operation"); 512 luaD_error(L, "undefined operation");
539 top--; 513 top--;
540 break; 514 break;
@@ -543,14 +517,13 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
543 int n = GETARG_U(i); 517 int n = GETARG_U(i);
544 luaV_strconc(L, n, top); 518 luaV_strconc(L, n, top);
545 top -= n-1; 519 top -= n-1;
546 L->top = top;
547 luaC_checkGC(L); 520 luaC_checkGC(L);
548 break; 521 break;
549 } 522 }
550 case OP_MINUS: { 523 case OP_MINUS: {
551 if (tonumber(top-1)) { 524 if (tonumber(top-1)) {
552 setnilvalue(top); 525 setnilvalue(top);
553 call_arith(L, top+1, TM_UNM); 526 call_arith(L, top-1, TM_UNM);
554 } 527 }
555 else 528 else
556 nvalue(top-1) = -nvalue(top-1); 529 nvalue(top-1) = -nvalue(top-1);
@@ -574,22 +547,22 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
574 } 547 }
575 case OP_JMPLT: { 548 case OP_JMPLT: {
576 top -= 2; 549 top -= 2;
577 if (luaV_lessthan(L, top, top+1, top+2)) dojump(pc, i); 550 if (luaV_lessthan(L, top, top+1)) dojump(pc, i);
578 break; 551 break;
579 } 552 }
580 case OP_JMPLE: { /* a <= b === !(b<a) */ 553 case OP_JMPLE: { /* a <= b === !(b<a) */
581 top -= 2; 554 top -= 2;
582 if (!luaV_lessthan(L, top+1, top, top+2)) dojump(pc, i); 555 if (!luaV_lessthan(L, top+1, top)) dojump(pc, i);
583 break; 556 break;
584 } 557 }
585 case OP_JMPGT: { /* a > b === (b<a) */ 558 case OP_JMPGT: { /* a > b === (b<a) */
586 top -= 2; 559 top -= 2;
587 if (luaV_lessthan(L, top+1, top, top+2)) dojump(pc, i); 560 if (luaV_lessthan(L, top+1, top)) dojump(pc, i);
588 break; 561 break;
589 } 562 }
590 case OP_JMPGE: { /* a >= b === !(a<b) */ 563 case OP_JMPGE: { /* a >= b === !(a<b) */
591 top -= 2; 564 top -= 2;
592 if (!luaV_lessthan(L, top, top+1, top+2)) dojump(pc, i); 565 if (!luaV_lessthan(L, top, top+1)) dojump(pc, i);
593 break; 566 break;
594 } 567 }
595 case OP_JMPT: { 568 case OP_JMPT: {
@@ -675,11 +648,11 @@ StkId luaV_execute (lua_State *L, const Closure *cl, StkId base) {
675 } 648 }
676 case OP_CLOSURE: { 649 case OP_CLOSURE: {
677 int nup = GETARG_B(i); 650 int nup = GETARG_B(i);
651 luaC_checkGC(L);
678 L->top = top; 652 L->top = top;
679 luaV_Lclosure(L, tf->kproto[GETARG_A(i)], nup); 653 luaV_Lclosure(L, tf->kproto[GETARG_A(i)], nup);
680 top -= (nup-1); 654 top -= (nup-1);
681 lua_assert(top == L->top); 655 L->top = base+tf->maxstacksize;
682 luaC_checkGC(L);
683 break; 656 break;
684 } 657 }
685 } 658 }