Your parent process needs to wait() for the children to exit.
Have you traced what your program does? Lets give it the arguments @ARGV = ( 3, "echo", "Foo!").
The trouble begins if the parent's instance of system(@ARGV) runs longer than some of the kids do. By not calling wait() for the dead kids, the parent leaves them zombie.
I won't worry here about the lack of error checking, use strict;, or the mishandling of the kids. Instead, I'll ask if this would serve you better:
The select code is an accurate sleep, giving more even timing than the one second granularity of sleep() allows. This will do what you want if the system call is brief.#!/usr/bin/perl -w use strict; my $count = shift; my $interval = 60 / $count; for (1..$count) { system(@ARGV); select(undef,undef,undef,$interval); }
If you need evenly spaced start times for long running calls, you do need to fork them off. Here's one way to do that:
Using exec() instead of system() lets us avoid handling their return. They will exit on their own. The hash trick for keeping track of children is one of my favorites.#!/usr/bin/perl -w use strict; my $count = shift; my $interval = 60 / $count; my ($pid,%kids); for (1..$count) { defined($pid = fork()) or warn $! and last; # can't die, kids to t +end $pid or exec(@ARGV); $kids{$pid}++; select(undef,undef,undef,$interval); } delete $kids{wait()} while %kids;
Update: Taint mode would be a very good thing for this program.
Update2 tye is correct, init will kill only if the session ends. A cron job is a session leader (at least on my Vixie cron). petral may well be right, but I took the question to be about running something every 10 seconds or so from a cron job that fires every minute.
After Compline,
Zaxo
In reply to Re: zombies after forking
by Zaxo
in thread zombies after forking
by very empty
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |