This queue is for tickets about the Class-Std CPAN distribution.

Report information
The Basics
Id:
14431
Status:
open
Priority:
Low/Low
Queue:

People
Owner:
Nobody in particular
Requestors:
luke [...] daeron.com
Cc:
AdminCc:

BugTracker
Severity:
Normal
Broken in:
  • 0.0.4
  • 0.0.9
  • 0.011
Fixed in:
(no value)



Subject: subtle bug created by wrapping UNIVERSAL::can
Because of this module, I keep bumping into corners of Perl I hadn't explored yet :-) Today's discovery came after trying to figure out why the following failed: $ perl -wle 'use Config::Std; use Template::Timer;' Died at /Library/Perl/5.8.6/Template/Timer.pm line 63. The uses wouldn't fail if performed in the opposite order. Template::Timer looked too simple to give rise to any real weirdness, so I looked through Class::Std to see if anything unusual was going on, and came across the replacement of UNIVERSAL::can. And sure enough, the offending line in Template::Timer was a call to can() with a form I'd never seen before: my $super = __PACKAGE__->can("SUPER::$sub") or die; I didn't even know that was possible! The error introduced by Class::Std is, I think, that SUPER::whatever has a meaning based on the context of the call, not the class of the invocant. Class::Std, in wrapping UNIVERSAL::can, moves the context of the call to itself, which will never completely work, at least without some ugly hacking for this corner case. Since Template::Timer is using simple inheritance it seems it could be easily rewritten to be both less cryptic and compatible with Class::Std. But this feature could be pretty useful with multiple inheritance, and breaking unrelated code is obviously a bad thing... I have attached a test case that demonstrates the problem succinctly.
use strict; package A; sub foo { 1 } package B; our @ISA = 'A'; use Test::More tests => 2; BEGIN { is( B->can("foo"), B->can("SUPER::foo"), "can(SUPER::method) finds sub"); } use Class::Std; is( B->can("foo"), B->can("SUPER::foo"), "can(SUPER::method) after UNIVERSAL::can replaced" );
Date: Sat, 05 Nov 2005 10:28:12 -0800
To: bug-Class-Std@rt.cpan.org
Subject: Re: [cpan #14431] subtle bug created by wrapping UNIVERSAL::can
From: Damian Conway <thoughtstream@gmail.com>
RT-Send-Cc:
Show quoted text
> Today's discovery came after trying to figure out why the following failed: > $ perl -wle 'use Config::Std; use Template::Timer;' > Died at /Library/Perl/5.8.6/Template/Timer.pm line 63. > > The uses wouldn't fail if performed in the opposite order. > > Template::Timer looked too simple to give rise to any real weirdness, > so I looked through Class::Std to see if anything unusual was going > on, and came across the replacement of UNIVERSAL::can. And sure > enough, the offending line in Template::Timer was a call to can() with > a form I'd never seen before: > > my $super = __PACKAGE__->can("SUPER::$sub") or die; > > I didn't even know that was possible! The error introduced by > Class::Std is, I think, that SUPER::whatever has a meaning based on > the context of the call, not the class of the invocant. Class::Std, in > wrapping UNIVERSAL::can, moves the context of the call to itself, > which will never completely work, at least without some ugly hacking > for this corner case. Since Template::Timer is using simple > inheritance it seems it could be easily rewritten to be both less > cryptic and compatible with Class::Std. But this feature could be > pretty useful with multiple inheritance, and breaking unrelated code > is obviously a bad thing...
Fixed by rearranging the replacement C<UNIVERSAL::can()> so that it eventually does a: goto &{$real_can}; Thanks, Damian
From: Mark Blythe
This still seems to be broken as of Class::Std v0.08. Will the mentioned fix be published soon?
On Sun Apr 02 03:53:58 2006, guest wrote:
Show quoted text
> This still seems to be broken as of Class::Std v0.08. Will the > mentioned fix be published soon?
fixed in 0.0.9 via rt 30833, thanks!
Show quoted text
> fixed in 0.0.9 via rt 30833, thanks!
Also, please reopen with details if this is in actuality not fixed in 0.0.9's UNIVERSAL::can fix, thanks!
I think this is still broken. I checked the unit test attached to this ticket and it fails in 0.0.9 and 0.011. I can give more details if you need them, but I think the attached test is an accurate description of my problem.


This service runs on Request Tracker, is sponsored by The Perl Foundation, and maintained by Best Practical Solutions.

Please report any issues with rt.cpan.org to rt-cpan-admin@bestpractical.com.