summaryrefslogtreecommitdiff
path: root/gv.c
diff options
context:
space:
mode:
authorFather Chrysostomos <sprout@cpan.org>2010-11-26 07:22:47 -0800
committerFather Chrysostomos <sprout@cpan.org>2010-11-26 09:39:51 -0800
commit75bd28cfd597653e1169cbeb4920b7ba42eb8503 (patch)
tree4ce63bcfc2b1cb321bf8127b0e8293eded8bb985 /gv.c
parentabf9167d3fff002ddaed53abb44d638387bca978 (diff)
downloadperl-75bd28cfd597653e1169cbeb4920b7ba42eb8503.tar.gz
[perl #78634] Conflict in defining constant INIT
When gv_init tries to turn a constant named INIT into a CV, the auto- matic special processing of the INIT ‘block’ kicks in, which removes the CV from the GV. This should not happen with gv_init, as $::{INIT} = \5 is supposed to be equivalent to *INIT = sub(){5}, which does not do that. This commit makes gv_init check for that, increase the reference count, and reassign the CV. It does not stop the CV from being called as a special block, but it is harmless to call a constant CV.
Diffstat (limited to 'gv.c')
-rw-r--r--gv.c3
1 files changed, 3 insertions, 0 deletions
diff --git a/gv.c b/gv.c
index b2cb5a4146..f51839e6a8 100644
--- a/gv.c
+++ b/gv.c
@@ -317,6 +317,9 @@ Perl_gv_init(pTHX_ GV *gv, HV *stash, const char *name, STRLEN len, int multi)
/* newCONSTSUB takes ownership of the reference from us. */
cv = newCONSTSUB(stash, (name0 ? name0 : name), has_constant);
+ /* In case op.c:S_process_special_blocks stole it: */
+ if (!GvCV(gv))
+ GvCV(gv) = SvREFCNT_inc_simple_NN(cv);
assert(GvCV(gv) == cv); /* newCONSTSUB should have set this */
if (name0)
Safefree(name0);