[英]waitpid not returning after child has exited
Using a fairly standard fork process: 使用相当标准的fork过程:
int pipe_to_child[2];
int pipe_from_child[2];
int child_exit_status = -1;
pid_t child_pid = fork();
if (child_pid == 0) {
close(pipe_from_child[0]); // close their read end
close(pipe_to_child[1]); // Close their write end
dup2(pipe_to_child[0], STDIN_FILENO); // Tie the in pipe to stdin
dup2(pipe_from_child[1], STDOUT_FILENO); // Tie stdout to the out pipe
// Run the child process
execve(file_to_run, argv_for_prog, env_for_prog);
}
else {
close(pipe_from_child[1]); // close their write end
close(pipe_to_child[0]); // Close their read end
if (input_to_prog != NULL) write(pipe_to_child[1], input_to_prog, strlen(input_to_prog)); // Send the stdin stuff
close(pipe_to_child[1]); // Done so send EOF
// Wait for the child to end
waitpid(child_pid, &child_exit_status, 0);
// Do post end-of-child stuff
}
This generally works as expected. 这通常按预期工作。
However, when the child process, a shell script, sets a further process off in the background. 但是,当子进程(shell脚本)在后台启动另一个进程时。 Even though the child process then exits (and is no longer listed by
ps
), the waitpid doesn't return. 即使子进程随后退出(并且不再由
ps
列出),waitpid也不会返回。
The script is this case is meant to start inadyn-mt (a DDNS updater) running in the background. 这种情况下的脚本旨在启动在后台运行的inadyn-mt(DDNS更新程序)。
#!/bin/sh
inadyn-mt --background
(If I put an & after inadyn-mt it makes no difference) (如果我在inadyn-mt之后加上&,则没有区别)
It turns out that the issue is that the pipes don't get closed. 事实证明,问题在于管道没有关闭。 Although the child process exits fine, because it has spawned a further process, this process (even though it doesn't want them) is tied to the pipes to the child's stdin and stdout.
尽管子进程退出正常,但由于它已生成了一个进一步的进程,因此,该进程(即使不希望它们)也绑定到子级stdin和stdout的管道。 The solution I used was to not set up the pipes when I was going to spin off a child from the child.
我使用的解决方案是,当我要从一个孩子中分出一个孩子时,不设置管道。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.