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

I'm trying to convert some nasty Windows batch scripts into Perl, but I ran into a problem.

I know that when I run a Perl program, it gets its own environment, so changes made to variables disappear after the program's done. That's fine, I can live with that. But I just found out by experimentation (see code) that each call to system() also gets its own environment. Bugger.

Is there a way to force calls to system() to use the same environment as the main Perl program? If possible, I'd like to do this without modules outside the main Perl install, for easier distribution to those who'll be using it.

Here's my test code. When I run it, monkeylikes is always reported to be "bananas".

$ENV{'MonkeyLikes'} = "bananas"; print "$ENV{'MonkeyLikes'}\n"; system("echo %monkeylikes%"); system("set monkeylikes=flinging poo"); system("echo %monkeylikes%");
--- I'm too sexy for my .sig.

Replies are listed 'Best First'.
Re: Persistent environment (Windows)
by Rudif (Hermit) on Apr 10, 2001 at 02:47 UTC
    Is there a way to force calls to system() to use the same environment as the main Perl program?

    I am confused. To me, your test shows that the calls to system() inherit the environment from the main Perl program, but that changes made to the environment inside the system() call do not propagate back into the Perl program's environment.

    Dave Roth's book Win32 Perl Scripting, Chapter 6, has a section on 'Modifying the User Environment', which might be worth a glance. He shows how to set permanently e.g. $ENV{'MonkeyLikes'}, using his module Win32::AdminMisc - close, but different from what you want to do.


    PS. By an amazing coincidence, the Chapter 6 of Dave's book is available online at the above URL as a sample chapter.

      This is correct. The line
      system("set monkeylikes=flinging poo");
      sets %monkeylikes% for that system call only. You would need Win32::AdminMisc to set the variable permanently, or do
      $ENV{'MonkeyLikes'} = "bananas"; print "$ENV{'MonkeyLikes'}\n"; system("echo %monkeylikes%"); $ENV{'MonkeyLikes'} = "flinging poo"; system("echo %monkeylikes%");
      for on-the-fly while-the-script-executes kind-of stuff. It yields

      flinging poo

      I believe from the parent post that this is what you are looking for, but that is just my opinion. I could be wrong.


(tye)Re: Persistent environment (Windows)
by tye (Sage) on Apr 10, 2001 at 01:47 UTC

    I noticed something very similar to this in the release notes to Perl 5.6.1. You might want to grab that and see if it solves your problem or do more research into that bug and how it was fixed (as you could probably work around it).

            - tye (but my friends call me "Tye")
Re: Persistent environment (Windows)
by monk2b (Pilgrim) on Apr 10, 2001 at 01:54 UTC
    If I understand the question you should be able to use exec instead of system

    learning too
      If I remember right, exec() makes the program quit and execute whatever's inside the (). I don't want to do that, since I'll need to execute several commands, not just one.

      --- I'm too sexy for my .sig.