2012-04-08 146 views
1

基于这个SO postexample,我期望当我使用fork()时,将允许我以非阻塞方式执行system/execvp。但是,当我尝试在上述示例代码中的fork块中发出长时间运行的子进程时,该控件不会返回到父块,直到子结束。使用fork的C++程序中的非阻塞系统调用

你可以告诉一个方法,我应该如何设计代码以允许在C/C++代码中对系统进行非阻塞调用。此外,我计划编写一个程序,其中不止一个孩子是从同一个父母派生出来的。我怎样才能得到孩子们的pid?

感谢你的帮助。

+1

请添加一些代码来说明你在做什么。 – 2012-04-08 21:19:32

回答

3

fork将立即返回到子和父两者。但是,该示例(test3.c)调用wait4,它听起来像等待另一个进程执行某些操作(在本例中为exit)。

+0

谢谢。解决了这个问题。你还可以告诉我,如果我必须发出很多流程,叉子的相同方法是否会起作用。另外,当我使用fork得到一个子进程的PID时,它会给出0.如何获得正确的PID? – user984260 2012-04-08 21:26:53

+2

这就是叉的工作原理。它将子进程的PID返回给父进程,并将其返回给子进程。如果这没有发生,那么没有(简单的)方法来确定哪个进程是哪个进程。基本上,如果你需要自己的PID,你必须按照通常的方式得到它,现在我不记得了,但我相信你可以查看它。 – 2012-04-08 21:32:52

+2

@ user984260'fork'返回父进程中新进程的PID。在孩子中,它返回0.要获得当前进程的PID,你可以调用'getpid'。手册页是你的朋友! – 2012-04-08 21:33:29

1

提到的示例代码等待孩子产卵后返回 - 这就是为什么它会阻止。

要获得子进程的PID,使用fork的返回值()。 fork()是返回两个不同值的单个系统代码 - 父进程的子进程号和子进程的进程号。这就是为什么你可以区分你的程序中应该由父母和孩子执行的代码块。

参考man叉(2)。

另一件事你应该注意有关fork()和wait()有,经过子进程退出内核仍持有一些关于它的信息(例如,退出状态),应以某种方式消耗掉。否则,这个过程将变成'zombie'(ps输出中的Z)。这是等待*()调用完成的工作。此外,小孩退出其父后由内核以SIGCHLD通知。如果你不想处理孩子的返回值,你可以通知系统你将忽略SIGCHLD与signal(),sigaction()等等。在这种情况下,附加数据会自动收回。这种行为可能是您系统上的默认行为,但仍然建议您明确声明此类行为以提高程序的可移植性。