当我破坏了它的写作结束时管道终止了吗?

时间:2017-11-08 13:05:04

标签: c

我有父进程创建两个子进程。第一个孩子将写入管道,第二个孩子将从管道读取。 5秒后,父母将终止第一个孩子。(所以它的写入结束应该自动关闭,不是吗?)。我需要第二个孩子自动终止,因为它使用管道,在第一个孩子终止后,管道也应该终止。我的问题:当我杀死孩子1时,我怎么能强迫孩子2立即死亡?(孩子1死后,我不需要孩子2打印东西,即使他仍然在管道缓冲区中有任何信息要读)。我应该使用pipe2而不是简单的管道吗?

void do_close(int fd){
    if(close(fd) != 0){
        perror("close");
        exit(2);
    }

}
void signalhandler(int signum){
    fprintf(stderr, "f1 terminated!\n");
    exit(1);
}
int main(){
pid_t f1 = -1, f2 = -1;
int pipefd[2];
if(pipe(pipefd) == -1){
    perror("pipe");
    exit(2);
}
f1 = fork();
if(f1 > 0){
    f2 = fork();
}

if(f1 > 0 && f2 > 0){
    do_close(pipefd[0]);
    do_close(pipefd[1]);
    sleep(5);
    kill(f1, SIGTERM);  
    waitpid(f1, NULL, 0);
    waitpid(f2, NULL, 0);
}
else if(f1 == 0){
    signal(SIGTERM, signalhandler);
    do_close(pipefd[0]);
    while(1){
        fflush(stdout);
        write(pipefd[1], "Hello world!\n", 13);
        sleep(1);
    }
}
else if(f2 == 0){
    do_close(pipefd[1]);
    char *buf = (char*)malloc(13);
        while(read(pipefd[0], buf, 13) > 0){
            for(int i = 0; i < 13; i++){
                printf("%c", buf[i]);
            }
            sleep(3);
        }

}

return 0;
}

1 个答案:

答案 0 :(得分:1)

&#34;终止&#34;不是管道的通常术语,它可能会引起轻微的误解。写作过程的终止不会立即感觉到#34;如果缓冲区中仍有数据,则由读者阅读。

要总结该程序,您有一个进程以每秒1行的速率写入管道5秒钟,然后死掉。另一个过程从管道读取,每3秒一行,直到EOF或错误,然后退出。

线条很小且尺寸固定,因此无法读取不完整的线条。

程序中的任何内容都不应该导致管道出错,因此第二个子进程将读取直到EOF。

管道上的EOF在满足2个条件时发生:没有写入器,缓冲区为空。第一个子进程的死亡完成了第一个条件。第二个条件不是立即成立,因为在5秒标记处,已经有5行写入管道,其中只有2行已被读取(一个在开始时,一个在3秒后)。

第二个子进程继续读取,拉入剩余的行,最终在大约5 * 3 = 15秒后退出。

(时间不是非常精确,因此你不能保证准确地将5行写入管道。当我运行时,我得到6。)