more cleanups for change#4539
authorGurusamy Sarathy <gsar@cpan.org>
Wed, 10 Nov 1999 18:19:12 +0000 (18:19 +0000)
committerGurusamy Sarathy <gsar@cpan.org>
Wed, 10 Nov 1999 18:19:12 +0000 (18:19 +0000)
p4raw-link: @4539 on //depot/perl: 350de78d9c02710bb008e9ca922c78ba251ec366

p4raw-id: //depot/perl@4544

gv.h
op.c
op.h
pp_ctl.c
pp_hot.c

diff --git a/gv.h b/gv.h
index 99d534e..fde836d 100644 (file)
--- a/gv.h
+++ b/gv.h
@@ -80,6 +80,7 @@ HV *GvHVn();
 #define GVf_INTRO      0x01
 #define GVf_MULTI      0x02
 #define GVf_ASSUMECV   0x04
+#define GVf_IN_PAD     0x08
 #define GVf_IMPORTED   0xF0
 #define GVf_IMPORTED_SV          0x10
 #define GVf_IMPORTED_AV          0x20
@@ -118,6 +119,10 @@ HV *GvHVn();
 #define GvIMPORTED_CV_on(gv)   (GvFLAGS(gv) |= GVf_IMPORTED_CV)
 #define GvIMPORTED_CV_off(gv)  (GvFLAGS(gv) &= ~GVf_IMPORTED_CV)
 
+#define GvIN_PAD(gv)           (GvFLAGS(gv) & GVf_IN_PAD)
+#define GvIN_PAD_on(gv)                (GvFLAGS(gv) |= GVf_IN_PAD)
+#define GvIN_PAD_off(gv)       (GvFLAGS(gv) &= ~GVf_IN_PAD)
+
 #define Nullgv Null(GV*)
 
 #define DM_UID   0x003
diff --git a/op.c b/op.c
index 052d1c1..79255a6 100644 (file)
--- a/op.c
+++ b/op.c
@@ -448,7 +448,7 @@ Perl_pad_alloc(pTHX_ I32 optype, U32 tmptype)
                   (sv = names[PL_padix]) && sv != &PL_sv_undef)
                continue;
            sv = *av_fetch(PL_comppad, PL_padix, TRUE);
-           if (!(SvFLAGS(sv) & (SVs_PADTMP|SVs_PADMY)))
+           if (!(SvFLAGS(sv) & (SVs_PADTMP|SVs_PADMY)) && !IS_PADGV(sv))
                break;
        }
        retval = PL_padix;
@@ -719,10 +719,12 @@ S_op_clear(pTHX_ OP *o)
     case OP_AELEMFAST:
 #ifdef USE_ITHREADS
        if (PL_curpad) {
-           SvREFCNT_dec(cGVOPo);
-           PL_curpad[cPADOPo->op_padix] = Nullsv;
+           GV *gv = cGVOPo;
+           pad_swipe(cPADOPo->op_padix);
+           /* No GvIN_PAD_off(gv) here, because other references may still
+            * exist on the pad */
+           SvREFCNT_dec(gv);
        }
-       pad_free(cPADOPo->op_padix);
        cPADOPo->op_padix = 0;
 #else
        SvREFCNT_dec(cGVOPo);
@@ -762,8 +764,10 @@ S_op_clear(pTHX_ OP *o)
        break;
     }
 
-    if (o->op_targ > 0)
+    if (o->op_targ > 0) {
        pad_free(o->op_targ);
+       o->op_targ = 0;
+    }
 }
 
 STATIC void
@@ -2935,6 +2939,7 @@ Perl_newGVOP(pTHX_ I32 type, I32 flags, GV *gv)
 {
     dTHR;
 #ifdef USE_ITHREADS
+    GvIN_PAD_on(gv);
     return newPADOP(type, flags, SvREFCNT_inc(gv));
 #else
     return newSVOP(type, flags, SvREFCNT_inc(gv));
@@ -3229,7 +3234,7 @@ Perl_newASSIGNOP(pTHX_ I32 flags, OP *left, I32 optype, OP *right)
                {
                    tmpop = ((UNOP*)left)->op_first;
                    if (tmpop->op_type == OP_GV && !pm->op_pmreplroot) {
-                       pm->op_pmreplroot = (OP*)((SVOP*)tmpop)->op_sv; /* XXXXXX */
+                       pm->op_pmreplroot = (OP*)cGVOPx(tmpop);
                        pm->op_pmflags |= PMf_ONCE;
                        tmpop = cUNOPo->op_first;       /* to list (nulled) */
                        tmpop = ((UNOP*)tmpop)->op_first; /* to pushmark */
@@ -3739,11 +3744,13 @@ Perl_newFOROP(pTHX_ I32 flags,char *label,line_t forline,OP *sv,OP *expr,OP *blo
        }
        else if (sv->op_type == OP_PADSV) { /* private variable */
            padoff = sv->op_targ;
+           sv->op_targ = 0;
            op_free(sv);
            sv = Nullop;
        }
        else if (sv->op_type == OP_THREADSV) { /* per-thread variable */
            padoff = sv->op_targ;
+           sv->op_targ = 0;
            iterflags |= OPf_SPECIAL;
            op_free(sv);
            sv = Nullop;
@@ -3898,9 +3905,9 @@ Perl_cv_undef(pTHX_ CV *cv)
     }
 }
 
-#ifdef DEBUG_CLOSURES
+#ifdef DEBUGGING
 STATIC void
-cv_dump(CV *cv)
+S_cv_dump(pTHX_ CV *cv)
 {
     CV *outside = CvOUTSIDE(cv);
     AV* padlist = CvPADLIST(cv);
@@ -3943,7 +3950,7 @@ cv_dump(CV *cv)
                          SvIVX(pname[ix]));
     }
 }
