summaryrefslogtreecommitdiff
path: root/sv.c
diff options
context:
space:
mode:
authorDave Mitchell <davem@fdisolutions.com>2004-01-08 22:32:28 +0000
committerDave Mitchell <davem@fdisolutions.com>2004-01-08 22:32:28 +0000
commitb23f1a86dd8a81ae1056d802240e99273db9cd3a (patch)
tree27ba4e3e880421d36c75d1d83f13be0340261541 /sv.c
parent95143fff86b7efc2ca19a65dbad4c11842f65021 (diff)
downloadperl-b23f1a86dd8a81ae1056d802240e99273db9cd3a.tar.gz
segv in pad.c with threads (was: DBD::Oracle and Perl 5.8.2 threads)
Message-ID: <20040107121357.GD82921@dansat.data-plan.com> Returning a closure from a thread (via join) could mess up because pointers to PL_sv_undef weren't rejigged to point at the joiner's version of PL_sv_undef. Also, the closure's CvGV got cloned too but never freed, since CvGV isn't refcounted. p4raw-id: //depot/perl@22102
Diffstat (limited to 'sv.c')
-rw-r--r--sv.c5
1 files changed, 4 insertions, 1 deletions
diff --git a/sv.c b/sv.c
index 5efd546747..995be328ca 100644
--- a/sv.c
+++ b/sv.c
@@ -10374,7 +10374,10 @@ Perl_sv_dup(pTHX_ SV *sstr, CLONE_PARAMS* param)
SvREFCNT_inc(CvXSUBANY(sstr).any_ptr) :
sv_dup_inc(CvXSUBANY(sstr).any_ptr, param);
}
- CvGV(dstr) = gv_dup(CvGV(sstr), 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) = (param->flags & CLONEf_JOIN_IN) ?
+ Nullgv : gv_dup(CvGV(sstr), param) ;
if (param->flags & CLONEf_COPY_STACKS) {
CvDEPTH(dstr) = CvDEPTH(sstr);
} else {