我一直在搜索和阅读手册,但仍然无法了解管道机制。我正在制作一个程序,它应该执行以下操作:
父进程创建管道,两个子进程并等待。
- 第一个 child 生成一对随机数,并通过管道将它们之间的空格传递给第二个进程。它一直持续到 从 parent 那里得到信号。
- 第二个 child 重定向它的输入,因此它是第一个 child 的输出,并将输出重定向到 out.txt 文件。然后执行 已经编译的程序,从 (1) 计算数字的 GCD;
parent 关闭管道并杀死 child 。
所以我得到了这个 C 代码(我减少了它以便帖子符合规则):
const int PIPE_READEND=0;
const int PIPE_WRITEEND=1;
(...)
if (child1 == 0) {
//Child1 code here
close(fd[1]);
struct sigaction sa;
sa.sa_handler = sigHandler;
sigemptyset(&sa.sa_mask);
sa.sa_flags = 0;
if (sigaction(SIGUSR1,&sa,NULL) == -1){ //Handling SIGUSR1 signal
perror("Signal handling unexpected error");
exit(errno);
}
int a,b;
srand(time(&t));
if (dup2(fd[PIPE_READEND],1) < 0){ //Redirecting stdout to the pipe fd.
perror("In Child1 Redirecting stdout to pipe error");
exit(errno);
}
close(fd[0]);
while(1){
a = rand();
b = rand();
printf("%d %d\n", a, b);
sleep(1);
}
(...)
if ((child2 = fork()) < 0){
perror("Fork error in Child2 process");
exit(errno);
} else if (child2 == 0){
//Child2 code here
close(fd[PIPE_READEND]);
FILE *outfile = fopen("out.txt","w");
dup2(fd[PIPE_WRITEEND],0);
dup2(outfile,1);
close(fd[PIPE_WRITEEND]);
execl("c1/main","main",(char *)NULL);
问题是,执行后,out.txt 保持为空。我对管道数组索引感到失望,哪个用于什么。
最佳答案
您从错误的管道索引写入和读取。您需要更改它们:
这会将标准输出重定向到管道输入。
close(fd[0]);
dup2(fd[1], STDOUT_FILENO);
这会将管道输出重定向到标准输入。
close(fd[1]);
dup2(fd[0], STDIN_FILENO);
另外 dup2
接受整数,而不是指针,所以你应该这样做:
f = fopen("out.txt", "w");
dup2(fileno(f), STDOUT_FILENO);
关于C - 在不同的过程中使用不同的管端,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41029398/