How to execute another exe from a C++ program in Windows - c++

I want my C++ program to execute another .exe, in Windows. How would I do this? I am using Visual C++ 2010.
Here is my code
#include "stdafx.h"
#include <iostream>
using namespace std;
int _tmain(int argc, _TCHAR* argv[])
{
unsigned int input;
cout << "Enter 1 to execute program." << endl;
cin >> input;
if(input == 1) /*execute program here*/;
return 0;
}

This is a solution I found when looking for an answer previously.
It stated that you should always avoid using system() because:
It is resource heavy
It defeats security -- you don't know you it's a valid command or does the same thing on every system, you could even start up programs you didn't intend to start up. The danger is that when you directly execute a program, it gets the same privileges as your program -- meaning that if, for example, you are running as system administrator then the malicious program you just inadvertently executed is also running as system administrator.
Anti virus programs hate it, your program could get flagged as a virus.
Instead CreateProcess() can be used. Createprocess() is used to just start up an .exe and creating a new process for it. The application will run independent from the calling application.
#include <Windows.h>
void startup(LPCSTR lpApplicationName)
{
// additional information
STARTUPINFOA si;
PROCESS_INFORMATION pi;
// set the size of the structures
ZeroMemory(&si, sizeof(si));
si.cb = sizeof(si);
ZeroMemory(&pi, sizeof(pi));
// start the program up
CreateProcessA
(
lpApplicationName, // the path
argv[1], // Command line
NULL, // Process handle not inheritable
NULL, // Thread handle not inheritable
FALSE, // Set handle inheritance to FALSE
CREATE_NEW_CONSOLE, // Opens file in a separate console
NULL, // Use parent's environment block
NULL, // Use parent's starting directory
&si, // Pointer to STARTUPINFO structure
&pi // Pointer to PROCESS_INFORMATION structure
);
// Close process and thread handles.
CloseHandle(pi.hProcess);
CloseHandle(pi.hThread);
}

you can use the system function
int result = system("C:\\Program Files\\Program.exe");

Use the CreateProcess() Function.
See http://msdn.microsoft.com/en-us/library/windows/desktop/ms682425%28v=vs.85%29.aspx for details

You can make a call using system
system("./some_command")

I believe this answer should work with different programs, I tested it with Chrome.
// open program.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include "string"
using namespace std;
int _tmain(int argc, _TCHAR* argv[])
{
string command = "start chrome https://www.google.com/";
system(command.c_str());
return 0;
}

Related

FreeConsole() does not detach application from cmd

