如何将单个文件描述符上的读取和写入发送到不同的地方?

如何将单个文件描述符上的读取和写入发送到不同的地方?

我有一个 Linux 可执行文件foo,它从 fd 0 读取输入并将输出写入 fd 0 (不是FD 1)。这对于终端中的交互使用来说效果很好。

在 shell 命令行中,如何执行该程序,以便从一个文件读取 fd 0,但将 fd 0 写入另一文件?

我能想到的最好的办法是$ goo input.txt output.txt | foo哪里goo有一些帮助程序,但我不知道任何现有的帮助程序,我什至不知道设置的管道是否|是双向的。

答案1

使用socat(版本 2 或更高版本):

socat 'system:cat input.txt & cat > output.txt,commtype=socketpair' \
      'system:foo,nofork'

或者甚至更好:

socat 'CREATE:output.txt%OPEN:input.txt' 'system:foo,commtype=socketpair'

我们使用的socketpair是双向的(Linux 上的管道不是双向的)。另一种选择是通过上面的方法使用伪终端(也是双向的)commtype=pty。如果foo希望与终端对话,这可能是更好的方法。

或者您可以像这样实现该socketpair方法perl

perl -MSocket -e '
  socketpair(A, B, AF_UNIX, SOCK_STREAM, PF_UNSPEC);
  if (fork) {
    close A;
    if (fork) {
      open STDOUT, ">&B";
      exec("cat", "input.txt")
    }
    open STDIN, "<&B";
    open STDOUT, ">output.txt";
    exec("cat")
  }
  close B;
  open STDIN, "<&A";
  exec "foo"'

(这里作为一个快速的概念验证,您可能需要添加错误检查并通过不使用那么多进程并避免执行来提高其效率cat)。

相关内容