Unix Pipes - Pipeline between three processes

老子叫甜甜 提交于 2019-12-23 05:43:07

问题


I'm creating a small program which contains three processes; a source process, a filter process and a sink process. The stdout of the source process is redirected to the stdin of the filter process, and the filter process' stdout is redirected to the sink process' stdin.

My problem is that no output is printed to stdout from the sink process. Can any of you see the problem in the following tiny snippet of code?

#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>


int main(int argc, char** argv)
{
     // Pipes
     // pipe1 is from source to filter, pipe2 is from filter to sink
     int pipe1[2], pipe2[2];

     // Create pipes
     if (pipe(pipe1) < 0 || pipe(pipe2) < 0)
     {
          perror("Creating pipes failed!");
     }

     if (fork() == 0)
     {
          close(1);
          dup(pipe1[1]);
          close(pipe1[0]);

          close(pipe2[0]);
          close(pipe2[1]);

          execlp("ls", "ls", NULL);
          exit(0);
     }
     else
     {
          if (fork() == 0)
          {
               close(0);
               dup(pipe1[0]);
               close(pipe1[1]);

               close(1);
               dup(pipe2[1]);
               close(pipe2[0]);

               execlp("sort", "sort", NULL);
               exit(0);
          }
          else
          {
               if (fork() == 0)
               {

                    close(0);
                    dup(pipe2[0]);

                    execlp("more", "more", NULL);
                    exit(0);
               }
          }
     }


     wait(NULL);
     printf("Done.\n");

     return 0;
}

BR

Jacob


回答1:


I think problem may be, wait will only wait for one process. And when the parent exits after first child returns, I suspect more command also decides to terminate, because it may get SIGHUP (speculation, not sure).

But, check for errors from on all system calls! Also for wait calls which succeeded, print why the child exited (was it signal or normal exit, and if it was normal exit, what was exit code).

Also note, perror does not exit, it only prints.

It is kind of pointless trying to see why some code fails, if it does not have error handling in it...




回答2:


Some easy way to do pipes for your scenario:

char cmd[MAX_LEN];
sprintf(cmd, "%s | %s | %s", app1, app2, app3); //app123 holds app name + args
system(cmd);

if you want to capture the output of the last app, use popen:

FILE pPipe = popen(cmd, "rt"); /* same access flag as fopen()*/
while (NULL != fget(buf, buf_len, pPipe)) {
    // do something with the read line in 'buf'
}


来源:https://stackoverflow.com/questions/20056084/unix-pipes-pipeline-between-three-processes

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!