1

If I run an external process via a perl program,the perl program will remain the parent of the process. Making process management easy.

system('sleep 3000'); # perl is still the parent

However if I try to run the process in the background so that the program does not have to wait for the process to exit...

system('sleep 3000 &'); 

The sleep process will be adopted by the systems init process and is no longer associated with the program that executed it.

What is the proper way to handle process management in this situation. How can I emulate running the process in the background but maintain process ancestry?

BryanK
  • 1,211
  • 4
  • 15
  • 33
  • 3
    See [How do I start a process in the background](http://perldoc.perl.org/perlfaq8.html#How-do-I-start-a-process-in-the-background?) in `perlfaq8`. – ThisSuitIsBlackNot Aug 21 '14 at 16:05

2 Answers2

2

You can use threads,

use threads;
my $t = async { system('sleep 3000'); };

# do something in parallel ..

# wait for thread to finish 
$t->join;

or fork

sub fasync(&) {
  my ($worker) = @_;

  my $pid = fork() // die "can't fork!"; 
  if (!$pid) { $worker->(); exit(0); }

  return sub {
    my ($flags) = @_;
    return waitpid($pid, $flags // 0);
  }
}

my $t = fasync { system('sleep 3000'); };

# do something in parallel ..

# wait for fork to finish 
$t->();
mpapec
  • 50,217
  • 8
  • 67
  • 127
  • I had come across `threads` but after reading this in perldoc : "The use of interpreter-based threads in perl is officially discouraged." I decided not to go any further. – BryanK Aug 21 '14 at 16:21
  • `fork` is what I wanted... took me a bit to learn basics of `fork` since I have never used it... you probably just copied `system` from my post, but in your example, to be more efficient, shouldn't we use `exec` since `system` also calls `fork`? – BryanK Aug 26 '14 at 18:01
  • 1
    @BryanK `exec` runs command and never returns execution control back to perl so it's not useful here. You could use open() with pipe if you just want to fork some shell command. http://stackoverflow.com/questions/25445456/how-can-i-get-process-id-of-unix-command-i-am-triggering-in-a-perl-script/25445847#25445847 – mpapec Aug 26 '14 at 18:47
0

fork/exec and wait().

Fork creates the child process by creating a copy of the parent, the parent receives the process id of the child, and calls wait() on the child process id.

Meanwhile, the child process uses exec() to overlay itself (a copy of the parent) with the process that you wish to execute.

If you need more than one concurrent background job, I recommend Parallel::ForkManager.

Len Jaffe
  • 3,442
  • 1
  • 21
  • 28
  • could you give a basic example using for/exec and wait along with the *nix sleep command as in my example? – BryanK Aug 21 '14 at 16:17