This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
Make SUPER::method respect method changes in moved pkg
authorFather Chrysostomos <sprout@cpan.org>
Fri, 14 Sep 2012 21:20:07 +0000 (14:20 -0700)
committerFather Chrysostomos <sprout@cpan.org>
Sat, 15 Sep 2012 05:29:47 +0000 (22:29 -0700)
commit37b0b3b2e3fecf62fbb5a9c784ad24707e8d3581
tree9d0f11f2160440fe168a5c0a62a2c8f1de04b691
parent0308a534a635b8c34297657046d32a3f05818821
Make SUPER::method respect method changes in moved pkg

->SUPER::method calls inside the Foo package cache the method for
reuse inside the stash Foo::SUPER.

Before the call, @Foo::SUPER::ISA is set to "Foo", so that those
caches will be invalidated properly.  (@ISA has the magic to make that
work.)  The actual value in @Foo::SUPER::ISA unused.

Now we have two types of package names.  If you alias the Foo package
and then clobber the original entry:

    *Bar:: = *Foo::;
    undef *Foo::;

__PACKAGE__ and HvNAME will return Foo still, but HvENAME (the effec-
tive name) will return Bar, because that is where the package is to be
found.

As of the previous commit, the package used for ISA is based on the
effective name, Bar::SUPER in this case.

But @Bar::SUPER::ISA is still set to Foo.  So even if we make changes
to methods inherited by what is now the Bar package, a previous method
cached in *Bar::SUPER::method will be reused.

BEGIN {
    *Bar:: = *Foo::;
    undef *Foo::;
}
package Bar;
@ISA = 'Baz';
*Baz::m = sub { "method 1" };
anthying->SUPER::m;
undef *Baz::m;
*Baz::m = sub { "method 2" };
warn anything->SUPER::m;
__END__
method 1 at - line 11.
gv.c
t/op/method.t