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

I have a script that opens an executable as a file handle ie: $pid = open(PRG, "| my.exe"); The script sends query commands, analyzes the output, and does some stuff if it finds something it doesn't like. Here's my problem, I run the script as an NT service when I stop the service the perl.exe stops but "my.exe" keeps on going. I have an exitGracefully sub routine that will stop "my.exe" cleanly, but I can't figure out how to call that sub when the script dies. I've tried using END blocks and sigtrap. Has anyone been able to accomplish this in NT?

Replies are listed 'Best First'.
Re: Stopping a file handle process in NT
by OzzyOsbourne (Chaplain) on Jan 19, 2001 at 21:58 UTC

    Have you looked into win32::Process for this? it contains win32::process::killprocess, I think.

    -OzzyOsbourne

      I've explored it (and will again), one problem I have with my code is the $pid comes back with a "1" not the actual process id. I don't know if it's something with the NT build or my code.

        Your code is giving a T/F response, I think. If you open the process with win32::process, I believe that you get the PID this way (not really tested)

        foreach $server (@servers){ Win32::Process::Create($ProcessObj, "c:\\perl\\bin\\perl.exe", "perl.exe c:\\script.pl", 0, NORMAL_PRIORITY_CLASS, ".")|| die ErrorReport(); $ProcessObj->GetProcessID()

        The last bit returns the process ID. To kill it, use:

        Win32::Process::KillProcess($pid, $exitcode)

        -OzzyOsbourne

Re: Stopping a file handle process in NT
by a (Friar) on Jan 20, 2001 at 10:28 UTC
    Not that I'll ever understand NT but, you're opening PRG as an input handle, but you analyze the output? Goes to a well known location? Can you open my.exe, do your business and close it each time? I'd poke around activestate and Dave Roth's site, seems the end service has to be using a trappable signal; you just need to find the right one. Finally, can you open my.exe first ("my.exe | perl my.pl") so that my.exe gets the service killed signal also? Just whistling past the NT-yard ...

    a

      My work around is have another script/batch file kick off the perl program when you start the service via GUI or net start. I added a sub routine to make sure the service is running "while(serviceRunning() ) {}" if you stop the service the perl program will exit gracefully. Trapping signals is much cooler but this works. thanks