summaryrefslogtreecommitdiff
path: root/lvm.c
diff options
context:
space:
mode:
Diffstat (limited to 'lvm.c')
-rw-r--r--lvm.c41
1 files changed, 28 insertions, 13 deletions
diff --git a/lvm.c b/lvm.c
index aad965d6..1535700f 100644
--- a/lvm.c
+++ b/lvm.c
@@ -866,7 +866,8 @@ void luaV_finishOp (lua_State *L) {
866#define ProtectNT(exp) (savepc(L), (exp), updatetrap(ci)) 866#define ProtectNT(exp) (savepc(L), (exp), updatetrap(ci))
867 867
868/* 868/*
869** Protect code that will finish the loop (returns). 869** Protect code that will finish the loop (returns) or can only raise
870** errors.
870*/ 871*/
871#define halfProtect(exp) (savepc(L), (exp)) 872#define halfProtect(exp) (savepc(L), (exp))
872 873
@@ -1457,7 +1458,8 @@ void luaV_execute (lua_State *L, CallInfo *ci) {
1457 vmbreak; 1458 vmbreak;
1458 } 1459 }
1459 vmcase(OP_TBC) { 1460 vmcase(OP_TBC) {
1460 luaF_newtbcupval(L, ra); /* create new to-be-closed upvalue */ 1461 /* create new to-be-closed upvalue */
1462 halfProtect(luaF_newtbcupval(L, ra));
1461 vmbreak; 1463 vmbreak;
1462 } 1464 }
1463 vmcase(OP_JMP) { 1465 vmcase(OP_JMP) {
@@ -1745,21 +1747,34 @@ void luaV_execute (lua_State *L, CallInfo *ci) {
1745 vmbreak; 1747 vmbreak;
1746 } 1748 }
1747 vmcase(OP_TFORPREP) { 1749 vmcase(OP_TFORPREP) {
1750 /* is 'state' a function or has a '__close' metamethod? */
1751 if (ttisfunction(s2v(ra + 1)) ||
1752 !ttisnil(luaT_gettmbyobj(L, s2v(ra + 1), TM_CLOSE))) {
1753 /* create to-be-closed upvalue for it */
1754 halfProtect(luaF_newtbcupval(L, ra + 1));
1755 }
1748 pc += GETARG_Bx(i); 1756 pc += GETARG_Bx(i);
1749 vmbreak; 1757 i = *(pc++); /* go to next instruction */
1758 lua_assert(GET_OPCODE(i) == OP_TFORCALL && ra == RA(i));
1759 goto l_tforcall;
1750 } 1760 }
1751 vmcase(OP_TFORCALL) { 1761 vmcase(OP_TFORCALL) {
1752 StkId cb = ra + 3; /* call base */ 1762 l_tforcall:
1753 setobjs2s(L, cb+2, ra+2); 1763 /* 'ra' has the iterator function, 'ra + 1' has the state,
1754 setobjs2s(L, cb+1, ra+1); 1764 and 'ra + 2' has the control variable. The call will use
1755 setobjs2s(L, cb, ra); 1765 the stack after these values (starting at 'ra + 3')
1756 L->top = cb + 3; /* func. + 2 args (state and index) */ 1766 */
1757 Protect(luaD_call(L, cb, GETARG_C(i))); 1767 /* push function, state, and control variable */
1758 if (trap) /* keep 'base' correct for next instruction */ 1768 memcpy(ra + 3, ra, 3 * sizeof(*ra));
1759 updatebase(ci); 1769 L->top = ra + 6;
1770 Protect(luaD_call(L, ra + 3, GETARG_C(i))); /* do the call */
1771 if (trap) { /* stack may have changed? */
1772 updatebase(ci); /* keep 'base' correct */
1773 ra = RA(i); /* keep 'ra' correct for next instruction */
1774 }
1760 i = *(pc++); /* go to next instruction */ 1775 i = *(pc++); /* go to next instruction */
1761 ra = RA(i); /* get its 'ra' */ 1776 ra += 2; /* adjust for next instruction */
1762 lua_assert(GET_OPCODE(i) == OP_TFORLOOP); 1777 lua_assert(GET_OPCODE(i) == OP_TFORLOOP && ra == RA(i));
1763 goto l_tforloop; 1778 goto l_tforloop;
1764 } 1779 }
1765 vmcase(OP_TFORLOOP) { 1780 vmcase(OP_TFORLOOP) {