summaryrefslogtreecommitdiff
path: root/sv.c
diff options
context:
space:
mode:
authorNicholas Clark <nick@ccl4.org>2005-06-07 14:57:35 +0000
committerNicholas Clark <nick@ccl4.org>2005-06-07 14:57:35 +0000
commitb8f9541a0e3495cf3f2a868f440b6b197d5c68ee (patch)
treed33e8a3c75c82fc8f3f6aec703db4504bb740706 /sv.c
parentce6e1103a66e3cbd2c2ec85914dcbaa395276c13 (diff)
downloadperl-b8f9541a0e3495cf3f2a868f440b6b197d5c68ee.tar.gz
Ensure string table counts are balanced. (Was not true in op/pack.t)
p4raw-id: //depot/perl@24732
Diffstat (limited to 'sv.c')
-rw-r--r--sv.c12
1 files changed, 10 insertions, 2 deletions
diff --git a/sv.c b/sv.c
index f3dbaf8051..81634de3e2 100644
--- a/sv.c
+++ b/sv.c
@@ -4447,7 +4447,13 @@ Perl_sv_setsv_flags(pTHX_ SV *dstr, register SV *sstr, I32 flags)
(void)SvPOK_only(dstr);
if (
- (sflags & (SVf_FAKE | SVf_READONLY)) != (SVf_FAKE | SVf_READONLY)
+ /* We're not already COW */
+ ((sflags & (SVf_FAKE | SVf_READONLY)) != (SVf_FAKE | SVf_READONLY)
+#ifndef PERL_COPY_ON_WRITE
+ /* or we are, but dstr isn't a suitable target. */
+ || (SvFLAGS(dstr) & CAN_COW_MASK) != CAN_COW_FLAGS
+#endif
+ )
&&
!(isSwipe =
(sflags & SVs_TEMP) && /* slated for free anyway? */
@@ -4513,9 +4519,9 @@ Perl_sv_setsv_flags(pTHX_ SV *dstr, register SV *sstr, I32 flags)
/* making another shared SV. */
STRLEN cur = SvCUR(sstr);
STRLEN len = SvLEN(sstr);
- assert (SvTYPE(dstr) >= SVt_PVIV);
#ifdef PERL_COPY_ON_WRITE
if (len) {
+ assert (SvTYPE(dstr) >= SVt_PVIV);
/* SvIsCOW_normal */
/* splice us in between source and next-after-source. */
SV_COW_NEXT_SV_SET(dstr, SV_COW_NEXT_SV(sstr));
@@ -4528,6 +4534,8 @@ Perl_sv_setsv_flags(pTHX_ SV *dstr, register SV *sstr, I32 flags)
UV hash = SvSHARED_HASH(sstr);
DEBUG_C(PerlIO_printf(Perl_debug_log,
"Copy on write: Sharing hash\n"));
+
+ assert (SvTYPE(dstr) >= SVt_PVIV);
SvPV_set(dstr,
sharepvn(SvPVX_const(sstr),
(sflags & SVf_UTF8?-cur:cur), hash));