无法在Linux中写入管道

时间:2013-10-03 14:18:50

标签: c++ c linux pipe popen

我有一个第三方实用程序,我必须从我的应用程序调用它来初始化它们的一些东西。我选择使用popen来调用它,因为我需要为stdin写一个密码。

我是一个简单的用例:

...
FILE *f = popen("utility-bin", "w");
fwrite(myPassword.c_str(), 1, myPassword.size(), f);
fflush(f);
pclose(f);
...

但是,无论我如何尝试,都不会发送流,并且实用程序仍会被阻塞,等待密码。

如果我从普通的Linux shell调用该实用程序,另一方面,我只需输入密码即可。

所以我的问题是:应用程序是否有可能阻止数据来自管道,但仍然接受普通用户shell?而且,如果是这样的话,我能做些什么让它接受我的管道输入吗?

PS:当我从shell调用该实用程序时,许多信号正在处理中。例如,ctrl+cctrl+z什么都不做。

1 个答案:

答案 0 :(得分:1)

  

应用程序是否可以阻止来自的数据   管道,但仍然接受普通用户shell

它可以调用isatty,它会告诉它输入是否来自终端。

  

如果是这样的话,我能做些什么让它接受我的   管道输入

有一种方法,但你可能不喜欢它:

  1. 使用posix_openpt grantptunlockpt打开伪终端。你现在有了 “大师”fd
  2. 分叉新流程
  3. 在新流程中调用setsid()以终止其终端关联
  4. 在第1步获得的fd上的儿童电话ptsname
  5. 打开从ptsname获取的名称并在其上调用TIOCSTTY - 它将成为控制终端
  6. 将步骤5中获取的描述符复制到STDIN_FILENO
  7. 执行您的计划
  8. 您可以从TLPI中调整the function ptyForkthe function pty_fork from APUE

    此时你可以在你的过程中写入主fd - 好像它是一个管道 - 孩子会认为它来自一个终端。