FAQ
Do you remember this little odd feature that allows to add
a coderef in @INC? See the digest for info :

http://www.perl.com/pub/a/2001/03/p5pdigest/THISWEEK-20010305.html#Coderef_INC

AFAIK, this feature has been left unfinished in the core :
there are no docs and no tests for it.

I've looked back into the p5p archives. You can add a coderef in @INC;
it should return a filehandle from which the Perl source to use/require
will be read. An arrayref in which the 1st element is a coderef will
also work.

The thing becomes more complicated when you learn that this coderef is
also allowed to return _another_ coderef (in addition to the filehandle)
that will act as a source filter. (I'm summarizing the API here, but
that's the big picture). Doesn't this duplicate the functionality
provided by the Filter::* modules? (TIMTOWTDI, but that's not a reason
to include in the core something that is also provided by separate
modules).

Anyway, documentation and tests are needed here. Also, I think that
the core modules that iterate over @INC, assuming that it contains
strings, should be reviewed.

Any hints or comments?

Search Discussions

  • Jonathan Stowe at Aug 22, 2001 at 8:05 am

    On Tue, 21 Aug 2001, Rafael Garcia-Suarez wrote:

    Do you remember this little odd feature that allows to add
    a coderef in @INC? See the digest for info :

    http://www.perl.com/pub/a/2001/03/p5pdigest/THISWEEK-20010305.html#Coderef_INC

    AFAIK, this feature has been left unfinished in the core :
    there are no docs and no tests for it.
    So I sat down with my computer with a view to seeing what I could do about
    this and whilst writing a test to determine what use could be made of the
    coderef that is passed to the subroutine I came up with :

    #!/usr/bin/perl -w

    use strict;

    BEGIN
    {
    push @INC , bless( sub { print "*@_*" }, 'Foo');
    }

    use Foggle;


    Which to my surprise gives :

    Can't locate object method "INC" via package "Foo" (perhaps you forgot to
    load "Foo"?) at inctest.pl line 10.
    BEGIN failed--compilation aborted at inctest.pl line 10.


    Now maybe I shouldnt be surprised and maybe I have missed something here
    but to me this looks like it wants me to define Foo::INC() - but even
    doing that doesnt help.

    A cursory examination of the code of pp_require() seems to suggest that it
    should work - is this just not finished ?

    /J\
    --
    Jonathan Stowe |
    <http://www.gellyfish.com> | This space for rent
  • Philippe M . Chiasson at Aug 22, 2001 at 8:20 am

    On Wed, Aug 22, 2001 at 08:27:10AM +0100, Jonathan Stowe wrote:
    On Tue, 21 Aug 2001, Rafael Garcia-Suarez wrote:

    Do you remember this little odd feature that allows to add
    a coderef in @INC? See the digest for info :

    http://www.perl.com/pub/a/2001/03/p5pdigest/THISWEEK-20010305.html#Coderef_INC

    AFAIK, this feature has been left unfinished in the core :
    there are no docs and no tests for it.
    So I sat down with my computer with a view to seeing what I could do about
    this and whilst writing a test to determine what use could be made of the
    coderef that is passed to the subroutine I came up with :

    #!/usr/bin/perl -w

    use strict;

    BEGIN
    {
    push @INC , bless( sub { print "*@_*" }, 'Foo');
    }

    use Foggle;


    Which to my surprise gives :

    Can't locate object method "INC" via package "Foo" (perhaps you forgot to
    load "Foo"?) at inctest.pl line 10.
    BEGIN failed--compilation aborted at inctest.pl line 10.
    You didn't place a CODE ref in @INC, but a blessed object.

    In the case of a CODE ref, like this :

    #!/usr/bin/perl -w

    use strict;

    BEGIN
    {
    push @INC ,sub {
    print "*@_*";
    open (FH, "/dev/null");
    return \*FH;
    };
    }
    use Foogle;

    you will see it works :

    Foggle.pm did not return a true value at t.pl line 14.

    If you put a blessed thing in there, it attempts to call ->INC('Foogle.pm') on it
    instead.

    #!/usr/bin/perl -w

    use strict;

    BEGIN
    {
    sub foo::INC {
    print "*@_*";
    open (FH, "/dev/null");
    return \*FH;
    }
    push @INC , bless {} ,'foo';
    }

    use Foggle;

    But for this to work, you need a _fairly_ recent version of perl.

    Hope this helps
    Now maybe I shouldnt be surprised and maybe I have missed something here
    but to me this looks like it wants me to define Foo::INC() - but even
    doing that doesnt help.

    A cursory examination of the code of pp_require() seems to suggest that it
    should work - is this just not finished ?

    /J\
    --
    Jonathan Stowe |
    <http://www.gellyfish.com> | This space for rent
    --
    Philippe M. Chiasson <gozer@cpan.org>
    Extropia's Resident System Guru
    http://www.eXtropia.com/

    Intelligent, well meaning programmers can insert bugs more
    quickly than they can be removed.
    -- Greg Stein

    perl -e '$$=\${gozer};{$_=unpack(P26,pack(L,$$));/^Just Another Perl Hacker!\n$/&&print||$$++&&redo}'
  • Rafael Garcia-Suarez at Aug 22, 2001 at 8:29 am

    On 2001.08.22 09:27:10 +0200 Jonathan Stowe wrote:
    So I sat down with my computer with a view to seeing what I could do about
    this and whilst writing a test to determine what use could be made of the
    coderef that is passed to the subroutine I came up with :

    #!/usr/bin/perl -w

    use strict;

    BEGIN
    {
    push @INC , bless( sub { print "*@_*" }, 'Foo');
    }

    use Foggle;


    Which to my surprise gives :

    Can't locate object method "INC" via package "Foo" (perhaps you forgot to
    load "Foo"?) at inctest.pl line 10.
    BEGIN failed--compilation aborted at inctest.pl line 10.
    This is not surprising -- you didn't define the method INC.
    Here's a test case that works :

    #!/opt/perl/bin/perl5.7.2 -w
    sub Foo::INC { print "*@_*\n"; undef } # return undef filehandle: file not found
    BEGIN
    {
    push @INC , bless( { }, 'Foo');
    }
    use Foggle;

    And this correctly reports :

    *Foo=HASH(0x81096f4) Foggle.pm*
    Can't locate Foggle.pm in @INC (@INC contains: /home/rafael/perllib /opt/perl/lib/5.7.2/i686-linux /opt/perl/lib/5.7.2 /opt/perl/lib/site_perl/5.7.2/i686-linux /opt/perl/lib/site_perl/5.7.2 /opt/perl/lib/site_perl . Foo=HASH(0x81096f4)) at /home/rafael/bin/quux line 9.
    BEGIN failed--compilation aborted at /home/rafael/bin/quux line 9.
    Now maybe I shouldnt be surprised and maybe I have missed something here
    but to me this looks like it wants me to define Foo::INC() - but even
    doing that doesnt help.
    You probably have missed that sub INC {...} always defines a subroutine in the
    main:: package.

    --
    Rafael Garcia-Suarez
  • Nicholas Clark at Aug 22, 2001 at 9:46 am

    On Tue, Aug 21, 2001 at 09:54:00PM +0200, Rafael Garcia-Suarez wrote:
    Do you remember this little odd feature that allows to add
    a coderef in @INC? See the digest for info :

    http://www.perl.com/pub/a/2001/03/p5pdigest/THISWEEK-20010305.html#Coderef_INC

    AFAIK, this feature has been left unfinished in the core :
    there are no docs and no tests for it.

    I've looked back into the p5p archives. You can add a coderef in @INC;
    Sort of here ish:
    http://www.xray.mpe.mpg.de/mailing-lists/perl5-porters/2001-02/msg01780.html
    it should return a filehandle from which the Perl source to use/require
    will be read. An arrayref in which the 1st element is a coderef will
    also work.
    Around Feb this year (I think) a patch from me was added so that if the
    "coderef" is actually a blessed reference then its INC method is called.
    I believe that in doing this I've actually bust a specific corner case of
    a blessed array reference (code in pp_ctl.c currently seems to dereference it
    to get 1st element and then do the "is it coderef or blessed?" check - this
    means that you can't use the INC method on an object that is a blessed
    hashref. This is probably wrong)
    The thing becomes more complicated when you learn that this coderef is
    also allowed to return _another_ coderef (in addition to the filehandle)
    that will act as a source filter. (I'm summarizing the API here, but
    that's the big picture). Doesn't this duplicate the functionality
    provided by the Filter::* modules? (TIMTOWTDI, but that's not a reason
    to include in the core something that is also provided by separate
    modules).
    The core filter is subtly broken in its implementation - see the message I
    reference for 1 case. At the time that Ken Fox provided the original patch
    Filter::* had not been assimilated. My opinion is that the core filter should
    be removed, and the pp_ctl.c code be rewritten to use Filter::Simple.
    However, I don't know (yet) how to implement the necessary perl opcodes
    to do this.
    Anyway, documentation and tests are needed here. Also, I think that
    the core modules that iterate over @INC, assuming that it contains
    strings, should be reviewed.
    A reasonable idea. Who gets to do this? :-)

    Gisle Aas already supplied a patch to stop chomp stringifying everything
    willy nilly, which was related to coderef INC:
    http://www.xray.mpe.mpg.de/mailing-lists/perl5-porters/2001-05/msg01445.html

    Nicholas Clark
  • Rafael Garcia-Suarez at Aug 22, 2001 at 8:35 pm

    On 2001.08.22 11:46 Nicholas Clark wrote:

    Around Feb this year (I think) a patch from me was added so that if the
    "coderef" is actually a blessed reference then its INC method is called.
    I believe that in doing this I've actually bust a specific corner case of
    a blessed array reference (code in pp_ctl.c currently seems to dereference it
    to get 1st element and then do the "is it coderef or blessed?" check - this
    means that you can't use the INC method on an object that is a blessed
    hashref. This is probably wrong)
    The Foo::INC method trick seems to work very well (see my reply to
    J. Stowe). Just remember that INC should always be fully qualified.
    The core filter is subtly broken in its implementation - see the message I
    reference for 1 case. At the time that Ken Fox provided the original patch
    Filter::* had not been assimilated. My opinion is that the core filter should
    be removed, and the pp_ctl.c code be rewritten to use Filter::Simple.
    However, I don't know (yet) how to implement the necessary perl opcodes
    to do this.
    Do we need the ability to include source code filters via hooks in @INC ?
    This is an undocumented feature, so backward compatibility is not very
    important here. My suggestion would be to drop this, and to say that the
    subroutines executed via @INC are called in scalar context, and should return
    undef or a filehandle.
    Anyway, documentation and tests are needed here. Also, I think that
    the core modules that iterate over @INC, assuming that it contains
    strings, should be reviewed.
    A reasonable idea. Who gets to do this? :-)
    Well, I'm slowly working on docs and tests. But I'm not fluent with PP
    code.

    About the docs, here the layout I've in mind (as suggested by Jarkko) :
    - a very small overview in perlvar/@INC
    - full explanation in perlfunc/require

    Where should the tests go ? I thought about making a new test file in t/op.
  • Rafael Garcia-Suarez at Aug 22, 2001 at 9:32 pm

    On 2001.08.22 22:38 Rafael Garcia-Suarez wrote:
    The Foo::INC method trick seems to work very well (see my reply to
    J. Stowe). Just remember that INC should always be fully qualified.
    Strange. I can use blessed hashrefs and scalar refs in @INC, but
    not blessed arrayrefs :

    #!/opt/perl/bin/perl5.7.2
    sub Foo::INC { print "@_\n"; undef }
    unshift @INC, bless([123], 'Foo');
    require Foo::Bar;

    Output :

    Undefined subroutine &main::123 called at /home/rafael/bin/quux line 5.

    That's a case for the bug you were referring to.
  • Nicholas Clark at Aug 25, 2001 at 1:50 pm

    On Wed, Aug 22, 2001 at 11:35:08PM +0200, Rafael Garcia-Suarez wrote:
    On 2001.08.22 22:38 Rafael Garcia-Suarez wrote:

    The Foo::INC method trick seems to work very well (see my reply to
    J. Stowe). Just remember that INC should always be fully qualified.
    Yes, I fell into that trap that first time :-)
    Strange. I can use blessed hashrefs and scalar refs in @INC, but
    not blessed arrayrefs :

    #!/opt/perl/bin/perl5.7.2
    sub Foo::INC { print "@_\n"; undef }
    unshift @INC, bless([123], 'Foo');
    require Foo::Bar;

    Output :

    Undefined subroutine &main::123 called at /home/rafael/bin/quux line 5.

    That's a case for the bug you were referring to.
    This should cure it:

    --- pp_ctl.c.orig Mon Aug 13 00:50:50 2001
    +++ pp_ctl.c Sat Aug 25 14:30:12 2001
    @@ -3153,7 +3153,8 @@
    int count;
    SV *loader = dirsv;

    - if (SvTYPE(SvRV(loader)) == SVt_PVAV) {
    + if (SvTYPE(SvRV(loader)) == SVt_PVAV
    + && !sv_isobject(loader)) {
    loader = *av_fetch((AV *)SvRV(loader), 0, TRUE);
    }



    Thanks for the documentation patch. You mentioned in an earlier message about
    tests - were you writing some? [I'd prefer not to write the tests, as I have
    a preconceived idea about how it all should work, and might miss a way to
    break it]

    One thing that worries me is this comment in pp_ctl.c:

    if (io) {
    tryrsfp = IoIFP(io);
    if (IoTYPE(io) == IoTYPE_PIPE) {
    /* reading from a child process doesn't
    nest -- when returning from reading
    the inner module, the outer one is
    unreadable (closed?) I've tried to
    save the gv to manage the lifespan of
    the pipe, but this didn't help. XXX */
    filter_child_proc = (GV *)arg;
    (void)SvREFCNT_inc(filter_child_proc);
    }

    Does anyone know exactly what the comment is about, and does anyone have
    code to demonstrate the problem?

    Nicholas Clark
  • Randal L. Schwartz at Aug 23, 2001 at 1:27 pm
    "Rafael" == Rafael Garcia-Suarez writes:
    Rafael> Do we need the ability to include source code filters via
    Rafael> hooks in @INC ?

    Wasn't this to support gzipped @INC hierarchies? Or does that use a
    different mechanism? I recall someone saying that they could get
    gzipped @INCs working now that ___ was done. Was this it?

    --
    Randal L. Schwartz - Stonehenge Consulting Services, Inc. - +1 503 777 0095
    <merlyn@stonehenge.com> <URL:http://www.stonehenge.com/merlyn/>
    Perl/Unix/security consulting, Technical writing, Comedy, etc. etc.
    See PerlTraining.Stonehenge.com for onsite and open-enrollment Perl training!
  • Simon Cozens at Aug 23, 2001 at 1:34 pm

    On Thu, Aug 23, 2001 at 06:27:21AM -0700, Randal L. Schwartz wrote:
    "Rafael" == Rafael Garcia-Suarez <rgarciasuarez@free.fr> writes:
    Rafael> Do we need the ability to include source code filters via
    Rafael> hooks in @INC ?

    Wasn't this to support gzipped @INC hierarchies? Or does that use a
    different mechanism? I recall someone saying that they could get
    gzipped @INCs working now that ___ was done. Was this it?
    Yes and no. It does enable support for zipped @INC, (See ex::lib::zip)
    but it's useful for lots of other things as well. (See ByteLoader)

    Simon
  • Nicholas Clark at Aug 23, 2001 at 1:53 pm

    On Thu, Aug 23, 2001 at 02:33:43PM +0100, Simon Cozens wrote:
    On Thu, Aug 23, 2001 at 06:27:21AM -0700, Randal L. Schwartz wrote:
    "Rafael" == Rafael Garcia-Suarez <rgarciasuarez@free.fr> writes:
    Rafael> Do we need the ability to include source code filters via
    Rafael> hooks in @INC ?

    Wasn't this to support gzipped @INC hierarchies? Or does that use a
    different mechanism? I recall someone saying that they could get
    gzipped @INCs working now that ___ was done. Was this it?
    Originally I was playing with source filters to decompress things.
    [Hmm. I have a module to do this. Maybe it should go onto CPAN]
    But it doesn't help with the data in <DATA>
    Yes and no. It does enable support for zipped @INC, (See ex::lib::zip)
    but it's useful for lots of other things as well. (See ByteLoader)
    Ah. But don't see ex::lib::zip right now because it SEGVs in all the tests. :-(
    Pressure of time meant I'd not looked at it since 5.7.1 and enough APIs have
    moved since then to break things. I'm also aware that its prerequisites
    PerlIO::gzip and PerlIO::subfile fail tests/are issuing warnings during
    testing. I started to attempt to track down the causes of all these bugs
    last night and fix them (hence the proposed perlio patch for the first small
    thing)

    Nicholas Clark
  • Rafael Garcia-Suarez at Aug 23, 2001 at 1:49 pm

    On 2001.08.23 15:27:21 +0200 Randal L. Schwartz wrote:
    "Rafael" == Rafael Garcia-Suarez <rgarciasuarez@free.fr> writes:
    Rafael> Do we need the ability to include source code filters via
    Rafael> hooks in @INC ?

    Wasn't this to support gzipped @INC hierarchies? Or does that use a
    different mechanism? I recall someone saying that they could get
    gzipped @INCs working now that ___ was done. Was this it?
    I had a quick look at ex::lib::zip 0.02 (I assume that's the module
    you recall) -- it puts an object in @INC and its INC method returns
    undef or a filehandle.

    The filter feature I was referring to is when the INC method returns a list
    containing a (possibly null) filehandle and a filter subroutine. And that's
    actually subtly broken and difficult to use (compared to Filter::Simple).
    I don't know if someone actually uses this.

    --
    Rafael Garcia-Suarez

Related Discussions

Discussion Navigation
viewthread | post
Discussion Overview
groupperl5-porters @
categoriesperl
postedAug 21, '01 at 7:51p
activeAug 25, '01 at 1:50p
posts12
users6
websiteperl.org

People

Translate

site design / logo © 2021 Grokbase