Thread: CreateProcess() + Command Line

  1. #1
    Registered User IndioDoido's Avatar
    Join Date
    Apr 2007
    Posts
    194

    CreateProcess() + Command Line

    hi...

    i'm trying to send a string to windows cmd so that it can run the command contained in the string.

    i'm using CreateProcess() to send known windows command lines (ex: net user, net localgroup, at, etc), and it works fine. But now i want to send a script (ex: echo test > test.txt) and it doesn't work

    Can anyone help me?

    Here is my CreateProcess() function:
    Code:
    int runScripts(char str[])
    {
    	PROCESS_INFORMATION pi;
    	STARTUPINFO si;
    
    	ZeroMemory(&si, sizeof(STARTUPINFO));
    	si.cb=sizeof(STARTUPINFO);
    	
    	/*
    	si.cbReserved2 = 0;
    	si.dwFillAttribute = 0;
    	si.dwFlags = 0;
    	si.dwX = 0;
    	si.dwXCountChars = 0;
    	si.dwXSize = 0;
    	si.dwY = 0;
    	si.dwYCountChars = 0;
    	si.dwYSize = 0;
    	si.dwY = 0;
    	si.dwYCountChars = 0;
    	si.hStdError = NULL;
    	si.hStdInput = NULL;
    	si.hStdOutput = NULL;
    	si.lpDesktop = NULL;
    	si.lpReserved = NULL;
    	si.lpReserved2 = NULL;
    	si.lpTitle = NULL;
    	si.wShowWindow = 0;
    	*/
    
    	if (CreateProcess("C:\\Windows\\System32\\cmd.exe", (LPSTR) str, NULL, NULL, 0, 0, NULL, NULL, &si, &pi))
    	{
    		CloseHandle(pi.hProcess);
    		CloseHandle(pi.hThread);
    		return 1; //success
    	}
    	else
    	{
    		CloseHandle(pi.hProcess);
    		CloseHandle(pi.hThread);
    		return 0; //failure
    	}
    }
    "Artificial Intelligence usually beats natural stupidity."

  2. #2
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Things like > and | are handled directly by the shell, just before the program is executed.

    CreateProcess() will see it just as a single string, and treat it rather more literally than you want.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  3. #3
    Registered User IndioDoido's Avatar
    Join Date
    Apr 2007
    Posts
    194
    Hi Salem, thanks for the reply

    But in that case, how can i get CreateProcess() to run scripts?
    I think the system() function will do the trick but i really want to use CreateProcess().
    "Artificial Intelligence usually beats natural stupidity."

  4. #4
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    > But in that case, how can i get CreateProcess() to run scripts?
    > I think the system() function will do the trick but i really want to use CreateProcess().
    - use system(), if it does indeed do what you want.
    - create a batch file containing the redirect, then use that instead of your original command. Creates another file on the file system though.
    - parse the command line locally, looking for redirects, then modify stdio streams accordingly before calling CreateProcess().
    Choose whichever is "easiest" or "least-evil" as appropriate.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  5. #5
    Registered User
    Join Date
    Oct 2008
    Posts
    55
    Quote Originally Posted by IndioDoido View Post
    i really want to use CreateProcess().
    To send commands to cmd from the command line, you must use either the "/C" or "/K" switches. Look at "help cmd". So your call to runScripts would be e.g.:
    Code:
    runScripts( " /K echo howdy");
    You are essentially re-implementing "system" as this is pretty much what it does.

  6. #6
    Registered User IndioDoido's Avatar
    Join Date
    Apr 2007
    Posts
    194
    Salem: i'm using named pipes to send the scripts in a string to the server. How do i send a file through a named pipe?

    hi nucleon: i tried your method (/C and /K) with these CreateProcess(), but they didn't work

    Code:
    CreateProcess(NULL, (LPSTR) str, NULL, NULL, 0, 0, NULL, NULL, &si, &pi);
    CreateProcess("C:\\Windows\\System32\\cmd.exe", (LPSTR) str, NULL, NULL, 0, 0, NULL, NULL, &si, &pi);
    "Artificial Intelligence usually beats natural stupidity."

  7. #7
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    > i'm using named pipes to send the scripts in a string to the server. How do i send a file through a named pipe?
    Same way as over the internet, one byte at a time.
    So long as both ends agree on "I'm sending xxx bytes of a file called foo.txt" then all should be well.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  8. #8
    Registered User IndioDoido's Avatar
    Join Date
    Apr 2007
    Posts
    194
    sorry Salem, but you lost me

    Here is my transactNamedPipe() function i use to send a string to the pipe and receive a string from it:
    Code:
    TransactNamedPipe(hPipe, str, lstrlen(str)+1, str, 1024, &dwReadWritten, NULL);
    How do i send a file using it?
    "Artificial Intelligence usually beats natural stupidity."

  9. #9
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Open the file, read bytes from the file, send bytes down the pipe, close the file.

    The other end opens a file, reads from the pipe.... got it?
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  10. #10
    Registered User IndioDoido's Avatar
    Join Date
    Apr 2007
    Posts
    194
    lol

    know i get it

    thanks, going to try it...
    "Artificial Intelligence usually beats natural stupidity."

  11. #11
    Registered User
    Join Date
    Mar 2005
    Location
    Mountaintop, Pa
    Posts
    1,058
    Quote Originally Posted by IndioDoido View Post
    hi...

    i'm trying to send a string to windows cmd so that it can run the command contained in the string.

    i'm using CreateProcess() to send known windows command lines (ex: net user, net localgroup, at, etc), and it works fine. But now i want to send a script (ex: echo test > test.txt) and it doesn't work

    Can anyone help me?

    Here is my CreateProcess() function:
    Code:
    int runScripts(char str[])
    {
    	PROCESS_INFORMATION pi;
    	STARTUPINFO si;
    
    	ZeroMemory(&si, sizeof(STARTUPINFO));
    	si.cb=sizeof(STARTUPINFO);
    	
    	/*
    	si.cbReserved2 = 0;
    	si.dwFillAttribute = 0;
    	si.dwFlags = 0;
    	si.dwX = 0;
    	si.dwXCountChars = 0;
    	si.dwXSize = 0;
    	si.dwY = 0;
    	si.dwYCountChars = 0;
    	si.dwYSize = 0;
    	si.dwY = 0;
    	si.dwYCountChars = 0;
    	si.hStdError = NULL;
    	si.hStdInput = NULL;
    	si.hStdOutput = NULL;
    	si.lpDesktop = NULL;
    	si.lpReserved = NULL;
    	si.lpReserved2 = NULL;
    	si.lpTitle = NULL;
    	si.wShowWindow = 0;
    	*/
    
    	if (CreateProcess("C:\\Windows\\System32\\cmd.exe", (LPSTR) str, NULL, NULL, 0, 0, NULL, NULL, &si, &pi))
    	{
    		CloseHandle(pi.hProcess);
    		CloseHandle(pi.hThread);
    		return 1; //success
    	}
    	else
    	{
    		CloseHandle(pi.hProcess);
    		CloseHandle(pi.hThread);
    		return 0; //failure
    	}
    }
    Transfer a batch file containing the following statement to your server

    Code:
    echo test > test.txt
    Let's call it Indio.bat. Save Indio.bat to the C:\temp folder on your server and then execute the following from your server:

    Code:
    #include <windows.h>
    #include <stdio.h>
    
    BOOL runScripts(CHAR *pFile)
    {
        STARTUPINFO si;
        PROCESS_INFORMATION pi;
    
        ZeroMemory( &si, sizeof(si) );
        si.cb = sizeof(si);
        ZeroMemory( &pi, sizeof(pi) );
        if( !CreateProcess( NULL,   
            pFile,        
            NULL,         
            NULL,         
            FALSE,        
            0,            
            NULL,           
            NULL,           
            &si,            
            &pi )           
            ) 
        {
            printf( "CreateProcess failed (%d)\n", GetLastError() );
            return FALSE;
        }
        WaitForSingleObject( pi.hProcess, INFINITE );
        CloseHandle( pi.hProcess );
        CloseHandle( pi.hThread );
        return TRUE;
    }
    
    int main(VOID)
    {
        if(runScripts("C:\\Temp\\Indio.bat") == FALSE )
            printf("runScripts failed\n");
        else
            printf("runScripts successful\n");
        return 0;
    }

  12. #12
    Registered User
    Join Date
    Oct 2008
    Posts
    55
    Quote Originally Posted by IndioDoido View Post
    i tried your method (/C and /K) with these CreateProcess(), but they didn't work
    This works for me:
    Code:
    int main()
    {
        STARTUPINFO si = {sizeof(STARTUPINFO)};
        PROCESS_INFORMATION pi;
        CreateProcess( "C:\\Windows\\System32\\cmd.exe",
                       " /K echo test > test2.txt",
                       NULL, NULL, 0, 0, NULL, NULL, &si, &pi);
    }

  13. #13
    Registered User IndioDoido's Avatar
    Join Date
    Apr 2007
    Posts
    194
    i've managed to run the script like this:
    Code:
    CreateProcess(NULL, "cmd /C echo test > c:\test.txt", NULL, NULL, 0, 0, NULL, NULL, &si, &pi))
    What are the differences?
    "Artificial Intelligence usually beats natural stupidity."

  14. #14
    Registered User
    Join Date
    Oct 2008
    Posts
    55
    /K keeps the console open while /C closes it afterwards.

  15. #15
    Registered User IndioDoido's Avatar
    Join Date
    Apr 2007
    Posts
    194
    something really strange is happening...

    i'm having no problems using createProcess() to execute commands like:

    cmd /C "net users > C:\usersList.txt\"
    cmd /C "at > C:\atList.txt\"
    but then run this simple command:
    cmd /C "net localgroup > C:\gList.txt\"
    it doesn't work
    it creates a empty gList.txt file...

    i tried to run this command with system() and it doesn't work either

    why is that?
    "Artificial Intelligence usually beats natural stupidity."

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. CreateProcess with arguments
    By Niara in forum Windows Programming
    Replies: 14
    Last Post: 09-08-2007, 05:41 AM
  2. CreateProcess with Resource of executable, not the Filename
    By Ktulu in forum Windows Programming
    Replies: 4
    Last Post: 11-04-2006, 01:07 AM
  3. question on CreateProcess() redirection
    By ac251404 in forum Windows Programming
    Replies: 13
    Last Post: 07-18-2006, 11:06 AM
  4. CreateProcess
    By Unregistered in forum Windows Programming
    Replies: 3
    Last Post: 05-12-2002, 06:45 AM
  5. CreateProcess()
    By Newfie in forum C++ Programming
    Replies: 2
    Last Post: 05-07-2002, 07:31 AM