使用管道的孩子的计算

时间:2017-03-30 14:51:51

标签: c linux pipe fork

我的任务是

一个。父母和两个孩子

湾父母从用户那里获取数据

℃。发送给孩子进行加法和减法。

d。再次从用户那里获取输入并发送给另一个孩子进行乘法和除法。

即第一个子进程创建另一个子C3。

F。两个子节点都将结果发送到子进程C3以显示输出。

克。完成每个子进程任务后,父进程终止进程。

我写了下面的代码,但我不知道我在哪里做错了,我试着调试它,但我不知道它有什么问题,它没有显示乘法和除法结果。

这是我的代码:

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

int main()
{
    int status = 0;
    int pfds[2];
    int pfds2[2];
    int pfds3[2];
    int pfds4[2];
    int val = 0;
    int val2 = 0;
    pipe(pfds);
    pipe(pfds2);
    pipe(pfds3);
    pipe(pfds4);
    printf("Enter FIRST Number:  ");
    scanf("%i", &val);
    printf("Enter SECOND Number:  ");
    scanf("%i", &val2);
    if (fork() == 0)
    {
//Child
        printf("I'm Child 1 and I'm Calculating Sum AND Differnece Of Numbers\n");
        read(pfds[0], &val, sizeof(val));
        read(pfds2[0], &val2, sizeof(val));
        int sum = val + val2;
        int sub = val - val2;
        write(pfds3[1], &sum, sizeof(val));
        write(pfds4[1], &sub, sizeof(val));
        if (fork() == 0)
        {
            read(pfds3[0], &val, sizeof(val));
            printf("Sum Of Numbers Is : %i\n", val);
            read(pfds4[0], &val, sizeof(val));
            printf("Sub Of Numbers Is : %i\n", val);
            read(pfds[0], &val, sizeof(val));
            printf("Mul Of Numbers Is : %i\n", val);
            read(pfds2[0], &val, sizeof(val));
            printf("Div Of Numbers Is : %i\n", val);
            exit(1);
        }
        else
        {
            wait(&status);
        }
        exit(1);
    }
    else
    {
        if (fork() == 0)
        {
//Child2
            printf("I'm Child 2 and I'm Calculating Multiplication and Division Of Number\n");
            read(pfds[0], &val, sizeof(val));
            read(pfds2[0], &val2, sizeof(val));
            int mul = val * val2;
            int div = val / val2;
            write(pfds[1], &mul, sizeof(val));
            write(pfds2[1], &div, sizeof(val));
            exit(0);
        }
        else
        {
//wait(&status);
            write(pfds[1], &val, sizeof(val));
            write(pfds2[1], &val2, sizeof(val));
            wait(&status);
        } //else1
    } //else2
} //main

它给了我以下输出:

Enter FIRST Number:  4
Enter SECOND Number:  2
I'm Child 1 and I'm Calculating Sum AND Differnece Of Numbers
I'm Child 2 and I'm Calculating Multiplication and Division Of Number
Sum Of Numbers Is : 6
Sub Of Numbers Is : 2

如果有人可以提供帮助,那么。

3 个答案:

答案 0 :(得分:1)

以下是您可以做的事情:

#include <stdio.h>
#include <unistd.h>
#include<stdlib.h>
int main()
{
int status = 0;
int fd1[2], fd2[2], fd3[2], fd4[2], a, b;
pipe(fd1); pipe(fd2);
pipe(fd3); pipe(fd4);
printf("Input two numbers for + and - ");
scanf("%d,", &a); scanf("%d,", &b);
write(fd1[1], &a, sizeof(int));
write(fd2[1], &b, sizeof(int));
printf("Input two numbers for multiplication and division\n");
scanf("%d,", &a); scanf("%d,", &b);
write(fd3[1], &a, sizeof(int));
write(fd4[1], &b, sizeof(int));
pid_t child1 = fork();
if (child1 == 0)
{
    int status = 0, a, b, c;
    read(fd1[0], &a, sizeof(int));
    read(fd2[0], &b, sizeof(int));
    printf("I'm 1st child and calculating + and -\n");
    c = a + b;
    a = a - b;
    write(fd1[1], &c, sizeof(int));
    write(fd2[1], &a, sizeof(int));
    pid_t c3 = fork();
    if (c3 == 0)
    {
        int sum, sub, mul, div;
        read(fd1[0], &sum, sizeof(int));
        read(fd2[0], &sub, sizeof(int));
        read(fd3[0], &mul, sizeof(int));
        read(fd4[0], &div, sizeof(int));
        printf("SUM = %d\n", sum);
        printf("SUB = %d\n", sub);
        printf("MUL = %d\n", mul);
        printf("DIV = %d\n", div);
    }
}
else
{
    pid_t child2 = fork();
    if (child2 == 0) {
        int status = 0, a, b, c;
        read(fd3[0], &a, sizeof(int));
        read(fd4[0], &b, sizeof(int));
        printf("I'm 2nd child and calculating multiplication and division");
        c = a*b;
        a = a / b;
        write(fd3[1], &c, sizeof(int));
        write(fd4[1], &a, sizeof(int));
    }
}
return 0;
}

希望这会对你有所帮助:)。

答案 1 :(得分:0)

问题可能是孙子使用了儿童2要读取的数据之一作为输入。子2然后挂起试图从管道读取,因为它本身是唯一留给该管道写任何东西的进程,并且在它完成读取之前它不能这样做。这可能发生,因为所有三个孩子都从相同的两个管道读取输入,而没有任何(其他)进程之间的同步。

总的来说,你的策略是可疑的。通过恰当的一个过程指定每个管道末端更安全和更健壮,从而指定每个整个管道以便在一对过程之间进行通信。切换到此策略需要相同数量的管道,但需要使用不同的模式:

    管道0上的
  • ,父项将两个输入发送到子项1,一个接一个地发送
  • 管道1上的
  • ,父节点将两个输入发送给子节点2,一个接一个地输入
  • 管道2上的
  • ,子项1将结果发送给孙子/子3,一个接一个地发送
  • 管道3上的
  • ,子项2将结果发送给孙子/子3,一个接一个地发送

这样,其中一个进程就不会错误地使用针对不同数据的数据,或者错误地将数据源误认为是发送给它的任何数据的含义。

答案 2 :(得分:0)

问题看起来你误解了管道是如何工作的。您的所有子进程都共享相同的管道。当孩子1从pfds[0]读取时,这意味着当孩子2尝试从中读取时,数据已经消失。或者孩子2可能首先读取数据,而孩子1则不会读取数据。无论哪种方式,只有一个孩子可以读取数据。

您应该仅为一次使用创建每个管道 - 即父母与孩子1交谈。

也许创建一个创建管道的函数并分叉一个可以根据需要重复使用的子进程,这就像是一样。

pid_t create_child(int *pipefds[2])
  {
  pipe(*pipefds);
  return fork();
  }