diff options
author | Father Chrysostomos <sprout@cpan.org> | 2012-11-28 08:36:34 -0800 |
---|---|---|
committer | Father Chrysostomos <sprout@cpan.org> | 2012-11-29 09:11:30 -0800 |
commit | 978a498e17ec54b6f1fc65f3375a62a68f321f99 (patch) | |
tree | cc9f490a623bb40458a8813f59a5bb64af80b188 /scope.c | |
parent | 6e1b2de7c59099adaa1866fe94957b98fabcd9c4 (diff) | |
download | perl-978a498e17ec54b6f1fc65f3375a62a68f321f99.tar.gz |
Reset method caches when GPs are shared
The new MRO stuff in 5.10 made PL_sub_generation++ mostly unnecessary,
and almost all uses of it were replaced with mro_method_changed_in.
There is only one problem: That doesn’t actually work properly. After
glob-to-glob assignment (*foo = *bar), both globs share the same GP
(glob pointer, or list of glob slots). But there is no list of GVs
associated with any GP. So there is no way, given a GV whose GP
is shared, to find out what other classes might need their method
caches reset.
sub B::b { "b" }
*A::b = *B::b;
@C::ISA = "A";
print C->b, "\n"; # should print "b"
eval 'sub B::b { "c" }';
print C->b, "\n"; # should print "c"
__END__
$ perl5.8.9 foo
b
c
$ perl5.10.0 foo
b
b
And it continues up to 5.16.x.
If a GP is shared, then those places where mro_method_changed_in is
called after the GP has been modified must do PL_sub_generation++
instead if the GP is shared, which can be detected through its refer-
ence count.
Diffstat (limited to 'scope.c')
-rw-r--r-- | scope.c | 2 |
1 files changed, 1 insertions, 1 deletions
@@ -861,7 +861,7 @@ Perl_leave_scope(pTHX_ I32 base) GvGP_set(gv, (GP*)ptr); /* putting a method back into circulation ("local")*/ if (GvCVu(gv) && (hv=GvSTASH(gv)) && HvENAME_get(hv)) - mro_method_changed_in(hv); + gv_method_changed(gv); SvREFCNT_dec(gv); break; case SAVEt_FREESV: |