This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
add CvGV_set() macro and make CvGV() rvalue only
authorDavid Mitchell <davem@iabyn.com>
Sun, 18 Jul 2010 17:18:50 +0000 (18:18 +0100)
committerDavid Mitchell <davem@iabyn.com>
Sun, 18 Jul 2010 17:39:18 +0000 (18:39 +0100)
Now that CvGV can sometimes be reference counted, stop people from directly
assigning to it (by using CvGV as an lvalue), and instead force them to use
CvGV_set()

cv.h
gv.c
op.c
pad.c
pp.c
sv.c

diff --git a/cv.h b/cv.h
index d762a06..7979a05 100644 (file)
--- a/cv.h
+++ b/cv.h
@@ -41,7 +41,8 @@ Returns the stash of the CV.
 #define CvROOT(sv)     ((XPVCV*)MUTABLE_PTR(SvANY(sv)))->xcv_root_u.xcv_root
 #define CvXSUB(sv)     ((XPVCV*)MUTABLE_PTR(SvANY(sv)))->xcv_root_u.xcv_xsub
 #define CvXSUBANY(sv)  ((XPVCV*)MUTABLE_PTR(SvANY(sv)))->xcv_start_u.xcv_xsubany
-#define CvGV(sv)       ((XPVCV*)MUTABLE_PTR(SvANY(sv)))->xcv_gv
+#define CvGV(sv)       (0+((XPVCV*)MUTABLE_PTR(SvANY(sv)))->xcv_gv)
+#define CvGV_set(cv,gv)        Perl_cvgv_set(aTHX_ cv, gv)
 #define CvFILE(sv)     ((XPVCV*)MUTABLE_PTR(SvANY(sv)))->xcv_file
 #ifdef USE_ITHREADS
 #  define CvFILE_set_from_cop(sv, cop) (CvFILE(sv) = savepv(CopFILE(cop)))
diff --git a/gv.c b/gv.c
index 917cfb7..a5c33d9 100644 (file)
--- a/gv.c
+++ b/gv.c
@@ -215,7 +215,7 @@ Perl_cvgv_set(pTHX_ CV* cv, GV* gv)
        }
     }
 
-    CvGV(cv) = gv;
+    SvANY(cv)->xcv_gv = gv;
     assert(!CvCVGV_RC(cv));
 
     if (!gv)
@@ -303,7 +303,7 @@ Perl_gv_init(pTHX_ GV *gv, HV *stash, const char *name, STRLEN len, int multi)
        LEAVE;
 
         mro_method_changed_in(GvSTASH(gv)); /* sub Foo::bar($) { (shift) } sub ASDF::baz($); *ASDF::baz = \&Foo::bar */
-       cvgv_set(cv, gv);
+       CvGV_set(cv, gv);
        CvFILE_set_from_cop(cv, PL_curcop);
        CvSTASH(cv) = PL_curstash;
        if (PL_curstash)
diff --git a/op.c b/op.c
index 3ae15cb..276e100 100644 (file)
--- a/op.c
+++ b/op.c
@@ -5459,7 +5459,7 @@ Perl_cv_undef(pTHX_ CV *cv)
        LEAVE;
     }
     SvPOK_off(MUTABLE_SV(cv));         /* forget prototype */
-    cvgv_set(cv, NULL);
+    CvGV_set(cv, NULL);
 
     pad_undef(cv);
 
@@ -5872,7 +5872,7 @@ Perl_newATTRSUB(pTHX_ I32 floor, OP *o, OP *proto, OP *attrs, OP *block)
        }
     }
     if (!CvGV(cv)) {
-       cvgv_set(cv, gv);
+       CvGV_set(cv, gv);
        CvFILE_set_from_cop(cv, PL_curcop);
        CvSTASH(cv) = PL_curstash;
        if (PL_curstash)
@@ -6236,7 +6236,7 @@ Perl_newXS(pTHX_ const char *name, XSUBADDR_t subaddr, const char *filename)
     }
     if (!name)
        CvANON_on(cv);
-    cvgv_set(cv, gv);
+    CvGV_set(cv, gv);
     (void)gv_fetchfile(filename);
     CvFILE(cv) = (char *)filename; /* NOTE: not copied, as it is expected to be
                                   an external constant string */
@@ -6285,7 +6285,7 @@ Perl_newFORM(pTHX_ I32 floor, OP *o, OP *block)
     }
     cv = PL_compcv;
     GvFORM(gv) = cv;
-    cvgv_set(cv, gv);
+    CvGV_set(cv, gv);
     CvFILE_set_from_cop(cv, PL_curcop);
 
 
diff --git a/pad.c b/pad.c
index 3582544..0b3c948 100644 (file)
--- a/pad.c
+++ b/pad.c
@@ -1571,7 +1571,7 @@ Perl_cv_clone(pTHX_ CV *proto)
 #else
     CvFILE(cv)         = CvFILE(proto);
 #endif
-    cvgv_set(cv,CvGV(proto));
+    CvGV_set(cv,CvGV(proto));
     CvSTASH(cv)                = CvSTASH(proto);
     if (CvSTASH(cv))
        Perl_sv_add_backref(aTHX_ MUTABLE_SV(CvSTASH(cv)), MUTABLE_SV(cv));
diff --git a/pp.c b/pp.c
index a78c1cc..129c948 100644 (file)
--- a/pp.c
+++ b/pp.c
@@ -838,7 +838,7 @@ PP(pp_undef)
            /* let user-undef'd sub keep its identity */
            GV* const gv = CvGV((const CV *)sv);
            cv_undef(MUTABLE_CV(sv));
-           cvgv_set(MUTABLE_CV(sv), gv);
+           CvGV_set(MUTABLE_CV(sv), gv);
        }
        break;
     case SVt_PVGV:
diff --git a/sv.c b/sv.c
index 1e756f2..10e41a9 100644 (file)
--- a/sv.c
+++ b/sv.c
@@ -5675,7 +5675,7 @@ S_anonymise_cv_maybe(pTHX_ GV *gv, CV* cv)
 
     /* will the CV shortly be freed by gp_free() ? */
     if (GvCV(gv) == cv && GvGP(gv)->gp_refcnt < 2 && SvREFCNT(cv) < 2) {
-       CvGV(cv) = NULL;
+       SvANY(cv)->xcv_gv = NULL;
        return;
     }
 
@@ -5688,7 +5688,7 @@ S_anonymise_cv_maybe(pTHX_ GV *gv, CV* cv)
 
     CvANON_on(cv);
     CvCVGV_RC_on(cv);
-    CvGV(cv) = MUTABLE_GV(SvREFCNT_inc(anongv));
+    SvANY(cv)->xcv_gv = MUTABLE_GV(SvREFCNT_inc(anongv));
 }
 
 
@@ -11438,7 +11438,7 @@ S_sv_dup_common(pTHX_ const SV *const sstr, CLONE_PARAMS *const param)
                }
                /* don't dup if copying back - CvGV isn't refcounted, so the
                 * duped GV may never be freed. A bit of a hack! DAPM */
-               CvGV(dstr) =
+               SvANY(MUTABLE_CV(dstr))->xcv_gv =
                    CvCVGV_RC(dstr)
                    ? gv_dup_inc(CvGV(sstr), param)
                    : (param->flags & CLONEf_JOIN_IN)