- /* Starting from perl 5.9 (more exactly commit b5c19bd7), cv_clone() is no
- * longer able to clone named subs propery. With this commit, pad_findlex()
- * stores the parent index of a fake pad entry in the NV slot of the
- * corresponding pad name SV, but only for anonymous subs (since named subs
- * aren't supposed to be cloned in pure Perl land). To fix this, we just
- * manually relink the new fake pad entries to the new ones.
- * For some reason perl 5.8 crashes too without this, supposedly because of
- * other closure bugs. Hence we enable it everywhere. */
- if (!CvCLONE(old_cv)) {
- const AV *old_padname = (const AV *) AvARRAY(CvPADLIST(old_cv))[0];
- AV *old_pad = (AV *) AvARRAY(CvPADLIST(old_cv))[1];
- AV *new_pad = (AV *) AvARRAY(CvPADLIST(new_cv))[1];
- const SV **old_aryname = (const SV **) AvARRAY(old_padname);
- SV **old_ary = AvARRAY(old_pad);
- SV **new_ary = AvARRAY(new_pad);
- I32 fname = AvFILLp(old_padname);
- I32 fpad = AvFILLp(old_pad);
- I32 ix;
-
- for (ix = fpad; ix > 0; ix--) {
- const SV *namesv = (ix <= fname) ? old_aryname[ix] : NULL;
-
- if (namesv && namesv != &PL_sv_undef && SvFAKE(namesv)) {
- SvREFCNT_dec(new_ary[ix]);
- new_ary[ix] = SvREFCNT_inc(old_ary[ix]);
- }
- }
+ CvGV_set(cv, gv);
+ CvSTASH_set(cv, CvSTASH(proto));
+ /* Commit 4c74a7df, publicized with perl 5.13.3, began to add backrefs to
+ * stashes. CvSTASH_set() started to do it as well with commit c68d95645
+ * (which was part of perl 5.13.7). */
+#if SU_HAS_PERL(5, 13, 3) && !SU_HAS_PERL(5, 13, 7)
+ if (CvSTASH(proto))
+ Perl_sv_add_backref(aTHX_ CvSTASH(proto), MUTABLE_SV(cv));
+#endif
+
+ if (CvISXSUB(proto)) {
+ CvXSUB(cv) = CvXSUB(proto);
+ CvXSUBANY(cv) = CvXSUBANY(proto);
+ } else {
+ OP_REFCNT_LOCK;
+ CvROOT(cv) = OpREFCNT_inc(CvROOT(proto));
+ OP_REFCNT_UNLOCK;
+ CvSTART(cv) = CvSTART(proto);