两个过滤器由Linux上的两个命名管道(FIFO)循环链接

时间:2011-01-25 14:21:46

标签: c linux named-pipes fifo cat

我想让两个进程通过Linux上的两个命名管道相互通信。 每个进程都是一个Unix过滤器:它读取标准输入的数据并在其标准输出上写入数据。 它们是循环链接的,第一个的输出是第二个的输入,反之亦然。

这是第一个过滤器(a.c)的代码:

#include <stdio.h>

int main( void  ){
  FILE* ferr = fopen( "/dev/stderr", "w" );
  double d;

  fprintf(ferr,"A is going to write\n");
  printf("%lf\n",1.);
  fprintf(ferr,"A wrote %lf\n",1.);

  while( 1 ){
    fprintf(ferr,"A is going to read\n");
    if( scanf("%lf",&d) == EOF ){
      break;
    }
    fprintf(ferr,"A recieved : %lf\n",d);
    d += 1;
    fprintf(ferr,"A is going to write\n");
    printf("%lf\n",d);
    fprintf(ferr,"A wrote %lf\n",d);
  }
  return 0;
}

这是第二个过滤器的代码(b.c):

#include <stdio.h>

int main( void  ){
  FILE* ferr = fopen( "/dev/stderr", "w" );
  double d;

  while( 1 ){
    fprintf(ferr,"B is going to read\n");
    if( scanf("%lf",&d) == EOF ){
      break;
    }
    fprintf(ferr,"B recieved : %lf\n",d);
    d += 1;
    fprintf(ferr,"B is going to write\n");
    printf("%lf\n",d);
    fprintf(ferr,"B wrote %lf\n",d);
  }
  return 0;
}

我编译(gcc -o A a.c && gcc -o B b.c),创建两个fifos(mkfifo b2a ; mkfifo a2b),在终端(cat a2b | ./B > b2a)中运行第一个程序,打开一个新终端并运行第二个程序({ {1}})。

我所期待的是A和B依次增加数量的无限循环,但我得到的是B卡住,无法读取A写的内容。

在我推出B的期间,我得到:

cat b2a | ./A > a2b

在我发布A的终端中,我得到:

B is going to read

如果我使用lsof:

A is going to write
A wrote 1.000000
A is going to read

为什么我达不到预期?

提前致谢。

1 个答案:

答案 0 :(得分:6)

写入后需要显式fflush,以便输出通过管道。否则,输出可能会保留在写入过程'stdio缓冲区中。 (您也可以使用setvbuf(stdio, NULL, _IONBF, 0)关闭缓冲。)