进程组
进程组,就是一个或是多个进程的集合,每个进程都有一个标识组ID,表示该进程属于哪个进程组。 bash进程启动之后,它会自己调用setsid 系统函数把自己设置为会话首进程,也会设置自己为组长进程
$pid = posix_getpid();
fprintf(STDOUT,"pid=%d,ppid=%d,pgid=%d,sid=%d\n",$pid,posix_getppid(),posix_getpgid($pid),posix_getsid($pid));
执行上述代码后可以发现由于 /bin/bash 进程启动时会调用setsid 函数把自己设置为会话首进程,也会设置自己为组长进程,所有看到执行demo1.php 进程的父进程是29228 因为demo1.php在bash进程下执行,会话进程也是29228,使用echo $$ 打印当前 bash 进程pid 为 29228.
为什么pgid 不等于29228 呢? 上面我们说过/bin/bash 启动后会调用 setsid 函数设置自己为会话首进程和组长进程,但是自己脚本显示的组长进程却不是/bin/bash 的pid,这是因为脚本执行会调用 setpgid 函数把当前进程设置为组进程,所以显示的pgid不是29228 而是 2893
接下来我们来看个例子
function show(){
$pid = posix_getpid();
fprintf(STDOUT,"pid=%d,ppid=%d,pgid=%d,sid=%d\n",$pid,posix_getppid(),posix_getpgid($pid),posix_getsid($pid));
}
show();
$map_pid = [];
$pid = pcntl_fork();
if($pid > 0){
$map_pid[$pid] = $pid;
$pid = pcntl_fork();
if($pid >0){
$map_pid[$pid] = $pid;
}else{
$pid = posix_getpid();
posix_setpgid($pid,$pid);
$pid = pcntl_fork();
if($pid > 0){
$map_pid[$pid] = $pid;
}
}
}
show();
if($pid > 0){
while(1){
$pid = pcntl_waitpid(-1, $status);
if($pid > 0){
print("pid= $pid 已经结束\n");
unset($map_pid[$pid]);
}
if(empty($map_pid)){
exit(0);
}
}
}
执行上面代码我们可以通过 posix_setpgid 函数设置进程为组长进程,需要传入两个参数,第一个是进程pid,第二个是要设置为组长进程的pid
|