c - fork 为这个 c 程序生成不正确的输出?

标签 c linux gcc fork

我有这个c代码

/* SIGCHLD handler. */
static void sigchld_hdl (int sig)
{
    /* Wait for all dead processes.
     * We use a non-blocking call to be sure this signal handler will not
     * block if a child was cleaned up in another part of the program. */
     //printf("Inside handler:  \n");
    while (waitpid(-1, NULL, WNOHANG) > 0) {
        printf("reaped\n");
    }
     //printf("Outside handler:  \n");

}

int main (int argc, char *argv[])
{
    struct sigaction act;
    int i;

    memset (&act, 0, sizeof(act));
    act.sa_handler = sigchld_hdl;

    if (sigaction(SIGCHLD, &act, 0)) {
        perror ("sigaction");
        return 1;
    }

    /* Make some children. */
    for (i = 0; i < 5; i++) {
        switch (fork()) {
            case -1:
                perror ("fork");
                return 1;
            case 0:
                 exit(0);
                return 0;
            default:
                //printf("inside parent\n");
                printf("Created child %d\n", i);

        }
    }

    /* Wait until we get a sleep() call that is not interrupted by a signal. */
    while (sleep(1)) {
        printf("inside parent while loop\n");
    }

    return 0;
}

我调用了 5 次 fork,所以我预计总共有 5 个子进程和 1 个父进程。当我运行这段代码时,我得到了这个输出

Created child 0
Created child 1
reaped
reaped
Created child 2
Created child 3
Created child 3
reaped
reaped
Created child 4
reaped
inside parent while loop

我不太明白为什么我会看到 child3 两次。关于 i 不应该有任何重复,因为 i 在每次迭代中递增。

有人能解释一下为什么我会看到 child3 两次吗?

最佳答案

stdio 缓冲区的状态包含在进程的内存空间中。如果在 fork 时缓冲区不为空,则父进程和子进程都有一份信息副本,内容为 "Child process 3\n" is in the stdout buffer, waiting to be flushed .

他们最终都会把它冲掉。

您可以通过在子进程中调用 _exit 而不是 exit 来避免这种情况。 exit 通常是一个坏主意,当您处于一个自创建以来尚未成功完成 exec 的进程中时。

关于c - fork 为这个 c 程序生成不正确的输出?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43600347/

相关文章:

c++ - EAI_NODATA 和 EAI_ADDRFAMILY 未声明(Linux 操作系统)

c - 在函数参数中弹出队列

c - 为什么这段 'C'代码的输出是这样的呢?

c - Socket 客户端发送 1 个长字符串而不是 3 个字符串

Docker 容器中的 MySQL

linux - 如何使用 'copy_to_user'?

C/Fortran 混合代码以一种奇怪的方式使用 MPI/ScaLAPACK 段错误

在C中将数据从一个结构复制到另一个

c++ - 堆栈跟踪中的 "pure virtual"调用是什么意思?

ios - cmake 命令 CXX 编译器 ABI 信息失败