通过管道传递变量,通过分叉进程执行Shell命令

时间:2017-06-12 01:45:10

标签: c linux pipe fork

这是一种无关紧要的特殊情景。我想知道我在做什么错误。

情境:
1.分叉子进程 2.子进程应执行shell命令(例如 cat 对文件进行排序) 3. shell命令的参数从父进程通过管道传递(例如g。 cat 排序的文件输入)

我已经编写了下面的程序,但它显示的是文件名,而不是打印出文件内容。但它挂起时没有给屏幕输出任何内容

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

int main(){

  int pipefd[2];
  pipe(pipefd);

  //create a pipe before you fork a child process
  pid_t cpid = fork();
  if(cpid < 0){
    perror("Fork");
  }
  else if(cpid == 0){
    printf("This is child process\n");

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

    dup2(pipefd[0],0);

    execlp("sort", "sort", NULL);

    exit(0);

  }
  else{
    printf("This is parent process\n");
    close(pipefd[0]);

    char *sort_array[] = {"hello", "amigos", "gracias", "hola"};
    for (int i=0; i<4; i++){
      write(pipefd[1],sort_array[i],strlen(sort_array[i]));
      write(pipefd[1], "\n",1);
    }


    int cstatus;
    wait(&cstatus);

  }


}

更新:
原始示例无效。我已更新为sort命令。
我正在尝试对内容进行排序。但屏幕悬空没有任何输出

2 个答案:

答案 0 :(得分:1)

当您使用dup时,您使用管道输入模拟子进程stdin,因此当您执行sort而没有任何参数时,它会从stdin读取并{读到它看到EOF所以你必须写入管道然后关闭它。

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

int main(){

   int pipefd[2];
   //create a pipe before you fork a child process
   pipe(pipefd);

   pid_t cpid = fork();
   if(cpid < 0){
       perror("Fork");
   } else if(cpid == 0) {
       printf("This is child process\n");

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

       dup2(pipefd[0],0);

       execlp("sort", "sort", NULL);

       exit(0);

  } else {
      printf("This is parent process\n");
      close(pipefd[0]);

      char *sort_array[] = {"hello", "amigos", "gracias", "hola"};
      for (int i=0; i<4; i++){
          write(pipefd[1],sort_array[i],strlen(sort_array[i]));
          write(pipefd[1], "\n",1);
      }
      close(pipefd[1]);


      int cstatus;
      wait(&cstatus);

    }
}

答案 1 :(得分:0)

pipe(pipefd);  // N.B. failed to check the return value, potential error

//create a pipe before you fork a child process
pid_t cpid = fork();
if (cpid < 0)  // `if` is a language keyword, not a function, space after
{              // opening brace on next line makes reading code easier
    perror("Fork");
}
else if (cpid == 0)
{
    printf("This is child process\n");

    close(pipefd[1]);  // closing "write" end of pipe in child
    close(0);          // closing stdin in child

    dup2(pipefd[0],0); // returned handle is not stored, see https://linux.die.net/man/3/dup2

    execlp("cat", "cat", NULL);  // function prototype is int execlp(const char *file, const char *arg, ...);
                                 // what are you trying to accomplish?

    exit(0);
}
else
{
    printf("This is parent process\n");
    close(pipefd[0]);  // close "read" end of pipe in parent process

    write(pipefd[1], "s.txt", 5);  // write text into pipe

    int cstatus;
    wait(&cstatus);    // wait for ??? something
}

您希望将其名称传递到管道中的文件打开并写入输出?