问题描述
我需要创建一个流程树,其中的关系如图所示。
问题是我必须按字母顺序创建所有“节点”。我已经走了这么远,但我的订单不一致。我认为我错误地使用了 waitpid
?
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
int main(int argc,char **argv)
{
pid_t pidA,pidB,pidC,pidD,pidE,pidF,pidG,pidI;
pidA = fork();
if (pidA < 0)
{
perror("A");
exit(1);
}
else if (pidA == 0)
{
printf("%d: A\n",getpid());
pidB = fork();
if (pidB < 0)
{
perror("B");
exit(1);
}
else if (pidB == 0)
{
printf("%d: B\n",getpid());
waitpid(pidD,NULL,0);
pidE = fork();
if (pidE < 0)
{
perror("E");
exit(1);
}
else if (pidE == 0)
{
printf("%d: E\n",getpid());
waitpid(pidG,0);
pidI = fork();
if (pidI < 0)
{
perror("E");
exit(1);
}
else if (pidI == 0)
{
printf("%d: I\n",getpid());
}
else
{
;
}
}
else
{
pidF = fork();
if (pidF < 0)
{
perror("F");
exit(1);
}
else if (pidF == 0)
{
printf("%d: F\n",getpid());
}
else
{
;
}
}
}
else
{
pidC = fork();
if (pidC < 0)
{
perror("B");
exit(1);
}
else if (pidC == 0)
{
printf("%d: C\n",getpid());
waitpid(pidF,0); // !
pidG = fork();
if (pidG < 0)
{
perror("G");
exit(1);
}
else if (pidG == 0)
{
printf("%d: G\n",getpid());
}
else
{
;
}
}
else
{
pidD = fork();
if (pidD < 0)
{
perror("B");
exit(1);
}
else if (pidD == 0)
{
printf("%d: D\n",getpid());
}
else
{
;
}
}
}
}
else
{
;
}
return 0;
}
输出不一致,所以我认为这部分没有多大帮助。
5644: A
5645: B
5646: C
5647: D
5648: G
5650: F
5649: E
5651: I
解决方法
这里的主要问题是 waitpid
仅在所有进程线性相关(即父进程、子进程、“孙子”进程等)时才满足同步。
但是,如图所示,您的流程并不是线性相关的。当您从 B 进程中调用 waitpid(pidD,NULL,0);
时,您会发现此问题出现。在此上下文中不仅没有定义 pidD
,而且 D 进程不是 B 进程的子进程,因此 waitpid
是不合适的。
@EOF 提出了一个很好的观点,即尝试串联运行多个进程违背了拥有多个进程的目的。但是,如果您只是想将此练习作为一个有趣的脑筋急转弯来进行,我建议您在原始进程中设置 pipe
,然后在适当的进程想要发出它已退出的信号时关闭写入端。等待第一个进程结束的进程可以在读取端调用 select
。