关于wait()和waitpid()

4

我用C语言编写了这段代码。我创建了一个父进程,它有两个子进程,其中一个成为了僵尸进程。在一秒钟后,它退出,等待他的父进程也结束了。另一个子进程则变成孤儿进程,然后结束了。我的问题是,如果我将wait改为waitpid会发生什么。

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>

int main() {
    pid_t pid;
    int status, value;

    pid = fork();

    if (pid > 0) { // Father

        pid = fork();

        if (pid > 0) { // Father
            wait(&status);
            value = WEXITSTATUS(status);

            if (value == 2)
                printf("Child 2");
            else if (value == 3)
                printf("Child 1");

        } else if (pid == 0) { //Child 2 - Orphan
            sleep(4);
            exit(2);

        } else {
            exit(1);
        }

    } else if (pid == 0) { // Child 1 - Zombie
        sleep(1);
        exit(3);

    } else {
        printf("Error al ejecutar el fork");
        exit(1);
    }



    return 0;
}

1
第一个子进程将变成僵尸状态,直到父进程退出,然后它将成为孤儿。 - Barmar
@Barmar 但这怎么可能呢?第一个子进程(成为僵尸进程)也已经退出了。 - Mr. Kevin
1
如果进程的父进程退出时没有等待它,那么该进程将变成孤儿进程。即使子进程已经退出也是如此。当进程成为孤儿进程时,init 接管该进程,等待它,然后该进程消失。 - Barmar
@Barmar 所以,两个子进程都变成孤儿了? - Mr. Kevin
1
不,使用waitpid()等待的进程不会变成孤儿,因为你正在等待它。 - Barmar
1个回答

4
引用自wait/waitpid
waitpid()函数提供了三个原因:
- 支持作业控制 - 允许非阻塞版本的wait()函数 - 允许库例程(如system()或pclose())等待其子进程,而不会影响其他已终止但该进程尚未等待的子进程
而且,
如果pid参数为(pid_t)-1且options参数为0,则waitpid()函数等效于wait()。否则,其行为将受到pid和options参数值的修改。
因此,waitpid()的行为取决于其参数。

我猜他的意思是 waitpid(pid, &status); - Barmar
@Ayak973,wait() 函数的非阻塞版本是什么? - Mr. Kevin
@Mr.Kevin如果您在调用waitpid时使用了WNOHANG选项,它就不会阻塞。 - Barmar
@Barmar:如果他按照你的建议编写代码,那么代码将无法编译(waitpid()需要三个参数)。 - Jonathan Leffler
是的,我缩写只是为了表明我的观点,即他正在等待特定的pid。 - Barmar

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接