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

Hello. I'm trying to use the Safe module.

The problem I'm having is that, if the code calls an undefined subroutine, no error is reported if one of the parameters is a call to a Safe::Hole wrapper.

For example:

# "foo" is undefined
# "bar" is a Safe::Hole wrapper
foo(bar()); # no errors reported - not expected behavior
foo(); # Undefined subroutine reported as expected

Any suggestions?

Replies are listed 'Best First'.
Re: Safe module and undefined subroutines
by thanos1983 (Parson) on Aug 25, 2017 at 09:46 UTC

    Hello bovlb,

    Welcome to the Monastery. Just a minor note to make here. You have not answered the question of Anonymous Monk What problem are you trying to solve with it?.

    Why you want to call one subroutine as a parameter within another one? If you want to call a local subroutine withing another subroutine why you do not call it like this?

    #!/usr/bin/perl use strict; use warnings; use feature 'say'; sub a { say 'sub a'; local *_b = sub { say 'sub b'; }; _b(); } a(); __END__ $ perl test.pl sub a sub b

    Update: You can make it even more complicated if you want.

    #!/usr/bin/perl use strict; use warnings; use feature 'say'; sub a { local *_b = sub { say @_; return 'sub b'; }; return _b('sub a'); } say a(); __END__ $ perl test.pl sub a sub b

    Update2: You can make it even more complicated if you want, which is like calling a subroutine withing another subroutine a(_b()).

    #!/usr/bin/perl use strict; use warnings; use feature 'say'; sub a { local *_b = sub { return @_; }; return _b(@_); } say a('sub a'); __END__ $ perl test.pl sub a

    You can read more about this from this question Defining a sub within a sub: OK?. Tell us what you are trying to achieve? Many people here (not me) are very experienced so they can help you in many areas / ideas.

    Looking forward to your update, BR.

    Seeking for Perl wisdom...on the process of learning...not there...yet!

      Why you want to call one subroutine as a parameter within another one?

      It is rather common to do that. What's wrong with it, in your view?

      use strict; use warnings; use feature 'say'; print_timestamp('nigh'); print_timestamp( get_formatted_time() ); sub print_timestamp { say 'The time was ' . shift() } sub get_formatted_time { return uc scalar localtime } __END__


      The way forward always starts with a minimal test.

        Hello 1nickt,

        Maybe you missed understand what I was writing / asking. I am asking what was his target in total. It looks like XY Problem

        I never used it they way that you are using it, I would use it like this:

        #!/usr/bin/perl use strict; use warnings; use feature 'say'; sub print_timestamp { local *_get_formatted_time = sub { return $_[0] . uc scalar localtime; }; return _get_formatted_time(@_); } say print_timestamp('The time was: '); __END__ $ perl test.pl The time was: FRI AUG 25 15:18:08 2017

        Instead of:

        #!/usr/bin/perl use strict; use warnings; use feature 'say'; print_timestamp('nigh'); print_timestamp( get_formatted_time() ); sub print_timestamp { say 'The time was ' . shift() } sub get_formatted_time { return uc scalar localtime } __END__ $ perl test.pl The time was nigh The time was FRI AUG 25 15:20:10 2017

        Update: When you are calling a subroutine withing another subroutine like this:

        sub a { sub b{ } }

        It is basically the same as:

        sub a { } sub b{ }

        End of Update: So since he is try to test if a subroutine is safe (foo(bar()); # no errors reported - not expected behavior and foo(); # Undefined subroutine reported as expected). Why not simply calling it one by one, since it is the same thing if they are not defined locally?

        But I suppose it depends the case. Thanks for sharing other ideas, BR.

        Seeking for Perl wisdom...on the process of learning...not there...yet!
Re: Safe module and undefined subroutines
by Anonymous Monk on Aug 24, 2017 at 22:00 UTC
    Safe isn't really safe. What problem are you trying to solve with it?
Re: Safe module and undefined subroutines
by locked_user sundialsvc4 (Abbot) on Aug 25, 2017 at 01:22 UTC
    Could be a bug.   Write it up and see what happens.   It certainly seems to me that this would qualify as incorrect behavior.

      Hello sundialsvc4,

      Just to make a minor note here. In case of someone reports a new bug I do not know how fast it can be addressed?

      The last updated date on github/Safe-Hole was 7-8 years ago. Not that this should stop you of reporting a possible bug but I do not know how fast it can be resolved.

      Hope this helps, BR.

      Seeking for Perl wisdom...on the process of learning...not there...yet!
        The last updated date on github/Safe-Hole was 7-8 years ago

        The current maintainer of Safe::Hole (Todd Rinaldo) has, this year, updated a couple of other modules that he maintains.
        I would therefore expect that he would respond to any Safe::Hole bug report that was submitted. (No guarantees, of course.)

        Cheers,
        Rob
Re: Safe module and undefined subroutines
by bovlb (Initiate) on Aug 31, 2017 at 17:00 UTC
    Thank you for the suggestions. I have reported a bug on CPAN, with a more complete example.
    perl -we 'use Safe; use Safe::Hole; printf("%s, %s\n", $Safe::VERSION, + $Safe::Hole::VERSION); use JSON; my $safe = Safe->new; my $hole = ne +w Safe::Hole {}; sub w() { print "In wrapped w() subroutine.\n"; retu +rn $hole->wrap(JSON->new); } $hole->wrap(\&w, $safe, "&w"); print "Th +is should fail:\n"; $safe->reval("sub x { return \&w; } f(x());"); pr +int "It succeeded\n" unless($@);'
    2.35, 0.10 This should fail: In wrapped w() subroutine. Use of uninitialized value $typechar in string eq at /usr/lib64/perl5/ +vendor_perl/Safe/Hole.pm line 121. It succeeded