diff options
author | David Mitchell <davem@iabyn.com> | 2015-10-17 12:56:15 +0100 |
---|---|---|
committer | David Mitchell <davem@iabyn.com> | 2016-02-03 09:18:30 +0000 |
commit | 1bef65a2c897ceb4139a39df14a8514b260493bd (patch) | |
tree | 84844d6a1097fd8fee39e093df06f2bc043955c8 /pp_ctl.c | |
parent | 8a1f10dd1e1964fa64cd0dff7196cf3f1f503ae1 (diff) | |
download | perl-1bef65a2c897ceb4139a39df14a8514b260493bd.tar.gz |
Eliminate cx->blk_loop.resetsp
Of all the loop types, only CXt_LOOP_LIST, i.e. for (1,2,3) {},
needs to keep anything on the stack, i.e. for all the others,
cx->blk_loop.resetsp can always equal cx->blk_oldsp.
For CXt_LOOP_LIST, the same value as resetsp is stored as
blk_loop.state_u.stack.basesp.
So we can eliminate the resetsp field. This is good as the loop substruct
is the largest (ITHREADS) or joint largest with eval (non-threaded).
Also, we now don't have to store that value for non-CXt_LOOP_LIST loops.
The downside is we now have to choose between basesp and oldsp in
pp_leaveloop and pp_last, based on CX type.
Diffstat (limited to 'pp_ctl.c')
-rw-r--r-- | pp_ctl.c | 21 |
1 files changed, 12 insertions, 9 deletions
@@ -2186,8 +2186,8 @@ PP(pp_enteriter) if (PL_op->op_private & OPpITER_DEF) cxflags |= CXp_FOR_DEF; - PUSHBLOCK(cx, cxflags, SP); - PUSHLOOP_FOR(cx, itervarp, itersave, MARK); + PUSHBLOCK(cx, cxflags, MARK); + PUSHLOOP_FOR(cx, itervarp, itersave); if (PL_op->op_flags & OPf_STACKED) { SV *maybe_ary = POPs; if (SvTYPE(maybe_ary) != SVt_PVAV) { @@ -2204,10 +2204,6 @@ PP(pp_enteriter) DIE(aTHX_ "Range iterator outside integer range"); cx->blk_loop.state_u.lazyiv.cur = SvIV_nomg(sv); cx->blk_loop.state_u.lazyiv.end = SvIV_nomg(right); -#ifdef DEBUGGING - /* for correct -Dstv display */ - cx->blk_oldsp = sp - PL_stack_base; -#endif } else { cx->cx_type |= CXt_LOOP_LAZYSV; @@ -2239,6 +2235,7 @@ PP(pp_enteriter) } else { /* iterating over items on the stack */ cx->cx_type |= CXt_LOOP_LIST; + cx->blk_oldsp = SP - PL_stack_base; cx->blk_loop.state_u.stack.basesp = MARK - PL_stack_base; cx->blk_loop.state_u.stack.ix = (PL_op->op_private & OPpITER_REVERSED) @@ -2259,7 +2256,7 @@ PP(pp_enterloop) const I32 gimme = GIMME_V; PUSHBLOCK(cx, CXt_LOOP_PLAIN, SP); - PUSHLOOP_PLAIN(cx, SP); + PUSHLOOP_PLAIN(cx); RETURN; } @@ -2274,7 +2271,9 @@ PP(pp_leaveloop) cx = &cxstack[cxstack_ix]; assert(CxTYPE_is_LOOP(cx)); mark = PL_stack_base + cx->blk_oldsp; - newsp = PL_stack_base + cx->blk_loop.resetsp; + newsp = CxTYPE(cx) == CXt_LOOP_LIST + ? PL_stack_base + cx->blk_loop.state_u.stack.basesp + : mark; gimme = cx->blk_gimme; if (gimme == G_VOID) @@ -2579,7 +2578,11 @@ PP(pp_last) cx = &cxstack[cxstack_ix]; assert(CxTYPE_is_LOOP(cx)); - PL_stack_sp = PL_stack_base + cx->blk_loop.resetsp; + PL_stack_sp = PL_stack_base + + (CxTYPE(cx) == CXt_LOOP_LIST + ? cx->blk_loop.state_u.stack.basesp + : cx->blk_oldsp + ); TAINT_NOT; |