aboutsummaryrefslogtreecommitdiff
path: root/lparser.c
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2017-04-28 17:57:45 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2017-04-28 17:57:45 -0300
commit502a1d1108d4e3b97e012d2ed9a496fd003b08db (patch)
tree0d1daa63ebe8af89a35ec5ecbc48f7e055eb0374 /lparser.c
parent173e41b2ebed59a716d299470de25e50aee3b921 (diff)
downloadlua-502a1d1108d4e3b97e012d2ed9a496fd003b08db.tar.gz
lua-502a1d1108d4e3b97e012d2ed9a496fd003b08db.tar.bz2
lua-502a1d1108d4e3b97e012d2ed9a496fd003b08db.zip
new opcodes for table access with constant keys (strings and integers)
Diffstat (limited to 'lparser.c')
-rw-r--r--lparser.c40
1 files changed, 24 insertions, 16 deletions
diff --git a/lparser.c b/lparser.c
index 25134f11..f78f64bd 100644
--- a/lparser.c
+++ b/lparser.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lparser.c,v 2.155 2016/08/01 19:51:24 roberto Exp roberto $ 2** $Id: lparser.c,v 2.156 2017/04/20 19:53:55 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*/
@@ -647,8 +647,7 @@ static void recfield (LexState *ls, struct ConsControl *cc) {
647 /* recfield -> (NAME | '['exp1']') = exp1 */ 647 /* recfield -> (NAME | '['exp1']') = exp1 */
648 FuncState *fs = ls->fs; 648 FuncState *fs = ls->fs;
649 int reg = ls->fs->freereg; 649 int reg = ls->fs->freereg;
650 expdesc key, val; 650 expdesc tab, key, val;
651 int rkkey;
652 if (ls->t.token == TK_NAME) { 651 if (ls->t.token == TK_NAME) {
653 checklimit(fs, cc->nh, MAX_INT, "items in a constructor"); 652 checklimit(fs, cc->nh, MAX_INT, "items in a constructor");
654 checkname(ls, &key); 653 checkname(ls, &key);
@@ -657,9 +656,10 @@ static void recfield (LexState *ls, struct ConsControl *cc) {
657 yindex(ls, &key); 656 yindex(ls, &key);
658 cc->nh++; 657 cc->nh++;
659 checknext(ls, '='); 658 checknext(ls, '=');
660 rkkey = luaK_exp2RK(fs, &key); 659 tab = *cc->t;
660 luaK_indexed(fs, &tab, &key);
661 expr(ls, &val); 661 expr(ls, &val);
662 luaK_codeABC(fs, OP_SETTABLE, cc->t->u.info, rkkey, luaK_exp2RK(fs, &val)); 662 luaK_storevar(fs, &tab, &val);
663 fs->freereg = reg; /* free registers */ 663 fs->freereg = reg; /* free registers */
664} 664}
665 665
@@ -1121,17 +1121,25 @@ static void check_conflict (LexState *ls, struct LHS_assign *lh, expdesc *v) {
1121 int extra = fs->freereg; /* eventual position to save local variable */ 1121 int extra = fs->freereg; /* eventual position to save local variable */
1122 int conflict = 0; 1122 int conflict = 0;
1123 for (; lh; lh = lh->prev) { /* check all previous assignments */ 1123 for (; lh; lh = lh->prev) { /* check all previous assignments */
1124 if (lh->v.k == VINDEXED) { /* assigning to a table? */ 1124 if (vkisindexed(lh->v.k)) { /* assignment to table field? */
1125 /* table is the upvalue/local being assigned now? */ 1125 if (lh->v.k == VINDEXUP) { /* is table an upvalue? */
1126 if (lh->v.u.ind.vt == v->k && lh->v.u.ind.t == v->u.info) { 1126 if (v->k == VUPVAL && lh->v.u.ind.t == v->u.info) {
1127 conflict = 1; 1127 conflict = 1; /* table is the upvalue being assigned now */
1128 lh->v.u.ind.vt = VLOCAL; 1128 lh->v.k = VINDEXSTR;
1129 lh->v.u.ind.t = extra; /* previous assignment will use safe copy */ 1129 lh->v.u.ind.t = extra; /* assignment will use safe copy */
1130 }
1130 } 1131 }
1131 /* index is the local being assigned? (index cannot be upvalue) */ 1132 else { /* table is a register */
1132 if (v->k == VLOCAL && lh->v.u.ind.idx == v->u.info) { 1133 if (v->k == VLOCAL && lh->v.u.ind.t == v->u.info) {
1133 conflict = 1; 1134 conflict = 1; /* table is the local being assigned now */
1134 lh->v.u.ind.idx = extra; /* previous assignment will use safe copy */ 1135 lh->v.u.ind.t = extra; /* assignment will use safe copy */
1136 }
1137 /* is index the local being assigned? */
1138 if (lh->v.k == VINDEXED && v->k == VLOCAL &&
1139 lh->v.u.ind.idx == v->u.info) {
1140 conflict = 1;
1141 lh->v.u.ind.idx = extra; /* previous assignment will use safe copy */
1142 }
1135 } 1143 }
1136 } 1144 }
1137 } 1145 }
@@ -1151,7 +1159,7 @@ static void assignment (LexState *ls, struct LHS_assign *lh, int nvars) {
1151 struct LHS_assign nv; 1159 struct LHS_assign nv;
1152 nv.prev = lh; 1160 nv.prev = lh;
1153 suffixedexp(ls, &nv.v); 1161 suffixedexp(ls, &nv.v);
1154 if (nv.v.k != VINDEXED) 1162 if (!vkisindexed(nv.v.k))
1155 check_conflict(ls, lh, &nv.v); 1163 check_conflict(ls, lh, &nv.v);
1156 checklimit(ls->fs, nvars + ls->L->nCcalls, LUAI_MAXCCALLS, 1164 checklimit(ls->fs, nvars + ls->L->nCcalls, LUAI_MAXCCALLS,
1157 "C levels"); 1165 "C levels");