Redirecting stdout output in cpp

泄露秘密 提交于 2019-12-13 00:58:54

问题


I've been searching for an answer regarding this issue for a few days now, I hope you guys will be able to assist me. (I've searched and found some solutions, but each has its own issue...).

Here is the thing: I'm writing an automation at work, which is responsible for launching an external ".exe" file of a code written by my colleagues. As those programs they write go to customers, I'm not allowed to make any modification to their code. Those programs, once launched, are waiting for specific key strokes, and prints a message when a legal key stroke has been received.

My goal is this: To write a program which will execute the external program, send it key strokes, and receive the output from their stdout. So far, I have been able to run the program from my program (using ShellExecute), and simulate some sort of keyboard listener (using SendMessage) to the other program. I can see that it works - I can see the output in the tested program's console.

I'm trying to fetch the messages printed on the tested program's shell in real-time (and just get a bulk of data when the program terminates) so that I could analyse it when it occurs.

Those I've tried:

  • Writing an external batch file with inline output redirection to a text file.
  • Using freopen.
  • Redirecting the output while exectuing "ShellExecute".

回答1:


You use handles for stdin, stdout, and stderr. Create process with CreateProcess function to get that handles. Sample code - incomplete for your case, but good example of how to do it:

#include <windows.h>
#include <stdio.h>
#include <tchar.h>

    /*for test.exe
#include <iostream>
#include <string> */

void _tmain( int argc, TCHAR *argv[] )
{
    /*for test.exe
    std::cout << "test output" << std::endl;
    for (;;)
    {
        std::string line;
        std::getline(std::cin, line);
        std::cout << "line: " << line << std::endl;
    }
    return;*/
    STARTUPINFO si;
    PROCESS_INFORMATION pi;

    ZeroMemory( &si, sizeof(si) );
    si.cb = sizeof(si);
    ZeroMemory( &pi, sizeof(pi) );

    // Start the child process. 
    if( !CreateProcess( NULL,   // No module name (use command line)
        "test.exe",        // Command line
        NULL,           // Process handle not inheritable
        NULL,           // Thread handle not inheritable
        FALSE,          // Set handle inheritance to FALSE
        0,              // No creation flags
        NULL,           // Use parent's environment block
        NULL,           // Use parent's starting directory 
        &si,            // Pointer to STARTUPINFO structure
        &pi )           // Pointer to PROCESS_INFORMATION structure
    ) 
    {
        printf( "CreateProcess failed (%d)\n", GetLastError() );
        return;
    }

   /*     HANDLE  hStdInput;
    HANDLE  hStdOutput;
    HANDLE  hStdError;*/
    HANDLE me_hStdInput = GetStdHandle(STD_INPUT_HANDLE);
    HANDLE me_hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
    HANDLE proc_hStdInput = si.hStdInput;
    HANDLE proc_hStdOutput = si.hStdOutput;

                char buff[64];
                DWORD chars;
    while (!ReadConsole(me_hStdInput, buff, sizeof(buff), &chars, NULL))
    {
                    for (DWORD written = 0, writtenThisTime; written < chars; written += writtenThisTime)                   
                        if (!WriteConsole(proc_hStdOutput, buff + written, chars - written, &writtenThisTime, NULL))
                        {
                            //handle error - TODO
                        }
                }
                //possibly handle error for ReadConsole - TODO  


    // Wait until child process exits.
    //WaitForSingleObject( pi.hProcess, INFINITE );

    // Close process and thread handles. 
    CloseHandle( pi.hProcess );
    CloseHandle( pi.hThread );
}


来源:https://stackoverflow.com/questions/11176746/redirecting-stdout-output-in-cpp

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!