|
@@ -32,7 +32,6 @@ HANDLE g_hInputFile = NULL;
|
|
PROCESS_INFORMATION piProcInfo;
|
|
PROCESS_INFORMATION piProcInfo;
|
|
DWORD exit_code;
|
|
DWORD exit_code;
|
|
|
|
|
|
-void CreateChildProcess(void);
|
|
|
|
void WriteToPipe(void);
|
|
void WriteToPipe(void);
|
|
void ReadFromPipe(void);
|
|
void ReadFromPipe(void);
|
|
void ErrorExit(PTSTR);
|
|
void ErrorExit(PTSTR);
|
|
@@ -42,129 +41,107 @@ OVERLAPPED oOverlap;
|
|
ULONG PipeSerialNumber;
|
|
ULONG PipeSerialNumber;
|
|
|
|
|
|
BOOL MyCreatePipeEx(
|
|
BOOL MyCreatePipeEx(
|
|
- OUT LPHANDLE lpReadPipe,
|
|
|
|
- OUT LPHANDLE lpWritePipe,
|
|
|
|
- IN LPSECURITY_ATTRIBUTES lpPipeAttributes,
|
|
|
|
- IN DWORD nSize,
|
|
|
|
- DWORD dwReadMode,
|
|
|
|
- DWORD dwWriteMode)
|
|
|
|
|
|
+ OUT LPHANDLE lpReadPipe,
|
|
|
|
+ OUT LPHANDLE lpWritePipe,
|
|
|
|
+ IN LPSECURITY_ATTRIBUTES lpPipeAttributes,
|
|
|
|
+ IN DWORD nSize,
|
|
|
|
+ DWORD dwReadMode,
|
|
|
|
+ DWORD dwWriteMode)
|
|
{
|
|
{
|
|
- HANDLE ReadPipeHandle, WritePipeHandle;
|
|
|
|
- DWORD dwError;
|
|
|
|
- UCHAR PipeNameBuffer[ MAX_PATH ];
|
|
|
|
-
|
|
|
|
- //
|
|
|
|
- // Only one valid OpenMode flag - FILE_FLAG_OVERLAPPED
|
|
|
|
- //
|
|
|
|
-
|
|
|
|
- if ((dwReadMode | dwWriteMode) & (~FILE_FLAG_OVERLAPPED)) {
|
|
|
|
- SetLastError(ERROR_INVALID_PARAMETER);
|
|
|
|
- return FALSE;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- //
|
|
|
|
- // Set the default timeout to 120 seconds
|
|
|
|
- //
|
|
|
|
|
|
+ HANDLE ReadPipeHandle, WritePipeHandle;
|
|
|
|
+ DWORD dwError;
|
|
|
|
+ UCHAR PipeNameBuffer[MAX_PATH];
|
|
|
|
+
|
|
|
|
+ // Only one valid OpenMode flag - FILE_FLAG_OVERLAPPED
|
|
|
|
+ if ((dwReadMode | dwWriteMode) & (~FILE_FLAG_OVERLAPPED)) {
|
|
|
|
+ SetLastError(ERROR_INVALID_PARAMETER);
|
|
|
|
+ return FALSE;
|
|
|
|
+ }
|
|
|
|
|
|
- if (nSize == 0) {
|
|
|
|
- nSize = 4096;
|
|
|
|
- }
|
|
|
|
|
|
+ // Set the default timeout to 120 seconds
|
|
|
|
+ if (nSize == 0) nSize = 4096;
|
|
|
|
|
|
//PipeSerialNumber++;
|
|
//PipeSerialNumber++;
|
|
InterlockedIncrement(&PipeSerialNumber);
|
|
InterlockedIncrement(&PipeSerialNumber);
|
|
|
|
|
|
- sprintf( PipeNameBuffer,
|
|
|
|
- "\\\\.\\Pipe\\RemoteExeAnon.%08x.%08x",
|
|
|
|
- GetCurrentProcessId(),
|
|
|
|
- PipeSerialNumber
|
|
|
|
- );
|
|
|
|
-
|
|
|
|
- ReadPipeHandle = CreateNamedPipeA(
|
|
|
|
- PipeNameBuffer,
|
|
|
|
- PIPE_ACCESS_INBOUND | dwReadMode,
|
|
|
|
- PIPE_TYPE_BYTE | PIPE_WAIT,
|
|
|
|
- 1, // Number of pipes
|
|
|
|
- nSize, // Out buffer size
|
|
|
|
- nSize, // In buffer size
|
|
|
|
- 120 * 1000, // Timeout in ms
|
|
|
|
- lpPipeAttributes
|
|
|
|
- );
|
|
|
|
-
|
|
|
|
- if (! ReadPipeHandle) {
|
|
|
|
- return FALSE;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- WritePipeHandle = CreateFileA(
|
|
|
|
- PipeNameBuffer,
|
|
|
|
- GENERIC_WRITE,
|
|
|
|
- 0, // No sharing
|
|
|
|
- lpPipeAttributes,
|
|
|
|
- OPEN_EXISTING,
|
|
|
|
- FILE_ATTRIBUTE_NORMAL | dwWriteMode,
|
|
|
|
- NULL // Template file
|
|
|
|
- );
|
|
|
|
-
|
|
|
|
- if (INVALID_HANDLE_VALUE == WritePipeHandle) {
|
|
|
|
- dwError = GetLastError();
|
|
|
|
- CloseHandle( ReadPipeHandle );
|
|
|
|
- SetLastError(dwError);
|
|
|
|
- return FALSE;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- *lpReadPipe = ReadPipeHandle;
|
|
|
|
- *lpWritePipe = WritePipeHandle;
|
|
|
|
- return( TRUE );
|
|
|
|
|
|
+ sprintf(PipeNameBuffer,
|
|
|
|
+ "\\\\.\\Pipe\\RemoteExeAnon.%08x.%08x",
|
|
|
|
+ GetCurrentProcessId(),
|
|
|
|
+ PipeSerialNumber);
|
|
|
|
+
|
|
|
|
+ ReadPipeHandle = CreateNamedPipeA(
|
|
|
|
+ PipeNameBuffer,
|
|
|
|
+ PIPE_ACCESS_INBOUND | dwReadMode,
|
|
|
|
+ PIPE_TYPE_BYTE | PIPE_WAIT,
|
|
|
|
+ 1, // Number of pipes
|
|
|
|
+ nSize, // Out buffer size
|
|
|
|
+ nSize, // In buffer size
|
|
|
|
+ 120 * 1000, // Timeout in ms
|
|
|
|
+ lpPipeAttributes);
|
|
|
|
+
|
|
|
|
+ if (!ReadPipeHandle) return FALSE;
|
|
|
|
+
|
|
|
|
+ WritePipeHandle = CreateFileA(
|
|
|
|
+ PipeNameBuffer,
|
|
|
|
+ GENERIC_WRITE,
|
|
|
|
+ 0, // No sharing
|
|
|
|
+ lpPipeAttributes,
|
|
|
|
+ OPEN_EXISTING,
|
|
|
|
+ FILE_ATTRIBUTE_NORMAL | dwWriteMode,
|
|
|
|
+ NULL); // Template file
|
|
|
|
+
|
|
|
|
+ if (INVALID_HANDLE_VALUE == WritePipeHandle) {
|
|
|
|
+ dwError = GetLastError();
|
|
|
|
+ CloseHandle(ReadPipeHandle);
|
|
|
|
+ SetLastError(dwError);
|
|
|
|
+ return FALSE;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ *lpReadPipe = ReadPipeHandle;
|
|
|
|
+ *lpWritePipe = WritePipeHandle;
|
|
|
|
+ return TRUE;
|
|
}
|
|
}
|
|
|
|
|
|
-int StartProcess(char *process) {
|
|
|
|
|
|
+int StartProcessIn(char *process, char *dir) {
|
|
SECURITY_ATTRIBUTES saAttr;
|
|
SECURITY_ATTRIBUTES saAttr;
|
|
|
|
|
|
-// Set the bInheritHandle flag so pipe handles are inherited.
|
|
|
|
|
|
+ if (dir && dir[0] == '\0') dir = NULL;
|
|
|
|
|
|
|
|
+ // Set the bInheritHandle flag so pipe handles are inherited.
|
|
saAttr.nLength = sizeof(SECURITY_ATTRIBUTES);
|
|
saAttr.nLength = sizeof(SECURITY_ATTRIBUTES);
|
|
saAttr.bInheritHandle = TRUE;
|
|
saAttr.bInheritHandle = TRUE;
|
|
saAttr.lpSecurityDescriptor = NULL;
|
|
saAttr.lpSecurityDescriptor = NULL;
|
|
|
|
|
|
-// Create a pipe for the child process's STDOUT.
|
|
|
|
-
|
|
|
|
- if ( ! MyCreatePipeEx(&g_hChildStd_OUT_Rd, &g_hChildStd_OUT_Wr, &saAttr, 0, FILE_FLAG_OVERLAPPED, 0) )
|
|
|
|
- ErrorExit(TEXT("StdoutRd CreatePipe"));
|
|
|
|
- //if ( ! CreatePipe(&g_hChildStd_OUT_Rd, &g_hChildStd_OUT_Wr, &saAttr, 0) )
|
|
|
|
- // ErrorExit(TEXT("StdoutRd CreatePipe"));
|
|
|
|
-
|
|
|
|
-// Ensure the read handle to the pipe for STDOUT is not inherited.
|
|
|
|
-
|
|
|
|
- if ( ! SetHandleInformation(g_hChildStd_OUT_Rd, HANDLE_FLAG_INHERIT, 0) )
|
|
|
|
- ErrorExit(TEXT("Stdout SetHandleInformation"));
|
|
|
|
|
|
+ // Create a pipe for the child process's STDOUT.
|
|
|
|
+ if (!MyCreatePipeEx(&g_hChildStd_OUT_Rd, &g_hChildStd_OUT_Wr, &saAttr, 0, FILE_FLAG_OVERLAPPED, 0) )
|
|
|
|
+ ErrorExit(TEXT("StdoutRd CreatePipe"));
|
|
|
|
|
|
-// Create a pipe for the child process's STDIN.
|
|
|
|
|
|
+ // Ensure the read handle to the pipe for STDOUT is not inherited.
|
|
|
|
+ if (!SetHandleInformation(g_hChildStd_OUT_Rd, HANDLE_FLAG_INHERIT, 0) )
|
|
|
|
+ ErrorExit(TEXT("Stdout SetHandleInformation"));
|
|
|
|
|
|
- if (! MyCreatePipeEx(&g_hChildStd_IN_Rd, &g_hChildStd_IN_Wr, &saAttr, 0, FILE_FLAG_OVERLAPPED, 0))
|
|
|
|
- ErrorExit(TEXT("Stdin CreatePipe"));
|
|
|
|
|
|
+ // Create a pipe for the child process's STDIN.
|
|
|
|
+ if (!MyCreatePipeEx(&g_hChildStd_IN_Rd, &g_hChildStd_IN_Wr, &saAttr, 0, FILE_FLAG_OVERLAPPED, 0))
|
|
|
|
+ ErrorExit(TEXT("Stdin CreatePipe"));
|
|
|
|
|
|
-// Ensure the write handle to the pipe for STDIN is not inherited.
|
|
|
|
-
|
|
|
|
- if ( ! SetHandleInformation(g_hChildStd_IN_Wr, HANDLE_FLAG_INHERIT, 0) )
|
|
|
|
- ErrorExit(TEXT("Stdin SetHandleInformation"));
|
|
|
|
|
|
+ // Ensure the write handle to the pipe for STDIN is not inherited.
|
|
|
|
+ if (!SetHandleInformation(g_hChildStd_IN_Wr, HANDLE_FLAG_INHERIT, 0) )
|
|
|
|
+ ErrorExit(TEXT("Stdin SetHandleInformation"));
|
|
|
|
|
|
ZeroMemory(&oOverlap, sizeof(oOverlap));
|
|
ZeroMemory(&oOverlap, sizeof(oOverlap));
|
|
|
|
|
|
// ACTUAL START PROCESS
|
|
// ACTUAL START PROCESS
|
|
|
|
|
|
-
|
|
|
|
-
|
|
|
|
//TCHAR szCmdline[]=TEXT(process);
|
|
//TCHAR szCmdline[]=TEXT(process);
|
|
STARTUPINFO siStartInfo;
|
|
STARTUPINFO siStartInfo;
|
|
BOOL bSuccess = FALSE;
|
|
BOOL bSuccess = FALSE;
|
|
|
|
|
|
-// Set up members of the PROCESS_INFORMATION structure.
|
|
|
|
-
|
|
|
|
- ZeroMemory( &piProcInfo, sizeof(PROCESS_INFORMATION) );
|
|
|
|
-
|
|
|
|
-// Set up members of the STARTUPINFO structure.
|
|
|
|
-// This structure specifies the STDIN and STDOUT handles for redirection.
|
|
|
|
|
|
+ // Set up members of the PROCESS_INFORMATION structure.
|
|
|
|
+ ZeroMemory(&piProcInfo, sizeof(PROCESS_INFORMATION));
|
|
|
|
|
|
- ZeroMemory( &siStartInfo, sizeof(STARTUPINFO) );
|
|
|
|
|
|
+ // Set up members of the STARTUPINFO structure.
|
|
|
|
+ // This structure specifies the STDIN and STDOUT handles for redirection.
|
|
|
|
+ ZeroMemory(&siStartInfo, sizeof(STARTUPINFO));
|
|
siStartInfo.cb = sizeof(STARTUPINFO);
|
|
siStartInfo.cb = sizeof(STARTUPINFO);
|
|
siStartInfo.hStdError = g_hChildStd_OUT_Wr;
|
|
siStartInfo.hStdError = g_hChildStd_OUT_Wr;
|
|
siStartInfo.hStdOutput = g_hChildStd_OUT_Wr;
|
|
siStartInfo.hStdOutput = g_hChildStd_OUT_Wr;
|
|
@@ -172,34 +149,28 @@ int StartProcess(char *process) {
|
|
siStartInfo.dwFlags |= STARTF_USESTDHANDLES;
|
|
siStartInfo.dwFlags |= STARTF_USESTDHANDLES;
|
|
siStartInfo.wShowWindow = SW_HIDE;
|
|
siStartInfo.wShowWindow = SW_HIDE;
|
|
|
|
|
|
-// Create the child process.
|
|
|
|
-
|
|
|
|
|
|
+ // Create the child process.
|
|
bSuccess = CreateProcess(NULL,
|
|
bSuccess = CreateProcess(NULL,
|
|
- process, //szCmdline, // command line
|
|
|
|
- NULL, // process security attributes
|
|
|
|
- NULL, // primary thread security attributes
|
|
|
|
- TRUE, // handles are inherited
|
|
|
|
- CREATE_NO_WINDOW, // creation flags
|
|
|
|
- NULL, // use parent's environment
|
|
|
|
- NULL, // use parent's current directory
|
|
|
|
- &siStartInfo, // STARTUPINFO pointer
|
|
|
|
- &piProcInfo); // receives PROCESS_INFORMATION
|
|
|
|
|
|
+ process, //szCmdline, // command line
|
|
|
|
+ NULL, // process security attributes
|
|
|
|
+ NULL, // primary thread security attributes
|
|
|
|
+ TRUE, // handles are inherited
|
|
|
|
+ CREATE_NO_WINDOW, // creation flags
|
|
|
|
+ NULL, // use parent's environment
|
|
|
|
+ dir, // current directory of the process
|
|
|
|
+ &siStartInfo, // STARTUPINFO pointer
|
|
|
|
+ &piProcInfo); // receives PROCESS_INFORMATION
|
|
|
|
|
|
// If an error occurs, exit the application.
|
|
// If an error occurs, exit the application.
|
|
- if ( ! bSuccess )
|
|
|
|
- ErrorExit(TEXT("CreateProcess"));
|
|
|
|
- else
|
|
|
|
- {
|
|
|
|
- // Close handles to the child process and its primary thread.
|
|
|
|
- // Some applications might keep these handles to monitor the status
|
|
|
|
- // of the child process, for example.
|
|
|
|
-
|
|
|
|
- //CloseHandle(piProcInfo.hProcess);
|
|
|
|
- //CloseHandle(piProcInfo.hThread);
|
|
|
|
- }
|
|
|
|
|
|
+ if (!bSuccess) ErrorExit(TEXT("CreateProcess"));
|
|
|
|
+
|
|
return bSuccess ? 1 : 0;
|
|
return bSuccess ? 1 : 0;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+int StartProcess(char *process) {
|
|
|
|
+ return StartProcessIn(process, (char *)NULL);
|
|
|
|
+}
|
|
|
|
+
|
|
int ProcessFinished(int *err) {
|
|
int ProcessFinished(int *err) {
|
|
GetExitCodeProcess(piProcInfo.hProcess, &exit_code);
|
|
GetExitCodeProcess(piProcInfo.hProcess, &exit_code);
|
|
int result = exit_code != STILL_ACTIVE;
|
|
int result = exit_code != STILL_ACTIVE;
|
|
@@ -218,17 +189,7 @@ int ProcessFinished(int *err) {
|
|
|
|
|
|
void WriteToProcess(char *buf, int len) {
|
|
void WriteToProcess(char *buf, int len) {
|
|
DWORD dwWritten;
|
|
DWORD dwWritten;
|
|
-// CHAR chBuf[BUFSIZE];
|
|
|
|
-// BOOL bSuccess = FALSE;
|
|
|
|
-
|
|
|
|
- //bSuccess = ReadFile(hParentStdIn, chBuf, BUFSIZE, &dwRead, NULL);
|
|
|
|
- //if ( ! bSuccess || dwRead == 0 ) break;
|
|
|
|
WriteFile(g_hChildStd_IN_Wr, buf, len, &dwWritten, NULL);
|
|
WriteFile(g_hChildStd_IN_Wr, buf, len, &dwWritten, NULL);
|
|
-
|
|
|
|
-// Close the pipe handle so the child process stops reading.
|
|
|
|
-
|
|
|
|
- //if ( ! CloseHandle(g_hChildStd_IN_Wr) )
|
|
|
|
- //ErrorExit(TEXT("StdInWr CloseHandle"));
|
|
|
|
}
|
|
}
|
|
|
|
|
|
void ReadFromProcess(char *buf, int *len, int limit) {
|
|
void ReadFromProcess(char *buf, int *len, int limit) {
|
|
@@ -269,165 +230,53 @@ void ReadFromProcess(char *buf, int *len, int limit) {
|
|
//printf("len = %u\n===============\n", *len);
|
|
//printf("len = %u\n===============\n", *len);
|
|
}
|
|
}
|
|
|
|
|
|
-/*
|
|
|
|
-int _tmain(int argc, TCHAR *argv[])
|
|
|
|
-{
|
|
|
|
- SECURITY_ATTRIBUTES saAttr;
|
|
|
|
-
|
|
|
|
- printf("\n->Start of parent execution.\n");
|
|
|
|
-
|
|
|
|
-// 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(&g_hChildStd_OUT_Rd, &g_hChildStd_OUT_Wr, &saAttr, 0) )
|
|
|
|
- ErrorExit(TEXT("StdoutRd CreatePipe"));
|
|
|
|
-
|
|
|
|
-// Ensure the read handle to the pipe for STDOUT is not inherited.
|
|
|
|
-
|
|
|
|
- if ( ! SetHandleInformation(g_hChildStd_OUT_Rd, HANDLE_FLAG_INHERIT, 0) )
|
|
|
|
- ErrorExit(TEXT("Stdout SetHandleInformation"));
|
|
|
|
-
|
|
|
|
-// Create a pipe for the child process's STDIN.
|
|
|
|
-
|
|
|
|
- if (! CreatePipe(&g_hChildStd_IN_Rd, &g_hChildStd_IN_Wr, &saAttr, 0))
|
|
|
|
- ErrorExit(TEXT("Stdin CreatePipe"));
|
|
|
|
-
|
|
|
|
-// Ensure the write handle to the pipe for STDIN is not inherited.
|
|
|
|
-
|
|
|
|
- if ( ! SetHandleInformation(g_hChildStd_IN_Wr, HANDLE_FLAG_INHERIT, 0) )
|
|
|
|
- ErrorExit(TEXT("Stdin SetHandleInformation"));
|
|
|
|
-
|
|
|
|
-// Create the child process.
|
|
|
|
-
|
|
|
|
- CreateChildProcess();
|
|
|
|
-
|
|
|
|
- WriteToPipe();
|
|
|
|
- printf( "\n->Contents of %s written to child STDIN pipe.\n", argv[1]);
|
|
|
|
-
|
|
|
|
-// Read from pipe that is the standard output for child process.
|
|
|
|
-
|
|
|
|
- printf( "\n->Contents of child process STDOUT:\n\n", argv[1]);
|
|
|
|
- ReadFromPipe();
|
|
|
|
-
|
|
|
|
- printf("\n->End of parent execution.\n");
|
|
|
|
-
|
|
|
|
-// The remaining open handles are cleaned up when this process terminates.
|
|
|
|
-// To avoid resource leaks in a larger application, close handles explicitly.
|
|
|
|
-
|
|
|
|
- return 0;
|
|
|
|
-}
|
|
|
|
-*/
|
|
|
|
-
|
|
|
|
-void CreateChildProcess()
|
|
|
|
-// Create a child process that uses the previously created pipes for STDIN and STDOUT.
|
|
|
|
-{
|
|
|
|
- TCHAR szCmdline[]=TEXT("prog.exe");
|
|
|
|
- PROCESS_INFORMATION piProcInfo;
|
|
|
|
- STARTUPINFO siStartInfo;
|
|
|
|
- BOOL bSuccess = FALSE;
|
|
|
|
-
|
|
|
|
-// Set up members of the PROCESS_INFORMATION structure.
|
|
|
|
-
|
|
|
|
- ZeroMemory( &piProcInfo, sizeof(PROCESS_INFORMATION) );
|
|
|
|
-
|
|
|
|
-// Set up members of the STARTUPINFO structure.
|
|
|
|
-// This structure specifies the STDIN and STDOUT handles for redirection.
|
|
|
|
-
|
|
|
|
- ZeroMemory( &siStartInfo, sizeof(STARTUPINFO) );
|
|
|
|
- siStartInfo.cb = sizeof(STARTUPINFO);
|
|
|
|
- siStartInfo.hStdError = g_hChildStd_OUT_Wr;
|
|
|
|
- siStartInfo.hStdOutput = g_hChildStd_OUT_Wr;
|
|
|
|
- siStartInfo.hStdInput = g_hChildStd_IN_Rd;
|
|
|
|
- siStartInfo.dwFlags |= STARTF_USESTDHANDLES;
|
|
|
|
-
|
|
|
|
-// Create the child process.
|
|
|
|
-
|
|
|
|
- bSuccess = CreateProcess(NULL,
|
|
|
|
- szCmdline, // command line
|
|
|
|
- NULL, // process security attributes
|
|
|
|
- NULL, // primary thread security attributes
|
|
|
|
- TRUE, // handles are inherited
|
|
|
|
- 0, // creation flags
|
|
|
|
- NULL, // use parent's environment
|
|
|
|
- NULL, // use parent's current directory
|
|
|
|
- &siStartInfo, // STARTUPINFO pointer
|
|
|
|
- &piProcInfo); // receives PROCESS_INFORMATION
|
|
|
|
-
|
|
|
|
- // If an error occurs, exit the application.
|
|
|
|
- if ( ! bSuccess )
|
|
|
|
- ErrorExit(TEXT("CreateProcess"));
|
|
|
|
- else
|
|
|
|
- {
|
|
|
|
- // Close handles to the child process and its primary thread.
|
|
|
|
- // Some applications might keep these handles to monitor the status
|
|
|
|
- // of the child process, for example.
|
|
|
|
-
|
|
|
|
- CloseHandle(piProcInfo.hProcess);
|
|
|
|
- CloseHandle(piProcInfo.hThread);
|
|
|
|
- }
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-void WriteToPipe(void)
|
|
|
|
-
|
|
|
|
// Read from a file and write its contents to the pipe for the child's STDIN.
|
|
// Read from a file and write its contents to the pipe for the child's STDIN.
|
|
// Stop when there is no more data.
|
|
// Stop when there is no more data.
|
|
-{
|
|
|
|
|
|
+void WriteToPipe(void) {
|
|
DWORD dwRead, dwWritten;
|
|
DWORD dwRead, dwWritten;
|
|
CHAR chBuf[BUFSIZE];
|
|
CHAR chBuf[BUFSIZE];
|
|
BOOL bSuccess = FALSE;
|
|
BOOL bSuccess = FALSE;
|
|
|
|
|
|
- //bSuccess = ReadFile(hParentStdIn, chBuf, BUFSIZE, &dwRead, NULL);
|
|
|
|
- //if ( ! bSuccess || dwRead == 0 ) break;
|
|
|
|
- chBuf[0] = '3';
|
|
|
|
- chBuf[1] = '5';
|
|
|
|
- chBuf[2] = 13;
|
|
|
|
- chBuf[3] = 10;
|
|
|
|
- dwRead = 4;
|
|
|
|
- bSuccess = WriteFile(g_hChildStd_IN_Wr, chBuf, dwRead, &dwWritten, NULL);
|
|
|
|
-
|
|
|
|
-// Close the pipe handle so the child process stops reading.
|
|
|
|
-
|
|
|
|
- if ( ! CloseHandle(g_hChildStd_IN_Wr) )
|
|
|
|
- ErrorExit(TEXT("StdInWr CloseHandle"));
|
|
|
|
|
|
+ //bSuccess = ReadFile(hParentStdIn, chBuf, BUFSIZE, &dwRead, NULL);
|
|
|
|
+ //if (!bSuccess || dwRead == 0) break;
|
|
|
|
+ chBuf[0] = '3';
|
|
|
|
+ chBuf[1] = '5';
|
|
|
|
+ chBuf[2] = 13;
|
|
|
|
+ chBuf[3] = 10;
|
|
|
|
+ dwRead = 4;
|
|
|
|
+ bSuccess = WriteFile(g_hChildStd_IN_Wr, chBuf, dwRead, &dwWritten, NULL);
|
|
|
|
+
|
|
|
|
+ // Close the pipe handle so the child process stops reading.
|
|
|
|
+ if (!CloseHandle(g_hChildStd_IN_Wr)) ErrorExit(TEXT("StdInWr CloseHandle"));
|
|
}
|
|
}
|
|
|
|
|
|
-void ReadFromPipe(void)
|
|
|
|
-
|
|
|
|
// Read output from the child process's pipe for STDOUT
|
|
// Read output from the child process's pipe for STDOUT
|
|
// and write to the parent process's pipe for STDOUT.
|
|
// and write to the parent process's pipe for STDOUT.
|
|
// Stop when there is no more data.
|
|
// Stop when there is no more data.
|
|
-{
|
|
|
|
|
|
+void ReadFromPipe(void) {
|
|
DWORD dwRead, dwWritten;
|
|
DWORD dwRead, dwWritten;
|
|
CHAR chBuf[BUFSIZE];
|
|
CHAR chBuf[BUFSIZE];
|
|
BOOL bSuccess = FALSE;
|
|
BOOL bSuccess = FALSE;
|
|
HANDLE hParentStdOut = GetStdHandle(STD_OUTPUT_HANDLE);
|
|
HANDLE hParentStdOut = GetStdHandle(STD_OUTPUT_HANDLE);
|
|
|
|
|
|
- for (;;)
|
|
|
|
- {
|
|
|
|
- bSuccess = ReadFile( g_hChildStd_OUT_Rd, chBuf, BUFSIZE, &dwRead, NULL);
|
|
|
|
- if( ! bSuccess || dwRead == 0 ) break;
|
|
|
|
|
|
+ while (1) {
|
|
|
|
+ bSuccess = ReadFile( g_hChildStd_OUT_Rd, chBuf, BUFSIZE, &dwRead, NULL);
|
|
|
|
+ if (!bSuccess || dwRead == 0) break;
|
|
|
|
|
|
- bSuccess = WriteFile(hParentStdOut, chBuf,
|
|
|
|
- dwRead, &dwWritten, NULL);
|
|
|
|
- if (! bSuccess ) break;
|
|
|
|
|
|
+ bSuccess = WriteFile(hParentStdOut, chBuf,
|
|
|
|
+ dwRead, &dwWritten, NULL);
|
|
|
|
+ if (!bSuccess) break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
-void ErrorExit(PTSTR lpszFunction)
|
|
|
|
-
|
|
|
|
// Format a readable error message, display a message box,
|
|
// Format a readable error message, display a message box,
|
|
// and exit from the application.
|
|
// and exit from the application.
|
|
-{
|
|
|
|
- LPVOID lpMsgBuf;
|
|
|
|
- LPVOID lpDisplayBuf;
|
|
|
|
- DWORD dw = GetLastError();
|
|
|
|
|
|
+void ErrorExit(PTSTR lpszFunction) {
|
|
|
|
+ LPVOID lpMsgBuf;
|
|
|
|
+ LPVOID lpDisplayBuf;
|
|
|
|
+ DWORD dw = GetLastError();
|
|
|
|
|
|
- FormatMessage(
|
|
|
|
|
|
+ FormatMessage(
|
|
FORMAT_MESSAGE_ALLOCATE_BUFFER |
|
|
FORMAT_MESSAGE_ALLOCATE_BUFFER |
|
|
FORMAT_MESSAGE_FROM_SYSTEM |
|
|
FORMAT_MESSAGE_FROM_SYSTEM |
|
|
FORMAT_MESSAGE_IGNORE_INSERTS,
|
|
FORMAT_MESSAGE_IGNORE_INSERTS,
|
|
@@ -435,21 +284,21 @@ void ErrorExit(PTSTR lpszFunction)
|
|
dw,
|
|
dw,
|
|
MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
|
|
MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
|
|
(LPTSTR) &lpMsgBuf,
|
|
(LPTSTR) &lpMsgBuf,
|
|
- 0, NULL );
|
|
|
|
|
|
+ 0, NULL);
|
|
|
|
|
|
- lpDisplayBuf = (LPVOID)LocalAlloc(LMEM_ZEROINIT,
|
|
|
|
|
|
+ lpDisplayBuf = (LPVOID)LocalAlloc(LMEM_ZEROINIT,
|
|
(lstrlen((LPCTSTR)lpMsgBuf)+lstrlen((LPCTSTR)lpszFunction)+40)*sizeof(TCHAR));
|
|
(lstrlen((LPCTSTR)lpMsgBuf)+lstrlen((LPCTSTR)lpszFunction)+40)*sizeof(TCHAR));
|
|
|
|
|
|
- snprintf((LPTSTR)lpDisplayBuf,
|
|
|
|
|
|
+ snprintf((LPTSTR)lpDisplayBuf,
|
|
LocalSize(lpDisplayBuf) / sizeof(TCHAR),
|
|
LocalSize(lpDisplayBuf) / sizeof(TCHAR),
|
|
TEXT("%s failed with error %d: %s"),
|
|
TEXT("%s failed with error %d: %s"),
|
|
lpszFunction, dw, lpMsgBuf);
|
|
lpszFunction, dw, lpMsgBuf);
|
|
|
|
|
|
- MessageBox(NULL, (LPCTSTR)lpDisplayBuf, TEXT("Error"), MB_OK);
|
|
|
|
|
|
+ MessageBox(NULL, (LPCTSTR)lpDisplayBuf, TEXT("Error"), MB_OK);
|
|
|
|
|
|
- LocalFree(lpMsgBuf);
|
|
|
|
- LocalFree(lpDisplayBuf);
|
|
|
|
- ExitProcess(1);
|
|
|
|
|
|
+ LocalFree(lpMsgBuf);
|
|
|
|
+ LocalFree(lpDisplayBuf);
|
|
|
|
+ ExitProcess(1);
|
|
}
|
|
}
|
|
|
|
|
|
int RunProcess(char *cmd, char *buf, int limit, int *len, int *err) {
|
|
int RunProcess(char *cmd, char *buf, int limit, int *len, int *err) {
|