Beefy Boxes and Bandwidth Generously Provided by pair Networks
Syntactic Confectionery Delight
 
PerlMonks  

Reading sourcecode at parsing/compilation (CHECK) time?

by LanX (Saint)
on Apr 03, 2010 at 11:58 UTC ( [id://832612]=perlquestion: print w/replies, xml ) Need Help??

LanX has asked for the wisdom of the Perl Monks concerning the following question:

Hi

motivation

An old trick is that when seeking the DATA filehandle to the beginning it's possible to read the sourcecode even before __DATA__ starts.

But with source in multiple files, modules and packages this becomes hairy.

approach

I was looking for a possibility to grab the source right away when its parsed.

Thats why I extended this example code from Attribute::Handlers to access DATA when CHECKing and print the line of the sub foo1() declaration:

package LoudDecl; use Attribute::Handlers; no warnings; sub Loud :ATTR { my ($package, $symbol, $referent, $attr, $data, $phase, $filename , $linenum) = @_; print STDERR ref($referent), " ", *{$symbol}{NAME}, " ", "($referent) ", "was just declared ", "and ascribed the ${attr} attribute ", "with data ($data)\n", "in phase $phase\n", "in file $filename at line $linenum\n"; my $tell=tell DATA; seek DATA,0,0; while (<DATA>) {print "> $_" if $.==$linenum }; seek DATA,$tell,0; } sub foo1 :Loud {print "HAHA"}; __DATA__ huhu

problem

well it works but I get a weird error from Attribut::Handlers, which only goes away after commenting out the while(<DATA>) line. I'm confused...

OUTPUT

CODE foo1 (CODE(0x8eba020)) was just declared and ascribed the Loud a +ttribute with data () in phase CHECK in file /home/lanx/perl/exp/tell.pl at line 23 > sub foo1 :Loud {print "HAHA"}; Can't use an undefined value as an ARRAY reference at /usr/share/perl/ +5.10/Attribute/Handlers.pm line 185, <DATA> line 31. INIT failed--call queue aborted, <DATA> line 31. Can't use an undefined value as an ARRAY reference at /usr/share/perl/ +5.10/Attribute/Handlers.pm line 185, <DATA> line 31. END failed--call queue aborted, <DATA> line 31.

question

What's going on, what can I do alternatively?

Cheers Rolf

UPDATE: I have the same error when directly opening the source file... it seems Attribute::Handlers is buggy...

Replies are listed 'Best First'.
Re: Reading sourcecode at parsing/compilation (CHECK) time? ($_)
by tye (Sage) on Apr 04, 2010 at 03:34 UTC

    You are clobbering $_. Put local($_); before your while() loop.

    - tye        

      thanks, switching to a lexical loop variable solved the problem!

      Silly me... I don't know why I was expecting that a core module either treats $_ safely when calling foreign code or documents warnings about possible side effects...

      Cheers Rolf

      PS: maybe the author should take a look into PBP? (SCNR ;)

Re: Reading sourcecode at parsing/compilation (CHECK) time?
by LanX (Saint) on Apr 03, 2010 at 14:59 UTC
    hmm ...

    this workaround helps caching a snapshot of the source of the corresponding file (path is in $0) and bypasses the problems of Attribute::Handlers.

    UNITCHECK { my $pos=tell DATA; seek DATA,0,0; $main::SOURCE{$0}=[<DATA>]; seek DATA,$pos,0; }

    works fine I can access the hash %main::SOURCE from everywhere, but ATM I'll have to include this block in any module I wanna process.

    Is there a global option to automatically include an UNITCHECK in any compiled file?

    UPDATE: Hmm ...or maybe I could gather all processed filenames so far from %INC, which I may process in one global CHECK block...

    Cheers Rolf

Re: Reading sourcecode at parsing/compilation (CHECK) time?
by LanX (Saint) on Apr 04, 2010 at 00:21 UTC
    very strange ...

    replacing the while(<DATA>)... code in the attribute handler with

    my $pos=tell DATA; seek DATA,0,0; my @src=<DATA>; print "> $src[$linenum-1]\n"; seek DATA,$pos,0;

    works fine!

    while(<DATA>) seems to have a special magic causing trouble...

    BUT if the __DATA__ literal is missing at the end of the code, there doesn't seem to be any open file handle for the source code...

    Seems like explicitely opening and closing the file path seems the only way to go...

    Cheers Rolf

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://832612]
Approved by moritz
Front-paged by ww
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others studying the Monastery: (6)
As of 2024-04-16 11:15 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found