2012-09-26 172 views
4

我的錯誤如下Perl模塊,ForkManager不工作

,而你在/usr/lib/perl5/site_perl/5.8.6/Parallel/ForkManager.pm線463子進程無法啓動另一個進程。

我的代碼中有問題的部分在下面,我的代碼下面是在forkmanager中失敗的子例程,我找不到原因。沒有forkmanager我可以運行得很好。

my $pm = new Parallel::ForkManager($MAX_PROCESSES); 
for (0..$SCOUNT) 
{ 
my $pid = $pm->start and next; 
    my %shash =(); 
    %shash = 
    ( ID  => "$SREF->[$_]->[0]", 
     typeID => "$SREF->[$_]->[1]", 
     extIP => "$SREF->[$_]->[2]", 
     intIP => "$SREF->[$_]->[3]", 
     NAME => "$SREF->[$_]->[4]", 
     buTYPE => "NULL" 
    ); 
    if ($shash{typeID} =~ /^(4|16|17|25|27|28|42|49|50|51|54|58|60|63|19)$/){$shash{buTYPE} = 'LINUX DEDICATED';} 
    if ($shash{typeID} =~ /^(11|14|22|32|34|36|37|46)$/)     {$shash{buTYPE} = 'LINUX FULL';} 
    if ($shash{typeID} =~ /^(44)$/)           {$shash{buTYPE} = 'EMAIL MARKETER';} 
    if ($shash{typeID} =~ /^(43)$/)           {$shash{buTYPE} = 'TYip1';} 
    if ($shash{typeID} =~ /^(45)$/)           {$shash{buTYPE} = 'DDDOMAINS';} 
    if ($shash{typeID} =~ /^(56)$/)           {$shash{buTYPE} = 'AT MAIL';} 
    if ($shash{typeID} =~ /^(65|66)$/)          {$shash{buTYPE} = 'ENT MAIL';} 
    if ($shash{typeID} =~ /^(1|3)$/)          {$shash{buTYPE} = 'LINUX PROD';} 

    if ($shash{buTYPE} eq 'LINUX DEDICATED' || $shash{buTYPE} eq 'LINUX FULL') 
    #if ($shash{buTYPE} eq 'LINUX FULL') 
    { 
     next if (`grep $shash{NAME} $excludes`); 
     my $ip; 
     my $ipchoice=0; 
     print "Doing $shash{NAME}.\n"; 
     my $testport = testport("$shash{intIP}",'1500'); 
     if(!$testport) 
     { 
      $ipchoice=1; 
      $testport = testport("$shash{extIP}",'1500'); 
     } 
     unless ($testport) 
     { 
      log_event("$log/rsync_error.$date_string","Port 1500 closed for $shash{NAME}\n"); 
      next; 
     } 
     if ($ipchoice==0) 
     { $ip = $shash{intIP}; 
     }else{ 
      $ip = $shash{extIP}; 
     } 
#  send_file("$repo/rsyncd.conf","$shash{intIP}","/etc/rsyncd.conf"); 
     check_rsync($shash{NAME},$ip); 
#  do_backup($shash{NAME},$ip,$shash{buTYPE}); 
    } 
    $pm->finish; 
} 
$pm->wait_all_children; 

ForkManager.pm編碼。

sub start { my ($s,$identification)[email protected]_; 
    die "Cannot start another process while you are in the child process" 
    if $s->{in_child}; 
    while ($s->{max_proc} && (keys %{ $s->{processes} }) >= $s->{max_proc}) { 
    $s->on_wait; 
    $s->wait_one_child(defined $s->{on_wait_period} ? &WNOHANG : undef); 
    }; 
    $s->wait_children; 
    if ($s->{max_proc}) { 
    my $pid=fork(); 
    die "Cannot fork: $!" if !defined $pid; 
    if ($pid) { 
     $s->{processes}->{$pid}=$identification; 
     $s->on_start($pid,$identification); 
    } else { 
     $s->{in_child}=1 if !$pid; 
    } 
    return $pid; 
    } else { 
    $s->{processes}->{$$}=$identification; 
    $s->on_start($$,$identification); 
    return 0; # Simulating the child which returns 0 
    } 
} 

回答

9

您在子進程代碼中調用next。它試圖執行for(0..$COUNT)的下一次迭代,然後再次嘗試fork,這不是您想要的。

你可能想改變

next if (`grep $shash{NAME} $excludes`); 

$pm->finish if (`grep $shash{NAME} $excludes`); 
+0

'$ S->光潔度;','不exit',是記錄的方式。請注意,如果你沒有通過任何參數,那就簡單地稱之爲「退出」。 – ikegami

+0

好點 - 固定。 – friedo

+0

謝謝friedo,這讓我走上了正確的道路,基本上修復了每一個下一個語句,pm-> finish,我忽略了愚蠢的錯誤,再次感謝 – ThatGuy