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

I want to call a Perl function and be sure it cannot access any variables declared in its context, just its local variables and passed arguments. Is this possible?
  • Comment on How to call a perl function without its context?

Replies are listed 'Best First'.
Re: How to call a perl function without its context?
by Corion (Patriarch) on Jul 28, 2015 at 09:40 UTC

    There is no easy way to eliminate all variables that a function has closed over. Most likely, you can get at the list of closed over variables using PadWalker, and you can reassign these variables too, using the set_closed_over function. But the variables themselves cannot be eliminated.

    Also, your use of "local variables" is confusing, because Perl has the local keyword. I think you mean "lexical variables declared within the function scope".

    Maybe you can tell us what kind of problem you are trying to solve. Maybe the local keyword already solves most of your problems?

Re: How to call a perl function without its context?
by BrowserUk (Patriarch) on Jul 28, 2015 at 09:42 UTC
    I want to call a Perl function and be sure it cannot access any variables declared in its context, just its local variables and passed arguments. Is this possible?

    Yes. Just call it.

    If the subroutine was declared to use variables from outside of its own body -- ie. closures or global variables -- then from the point of view of the caller of that function, those variables are "local variables".

    Or no.

    If the subroutine was declared to use variables from outside of its own body -- ie. closures or global variables -- then the function wouldn't work if it didn't have access to them; so there would be no point in calling it if the caller could deny access to them.

    All of which suggests you are trying to fix something; but you are going about it in the wrong way.

    Your best bet would be to explain what it is that you are trying to 'fix'; perhaps then we can help you to a solution.


    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". I knew I was on the right track :)
    In the absence of evidence, opinion is indistinguishable from prejudice.
    I'm with torvalds on this Agile (and TDD) debunked I told'em LLVM was the way to go. But did they listen!
Re: How to call a perl function without its context?
by anonymized user 468275 (Curate) on Jul 28, 2015 at 09:58 UTC
    I agree with browserUK on this one, but would add also:

    - use 'use strict;' in your sources, to ensure no auto-declarations are allowed.

    - avoid global variables where possible and use 'use constant;' for the cases where you want a global constant like pi to be immutable and ubiquitously available.

    - use classes (and possibly Moo) to reduce the need for randomly scoped identifiers and to manage the scope and access to attributes.

    One world, one people

Re: How to call a perl function without its context?
by GrandFather (Saint) on Jul 28, 2015 at 10:39 UTC

    This is Perl we are talking about? Not JavaScript? If you have come from a JavaScript background you have a bunch of stuff about scope and lifetime to unlearn.

    If you don't have JavaScript baggage you need to tell us more about what your concerns are. Show us some code and tell us more about why this "protection" is important to you.

    Premature optimization is the root of all job security
      I do not have any code to show at the moment because I am just "thinking about the problem" right now. I want to automatically create testsuites for functions that create random inputs to detect any errors or misbehaviours. But in order to make sure a function is actually pure (not grabbing anything from global namespace or closure-scope) I would like to run it some kind of "sandbox".
Re: How to call a perl function without its context?
by KurtSchwind (Chaplain) on Jul 28, 2015 at 11:59 UTC

    You could make a package that doesn't reference anything else. Slap a function in the object and call it.

    package MyIsolatedFunction; my $singleton = undef; sub new { my( $class ) = @_; return $singleton if defined $singleton; my $self = 0; $singleton = bless \$self, $class; return $singleton; } sub isolatedFunction { ... # Normal function stuff here. } 1;
    --
    “For the Present is the point at which time touches eternity.” - CS Lewis
Re: How to call a perl function without its context?
by Anonymous Monk on Jul 28, 2015 at 09:40 UTC
      Yes for security reasons I want to make sure a function does not access anything beyond its "lexical variables declared within the function scope" (Thank you BrowserUk). Basicly I want to write pure functions that will throw a compile-time error when they are not pure.

        Basicly I want to write pure functions that will throw a compile-time error when they are not pure.

        Your definition of 'pure' is different from my definition of 'pure'.

        A 'pure' (as in functional programming) function ~can~ use external variables and still be called pure. It must not modify these variables, but it would be perfectly fine to have a sin(x) where you provide π as an external value. Changing π will change the actual output value, but if you repeat the calculation it will a) result in the same output value and b) x and π will not be modified.

        If you want to reject functions that access global state, consider what B::Xref provides you. With that, you can get at a list of global variables used by a function.

        I'll need to check out Safeand its family, as they may have addressed the problem.

        My current thought would be to develop each function (presuming this is synonymous with a Perl subroutine in this context) initially as a stand-alone file, with use strict;and use warnings;at the top and a calling routine built in.

        If it compiles without errors, there are no external references.

        Then a quick process to extract only the subroutine into your main code and you're off to the races.

        The weakness is that if one bypasses the build procedure, one can violate the constraint.

Re: How to call a perl function without its context?
by Anonymous Monk on Jul 28, 2015 at 09:56 UTC
      Thats a start, thank you!
Re: How to call a perl function without its context?
by Your Mother (Archbishop) on Jul 30, 2015 at 17:03 UTC
A reply falls below the community's threshold of quality. You may see it by logging in.