Perl / perl5

🐪 The Perl programming language
https://dev.perl.org/perl5/
Other
1.9k stars 540 forks source link

$vglob{SCALAR} in base.pm #3948

Closed p5pRT closed 13 years ago

p5pRT commented 23 years ago

Migrated from rt.perl.org#6943 (status was 'resolved')

Searchable as RT6943$

p5pRT commented 23 years ago

From @andk

  > The attached file shows that the code in base.pm is brain-dead.   > This cripples Tk​::JPEG

Michael\, please take note. The change was made in your patch 9576 without any explanation what you'd tried to accomplish. So I dig out your posting that for some reason is not on the p5p archive. Appended below.

-- andreas

From​: Michael G Schwern \schwern@​pobox\.com Subject​: [PATCH lib/base.pm t/lib/base.t] Fix subtle $VERSION mistakes with base.pm To​: perl5-porters@​perl.org Date​: Thu\, 5 Apr 2001 21​:53​:21 +0100

Finally tracked down a very\, very\, very subtle bug in Class​::Fields's base.pm that drove me bonkers today. It goes like this...

On older perls \< 5.6\, Exporter has no $VERSION defined.

If something is used via base.pm that doesn't have a $VERSION\, it will set $VERSION = '-1\, set by base.pm'. It does this so it knows not to try to require it again (think about use base qw(Tie​::StdArray)).

Eariler versions of base.pm had a very subtle bug where instead of actually setting $VERSION it would instead do something nasty to that bit of the symbol table.

Consider the following...

  package Foo;   use base qw(Exporter);   use IO​::Socket;

IO​::Socket then does this...

  use Socket 1.3;

Socket.pm does this...

  require Exporter;   @​ISA = qw(Exporter);

What happens when you require a specific version number? Perl calls Socket->VERSION. Normally this falls back to UNIVERSAL​::VERSION\, but wait... *Exporter​::VERSION has been mucked up\, perl thinks there's a method defined there. It calls it and it returns undef (with lots of screaming. In fact\, 5.004 just segfaults). Suddenly\, perl thinks Socket is of a version \< 1.3 and dies horribly.

Anyhow\, that bug was fixed in 3302 I think but never tested. This patch adds a test for that.

There's another *even more subtle* bug here. Consider...

  package Foo;   sub VERSION { 42 }

  package Bar;   use base qw(Foo);

Does base.pm set $Foo​::VERSION? Nope. Why? Because the check just goes and sees if there's a VERSION entry in the symbol table but never actually checks if there's a scalar. This fixes that.

---end of forwarded message---

p5pRT commented 13 years ago

From @cpansprout

Fixed by 9936\, aka 7668bf4dc.

p5pRT commented 13 years ago

@cpansprout - Status changed from 'open' to 'resolved'