Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl Monk, Perl Meditation
 
PerlMonks  

Perl allows package names consisting entirely of colons

by tobyink (Abbot)
on Nov 27, 2012 at 12:43 UTC ( #1005846=obfuscated: print w/ replies, xml ) Need Help??

It seems quite bizarre that this works...

use v5.14; use strict; use warnings FATAL => qw(all); package :::::::: { sub x { printf "(%s)\n", __PACKAGE__ }; } ::::::::::x ();
perl -E'sub Monkey::do{say$_,for@_,do{($monkey=[caller(0)]->[3])=~s{::}{ }and$monkey}}"Monkey say"->Monkey::do'

Comment on Perl allows package names consisting entirely of colons
Download Code
Re: Perl allows package names consisting entirely of colons
by Athanasius (Monsignor) on Nov 27, 2012 at 13:06 UTC

    Seems to work only when the colons come in pairs:

    #! perl use strict; use warnings; package ::::: { sub x { printf "(%s)\n", __PACKAGE__; } } package main; :::::::x();

    Produces:

    23:01 >perl 405_Obfu.pl Bareword "::::::" refers to nonexistent package at 405_Obfu.pl line 27 +. Invalid version format (non-numeric data) at 405_Obfu.pl line 17, near + "package ::::" syntax error at 405_Obfu.pl line 17, near "package :::::" Execution of 405_Obfu.pl aborted due to compilation errors. 23:02 >
    “Curiouser and curiouser!” cried Alice.

    Update: D’oh! (slaps forehead). Of course! :: is a synonym for main, and so is ::main and therefore ::::, likewise ::::::, etc., etc. (See Packages.) This “insight” is wrong — see reply by tobyink, below.

    Athanasius <°(((><contra mundum

      In terms of the package keyword itself, :: and main are distinct packages, and :::: is another package entirely...

      $ perl -Mstrict -Mwarnings -E'package main; say __PACKAGE__' main $ perl -Mstrict -Mwarnings -E'package ::main; say __PACKAGE__' main $ perl -Mstrict -Mwarnings -E'package ::; say __PACKAGE__' :: $ perl -Mstrict -Mwarnings -E'package ::::; say __PACKAGE__' ::::
      { package main; sub xxx { 0 }; package ::; sub xxx { 1 }; package ::::; sub xxx { 2 }; } use 5.010; say ::xxx(); # 0 say ::::xxx(); # 1 say ::::::xxx(); # 2
      perl -E'sub Monkey::do{say$_,for@_,do{($monkey=[caller(0)]->[3])=~s{::}{ }and$monkey}}"Monkey say"->Monkey::do'
Re: Perl allows package names consisting entirely of colons
by BrowserUk (Pope) on Nov 27, 2012 at 13:12 UTC

    Do you consider that the cost of adding the tests to prevent this -- at every place where a package name can appear, at compile time or runtime -- would be worth having, in order to prevent this perfectly logical -- if weird -- possibility?


    With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
    Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
    "Science is about questioning the status quo. Questioning authority".
    In the absence of evidence, opinion is indistinguishable from prejudice.

    RIP Neil Armstrong

      I'm not entirely sure what I'd expect. warnings checks (sometimes at compile time, sometimes at run time) and warns about far less weird stuff, at cost.

      There would seem to be very little penalty in at least disallowing the package ::::::; syntax the same as package 123 is already disallowed, even if symbols in these packages can still be created by symbol table hackery.

      perl -E'sub Monkey::do{say$_,for@_,do{($monkey=[caller(0)]->[3])=~s{::}{ }and$monkey}}"Monkey say"->Monkey::do'
        There would seem to be very little penalty in at least disallowing the package ::::::; syntax the same as package 123 is already disallowed,

        Forgetting the cost for a moment; why disallow it?

        '::' is a separator. Multiple separators with nothing between them imply null namespaces. We allow the null top-level namespace $:: to good effect; albeit that it implies 'main'. Isn't allowing a null namespace at all levels just a logical -- if obscure and unfriendly -- extension of that.

        It is perfectly feasible to make the fuel filler mechanisms on cars so that it would be impossible to casually drop a lit match into the tank. We do not do that because whilst it does happen; the occurrence is so rare -- and always deliberate -- that the costs of doing so are disproportionate to the occurrence. Especially when the main source of the occurrence -- the deliberate arsonists, criminals and vandals -- can just as easily adopt some other mechanism to achieve their goals.

        For me, it all comes back to the pragmatism that lies at the heart of Perl. If people want to break encapsulation by directly accessing the instance data in objects; Perl doesn't try to stop them. Sure I can use inside out objects; but then "they" can always modify the source code to achieve their goals anyway, so I've imposed the cost of (at least one) extra dereference on every user in order to prevent the occasional perpetrator, who - if their need is sufficient, can still do it any way. And let's face it. Once my module is in their codebase; it is their code. Who am I to place restrictions upon what they need or choose to do with it?

        The greatest danger to Perl's continued popularity, and even existence, is the recent obsession to turn Perl away from its pragmatic origins into some theoretically Utopian perfection. Which is impossible, even if it were desirable. Which it isn't.

        Expending cycles trying to trap this particular piece of obscurism, when there are so many other possibilities:

        { package _'_'_'_'_; sub hi{ say 'hello from ', __PACKAGE__ } };; _'_'_'_'_::hi;; hello from _::_::_::_::_

        Just seems pointless.


        With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
        Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
        "Science is about questioning the status quo. Questioning authority".
        In the absence of evidence, opinion is indistinguishable from prejudice.

        RIP Neil Armstrong

      I don't think this would not be a significant cost. Only the package declaration would have to be checked (and there is already some checking of package names); everything else would work out to a normal syntax error or a nonexistent package error.

      That said, I'm fine with Perl's "if you want to do something stupid, who are we to stop you?" philosophy.



      When's the last time you used duct tape on a duct? --Larry Wall
        I don't think this would not be a significant cost. Only the package declaration would have to be checked ...

        Is that true? What about?:

        ::::::::fred = 1;

        But also, once you start trying to validate this, what other additional rules are you going to add? Should we allow package _::_::_;?

        That said, I'm fine with Perl's "if you want to do something stupid, who are we to stop you?" philosophy.

        I also think that we should stick to that principle.


        With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
        Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
        "Science is about questioning the status quo. Questioning authority".
        In the absence of evidence, opinion is indistinguishable from prejudice.

        RIP Neil Armstrong

        …if you want to do something stupid, who are we to stop you?

        I agree while asserting it might be amended–

        …if you want to do something stupid, who are we to stop you? You might be smarter or more creative than we were at that moment in time and it would be wrong to impose our limitations on our audience.

        …while not asserting that I personally might have ever been anything but stupid in this context.

Re: Perl allows package names consisting entirely of colons
by LanX (Canon) on Nov 27, 2012 at 16:42 UTC
    I'm more surprised about the package NAMESPACE BLOCK syntax which seems to be quite new.

    Well hopefully the old Perl4 namespace separator (i.e. Single'Quote ) can't be used the same way ... ;-)

    Cheers Rolf

      It was introduced in Perl 5.14. Perl 5.12 also introduced package NAME VERSION. The two can be combined, a la:

      package Foo::Bar 1.2 { ...; }
      perl -E'sub Monkey::do{say$_,for@_,do{($monkey=[caller(0)]->[3])=~s{::}{ }and$monkey}}"Monkey say"->Monkey::do'
Re: Perl allows package names consisting entirely of colons
by blackle (Beadle) on Nov 27, 2012 at 19:23 UTC

    I know you could've done this with regular variables, but using pairs of colons to access the packages' $_s looks really funny:

    perl -e '$::=$::::=($::==$::);map{$::::*=++$::;$::-=$::**--$::::>>$::}(++$::..++$::::**$::*$::);$::::+=$::*$::*$::+$::*$::*$::;$::::.=$::*$::::*++$::;@::::::=reverse($::::=~m/74|72|65|80/g);print map{chr}@::::::;print"\n"'

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: obfuscated [id://1005846]
Front-paged by Arunbear
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others meditating upon the Monastery: (3)
As of 2014-09-22 00:00 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    How do you remember the number of days in each month?











    Results (176 votes), past polls