简体   繁体   English

ReadFile在VS C ++ IDE内运行良好,但独立运行失败

[英]ReadFile works fine inside VS C++ IDE but fails stand-alone

Currently I have two apps, one with a GUI (written using MFC) and the other as a standard executable. 目前,我有两个应用程序,一个带有GUI(使用MFC编写),另一个作为标准可执行文件。 The GUI app (parent) triggers the standard app (child) using CreateProcessW call and parent receives messages from its child via an anonymous pipe. GUI应用程序(父级)使用CreateProcessW调用触发标准应用程序(子级),父级应用程序通过匿名管道从其子级接收消息。 The message receiving process works fine when I run the parent inside the VS IDE. 当我在VS IDE中运行父级时,消息接收过程工作正常。 However, if I run the parent standalone, parent does not receive any messages from its child (ie parent get hang in ReadFile call, waiting for messages). 但是,如果我独立运行父级,则父级不会从其子级收到任何消息(即,父级在ReadFile调用中挂起,等待消息)。

Any thoughts on this? 有什么想法吗?

Note: After creation of anonymous pipe, all read operations happens inside a separate thread and it does not block either UI or main thread. 注意:创建匿名管道后,所有读取操作都在单独的线程内进行,并且不会阻塞UI或主线程。 Some code related to child process creation and used parameters are given below. 下面给出一些与子进程创建和使用的参数有关的代码。

// pipe creation code
SECURITY_ATTRIBUTES saAttr; 
// Set the bInheritHandle flag so pipe handles are inherited.  
saAttr.nLength = sizeof(SECURITY_ATTRIBUTES); 
saAttr.bInheritHandle = TRUE; 
saAttr.lpSecurityDescriptor = NULL; 

// Create a pipe for the child process's STDOUT. 
if ( ! CreatePipe(&m_hChildStd_OUT_Rd, &m_hChildStd_OUT_Wr, &saAttr, 0) )
{
    m_logger->log( __FILE__, __LINE__, EventSeverity::WARNING, "Pipe cannot be created, will not receive meassages from child processes" );
}

// Ensure the read handle to the pipe for STDOUT is not inherited.
if ( ! SetHandleInformation(m_hChildStd_OUT_Rd, HANDLE_FLAG_INHERIT, 0) )
{
    m_logger->log( __FILE__, __LINE__, EventSeverity::WARNING, "Could not make the read handler of the anonymous pipe not-inheritable" );
}

SetStdHandle(STD_OUTPUT_HANDLE, m_hChildStd_OUT_Wr);
SetStdHandle(STD_ERROR_HANDLE, m_hChildStd_OUT_Wr);

//Child process creation code
m_startupInfo.lpDesktop   = NULL;
m_startupInfo.lpReserved  = NULL;
m_startupInfo.lpReserved2 = NULL;
m_startupInfo.lpTitle     = NULL;
m_startupInfo.hStdError   = GetStdHandle(STD_OUTPUT_HANDLE);
m_startupInfo.hStdOutput  = GetStdHandle(STD_OUTPUT_HANDLE);
m_startupInfo.dwFlags     = STARTF_USESHOWWINDOW|STARTF_USESTDHANDLES;
m_startupInfo.cb          = sizeof( m_startupInfo ); 

// launch the executable
m_isExecuting = CreateProcessW( app.exe,     // lpApplicationName
                                m_pwszParam,                                     // lpCommandLine
                                0,                                               // lpProcessAttributes
                                0,                                               // lpThreadAttributes
                                TRUE,                                            // bInheritHandles
                                CREATE_NEW_PROCESS_GROUP,                        // dwCreationFlags
                                NULL,                                            // lpEnvironment
                                curent working directory // lpCurrentDirectory
                                &m_startupInfo,                                  // lpStartupInfo
                                &m_processInfo                                   // lpProcessInformation
                              );

managed to solve this issue. 设法解决了这个问题。 Previously I was updating parent's output and error handlers to newly created handlers in order to retrieve them when creating a child process. 以前,我将父级的输出和错误处理程序更新为新创建的处理程序,以便在创建子进程时检索它们。 However, this doesn't seem to be working. 但是,这似乎不起作用。 When I modify the code to pass the pipe handlers via a pointer or a reference then things started to work fine. 当我修改代码以通过指针或引用传递管道处理程序时,事情开始正常进行。

However this does not explain the reason for running inside IDE and failing it in stand-alone mode. 但是,这并不能解释在IDE中运行并在独立模式下失败的原因。

//set the handler
SetStdHandle(STD_OUTPUT_HANDLE, m_hChildStd_OUT_Wr);
SetStdHandle(STD_ERROR_HANDLE, m_hChildStd_OUT_Wr);

//get the handler
m_startupInfo.hStdError   = GetStdHandle(STD_OUTPUT_HANDLE);
m_startupInfo.hStdOutput  = GetStdHandle(STD_OUTPUT_HANDLE);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM