CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Page 1 of 2 12 LastLast
Results 1 to 15 of 23
  1. #1
    Join Date
    Jul 2013
    Posts
    10

    Problem with AllocConsole and child processes Windows 7

    I have a GUI window that allocates a console using AllocConsole and then executes a child console process which should write to the console window I allocated. When I execute the program from the Start/Run menu or from a command prompt window,it works as expected. If I execute the program via the Windows Explorer or a desktop shortcut, the console window appears but nothing is written to it. I am using Windows 7 64bit. This problem did not occur under Windows XP.

    I am setting the bInheritHandles to TRUE, setting STARTF_USESTDHANDLES flag in the startupifno dwFlags, and am setting hStdOutput to GetStdHandle (STD_OUTPUT_HANDLE).

  2. #2
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: Problem with AllocConsole and child processes Windows 7

    It would be good to see your code that replicates the problem, compilable and runnable.
    Best regards,
    Igor

  3. #3
    Join Date
    Jul 2013
    Posts
    10

    Re: Problem with AllocConsole and child processes Windows 7

    Quote Originally Posted by Igor Vartanov View Post
    It would be good to see your code that replicates the problem, compilable and runnable.
    Hope this is enough for you.

    int execute_command(char *command)
    {
    HANDLE outp;
    COORD coord;
    STARTUPINFO si;
    PROCESS_INFORMATION pi;
    DWORD exitcode;
    BOOL ret;

    if(AllocConsole())
    {
    outp = GetStdHandle(STD_OUTPUT_HANDLE);
    coord.X = 80;
    coord.Y = 500;
    SetConsoleScreenBufferSize(outp,coord);
    SetConsoleTitle("Text Output");
    }

    GetStartupInfo(&si);
    memset(&pi,0,sizeof(PROCESS_INFORMATION));
    si.hStdInput = GetStdHandle (STD_INPUT_HANDLE);
    si.hStdOutput = GetStdHandle (STD_OUTPUT_HANDLE);
    si.hStdError = GetStdHandle (STD_ERROR_HANDLE);
    si.dwFlags |= STARTF_USESTDHANDLES;

    ret = CreateProcess(NULL,command,NULL,NULL,TRUE,0,NULL,NULL,&si,&pi);
    if (ret != TRUE)
    return(-1);

    exitcode = STILL_ACTIVE;
    if (pi.hProcess)
    {
    MSG msg;
    ret = WAIT_TIMEOUT;
    while (ret == WAIT_TIMEOUT || exitcode == STILL_ACTIVE)
    {
    ret = WaitForSingleObject(pi.hProcess,10);
    if (!GetExitCodeProcess(pi.hProcess,&exitcode))
    MessageBox(NULL, "GetExitCodeProcess Failure", NULL, MB_OK);
    if (PeekMessage(&msg,NULL,0,0,PM_REMOVE))
    DispatchMessage(&msg);
    }
    }
    if (pi.hProcess)
    CloseHandle(pi.hProcess);
    if (pi.hThread)
    CloseHandle(pi.hThread);

    return(exitcode);
    }
    Last edited by Rich C; July 26th, 2013 at 02:20 PM.

  4. #4
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: Problem with AllocConsole and child processes Windows 7

    This worked fine in my tests, Win XP and 7 64-bit:
    Code:
    int execute_command(char *command)
    {
    	HANDLE outp;
    	COORD coord;
    	STARTUPINFO si = {sizeof(si)};
    	PROCESS_INFORMATION pi = {0};
    	DWORD exitcode;
    	BOOL ret;
    
    	if(AllocConsole())
    	{
    		outp = GetStdHandle(STD_OUTPUT_HANDLE);
    		coord.X = 80;
    		coord.Y = 500;
    		SetConsoleScreenBufferSize(outp,coord);
    		SetConsoleTitle("Text Output");
    	}
    
    	ret = CreateProcess(NULL,command,NULL,NULL,TRUE,0,NULL,NULL,&si,&pi);
    	if (ret != TRUE)
    		return(-1);
    
    	exitcode = STILL_ACTIVE;
    	if (pi.hProcess)
    	{
    		MSG msg;
    		ret = WAIT_TIMEOUT;
    		while (ret == WAIT_TIMEOUT || exitcode == STILL_ACTIVE)
    		{
    			ret = WaitForSingleObject(pi.hProcess,10);
    			if (!GetExitCodeProcess(pi.hProcess,&exitcode))
    				MessageBox(NULL, "GetExitCodeProcess Failure", NULL, MB_OK);
    			if (PeekMessage(&msg,NULL,0,0,PM_REMOVE))
    				DispatchMessage(&msg);
    		}
    	}
    	if (pi.hProcess)
    		CloseHandle(pi.hProcess);
    	if (pi.hThread)
    		CloseHandle(pi.hThread);
    
    	return(exitcode);
    }
    Best regards,
    Igor

  5. #5
    Join Date
    Jul 2013
    Posts
    10

    Re: Problem with AllocConsole and child processes Windows 7

    Did your child process write to stdout and the output was shown in the console window?
    Did you try to run your program by double-clicking on the executable file in the windows explorer or running it from a desktop shortcut that has as its target the executable file?
    Last edited by Rich C; July 29th, 2013 at 01:01 PM.

  6. #6
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: Problem with AllocConsole and child processes Windows 7

    Quote Originally Posted by Rich C View Post
    Did your child process write to stdout and the output was shown in the console window?
    Did you try to run your program by double-clicking on the executable file in the windows explorer or running it from a desktop shortcut that has as its target the executable file?
    Rich, why don't you just try my code out yourself?
    Best regards,
    Igor

  7. #7
    Join Date
    Jul 2013
    Posts
    10

    Re: Problem with AllocConsole and child processes Windows 7

    Thanks Igor. Your code worked. When I first saw the code, I thought you were just repeating my code.

    The difference is in STARTUPINFO. You essentially zeroed it out (except for the size); I used GetStartupInfo and then set some fields in it. Looking at my code, do you know what fields I set incorrectly?

    Thanks again for the help.

  8. #8
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: Problem with AllocConsole and child processes Windows 7

    I'm pretty sure that there's something with proper handles duplication/security/inheritance, as your code gave me an 'Invalid handle' message been launched from explorer. (Sorry, I don't remember the details anymore, as I delved into this too many years ago. When I have some time for this, I'll take a more intent look.)

    When you provide no explicit startup info, Windows itself does that for you, and of course it does that proper way.
    Best regards,
    Igor

  9. #9
    Join Date
    Jul 2013
    Posts
    10

    Re: Problem with AllocConsole and child processes Windows 7

    What's interesting to me is that this worked in Windows XP and prior versions of Windows.

    Thanks again,
    Rich

  10. #10
    Join Date
    Apr 1999
    Posts
    27,449

    Re: Problem with AllocConsole and child processes Windows 7

    Quote Originally Posted by Rich C View Post
    What's interesting to me is that this worked in Windows XP and prior versions of Windows.
    There are a lot of code examples that work with older OSes but will not work or work erratically as soon as you go to a later operating system. Most of this due to programmer fault, and the other OSes just happen to not exercise the bad code. Other times it is documented that the OS handles things differently, but the programmer didn't do their research thoroughly.

    Regards,

    Paul McKenzie

  11. #11
    Join Date
    Jul 2013
    Posts
    10

    Re: Problem with AllocConsole and child processes Windows 7

    I have a feeling its the misuse of the GetStartupInfo function when spawing child processes.

    Rich

  12. #12
    Join Date
    Apr 1999
    Posts
    27,449

    Re: Problem with AllocConsole and child processes Windows 7

    Quote Originally Posted by Rich C View Post
    I have a feeling its the misuse of the GetStartupInfo function when spawing child processes.

    Rich
    If you read the documentation for the STARTUPINFO struct, you see the first member has to have the number of bytes set (cb). Your example didn't do this (next time, use code tags when posting code), but Igor's does.

    All the code I've ever written that uses STARTUPINFO has set the initial member to the number of bytes that the struct takes up. This goes back to Windows NT (maybe before that). So in reality, you were getting away with this mistake until now.

    Regards,

    Paul McKenzie
    Last edited by Paul McKenzie; July 30th, 2013 at 10:58 AM.

  13. #13
    Join Date
    Jul 2013
    Posts
    10

    Re: Problem with AllocConsole and child processes Windows 7

    Quote Originally Posted by Paul McKenzie View Post
    If you read the documentation for the STARTUPINFO struct, you see the first member has to have the number of bytes set (cb). Your example didn't do this (next time, use code tags when posting code), but Igor's does.

    Regards,

    Paul McKenzie
    I assumed when I called GetStartupInfo to fill in the STARTUPINFO structure, the first member of the STARTUPINFO structure would have been set

    Rich

  14. #14
    Join Date
    Apr 1999
    Posts
    27,449

    Re: Problem with AllocConsole and child processes Windows 7

    Quote Originally Posted by Rich C View Post
    I assumed when I called GetStartupInfo to fill in the STARTUPINFO structure, the first member of the STARTUPINFO structure would have been set

    Rich
    No. The Windows API probably checks this number and depending on what it is, does certain logic.

    Also, how could Windows set this to a correct number, when all you're doing is passing a pointer? You can't get the correct sizeof() a type by using a pointer. That's why your code has to set it, and then the API call picks up on this number and does whatever it does.

    For example, the Windows structure changes the number of members in a future version of the SDK. The Windows API function hopefully keeps track of this change, and looks at the cb member to figure out what to do with this version of that struct (is it an old version, new version, etc.). Another possible scenario is that the API call knows what the cb number should be, and checks if your version is the right one by looking at the cb member, who knows.

    All I am certain of is that any SDK struct that has a member where the number of bytes is set, you need to set it to ensure that the function doesn't behave erratically. That's been my experience, even if the API docs don't say so explicitly.

    Regards,

    Paul McKenzie
    Last edited by Paul McKenzie; July 30th, 2013 at 11:17 AM.

  15. #15
    Join Date
    Jul 2013
    Posts
    10

    Re: Problem with AllocConsole and child processes Windows 7

    Quote Originally Posted by Paul McKenzie View Post
    No. The Windows API probably checks this number and depending on what it is, does certain logic.

    Also, how could Windows set this, when all you're doing is passing a pointer? You can't get the correct sizeof() a type by using a pointer. That's why your code has to set it, and then the API call picks up on this number and does whatever it does.

    Regards,

    Paul McKenzie
    Thanks Paul. Good catch.

    Rich

Page 1 of 2 12 LastLast

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured