Beefy Boxes and Bandwidth Generously Provided by pair Networks
Think about Loose Coupling
 
PerlMonks  

How do I communicate with a Windows process?

by IOl01 (Novice)
on Jul 26, 2010 at 02:33 UTC ( [id://851312]=perlquestion: print w/replies, xml ) Need Help??

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

My goal is to capture the output of netstat and getmac without flashing up a command window every time I call them (this is on Windows 7).

The stripped down code I have so far (place in sandbox.pl):

use strict; use warnings; use Win32::Process; use Win32; use Data::Dumper; my $netstat_obj; my $create_status = Win32::Process::Create( $netstat_obj, 'C:/Windows/System32/netstat.exe', 'netstat -a -e -n -o -s -r' +, 0, DETACHED_PROCESS | CREATE_NO_WINDOW | CREATE_SUSPENDED, 'C:/temp/' ) || die Win32::FormatMessage(Win32::GetLastError() +); print Data::Dumper->new(['1', $create_status, $netstat_obj], ['where__ +________', 'create_status', 'netstat_obj'])->Indent(1)->Sortkeys(1)-> +Useqq(1)->Deparse(1)->Dump(); my $NETSTAT_FH; my $open_status = Win32::Process::Open( $NETSTAT_FH, $netstat_obj->GetProcessID(), 0 ) || die Win32::FormatMessage(Win32::GetLastError()); print Data::Dumper->new(['2', $open_status, $NETSTAT_FH], ['where_____ +_____', 'open_status', 'NETSTAT_FH'])->Indent(1)->Sortkeys(1)->Useqq( +1)->Deparse(1)->Dump(); $netstat_obj->Resume(); my $netstat_data = ''; { my $offset = 0; my $length = 1024; my $buffer = undef; while(my $bytes_read = $NETSTAT_FH->sysread($buffer, $length, $offse +t)) { if(defined $bytes_read) { $netstat_data .= $buffer; $buffer = undef; last if($bytes_read == 0); $offset += $bytes_read; } else { die "ERROR: Could not read from NETSTAT_FH: $! "; } } } $netstat_obj->Wait(2000); my $netstat_exit; $netstat_obj->GetExitCode($netstat_exit); print Data::Dumper->new(['3', $netstat_obj, $NETSTAT_FH, $netstat_data +], ['where__________', 'netstat_obj', 'NETSTAT_FH', 'netstat_data'])- +>Indent(1)->Sortkeys(1)->Useqq(1)->Deparse(1)->Dump();


The results of running the above code:

C:\temp>perl.exe sandbox.pl $where__________ = 1; $create_status = 1; $netstat_obj = bless( do{\(my $o = 1776208)}, 'Win32::Process' ); $where__________ = 2; $open_status = 1; $NETSTAT_FH = bless( do{\(my $o = 1777552)}, 'Win32::Process' ); Your vendor has not defined Win32::Process macro sysread, used at sand +box.pl line 32. (Error was: 'Invalid argument') at C:/xampp/perl/site/lib/Win32/Process.pm line 53.


What I am trying to do in the above code is:

  1. create a new (detached and suspended) Windows process sans command window
  2. open a filehandle to the newly created process for reading said process's STDOUT
  3. read all of the data from the filehandle
  4. and wait for netstat to exit, then find its exit code
As the above output demonstrates, I am stuck on #3 (and despite the CREATE_NO_WINDOW constant, a window is still being created :-/ ).

In place of the sysread, I have tried: read, getlines, and getline; all with the same error "Your vendor has not defined Win32::Process macro X, used at …", where X is one of the aforementioned methods.

So my question has a few parts:

  • How do you create a Windows process without a window?
  • How do you attach a filehandle to said process's STDOUT?
  • How do you read from said filehandle?

Thank-you for your thoughts and suggestions,
IOl01

Replies are listed 'Best First'.
Re: How do I communicate with a Windows process?
by BrowserUk (Patriarch) on Jul 26, 2010 at 02:48 UTC

    Try:

    my @info = qx[ start /b /wait netstat -a -e -n -o -s -r ];; print for @info;;

    Or is that too easy?


    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.

      Thanks, your result is exactly what I was looking for!   :-D
      I was complicating my code way too much…   :-/

      Is it safe to say "Stay away from the Win32:: namespace!" is a good idea?

        Is it safe to say "Stay away from the Win32:: namespace!" is a good idea?

        Hell no! There are lots of not just useful, but in many cases little-alternative-to, modules in there.

        It just pays to look for the simplest solution first.

        BTW: Does this also work for you? (If not, why not?):

        my @info = qx[ netstat -a -e -n -o -s -r ];; print for @info;;

        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.
Re: How do I communicate with a Windows process?
by morgon (Priest) on Jul 26, 2010 at 02:56 UTC
    How do you create a Windows process without a window?

    If you are using ActiveState (I don't know about Strawberry), then there is a "wperl.exe" that you can use (i.e. you start your script with "wperl script.pl"). This is just a normal Perl-interpreter but does not start a new command-window.

      Strawberry has wperl.exe as well. Same purpose.

Re: How do I communicate with a Windows process?
by furry_marmot (Pilgrim) on Jul 26, 2010 at 21:44 UTC

    Have you tried

    open NETSTAT, "netstat -a -e -n -o -s -r|" or die "Couldn't open netst +at for parsing: $!"; @lines = <NETSTAT>; #Parse as you like

    There are reasons to use Win32::Process to control a process. And there are reasons not to. This might be one of the latter.

    --marmot
Re: How do I communicate with a Windows process?
by ahmad (Hermit) on Jul 26, 2010 at 22:02 UTC

    netstat is a windows command, you can use it from the command line, so you just have to use back ticks and it will work without a cmd window or anything else

    my $cmd = `netstat -a -e -n -o -s -r`; print $cmd;

    You might want to use the full path for the netstat command.

Log In?
Username:
Password:

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

How do I use this?Last hourOther CB clients
Other Users?
Others lurking in the Monastery: (4)
As of 2024-04-24 06:55 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found