Beefy Boxes and Bandwidth Generously Provided by pair Networks
Don't ask to ask, just ask
 
PerlMonks  

Problems with IPC::Run module on Windows XP

by laoboss (Initiate)
on Mar 31, 2007 at 15:14 UTC ( [id://607629]=perlquestion: print w/replies, xml ) Need Help??

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

I'm writing a server using PERL (I'm running a Windows XP system). It needs to write some data to the an external console application and capture and process it's output. I looked through the web and found the IPC::Run module. It seemed to be, what I needed. At first I wrote a test program like that -
use IPC::Run qw(start pump finish); my @args; push @args, $app_path; my ($in, $out, $err); # starting the application my $handle = start \@args, \$in, \$out, \$err; # wait until prompted for input pump $handle until $out =~ /Login:/; $in .= "Boris\n"; # wait until prompted for password pump $handle until $out =~ /Password:/; # and so on ...
This script worked fine. But I needed to store the $in $out and $handle variables for further use. So I put them in the hash
$client_descr->{"Handle"} = $handle; $client_descr->{"In"} = $in; $client_descr->{"Out"} = $out; $client_descr->{"Err"} = $err;
But after that I had problems: From other sub I got $in $ out and $handle
my ($handle, $in, $out) = ($client_descr->{"Handle"}, $client_descr->{ +"In"}, $client_descr->{"Out"});
But I had problems - here in this pump loop nothing seemed to happed. This pump loop was just locked.
$in .= "new data\n"; pump $handle until $out =~ /data arrived:/; print $out;
Is it true, that I can use IPC::Run only in one module? And are there any other solutions of my problem? I tried to ise Open2, but it doesn't seem to be working.

Replies are listed 'Best First'.
Re: Problems with IPC::Run module on Windows XP
by shmem (Chancellor) on Mar 31, 2007 at 21:18 UTC
    Note that you pass references to the start methods:
    # starting the application my $handle = start \@args, \$in, \$out, \$err;

    After the fact, those references are lost for you, since you don't save them. Then you store copies of the scalars $in, $out, $err into the hash %client_descr for later use. But alas, those values don't have any connection with the handles IPC::Run operates with. So you are using a $out later that isn't the one IPC::Run is using.

    To fix that, either make your $in, $out, $err into references first and store those -

    my ($in, $out, $err); for($in,$out,$err) { $_ = \my $x } # starting the application my $handle = start \@args, $in, $out, $err; # wait until prompted for input pump $handle until $$out =~ /Login:/; # note the dereferencing +- $$out $in .= "Boris\n"; # wait until prompted for password pump $handle until $$out =~ /Password:/; # and so on ... # store them $client_descr->{"Handle"} = $handle; $client_descr->{"In"} = $in; $client_descr->{"Out"} = $out; $client_descr->{"Err"} = $err;

    - then you can use them in another sub too:

    $in .= "new data\n"; pump $handle until $$out =~ /data arrived:/; # note the dereferencing +- $$out print $$out;

    - or store references to those scalars into your hash:

    $client_descr->{"Handle"} = $handle; $client_descr->{"In"} = \$in; $client_descr->{"Out"} = \$out; $client_descr->{"Err"} = \$err; # later ... my ($handle, $in, $out) = ($client_descr->{"Handle"}, $client_descr->{ +"In"}, $client_descr->{"Out"}); $in .= "new data\n"; pump $handle until $$out =~ /data arrived:/; # note the dereferencing +- $$out print $$out;

    Here the references IPC::Run operates with and those stored in the hash are different, but that is okay since both point to the same my scalars, which won't get destroyed until the references IPC::Run and your %client_descr hold are released.

    You must use scalar dereferencing in "the other sub" since you cannot force $out in "the other sub" to have the same address as the original $out declared as a my variable in the first place, from which a reference was taken to pass it to start of IPC::Run.

    --shmem

    _($_=" "x(1<<5)."?\n".q·/)Oo.  G°\        /
                                  /\_¯/(q    /
    ----------------------------  \__(m.====·.(_("always off the crowd"))."·
    ");sub _{s./.($e="'Itrs `mnsgdq Gdbj O`qkdq")=~y/"-y/#-z/;$e.e && print}
      Thank you very much! That helped!

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://607629]
Approved by Joost
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others contemplating the Monastery: (2)
As of 2024-04-20 05:11 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found