[shell changes from patch from perl5.003_23 to perl5.003_24]
[p5sagit/p5-mst-13.2.git] / cop.h
diff --git a/cop.h b/cop.h
index c062dc6..d450e09 100644 (file)
--- a/cop.h
+++ b/cop.h
@@ -46,16 +46,22 @@ struct block_sub {
        cx->blk_sub.dfoutgv = defoutgv;                                 \
        (void)SvREFCNT_inc(cx->blk_sub.dfoutgv)
 
+/* We muck with cxstack_ix since _dec may call a DESTROY, overwriting cx. */
+
 #define POPSUB(cx)                                                     \
-       if (cx->blk_sub.hasargs) {   /* put back old @_ */              \
+       if (cx->blk_sub.hasargs) {                                      \
+           /* put back old @_ */                                       \
+           SvREFCNT_dec(GvAV(defgv));                                  \
            GvAV(defgv) = cx->blk_sub.savearray;                        \
+           /* destroy arg array */                                     \
+           av_clear(cx->blk_sub.argarray);                             \
+           AvREAL_off(cx->blk_sub.argarray);                           \
        }                                                               \
        if (cx->blk_sub.cv) {                                           \
            if (!(CvDEPTH(cx->blk_sub.cv) = cx->blk_sub.olddepth)) {    \
-               if (cx->blk_sub.hasargs) {                              \
-                   SvREFCNT_inc((SV*)cx->blk_sub.argarray);            \
-               }                                                       \
+               cxstack_ix++;                                           \
                SvREFCNT_dec((SV*)cx->blk_sub.cv);                      \
+               cxstack_ix--;                                           \
            }                                                           \
        }
 
@@ -104,14 +110,21 @@ struct block_loop {
        cx->blk_loop.redo_op = cLOOP->op_redoop;                        \
        cx->blk_loop.next_op = cLOOP->op_nextop;                        \
        cx->blk_loop.last_op = cLOOP->op_lastop;                        \
+       if (cx->blk_loop.itervar = (ivar))                              \
+           cx->blk_loop.itersave = SvREFCNT_inc(*cx->blk_loop.itervar);\
        cx->blk_loop.iterlval = Nullsv;                                 \
-       cx->blk_loop.itervar = ivar;                                    \
-       if (ivar)                                                       \
-           cx->blk_loop.itersave = *cx->blk_loop.itervar;
+       cx->blk_loop.iterary = Nullav;                                  \
+       cx->blk_loop.iterix = -1;
 
 #define POPLOOP(cx)                                                    \
        newsp           = stack_base + cx->blk_loop.resetsp;            \
-       SvREFCNT_dec(cx->blk_loop.iterlval)
+       SvREFCNT_dec(cx->blk_loop.iterlval);                            \
+       if (cx->blk_loop.itervar) {                                     \
+           SvREFCNT_dec(*cx->blk_loop.itervar);                        \
+           *cx->blk_loop.itervar = cx->blk_loop.itersave;              \
+       }                                                               \
+       if (cx->blk_loop.iterary && cx->blk_loop.iterary != curstack)   \
+           SvREFCNT_dec(cx->blk_loop.iterary);
 
 /* context common to subroutines, evals and loops */
 struct block {