我们有一个在Windows 8.1上运行的Qt(Qt 5.7)应用程序,我们希望从另一个Qt应用程序启动它。父流程应通过阅读其stdout
和stderr
并写入其stdin
来与子流程进行通信。
子进程是一个Windows GUI应用程序。在子进程中,我们有一个类ConsoleReader
,其中包含以下初始化代码(我们遵循找到的信息here):
QSharedPointer<QWinEventNotifier> mNotifier;
...
AttachConsole(GetCurrentProcessId());
// Reopen the std I/O streams to redirect I/O to the console.
freopen("CON", "w", stdout);
freopen("CON", "w", stderr);
freopen("CON", "r", stdin);
mNotifier.reset(new QWinEventNotifier(GetStdHandle(STD_INPUT_HANDLE)));
connect(mNotifier.data(), &QWinEventNotifier::activated,
this, &ConsoleReader::onData);
然后是插槽:
void ConsoleReader::onData()
{
QTextStream input(stdin, QIODevice::ReadOnly);
const QString line = input.readLine();
// Process line here
}
在父流程中,我们执行:
QProcess process;
process.setProcessChannelMode(QProcess::MergedChannels);
process.start(executablePath, arguments);
process.waitForStarted();
然后,我们使用
阅读子流程stdout
/ stderr
QTextStream inputStream(&process);
... inputStream.readLine();
并使用
写入子流程stdin
const QByteArray bytesToWrite = ...;
process.write(bytesToWrite);
从子进程读取工作。 另一方面,当父进程尝试写入时,在父进程上写入成功,但子进程没有收到任何数据。
请注意,相同的解决方案适用于Linux。在Linux上,ConsoleReader
中的初始化代码是
QSharedPointer<QSocketNotifier> mNotifier;
mNotifier.reset(new QSocketNotifier(STDIN_FILENO, QSocketNotifier::Read));
connect(mNotifier.data(), &QSocketNotifier::activated,
this, &ConsoleReader::onData);
并且其余代码是相同的。
那么,尝试在Windows上写入子进程的stdin
时可能会出现什么问题?