aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2002-08-20 17:03:05 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2002-08-20 17:03:05 -0300
commit6c283b2f4f8398322e7a9a62ec8e131852b4e015 (patch)
tree608d5b61b14dfdb91cc5cf72637e876337cffcb8
parent576bded5137babb9c669ccff5aedf19ed65a7598 (diff)
downloadlua-6c283b2f4f8398322e7a9a62ec8e131852b4e015.tar.gz
lua-6c283b2f4f8398322e7a9a62ec8e131852b4e015.tar.bz2
lua-6c283b2f4f8398322e7a9a62ec8e131852b4e015.zip
new simetric format for ABC instructions, to avoid exchanging operands
for `commutative' operators
-rw-r--r--lcode.c67
-rw-r--r--ldebug.c19
-rw-r--r--ldebug.h4
-rw-r--r--lopcodes.c82
-rw-r--r--lopcodes.h48
-rw-r--r--lparser.c10
-rw-r--r--lvm.c54
7 files changed, 131 insertions, 153 deletions
diff --git a/lcode.c b/lcode.c
index cd976cf0..61ff0701 100644
--- a/lcode.c
+++ b/lcode.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lcode.c,v 1.108 2002/06/13 13:39:55 roberto Exp $ 2** $Id: lcode.c,v 1.109 2002/08/05 14:07:34 roberto Exp roberto $
3** Code generator for Lua 3** Code generator for Lua
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -100,14 +100,14 @@ static Instruction *getjumpcontrol (FuncState *fs, int pc) {
100static int need_value (FuncState *fs, int list, int cond) { 100static int need_value (FuncState *fs, int list, int cond) {
101 for (; list != NO_JUMP; list = luaK_getjump(fs, list)) { 101 for (; list != NO_JUMP; list = luaK_getjump(fs, list)) {
102 Instruction i = *getjumpcontrol(fs, list); 102 Instruction i = *getjumpcontrol(fs, list);
103 if (GET_OPCODE(i) != OP_TEST || GETARG_B(i) != cond) return 1; 103 if (GET_OPCODE(i) != OP_TEST || GETARG_C(i) != cond) return 1;
104 } 104 }
105 return 0; /* not found */ 105 return 0; /* not found */
106} 106}
107 107
108 108
109static void patchtestreg (Instruction *i, int reg) { 109static void patchtestreg (Instruction *i, int reg) {
110 if (reg == NO_REG) reg = GETARG_C(*i); 110 if (reg == NO_REG) reg = GETARG_B(*i);
111 SETARG_A(*i, reg); 111 SETARG_A(*i, reg);
112} 112}
113 113
@@ -122,7 +122,7 @@ static void luaK_patchlistaux (FuncState *fs, int list,
122 luaK_fixjump(fs, list, dtarget); /* jump to default target */ 122 luaK_fixjump(fs, list, dtarget); /* jump to default target */
123 } 123 }
124 else { 124 else {
125 if (GETARG_B(*i)) { 125 if (GETARG_C(*i)) {
126 lua_assert(ttarget != NO_JUMP); 126 lua_assert(ttarget != NO_JUMP);
127 patchtestreg(i, treg); 127 patchtestreg(i, treg);
128 luaK_fixjump(fs, list, ttarget); 128 luaK_fixjump(fs, list, ttarget);
@@ -409,7 +409,7 @@ int luaK_exp2RK (FuncState *fs, expdesc *e) {
409 } 409 }
410 default: break; 410 default: break;
411 } 411 }
412 /* not a constant in the right range: put in a register */ 412 /* not a constant in the right range: put it in a register */
413 return luaK_exp2anyreg(fs, e); 413 return luaK_exp2anyreg(fs, e);
414} 414}
415 415
@@ -432,8 +432,8 @@ void luaK_storevar (FuncState *fs, expdesc *var, expdesc *exp) {
432 break; 432 break;
433 } 433 }
434 case VINDEXED: { 434 case VINDEXED: {
435 int e = luaK_exp2anyreg(fs, exp); 435 int e = luaK_exp2RK(fs, exp);
436 luaK_codeABC(fs, OP_SETTABLE, e, var->info, var->aux); 436 luaK_codeABC(fs, OP_SETTABLE, var->info, var->aux, e);
437 break; 437 break;
438 } 438 }
439 default: { 439 default: {
@@ -460,8 +460,9 @@ void luaK_self (FuncState *fs, expdesc *e, expdesc *key) {
460 460
461static void invertjump (FuncState *fs, expdesc *e) { 461static void invertjump (FuncState *fs, expdesc *e) {
462 Instruction *pc = getjumpcontrol(fs, e->info); 462 Instruction *pc = getjumpcontrol(fs, e->info);
463 lua_assert(testOpMode(GET_OPCODE(*pc), OpModeT)); 463 lua_assert(testOpMode(GET_OPCODE(*pc), OpModeT) &&
464 SETARG_B(*pc, !(GETARG_B(*pc))); 464 GET_OPCODE(*pc) != OP_TEST);
465 SETARG_A(*pc, !(GETARG_A(*pc)));
465} 466}
466 467
467 468
@@ -470,13 +471,13 @@ static int jumponcond (FuncState *fs, expdesc *e, int cond) {
470 Instruction ie = getcode(fs, e); 471 Instruction ie = getcode(fs, e);
471 if (GET_OPCODE(ie) == OP_NOT) { 472 if (GET_OPCODE(ie) == OP_NOT) {
472 fs->pc--; /* remove previous OP_NOT */ 473 fs->pc--; /* remove previous OP_NOT */
473 return luaK_condjump(fs, OP_TEST, NO_REG, !cond ,GETARG_B(ie)); 474 return luaK_condjump(fs, OP_TEST, NO_REG, GETARG_B(ie), !cond);
474 } 475 }
475 /* else go through */ 476 /* else go through */
476 } 477 }
477 discharge2anyreg(fs, e); 478 discharge2anyreg(fs, e);
478 freeexp(fs, e); 479 freeexp(fs, e);
479 return luaK_condjump(fs, OP_TEST, NO_REG, cond, e->info); 480 return luaK_condjump(fs, OP_TEST, NO_REG, e->info, cond);
480} 481}
481 482
482 483
@@ -605,11 +606,6 @@ void luaK_infix (FuncState *fs, BinOpr op, expdesc *v) {
605 luaK_exp2nextreg(fs, v); /* operand must be on the `stack' */ 606 luaK_exp2nextreg(fs, v); /* operand must be on the `stack' */
606 break; 607 break;
607 } 608 }
608 case OPR_SUB: case OPR_DIV: case OPR_POW: {
609 /* non-comutative operators */
610 luaK_exp2anyreg(fs, v); /* first operand must be a register */
611 break;
612 }
613 default: { 609 default: {
614 luaK_exp2RK(fs, v); 610 luaK_exp2RK(fs, v);
615 break; 611 break;
@@ -619,13 +615,11 @@ void luaK_infix (FuncState *fs, BinOpr op, expdesc *v) {
619 615
620 616
621static void codebinop (FuncState *fs, expdesc *res, BinOpr op, 617static void codebinop (FuncState *fs, expdesc *res, BinOpr op,
622 int o1, int o2, int ic) { 618 int o1, int o2) {
623 switch (op) { 619 switch (op) {
624 case OPR_SUB: 620 case OPR_SUB:
625 case OPR_DIV: 621 case OPR_DIV:
626 case OPR_POW: 622 case OPR_POW:
627 lua_assert(!ic);
628 /* go through */
629 case OPR_ADD: 623 case OPR_ADD:
630 case OPR_MULT: { /* ORDER OPR */ 624 case OPR_MULT: { /* ORDER OPR */
631 OpCode opc = cast(OpCode, (op - OPR_ADD) + OP_ADD); 625 OpCode opc = cast(OpCode, (op - OPR_ADD) + OP_ADD);
@@ -635,20 +629,21 @@ static void codebinop (FuncState *fs, expdesc *res, BinOpr op,
635 } 629 }
636 case OPR_NE: 630 case OPR_NE:
637 case OPR_EQ: { 631 case OPR_EQ: {
638 res->info = luaK_condjump(fs, OP_EQ, o1, (op == OPR_EQ), o2); 632 res->info = luaK_condjump(fs, OP_EQ, (op == OPR_EQ), o1, o2);
639 res->k = VJMP; 633 res->k = VJMP;
640 break; 634 break;
641 } 635 }
642 case OPR_LT:
643 case OPR_LE:
644 case OPR_GT: 636 case OPR_GT:
645 case OPR_GE: { /* ORDER OPR */ 637 case OPR_GE: { /* ORDER OPR */
646 OpCode opc; 638 int temp;
647 int i = op - OPR_LT; 639 temp = o1; o1 = o2; o2 = temp; /* o1 <==> o2 */
648 if (ic) /* operands were interchanged? */ 640 op -= 2; /* GT -> LT, GE -> LE */
649 i = (i+2)&3; /* correct operator */ 641 /* go through */
650 opc = cast(OpCode, i + OP_LT); 642 }
651 res->info = luaK_condjump(fs, opc, o1, 1, o2); 643 case OPR_LT:
644 case OPR_LE: {
645 OpCode opc = cast(OpCode, (op - OPR_LT) + OP_LT);
646 res->info = luaK_condjump(fs, opc, 1, o1, o2);
652 res->k = VJMP; 647 res->k = VJMP;
653 break; 648 break;
654 } 649 }
@@ -691,21 +686,11 @@ void luaK_posfix (FuncState *fs, BinOpr op, expdesc *e1, expdesc *e2) {
691 break; 686 break;
692 } 687 }
693 default: { 688 default: {
694 int o1, o2; 689 int o1 = luaK_exp2RK(fs, e1);
695 int ic; /* interchange flag */ 690 int o2 = luaK_exp2RK(fs, e2);
696 if (e1->k != VK) { /* not a constant operator? */
697 o1 = e1->info;
698 o2 = luaK_exp2RK(fs, e2); /* maybe other operator is constant... */
699 ic = 0;
700 }
701 else { /* interchange operands */
702 o2 = luaK_exp2RK(fs, e1); /* constant must be 2nd operand */
703 o1 = luaK_exp2anyreg(fs, e2); /* other operator must be in register */
704 ic = 1;
705 }
706 freeexp(fs, e2); 691 freeexp(fs, e2);
707 freeexp(fs, e1); 692 freeexp(fs, e1);
708 codebinop(fs, e1, op, o1, o2, ic); 693 codebinop(fs, e1, op, o1, o2);
709 } 694 }
710 } 695 }
711} 696}
diff --git a/ldebug.c b/ldebug.c
index d4d0eb00..55c53f9d 100644
--- a/ldebug.c
+++ b/ldebug.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: ldebug.c,v 1.131 2002/08/08 20:08:41 roberto Exp roberto $ 2** $Id: ldebug.c,v 1.132 2002/08/12 17:23:12 roberto Exp roberto $
3** Debug Interface 3** Debug Interface
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -269,6 +269,11 @@ static int checkopenop (const Proto *pt, int pc) {
269} 269}
270 270
271 271
272static int checkRK (const Proto *pt, int r) {
273 return (r < pt->maxstacksize || (r >= MAXSTACK && r-MAXSTACK < pt->sizek));
274}
275
276
272static Instruction luaG_symbexec (const Proto *pt, int lastpc, int reg) { 277static Instruction luaG_symbexec (const Proto *pt, int lastpc, int reg) {
273 int pc; 278 int pc;
274 int last; /* stores position of last instruction that changed `reg' */ 279 int last; /* stores position of last instruction that changed `reg' */
@@ -285,11 +290,13 @@ static Instruction luaG_symbexec (const Proto *pt, int lastpc, int reg) {
285 case iABC: { 290 case iABC: {
286 b = GETARG_B(i); 291 b = GETARG_B(i);
287 c = GETARG_C(i); 292 c = GETARG_C(i);
288 if (testOpMode(op, OpModeBreg)) 293 if (testOpMode(op, OpModeBreg)) {
289 checkreg(pt, b); 294 checkreg(pt, b);
290 if (testOpMode(op, OpModeCreg)) 295 }
291 check(c < pt->maxstacksize || 296 else if (testOpMode(op, OpModeBrk))
292 (c >= MAXSTACK && c-MAXSTACK < pt->sizek)); 297 check(checkRK(pt, b));
298 if (testOpMode(op, OpModeCrk))
299 check(checkRK(pt, c));
293 break; 300 break;
294 } 301 }
295 case iABx: { 302 case iABx: {
@@ -496,7 +503,7 @@ void luaG_concaterror (lua_State *L, StkId p1, StkId p2) {
496} 503}
497 504
498 505
499void luaG_aritherror (lua_State *L, StkId p1, const TObject *p2) { 506void luaG_aritherror (lua_State *L, const TObject *p1, const TObject *p2) {
500 TObject temp; 507 TObject temp;
501 if (luaV_tonumber(p1, &temp) == NULL) 508 if (luaV_tonumber(p1, &temp) == NULL)
502 p2 = p1; /* first operand is wrong */ 509 p2 = p1; /* first operand is wrong */
diff --git a/ldebug.h b/ldebug.h
index 19be8fee..e0d0a097 100644
--- a/ldebug.h
+++ b/ldebug.h
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: ldebug.h,v 1.29 2002/08/08 20:08:41 roberto Exp roberto $ 2** $Id: ldebug.h,v 1.30 2002/08/12 17:23:12 roberto Exp roberto $
3** Auxiliary functions from Debug Interface module 3** Auxiliary functions from Debug Interface module
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -23,7 +23,7 @@
23 23
24void luaG_typeerror (lua_State *L, const TObject *o, const char *opname); 24void luaG_typeerror (lua_State *L, const TObject *o, const char *opname);
25void luaG_concaterror (lua_State *L, StkId p1, StkId p2); 25void luaG_concaterror (lua_State *L, StkId p1, StkId p2);
26void luaG_aritherror (lua_State *L, StkId p1, const TObject *p2); 26void luaG_aritherror (lua_State *L, const TObject *p1, const TObject *p2);
27int luaG_ordererror (lua_State *L, const TObject *p1, const TObject *p2); 27int luaG_ordererror (lua_State *L, const TObject *p1, const TObject *p2);
28void luaG_runerror (lua_State *L, const char *fmt, ...); 28void luaG_runerror (lua_State *L, const char *fmt, ...);
29void luaG_errormsg (lua_State *L); 29void luaG_errormsg (lua_State *L);
diff --git a/lopcodes.c b/lopcodes.c
index 767c6bd5..8dd3bee3 100644
--- a/lopcodes.c
+++ b/lopcodes.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lopcodes.c,v 1.19 2002/05/13 13:09:00 roberto Exp roberto $ 2** $Id: lopcodes.c,v 1.20 2002/06/12 14:51:31 roberto Exp roberto $
3** extracted automatically from lopcodes.h by mkprint.lua 3** extracted automatically from lopcodes.h by mkprint.lua
4** DO NOT EDIT 4** DO NOT EDIT
5** See Copyright Notice in lua.h 5** See Copyright Notice in lua.h
@@ -39,8 +39,6 @@ const char *const luaP_opnames[] = {
39 "EQ", 39 "EQ",
40 "LT", 40 "LT",
41 "LE", 41 "LE",
42 "GT",
43 "GE",
44 "TEST", 42 "TEST",
45 "CALL", 43 "CALL",
46 "TAILCALL", 44 "TAILCALL",
@@ -56,49 +54,47 @@ const char *const luaP_opnames[] = {
56 54
57#endif 55#endif
58 56
59#define opmode(t,x,b,c,sa,k,m) (((t)<<OpModeT) | \ 57#define opmode(t,b,bk,ck,sa,k,m) (((t)<<OpModeT) | \
60 ((b)<<OpModeBreg) | ((c)<<OpModeCreg) | \ 58 ((b)<<OpModeBreg) | ((bk)<<OpModeBrk) | ((ck)<<OpModeCrk) | \
61 ((sa)<<OpModesetA) | ((k)<<OpModeK) | (m)) 59 ((sa)<<OpModesetA) | ((k)<<OpModeK) | (m))
62 60
63 61
64const lu_byte luaP_opmodes[NUM_OPCODES] = { 62const lu_byte luaP_opmodes[NUM_OPCODES] = {
65/* T _ B C sA K mode opcode */ 63/* T B Bk Ck sA K mode opcode */
66 opmode(0,0,1,0, 1,0,iABC) /* OP_MOVE */ 64 opmode(0, 1, 0, 0, 1, 0, iABC) /* OP_MOVE */
67 ,opmode(0,0,0,0, 1,1,iABx) /* OP_LOADK */ 65 ,opmode(0, 0, 0, 0, 1, 1, iABx) /* OP_LOADK */
68 ,opmode(0,0,0,0, 1,0,iABC) /* OP_LOADBOOL */ 66 ,opmode(0, 0, 0, 0, 1, 0, iABC) /* OP_LOADBOOL */
69 ,opmode(0,0,1,0, 1,0,iABC) /* OP_LOADNIL */ 67 ,opmode(0, 1, 0, 0, 1, 0, iABC) /* OP_LOADNIL */
70 ,opmode(0,0,0,0, 1,0,iABC) /* OP_GETUPVAL */ 68 ,opmode(0, 0, 0, 0, 1, 0, iABC) /* OP_GETUPVAL */
71 ,opmode(0,0,0,0, 1,1,iABx) /* OP_GETGLOBAL */ 69 ,opmode(0, 0, 0, 0, 1, 1, iABx) /* OP_GETGLOBAL */
72 ,opmode(0,0,1,1, 1,0,iABC) /* OP_GETTABLE */ 70 ,opmode(0, 1, 0, 1, 1, 0, iABC) /* OP_GETTABLE */
73 ,opmode(0,0,0,0, 0,1,iABx) /* OP_SETGLOBAL */ 71 ,opmode(0, 0, 0, 0, 0, 1, iABx) /* OP_SETGLOBAL */
74 ,opmode(0,0,0,0, 0,0,iABC) /* OP_SETUPVAL */ 72 ,opmode(0, 0, 0, 0, 0, 0, iABC) /* OP_SETUPVAL */
75 ,opmode(0,0,1,1, 0,0,iABC) /* OP_SETTABLE */ 73 ,opmode(0, 0, 1, 1, 0, 0, iABC) /* OP_SETTABLE */
76 ,opmode(0,0,0,0, 1,0,iABC) /* OP_NEWTABLE */ 74 ,opmode(0, 0, 0, 0, 1, 0, iABC) /* OP_NEWTABLE */
77 ,opmode(0,0,1,1, 1,0,iABC) /* OP_SELF */ 75 ,opmode(0, 1, 0, 1, 1, 0, iABC) /* OP_SELF */
78 ,opmode(0,0,1,1, 1,0,iABC) /* OP_ADD */ 76 ,opmode(0, 0, 1, 1, 1, 0, iABC) /* OP_ADD */
79 ,opmode(0,0,1,1, 1,0,iABC) /* OP_SUB */ 77 ,opmode(0, 0, 1, 1, 1, 0, iABC) /* OP_SUB */
80 ,opmode(0,0,1,1, 1,0,iABC) /* OP_MUL */ 78 ,opmode(0, 0, 1, 1, 1, 0, iABC) /* OP_MUL */
81 ,opmode(0,0,1,1, 1,0,iABC) /* OP_DIV */ 79 ,opmode(0, 0, 1, 1, 1, 0, iABC) /* OP_DIV */
82 ,opmode(0,0,1,1, 1,0,iABC) /* OP_POW */ 80 ,opmode(0, 0, 1, 1, 1, 0, iABC) /* OP_POW */
83 ,opmode(0,0,1,0, 1,0,iABC) /* OP_UNM */ 81 ,opmode(0, 1, 0, 0, 1, 0, iABC) /* OP_UNM */
84 ,opmode(0,0,1,0, 1,0,iABC) /* OP_NOT */ 82 ,opmode(0, 1, 0, 0, 1, 0, iABC) /* OP_NOT */
85 ,opmode(0,0,1,1, 1,0,iABC) /* OP_CONCAT */ 83 ,opmode(0, 1, 0, 1, 1, 0, iABC) /* OP_CONCAT */
86 ,opmode(0,0,0,0, 0,0,iAsBx) /* OP_JMP */ 84 ,opmode(0, 0, 0, 0, 0, 0, iAsBx) /* OP_JMP */
87 ,opmode(1,0,0,1, 0,0,iABC) /* OP_EQ */ 85 ,opmode(1, 0, 1, 1, 0, 0, iABC) /* OP_EQ */
88 ,opmode(1,0,0,1, 0,0,iABC) /* OP_LT */ 86 ,opmode(1, 0, 1, 1, 0, 0, iABC) /* OP_LT */
89 ,opmode(1,0,0,1, 0,0,iABC) /* OP_LE */ 87 ,opmode(1, 0, 1, 1, 0, 0, iABC) /* OP_LE */
90 ,opmode(1,0,0,1, 0,0,iABC) /* OP_GT */ 88 ,opmode(1, 1, 0, 0, 1, 0, iABC) /* OP_TEST */
91 ,opmode(1,0,0,1, 0,0,iABC) /* OP_GE */ 89 ,opmode(0, 0, 0, 0, 0, 0, iABC) /* OP_CALL */
92 ,opmode(1,0,0,1, 1,0,iABC) /* OP_TEST */ 90 ,opmode(0, 0, 0, 0, 0, 0, iABC) /* OP_TAILCALL */
93 ,opmode(0,0,0,0, 0,0,iABC) /* OP_CALL */ 91 ,opmode(0, 0, 0, 0, 0, 0, iABC) /* OP_RETURN */
94 ,opmode(0,0,0,0, 0,0,iABC) /* OP_TAILCALL */ 92 ,opmode(0, 0, 0, 0, 0, 0, iAsBx) /* OP_FORLOOP */
95 ,opmode(0,0,0,0, 0,0,iABC) /* OP_RETURN */ 93 ,opmode(1, 0, 0, 0, 0, 0, iABC) /* OP_TFORLOOP */
96 ,opmode(0,0,0,0, 0,0,iAsBx) /* OP_FORLOOP */ 94 ,opmode(0, 0, 0, 0, 0, 0, iAsBx) /* OP_TFORPREP */
97 ,opmode(1,0,0,0, 0,0,iABC) /* OP_TFORLOOP */ 95 ,opmode(0, 0, 0, 0, 0, 0, iABx) /* OP_SETLIST */
98 ,opmode(0,0,0,0, 0,0,iAsBx) /* OP_TFORPREP */ 96 ,opmode(0, 0, 0, 0, 0, 0, iABx) /* OP_SETLISTO */
99 ,opmode(0,0,0,0, 0,0,iABx) /* OP_SETLIST */ 97 ,opmode(0, 0, 0, 0, 0, 0, iABC) /* OP_CLOSE */
100 ,opmode(0,0,0,0, 0,0,iABx) /* OP_SETLISTO */ 98 ,opmode(0, 0, 0, 0, 1, 0, iABx) /* OP_CLOSURE */
101 ,opmode(0,0,0,0, 0,0,iABC) /* OP_CLOSE */
102 ,opmode(0,0,0,0, 1,0,iABx) /* OP_CLOSURE */
103}; 99};
104 100
diff --git a/lopcodes.h b/lopcodes.h
index f2d5b10b..7c695324 100644
--- a/lopcodes.h
+++ b/lopcodes.h
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lopcodes.h,v 1.99 2002/06/12 14:51:31 roberto Exp $ 2** $Id: lopcodes.h,v 1.100 2002/08/05 14:46:43 roberto Exp roberto $
3** Opcodes for Lua virtual machine 3** Opcodes for Lua virtual machine
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -14,9 +14,9 @@
14 We assume that instructions are unsigned numbers. 14 We assume that instructions are unsigned numbers.
15 All instructions have an opcode in the first 6 bits. 15 All instructions have an opcode in the first 6 bits.
16 Instructions can have the following fields: 16 Instructions can have the following fields:
17 `A' : 8 bits (25-32) 17 `A' : 8 bits
18 `B' : 8 bits (17-24) 18 `B' : 9 bits
19 `C' : 10 bits (7-16) 19 `C' : 9 bits
20 `Bx' : 18 bits (`B' and `C' together) 20 `Bx' : 18 bits (`B' and `C' together)
21 `sBx' : signed Bx 21 `sBx' : signed Bx
22 22
@@ -34,8 +34,8 @@ enum OpMode {iABC, iABx, iAsBx}; /* basic instruction format */
34/* 34/*
35** size and position of opcode arguments. 35** size and position of opcode arguments.
36*/ 36*/
37#define SIZE_C 10 37#define SIZE_C 9
38#define SIZE_B 8 38#define SIZE_B 9
39#define SIZE_Bx (SIZE_C + SIZE_B) 39#define SIZE_Bx (SIZE_C + SIZE_B)
40#define SIZE_A 8 40#define SIZE_A 8
41 41
@@ -112,16 +112,15 @@ enum OpMode {iABC, iABx, iAsBx}; /* basic instruction format */
112 112
113 113
114/* 114/*
115** invalid registers that fits in 8 bits 115** invalid register that fits in 8 bits
116*/ 116*/
117#define NO_REG MAXARG_A 117#define NO_REG MAXARG_A
118#define NO_REG1 (NO_REG+1)
119 118
120 119
121/* 120/*
122** R(x) - register 121** R(x) - register
123** Kst(x) - constant (in constant table) 122** Kst(x) - constant (in constant table)
124** R/K(x) == if x < MAXSTACK then R(x) else Kst(x-MAXSTACK) 123** RK(x) == if x < MAXSTACK then R(x) else Kst(x-MAXSTACK)
125*/ 124*/
126 125
127typedef enum { 126typedef enum {
@@ -135,21 +134,21 @@ OP_LOADNIL,/* A B R(A) := ... := R(B) := nil */
135OP_GETUPVAL,/* A B R(A) := UpValue[B] */ 134OP_GETUPVAL,/* A B R(A) := UpValue[B] */
136 135
137OP_GETGLOBAL,/* A Bx R(A) := Gbl[Kst(Bx)] */ 136OP_GETGLOBAL,/* A Bx R(A) := Gbl[Kst(Bx)] */
138OP_GETTABLE,/* A B C R(A) := R(B)[R/K(C)] */ 137OP_GETTABLE,/* A B C R(A) := R(B)[RK(C)] */
139 138
140OP_SETGLOBAL,/* A Bx Gbl[Kst(Bx)] := R(A) */ 139OP_SETGLOBAL,/* A Bx Gbl[Kst(Bx)] := R(A) */
141OP_SETUPVAL,/* A B UpValue[B] := R(A) */ 140OP_SETUPVAL,/* A B UpValue[B] := R(A) */
142OP_SETTABLE,/* A B C R(B)[R/K(C)] := R(A) */ 141OP_SETTABLE,/* A B C R(A)[RK(B)] := RK(C) */
143 142
144OP_NEWTABLE,/* A B C R(A) := {} (size = B,C) */ 143OP_NEWTABLE,/* A B C R(A) := {} (size = B,C) */
145 144
146OP_SELF,/* A B C R(A+1) := R(B); R(A) := R(B)[R/K(C)] */ 145OP_SELF,/* A B C R(A+1) := R(B); R(A) := R(B)[RK(C)] */
147 146
148OP_ADD,/* A B C R(A) := R(B) + R/K(C) */ 147OP_ADD,/* A B C R(A) := RK(B) + RK(C) */
149OP_SUB,/* A B C R(A) := R(B) - R/K(C) */ 148OP_SUB,/* A B C R(A) := RK(B) - RK(C) */
150OP_MUL,/* A B C R(A) := R(B) * R/K(C) */ 149OP_MUL,/* A B C R(A) := RK(B) * RK(C) */
151OP_DIV,/* A B C R(A) := R(B) / R/K(C) */ 150OP_DIV,/* A B C R(A) := RK(B) / RK(C) */
152OP_POW,/* A B C R(A) := R(B) ^ R/K(C) */ 151OP_POW,/* A B C R(A) := RK(B) ^ RK(C) */
153OP_UNM,/* A B R(A) := -R(B) */ 152OP_UNM,/* A B R(A) := -R(B) */
154OP_NOT,/* A B R(A) := not R(B) */ 153OP_NOT,/* A B R(A) := not R(B) */
155 154
@@ -157,13 +156,11 @@ OP_CONCAT,/* A B C R(A) := R(B).. ... ..R(C) */
157 156
158OP_JMP,/* sBx PC += sBx */ 157OP_JMP,/* sBx PC += sBx */
159 158
160OP_EQ,/* A B C if ((R(A) == R/K(C)) ~= B) then pc++ */ 159OP_EQ,/* A B C if ((RK(B) == RK(C)) ~= A) then pc++ */
161OP_LT,/* A B C if ((R(A) < R/K(C)) ~= B) then pc++ */ 160OP_LT,/* A B C if ((RK(B) < RK(C)) ~= A) then pc++ */
162OP_LE,/* A B C if ((R(A) <= R/K(C)) ~= B) then pc++ */ 161OP_LE,/* A B C if ((RK(B) <= RK(C)) ~= A) then pc++ */
163OP_GT,/* A B C if ((R(A) > R/K(C)) ~= B) then pc++ */
164OP_GE,/* A B C if ((R(A) >= R/K(C)) ~= B) then pc++ */
165 162
166OP_TEST,/* A B C if (R(C) <=> B) then R(A) := R(C) else pc++ */ 163OP_TEST,/* A B C if (R(B) <=> C) then R(A) := R(B) else pc++ */
167 164
168OP_CALL,/* A B C R(A), ... ,R(A+C-2) := R(A)(R(A+1), ... ,R(A+B-1)) */ 165OP_CALL,/* A B C R(A), ... ,R(A+C-2) := R(A)(R(A+1), ... ,R(A+B-1)) */
169OP_TAILCALL,/* A B C return R(A)(R(A+1), ... ,R(A+B-1)) */ 166OP_TAILCALL,/* A B C return R(A)(R(A+1), ... ,R(A+B-1)) */
@@ -207,12 +204,15 @@ OP_CLOSURE/* A Bx R(A) := closure(KPROTO[Bx], R(A), ... ,R(A+n)) */
207*/ 204*/
208enum OpModeMask { 205enum OpModeMask {
209 OpModeBreg = 2, /* B is a register */ 206 OpModeBreg = 2, /* B is a register */
210 OpModeCreg, /* C is a register/constant */ 207 OpModeBrk, /* B is a register/constant */
208 OpModeCrk, /* C is a register/constant */
211 OpModesetA, /* instruction set register A */ 209 OpModesetA, /* instruction set register A */
212 OpModeK, /* Bx is a constant */ 210 OpModeK, /* Bx is a constant */
213 OpModeT /* operator is a test */ 211 OpModeT /* operator is a test */
212
214}; 213};
215 214
215
216extern const lu_byte luaP_opmodes[NUM_OPCODES]; 216extern const lu_byte luaP_opmodes[NUM_OPCODES];
217 217
218#define getOpMode(m) (cast(enum OpMode, luaP_opmodes[m] & 3)) 218#define getOpMode(m) (cast(enum OpMode, luaP_opmodes[m] & 3))
diff --git a/lparser.c b/lparser.c
index bca90809..8a82db68 100644
--- a/lparser.c
+++ b/lparser.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lparser.c,v 1.190 2002/07/04 18:23:42 roberto Exp $ 2** $Id: lparser.c,v 1.191 2002/08/05 17:35:45 roberto Exp roberto $
3** Lua Parser 3** Lua Parser
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -324,7 +324,7 @@ static void open_func (LexState *ls, FuncState *fs) {
324 fs->bl = NULL; 324 fs->bl = NULL;
325 f->code = NULL; 325 f->code = NULL;
326 f->source = ls->source; 326 f->source = ls->source;
327 f->maxstacksize = 1; /* register 0 is always valid */ 327 f->maxstacksize = 2; /* registers 0/1 are always valid */
328 f->numparams = 0; /* default for main chunk */ 328 f->numparams = 0; /* default for main chunk */
329 f->is_vararg = 0; /* default for main chunk */ 329 f->is_vararg = 0; /* default for main chunk */
330} 330}
@@ -489,8 +489,8 @@ static void recfield (LexState *ls, struct ConsControl *cc) {
489 check(ls, '='); 489 check(ls, '=');
490 luaK_exp2RK(fs, &key); 490 luaK_exp2RK(fs, &key);
491 expr(ls, &val); 491 expr(ls, &val);
492 luaK_exp2anyreg(fs, &val); 492 luaK_codeABC(fs, OP_SETTABLE, cc->t->info, luaK_exp2RK(fs, &key),
493 luaK_codeABC(fs, OP_SETTABLE, val.info, cc->t->info, luaK_exp2RK(fs, &key)); 493 luaK_exp2RK(fs, &val));
494 fs->freereg = reg; /* free registers */ 494 fs->freereg = reg; /* free registers */
495} 495}
496 496
@@ -735,7 +735,7 @@ static const struct {
735 lu_byte right; /* right priority */ 735 lu_byte right; /* right priority */
736} priority[] = { /* ORDER OPR */ 736} priority[] = { /* ORDER OPR */
737 {6, 6}, {6, 6}, {7, 7}, {7, 7}, /* arithmetic */ 737 {6, 6}, {6, 6}, {7, 7}, {7, 7}, /* arithmetic */
738 {10, 9}, {5, 4}, /* power and concat (right associative) */ 738 {10, 9}, {5, 4}, /* power and concat (right associative) */
739 {3, 3}, {3, 3}, /* equality */ 739 {3, 3}, {3, 3}, /* equality */
740 {3, 3}, {3, 3}, {3, 3}, {3, 3}, /* order */ 740 {3, 3}, {3, 3}, {3, 3}, {3, 3}, /* order */
741 {2, 2}, {1, 1} /* logical (and/or) */ 741 {2, 2}, {1, 1} /* logical (and/or) */
diff --git a/lvm.c b/lvm.c
index fe30a27f..b0184b46 100644
--- a/lvm.c
+++ b/lvm.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lvm.c,v 1.251 2002/08/07 19:22:39 roberto Exp roberto $ 2** $Id: lvm.c,v 1.252 2002/08/12 17:23:12 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*/
@@ -318,7 +318,8 @@ void luaV_concat (lua_State *L, int total, int last) {
318} 318}
319 319
320 320
321static void Arith (lua_State *L, StkId ra, StkId rb, StkId rc, TMS op) { 321static void Arith (lua_State *L, StkId ra,
322 const TObject *rb, const TObject *rc, TMS op) {
322 TObject tempb, tempc; 323 TObject tempb, tempc;
323 const TObject *b, *c; 324 const TObject *b, *c;
324 if ((b = luaV_tonumber(rb, &tempb)) != NULL && 325 if ((b = luaV_tonumber(rb, &tempb)) != NULL &&
@@ -356,10 +357,9 @@ static void Arith (lua_State *L, StkId ra, StkId rb, StkId rc, TMS op) {
356 357
357#define RA(i) (base+GETARG_A(i)) 358#define RA(i) (base+GETARG_A(i))
358#define RB(i) (base+GETARG_B(i)) 359#define RB(i) (base+GETARG_B(i))
360#define RKB(i) ((GETARG_B(i) < MAXSTACK) ? RB(i) : k+GETARG_B(i)-MAXSTACK)
359#define RC(i) (base+GETARG_C(i)) 361#define RC(i) (base+GETARG_C(i))
360#define RKC(i) ((GETARG_C(i) < MAXSTACK) ? \ 362#define RKC(i) ((GETARG_C(i) < MAXSTACK) ? RC(i) : k+GETARG_C(i)-MAXSTACK)
361 base+GETARG_C(i) : \
362 k+GETARG_C(i)-MAXSTACK)
363#define KBx(i) (k+GETARG_Bx(i)) 363#define KBx(i) (k+GETARG_Bx(i))
364 364
365 365
@@ -423,7 +423,7 @@ StkId luaV_execute (lua_State *L) {
423 break; 423 break;
424 } 424 }
425 case OP_GETGLOBAL: { 425 case OP_GETGLOBAL: {
426 StkId rb = KBx(i); 426 TObject *rb = KBx(i);
427 const TObject *v; 427 const TObject *v;
428 lua_assert(ttisstring(rb) && ttistable(&cl->g)); 428 lua_assert(ttisstring(rb) && ttistable(&cl->g));
429 v = luaH_getstr(hvalue(&cl->g), tsvalue(rb)); 429 v = luaH_getstr(hvalue(&cl->g), tsvalue(rb));
@@ -456,7 +456,7 @@ StkId luaV_execute (lua_State *L) {
456 break; 456 break;
457 } 457 }
458 case OP_SETTABLE: { 458 case OP_SETTABLE: {
459 luaV_settable(L, RB(i), RKC(i), ra); 459 luaV_settable(L, ra, RKB(i), RKC(i));
460 break; 460 break;
461 } 461 }
462 case OP_NEWTABLE: { 462 case OP_NEWTABLE: {
@@ -482,8 +482,8 @@ StkId luaV_execute (lua_State *L) {
482 break; 482 break;
483 } 483 }
484 case OP_ADD: { 484 case OP_ADD: {
485 StkId rb = RB(i); 485 TObject *rb = RKB(i);
486 StkId rc = RKC(i); 486 TObject *rc = RKC(i);
487 if (ttisnumber(rb) && ttisnumber(rc)) { 487 if (ttisnumber(rb) && ttisnumber(rc)) {
488 setnvalue(ra, nvalue(rb) + nvalue(rc)); 488 setnvalue(ra, nvalue(rb) + nvalue(rc));
489 } 489 }
@@ -492,8 +492,8 @@ StkId luaV_execute (lua_State *L) {
492 break; 492 break;
493 } 493 }
494 case OP_SUB: { 494 case OP_SUB: {
495 StkId rb = RB(i); 495 TObject *rb = RKB(i);
496 StkId rc = RKC(i); 496 TObject *rc = RKC(i);
497 if (ttisnumber(rb) && ttisnumber(rc)) { 497 if (ttisnumber(rb) && ttisnumber(rc)) {
498 setnvalue(ra, nvalue(rb) - nvalue(rc)); 498 setnvalue(ra, nvalue(rb) - nvalue(rc));
499 } 499 }
@@ -502,8 +502,8 @@ StkId luaV_execute (lua_State *L) {
502 break; 502 break;
503 } 503 }
504 case OP_MUL: { 504 case OP_MUL: {
505 StkId rb = RB(i); 505 TObject *rb = RKB(i);
506 StkId rc = RKC(i); 506 TObject *rc = RKC(i);
507 if (ttisnumber(rb) && ttisnumber(rc)) { 507 if (ttisnumber(rb) && ttisnumber(rc)) {
508 setnvalue(ra, nvalue(rb) * nvalue(rc)); 508 setnvalue(ra, nvalue(rb) * nvalue(rc));
509 } 509 }
@@ -512,8 +512,8 @@ StkId luaV_execute (lua_State *L) {
512 break; 512 break;
513 } 513 }
514 case OP_DIV: { 514 case OP_DIV: {
515 StkId rb = RB(i); 515 TObject *rb = RKB(i);
516 StkId rc = RKC(i); 516 TObject *rc = RKC(i);
517 if (ttisnumber(rb) && ttisnumber(rc)) { 517 if (ttisnumber(rb) && ttisnumber(rc)) {
518 setnvalue(ra, nvalue(rb) / nvalue(rc)); 518 setnvalue(ra, nvalue(rb) / nvalue(rc));
519 } 519 }
@@ -522,7 +522,7 @@ StkId luaV_execute (lua_State *L) {
522 break; 522 break;
523 } 523 }
524 case OP_POW: { 524 case OP_POW: {
525 Arith(L, ra, RB(i), RKC(i), TM_POW); 525 Arith(L, ra, RKB(i), RKC(i), TM_POW);
526 break; 526 break;
527 } 527 }
528 case OP_UNM: { 528 case OP_UNM: {
@@ -556,35 +556,25 @@ StkId luaV_execute (lua_State *L) {
556 break; 556 break;
557 } 557 }
558 case OP_EQ: { /* skip next instruction if test fails */ 558 case OP_EQ: { /* skip next instruction if test fails */
559 if (equalobj(L, ra, RKC(i)) != GETARG_B(i)) pc++; 559 if (equalobj(L, RKB(i), RKC(i)) != GETARG_A(i)) pc++;
560 else dojump(pc, GETARG_sBx(*pc) + 1); 560 else dojump(pc, GETARG_sBx(*pc) + 1);
561 break; 561 break;
562 } 562 }
563 case OP_LT: { 563 case OP_LT: {
564 if (luaV_lessthan(L, ra, RKC(i)) != GETARG_B(i)) pc++; 564 if (luaV_lessthan(L, RKB(i), RKC(i)) != GETARG_A(i)) pc++;
565 else dojump(pc, GETARG_sBx(*pc) + 1); 565 else dojump(pc, GETARG_sBx(*pc) + 1);
566 break; 566 break;
567 } 567 }
568 case OP_LE: { 568 case OP_LE: {
569 if (luaV_lessequal(L, ra, RKC(i)) != GETARG_B(i)) pc++; 569 if (luaV_lessequal(L, RKB(i), RKC(i)) != GETARG_A(i)) pc++;
570 else dojump(pc, GETARG_sBx(*pc) + 1);
571 break;
572 }
573 case OP_GT: {
574 if (luaV_lessthan(L, RKC(i), ra) != GETARG_B(i)) pc++;
575 else dojump(pc, GETARG_sBx(*pc) + 1);
576 break;
577 }
578 case OP_GE: {
579 if (luaV_lessequal(L, RKC(i), ra) != GETARG_B(i)) pc++;
580 else dojump(pc, GETARG_sBx(*pc) + 1); 570 else dojump(pc, GETARG_sBx(*pc) + 1);
581 break; 571 break;
582 } 572 }
583 case OP_TEST: { 573 case OP_TEST: {
584 StkId rc = RKC(i); 574 TObject *rb = RB(i);
585 if (l_isfalse(rc) == GETARG_B(i)) pc++; 575 if (l_isfalse(rb) == GETARG_C(i)) pc++;
586 else { 576 else {
587 setobj(ra, rc); 577 setobj(ra, rb);
588 dojump(pc, GETARG_sBx(*pc) + 1); 578 dojump(pc, GETARG_sBx(*pc) + 1);
589 } 579 }
590 break; 580 break;