Inspired by http://perlmonks.org/?node_id=448016, I wrote this little function to figure out the name of a CODEref. Uses a nifty B:: hack.
use B; sub findit { my $ref = shift; die "I only work for CODErefs!" unless ref $ref eq 'CODE'; my $package = B::svref_2object($ref)->START->stashpv; local(*alias, *stash); *stash = *{"${package}::"}; while ((my $varname, my $globvalue) = each %stash){ next if $varname eq "alias"; *alias = $globvalue; if (defined(&alias)){ if ($ref == \&alias){ return $varname; } } } return undef; }

Replies are listed 'Best First'.
Re: Find the name of a CODEref
by imp (Priest) on Aug 25, 2006 at 12:06 UTC
    This should be equivalent:
    use B; sub codename { my $coderef = shift; return unless ref $coderef eq 'CODE'; my $cv = B::svref_2object($coderef); return $cv->GV->NAME; }
    But personally I would use Sub::Identify.
    use Sub::Identify qw(sub_name); sub foo {} print sub_name(\&foo);
Re: Find the name of a CODEref
by GrandFather (Saint) on Aug 25, 2006 at 04:01 UTC

    It would be better to simply return undef than die if it's not a code ref wouldn't it? Perhaps die if it is a coderef but you can't find it?


    DWIM is Perl's answer to Gödel
      It would be better to simply return undef than die if it's not a code ref wouldn't it?

      Well that's largely dependent on the coding conventions for you/your project. But in general I'd say No, it makes more sense to die, because it likely represents a programming error, which you'd like to catch during development. Put another way: it's probably better to ensure a priori that only code refs are being passed in, than to have to try to handle errors resulting from passing a non-code-ref.

      We're building the house of the future together.
Re: Find the name of a CODEref
by ysth (Canon) on Aug 25, 2006 at 16:26 UTC
Re: Find the name of a CODEref
by diotalevi (Canon) on Aug 28, 2006 at 14:23 UTC

    How do you plan to find functions that exist only in lexical pads or that exist in multiple locations? You're examining the package that the subroutine was compiled in but not looking to see all the places it is now. Anyway, imp and ysth's solution is equivalent to yours and more direct.

    ⠤⠤ ⠙⠊⠕⠞⠁⠇⠑⠧⠊