如何在不阻塞或不轮询的情况下从子进程的STDOUT接收输出

问题描述:

我有一个长期运行的基于控制台的应用程序Sender,它使用诸如cout << "Message" << flush()之类的非缓冲输出将简单文本发送到STDOUT.我想创建一个基于MFC对话框的应用程序(名为Receiver),该应用程序启动Sender并可以读取其输出. Receiver还应该能够检测Sender何时死亡,或者能够杀死Sender. SenderReciever一无所知,而且我无法更改Sender的代码.

I have a long-running console-based application Sender that sends simple text to STDOUT using non-buffered output such as cout << "Message" << flush(). I want to create an MFC dialog-based application (named Receiver) that starts Sender and can read it's output. Receiver should also be able to detect when Sender has died, or be able to kill Sender if it wants to. Sender knows nothing of Reciever, and I can't change Sender's code.

我的第一个尝试是使用子进程的重定向STDIN和STDOUT创建管道,并使用异步ReadFileEx调用读取Sender的数据.这无法正常工作,并且我已经单独发布了有关这些特定问题的线索.

My first attempt was to create pipes with redirected STDIN and STDOUT for the child process and use asynchronous ReadFileEx calls to read in Sender's data. This isn't working correctly, and I've posted a separate thread about those specific problems.

我的问题是,从总体上来讲,我应该怎么做?我不希望Receiver的主循环阻止或轮询,但应使用

My question is, how should I be doing this, in general architectural terms? I don't want Receiver's main loop to block or poll, but should use some flavor of Wait function.

您有2个基本选项.您已经尝试过的选项1,通过执行异步(也称为非阻塞)IO来从子进程中进行读取/写入.选项2是在Receiver进程中创建一个单独的线程,该线程确实阻止对子进程的读/写操作.

You have 2 basic options. Option 1 you've already tried, doing asynchronous (aka nonblocking) IO to read/write from the child process. Option 2 is to create a separate thread in the Receiver process that does blocking reads/writes from/to the child process.

我建议选择2,我发现它要容易得多.然后,您当然会遇到如何将数据从帮助程序线程获取到主线程的问题.您将需要使用锁,甚至可能需要使用信号灯.但是,与无阻塞IO相比,它应该没有麻烦.

I'd recommend option 2, I find it much easier. You then, of course, have the problem of how to get the data from the helper thread to the main thread. You'll need to use locks and maybe semaphores for that. It should be less of a hassle than nonblocking IO, however.