The code before isnt working for me cause the children are correctly started but not refreshed after they died. So keep in mind to use this instead and use the signal handler to know when a child exits to know when you have to start a new one. I added a few lines to the posting from {andy at cbeyond dot net} cause his post wasnt working for me as well (PHP5.1). Same effect like the one below.
<?php
declare(ticks = 1);
$max=5;
$child=0;
// function for signal handler
function sig_handler($signo) {
global $child;
switch ($signo) {
case SIGCHLD:
echo "SIGCHLD received\n";
$child--;
}
}
// install signal handler for dead kids
pcntl_signal(SIGCHLD, "sig_handler");
while (1){
$child++;
$pid=pcntl_fork();
if ($pid == -1) {
die("could not fork");
} else if ($pid) {
// we are the parent
if ( $child >= $max ){
pcntl_wait($status);
$child++;
}
} else {
// we are the child
echo "\t Starting new child | now we de have $child child processes\n";
// presumably doing something interesting
sleep(rand(3,5));
exit;
}
}
?>
pcntl_wait
(PHP 5)
pcntl_wait — 待つかフォークした子プロセスのステータスを返す
説明
この関数は、子プロセスが終了する・ カレントのプロセスを終了させるシグナルが送信される・シグナル処理関数を コールするシグナルが送信される のいずれかが発生するまでカレントのプロセスの実行を中断します。 子プロセスが、 コール時に 既に終了している場合("ゾンビ"プロセスと呼ばれます)、この関数は 直ちに処理を返します。子プロセスにより使用される全てのシステム リソースは、解放されます。waitpid のシステムでの動作に関する詳細は、 システムの wait(2) についての man ページを参照ください。
注意: この関数は、pid に -1 を指定し、options を何も設定せずに pcntl_waitpid() をコールするのと等価です。
パラメータ
- status
-
pcntl_wait() は、パラメータ status の中にステータス情報を保存します。 このステータスは、次の関数を用いて評価可能です。 pcntl_wifexited()、 pcntl_wifstopped()、 pcntl_wifsignaled()、 pcntl_wexitstatus()、 pcntl_wtermsig() および pcntl_wstopsig() 。
- options
-
システム上で wait3 が使用可能な場合 (ほとんどの BSD 系システムが 該当します)、オプションのパラメータ options を使用可能です。このパラメータが指定されない場合、wait はシステムコールに 対して使用されます。wait3 が使用できない場合、options に値を設定しても何の影響も及ぼしません。 options の値は、次の 2 つのグローバル定数の ゼロまたはそれ以上の論理和です。
options のとりうる値 WNOHANG 子プロセスが終了していない場合に直ちに処理を返します。 WUNTRACED 停止した子プロセスの場合に処理を返します。 そして、ステータスは報告されません。
返り値
pcntl_wait() は、終了した子プロセスの プロセス ID を返します。エラーの場合は -1、(wait3 が使用可能なシステムで) WNOHANG が使用され、子プロセスが利用できない場合に 0 を返します。
pcntl_wait
24-Mar-2006 11:19
19-Feb-2006 04:39
This a simple multi process application where you can choose
the maximun process that can run at the same time.
This is useful when you need to limit the fork of process.
When the MAXPROCESS is reached the program wait on pcntl_wait()
<?
DEFINE(MAXPROCESS,25);
for ($i=0;$i<100;$i++){
$pid = pcntl_fork();
if ($pid == -1) {
die("could not fork");
} elseif ($pid) {
echo "I'm the Parent $i\n";
$execute++;
if ($execute>=MAXPROCESS){
pcntl_wait($status);
$execute--;
}
} else {
echo "I am the child, $i pid = $pid \n";
sleep(rand(1,3));
echo "Bye Bye from $i\n";
exit;
}
}
?>
19-Oct-2005 07:14
Below is a simple example of forking some children and timing the total duration (useful for stress tests).
<?php
$isParent = true;
$children = array();
$start = microtime( true);
/* Fork you!
* (Sorry, I had to)
*/
$ceiling = $CONCURRENCY - 1;
for ( $i = 0; (( $i < $ceiling) && ( $isParent)); $i++) {
$pid = pcntl_fork();
if ( $pid === 0) {
$isParent = false;
} elseif ( $pid != -1) {
$children[] = $pid;
}
}
/* Process body */
echo "Do stuff here\n";
/* Cleanup */
if ( $isParent) {
$status = null;
while ( count( $children)) {
pcntl_wait( $status);
array_pop( $children);
}
echo "Completed in " . ( microtime( true) - $start) . " seconds.\n";
}
?>
