多向管道问题(父子)

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了多向管道问题(父子)相关的知识,希望对你有一定的参考价值。

我的小程序包括两个管道,用于创建父子之间的多向通信。

s2f [1]上的写入返回-1,但我不明白为什么。

你能帮助我吗?还有什么不起作用或我可以改进吗?

/*
Write a program in C language that in sequence:
1) create 2 pipes and a child (the 2 pipes will be used for two-way communication between the parent
and son);
2) the father, after the creation of the child, takes in input from the user a file name;
3) send the child the name of the file using the first pipe;
4) make the child look for the number of spaces in the file and communicate this number to the father through the use of the second pipe;
5) let the father print the number received from son;
*/

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

int main (int argc, char *argv[])
{
    int f2s[2]; 
    int s2f[2];
    int fd, n;
    pid_t p;
    char buf[20];
    char c;
    int countspace=0, valueofspace;
    if (argc<2)
    {
        printf("ERROR!\n");
        exit (-1);
    }
    if (pipe (f2s) == -1 && pipe (s2f) == -1)
        exit(-1);
    p=fork();
    if (p>0)
    {
        printf("I'm inside the father process.\n");
        close(f2s[0]);
        close(s2f[1]);
        write(f2s[1],argv[1],sizeof(argv[1]));

        read(s2f[0],&valueofspace, sizeof(int));
        printf("The spaces are %d", valueofspace);      
        printf("Father exit\n");
        exit(0);
    }
    if (p==0)
    {
        printf("I'm inside the child process.\n");
        close(f2s[1]);
        close(s2f[0]);
        read (f2s[0],buf,20);

        if (fd = open(buf, O_RDONLY) == -1)
            printf("Error when opening the file\n");

        while (read(fd,&c,1) > 0)
        {
            if (c==' ')
                countspace++;
        }
        close(fd);
        printf("Count: %d\n",countspace);
        n = write(s2f[1],&countspace, sizeof(countspace));
        printf("WRITE of %d BYTES\n", n);
        printf("Son exit \n");
        exit(0);
    }
}
答案

在写入之前,您已关闭管道s2f的读取端。

close(s2f[0]);

因此,当您写入管道时会出现EPIPE错误。来自online关于write的参考文献(重点强调):

当fd连接到读取端已关闭的管道或插槽时,会发生EPIPE错误。当发生这种情况时,写入过程也将收到SIGPIPE信号。 (因此,仅当程序捕获,阻止或忽略此信号时才会看到写入返回值。)

由于您的程序没有捕获,阻止或忽略此信号,因此写入返回值不是预期的,而是-1。

以上是关于多向管道问题(父子)的主要内容,如果未能解决你的问题,请参考以下文章

分布式系统中是不是存在父子进程关系和管道?

在 C 中使用管道在父子之间创建双向通信

在linux中使用管道使用父子进程

Linux_Centos进程间通信_管道(匿名管道_命名管道)

[Go] 通过 17 个简短代码片段,切底弄懂 channel 基础

Linux进程间通信-命名管道