-#endif /* DEBUG_CLOSURES */
+#endif /* DEBUGGING */
 
 STATIC CV *
 S_cv_clone2(pTHX_ CV *proto, CV *outside)
@@ -4038,6 +4045,9 @@ S_cv_clone2(pTHX_ CV *proto, CV *outside)
                PL_curpad[ix] = sv;
            }
        }
+       else if (IS_PADGV(ppad[ix])) {
+           PL_curpad[ix] = SvREFCNT_inc(ppad[ix]);
+       }
        else {
            SV* sv = NEWSV(0,0);
            SvPADTMP_on(sv);
@@ -4351,7 +4361,7 @@ Perl_newATTRSUB(pTHX_ I32 floor, OP *o, OP *proto, OP *attrs, OP *block)
        for (ix = AvFILLp(PL_comppad); ix > 0; ix--) {
            SV *namesv;
 
-           if (SvIMMORTAL(PL_curpad[ix]))
+           if (SvIMMORTAL(PL_curpad[ix]) || IS_PADGV(PL_curpad[ix]))
                continue;
            /*
             * The only things that a clonable function needs in its
@@ -4375,7 +4385,7 @@ Perl_newATTRSUB(pTHX_ I32 floor, OP *o, OP *proto, OP *attrs, OP *block)
        AvFLAGS(av) = AVf_REIFY;
 
        for (ix = AvFILLp(PL_comppad); ix > 0; ix--) {
-           if (SvIMMORTAL(PL_curpad[ix]))
+           if (SvIMMORTAL(PL_curpad[ix]) || IS_PADGV(PL_curpad[ix]))
                continue;
            if (!SvPADMY(PL_curpad[ix]))
                SvPADTMP_on(PL_curpad[ix]);
@@ -5046,6 +5056,7 @@ Perl_ck_rvconst(pTHX_ register OP *o)
 #ifdef USE_ITHREADS
            /* XXXXXX hack: dependence on sizeof(PADOP) <= sizeof(SVOP) */
            kPADOP->op_padix = pad_alloc(OP_GV, SVs_PADTMP);
+           GvIN_PAD_on(gv);
            PL_curpad[kPADOP->op_padix] = SvREFCNT_inc(gv);
 #else
            kid->op_sv = SvREFCNT_inc(gv);
@@ -5515,6 +5526,7 @@ Perl_ck_sassign(pTHX_ OP *o)
                    return o;
            }
            kid->op_targ = kkid->op_targ;
+           kkid->op_targ = 0;
            /* Now we do not need PADSV and SASSIGN. */
            kid->op_sibling = o->op_sibling;    /* NULL */
            cLISTOPo->op_first = NULL;
@@ -6099,11 +6111,13 @@ Perl_peep(pTHX_ register OP *o)
                            && (((LISTOP*)o)->op_first->op_sibling->op_type
                                == OP_PADSV)
                            && (((LISTOP*)o)->op_first->op_sibling->op_targ
-                               == o->op_next->op_targ))) {
+                               == o->op_next->op_targ)))
+                   {
                        goto ignore_optimization;
                    }
                    else {
                        o->op_targ = o->op_next->op_targ;
+                       o->op_next->op_targ = 0;
                        o->op_private |= OPpTARGET_MY;
                    }
                }
diff --git a/op.h b/op.h
index 2129572..a2e8429 100644 (file)
--- a/op.h
+++ b/op.h
@@ -311,6 +311,7 @@ struct loop {
 #  define      cGVOP_set(v)    (PL_curpad[cPADOP->op_padix] = (SV*)(v))
 #  define      cGVOPo_set(v)   (PL_curpad[cPADOPo->op_padix] = (SV*)(v))
 #  define      kGVOP_set(v)    (PL_curpad[kPADOP->op_padix] = (SV*)(v))
+#  define      IS_PADGV(v)     (v && SvTYPE(v) == SVt_PVGV && GvIN_PAD(v))
 #else
 #  define      cGVOPx(o)       ((GV*)cSVOPx(o)->op_sv)
 #  define      cGVOP           ((GV*)cSVOP->op_sv)
@@ -319,6 +320,7 @@ struct loop {
 #  define      cGVOP_set(v)    (cPADOP->op_sv = (SV*)(v))
 #  define      cGVOPo_set(v)   (cPADOPo->op_sv = (SV*)(v))
 #  define      kGVOP_set(v)    (kPADOP->op_sv = (SV*)(v))
+#  define      IS_PADGV(v)     FALSE
 #endif
 
 #define Nullop Null(OP*)
index 746f483..b8465cd 100644 (file)
--- a/pp_ctl.c
+++ b/pp_ctl.c
@@ -2138,6 +2138,9 @@ PP(pp_goto)
                                    SvPADMY_on(sv);
                                }
                            }
+                           else if (IS_PADGV(oldpad[ix])) {
+                               av_store(newpad, ix, sv = SvREFCNT_inc(oldpad[ix]));
+                           }
                            else {
                                av_store(newpad, ix, sv = NEWSV(0,0));
                                SvPADTMP_on(sv);
index 0c5fd16..815ddd8 100644 (file)
--- a/pp_hot.c
+++ b/pp_hot.c
@@ -2493,6 +2493,9 @@ try_autoload:
                            SvPADMY_on(sv);
                        }
                    }
+                   else if (IS_PADGV(oldpad[ix])) {
+                       av_store(newpad, ix, sv = SvREFCNT_inc(oldpad[ix]));
+                   }
                    else {
                        av_store(newpad, ix, sv = NEWSV(0,0));
                        SvPADTMP_on(sv);