I launch my application in cmd. I compiled it by Cmake without WIN32_EXECUTABLE, so it hangs in cmd (i.e. is launched as not detached). Now I want to close the console and try to achieve this by calling FreeConsole().
This works in case I double-click the application -- the black console is flashes quickly and gets closed. But it does not work when I launch it in cmd. The cmd is still attached to the launched application and FreeConsole() does not help.
Is there any way to detach it from cmd programmatically? I have found the opportunity to run start /b myapp, but I would like to do it in a programmatical way.
UPDATE
A rough implementation of the answer of Anders for those who are interested -- see below. In this implementation I pass all the arguments, supplied to main.com, to the child process main.exe.
// main.cpp
// cl main.cpp
// link main.obj /SUBSYSTEM:WINDOWS /ENTRY:"mainCRTStartup"
//
#include <stdio.h>
#include <Windows.h>
int main(int argc, char** argv)
{
if (AttachConsole(ATTACH_PARENT_PROCESS)) {
freopen("CONOUT$", "w", stdout);
freopen("CONOUT$", "w", stderr);
freopen("CONIN$", "r", stdin);
}
for (int i = 0; i < argc; i++)
printf("--%s", argv[i]);
printf("Hello\n");
int k = 0;
scanf("%d", &k);
printf("%d\n", k);
return 0;
}
// helper.cpp
// cl helper.cpp
// link helper.obj /OUT:main.com
//
#include <windows.h>
#include <stdio.h>
#include <string.h>
void main( int argc, char **argv )
{
STARTUPINFO si;
PROCESS_INFORMATION pi;
ZeroMemory( &si, sizeof(si) );
si.cb = sizeof(si);
ZeroMemory( &pi, sizeof(pi) );
// Reconstructing the command line args for main.exe:
char cmdLine[32767] = { 0 };
strcpy(cmdLine, "main.exe ");
int shift = strlen("main.exe ");
for (int i = 1 ; i < argc; i++)
{
strcpy(cmdLine + shift, argv[i]);
const int argLength = strlen(argv[i]);
cmdLine[shift + argLength] = ' ';
shift += (argLength + 1);
}
printf("\n!!!!%s!!!!!%s\n", cmdLine, GetCommandLine());
// Start the child process.
// https://learn.microsoft.com/en-us/windows/win32/procthread/creating-processes
//
if( !CreateProcess(NULL, // No module name (use command line)
cmdLine, // 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;
}
// Wait until child process exits.
WaitForSingleObject( pi.hProcess, INFINITE );
// Close process and thread handles.
CloseHandle( pi.hProcess );
CloseHandle( pi.hThread );
}
Creating a "perfect" application that can be both GUI or console is not possible on Windows.
When a .exe has its subsystem set to console, two things happen:
CreateProcess will attach it to the parents console. If the parent does not have one, a new console is created. This can only be suppressed by passing flags to CreateProcess.
cmd.exe will wait for the process to finish.
The trick of setting the subsystem to Windows and using AttachConsole is sub-optimal because cmd.exe will not wait.
The best solution is to create your main .exe as a Windows application. Create another console helper application that you rename from .exe to .com. The helper application will just launch the main app in GUI mode and then quit. In console mode it has to tell the main app that it needs to attach and you need to WaitForSingleObject on it. Example application available here .
Visual Studio uses this .com trick. The trick works because .com is listed before .exe in %pathext%.

c++ how to write to a process that was created with createProcess

I am creating a new Powershell process via createProcess and would like to write a command to that Powershell window and hit Enter. Here is what I have:
#include <cstdio>
#include <windows.h>
#include <tlhelp32.h>
#include <string>
#include <iostream>
using namespace std;
int main(int argc, char *argv[])
{
STARTUPINFO si;
PROCESS_INFORMATION pi;
ZeroMemory(&si, sizeof(si));
si.cb = sizeof(si);
ZeroMemory(&pi, sizeof(pi));
char myCommand[] = "cmd /c powershell.exe -NoExit";
CreateProcess(NULL, // No module name (use command line)
myCommand, // 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
Sleep(5000);
string strMytestString("ls");
cout << strMytestString.c_str();
Sleep(2000);
// ENTER key down
keybd_event(VK_RETURN, 0x9C, 0, 0);
// ENTER key up
keybd_event(VK_RETURN, 0x9C, KEYEVENTF_KEYUP, 0);
return 0;
}
It opens the powershell and writes "ls" into it and hits Enter but Powershell does not take it as a command and does not do the "ls" but write it as a normal text.
Is there a way to make Powershell execute that command that I pass to it as a String?
Try to read a little bit more about STDIN, STDOUT and STDERR.
To achieve your intention, you have to pass commands into STDIN of child process.
Take a look for MSDN post Creating a Child Process with Redirected Input and Output that shown exactly what you need.

Re-execute a program after machine exception

I have a pre-compiled exe (native C++11) which crashes (access violation error) at some point in iterative process. I can not afford debugging it and re-compile it again for now.
I thought of a dirty solution. I will make another program that is responsible for executing that exe and when it stopped working, I simply re-execute it again.
Is it possible? How can I know that the program was stopped?
Note: I am on Windows and doing development using MSVS.
I have found a solution with help of #Richard Hodges.
Make a new program with the this code:
#include <Windows.h>
#include <string>
#include <iostream>
#include <windows.h>
#include <stdio.h>
#include <tchar.h>
int main(int argc, const char**argv) {
while (true) {
TCHAR ProcessName[256];
STARTUPINFO si;
PROCESS_INFORMATION pi;
wcscpy(ProcessName, L"FaultyProgram.exe");
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)
ProcessName, // Command line
NULL, // Process handle not inheritable
NULL, // Thread handle not inheritable
FALSE, // Set handle inheritance to FALSE
CREATE_NEW_CONSOLE, // 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 0;
}
// Wait until child process exits.
WaitForSingleObject(pi.hProcess, INFINITE);
// Close process and thread handles.
CloseHandle(pi.hProcess);
CloseHandle(pi.hThread);
}
return 0;
}
And the most important part is to disable UI Error message when a program crash by changing this value in the registry:
HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows\Windows Error Reporting
"DontShowUI"=dword:00000001
instead of:
"DontShowUI"=dword:00000000

How to run a Videofile using VLC player Using C++

#include<Windows.h>
#include<direct.h>
int main()
{
_chdir`("C:\\Program Files (x86)\\VideoLAN\\VLC");
system("vlc C:\\Users\\Documents\\Wildlife.wmv");
return 0;
}
By using the above code i am successfully able to run the video using vlc player but as the video finishes,still the VLC player window doesn't get close.How to shut the VLC player window?
Please post your valuable suggestion
Use option --play-and-exit or vlc://quit, namely
system("vlc file:///C:\\Users\\Documents\\Wildlife.wmv --play-and-exit");
or
system("vlc file:///C:\\Users\\Documents\\Wildlife.wmv --vlc://quit");
If you want to use another system call to terminate it, try this on Windows:
system("taskkill /im vlc.exe");
Use CreateProcess to pass the correct commandline. See the example below. Note the use of \" separators.
#include <Windows.h>
int main()
{
const char *appname = "c:\\Program Files (x86)\\VideoLAN\\VLC\\vlc.exe";
const char *filename = "c:\\files\\my file.wav";
STARTUPINFOA si;
PROCESS_INFORMATION pi;
memset(&si, 0, sizeof(si));
si.cb = sizeof(si);
memset(&pi, 0, sizeof(pi));
char buf[MAX_PATH + 300];
wsprintfA(buf, "%s \"%s\" --play-and-exit", appname, filename);
CreateProcessA(0, buf, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi);
return 0;
}
Use Unicode if that's a proper Windows program.
You need to:
Get all process IDs running at that time using EnumProcesses():https://msdn.microsoft.com/en-us/library/windows/desktop/ms682629(v=vs.85).aspx
Call OpenProcess() on each process in that above list and get a HANDLE:http://msdn.microsoft.com/en-us/library/windows/desktop/ms684320(v=vs.85).aspx
If you managed to get a HANDLE call GetModuleBaseName() and get the process name:http://msdn.microsoft.com/en-us/library/windows/desktop/ms683196(v=VS.85).aspx
Check the name and if you have found your target process in this case "vlc", call TerminateProcess():http://msdn.microsoft.com/en-us/library/windows/desktop/ms686714(v=VS.85).aspx
This is just a way...

Redirecting stdout output in cpp

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".
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 );
}