user3490755
user3490755

Reputation: 995

QT send signal to another QT application?

I've got three applications:

  • ApplicationLauncher.exe
  • Updater.exe
  • MyApplication.exe

I want to use the ApplicationLauncher.exe to launch the Updater.exe and when the Updater.exe is finished updating it should send a signal to ApplicationLauncher.exe which then should launch MyApplication.exe

This reason for this is because Updater.exe requires admin rights to update, so I want to keep ApplicationLauncher.exe running while the updater is doing its work and then use ApplicationLauncher.exe to launch MyApplication.exe

To get this to work I need a way for ApplicationLauncher.exe to know when Updater.exe is done.

Any ideas how to accomplish this?

Upvotes: 3

Views: 1172

Answers (2)

Bgie
Bgie

Reputation: 513

You only need to spawn a process, and wait until it is finished. There is no data communicated, so no real IPC.

Because the updater requires elevated privileges, you can not use QProcess. We are on windows, and you need to fall back to the win32 API.

QDir exePath(QCoreApplication::instance()->applicationDirPath());
QString exeFileName = exePath.absoluteFilePath("update.exe");
QByteArray exeFileNameAnsi = exeFileName.toAscii();

    // we must use ShellExecuteEx because we need admin privileges on update
    // the standard QProcess functions do not provide this.
    SHELLEXECUTEINFOA lpExecInfo;
    lpExecInfo.cbSize  = sizeof(SHELLEXECUTEINFO);
    lpExecInfo.lpFile = exeFileNameAnsi.constData();
    lpExecInfo.fMask=SEE_MASK_DOENVSUBST|SEE_MASK_NOCLOSEPROCESS;
    lpExecInfo.hwnd = NULL;
    lpExecInfo.lpVerb = "open";
    lpExecInfo.lpParameters = NULL;
    lpExecInfo.lpDirectory = NULL;
    lpExecInfo.nShow = SW_SHOW ;
    lpExecInfo.hInstApp = (HINSTANCE)SE_ERR_DDEFAIL;
    if( ShellExecuteExA(&lpExecInfo) && lpExecInfo.hProcess != NULL) {
        DWORD retval;
        DWORD waitresult;
        do {

            waitresult = WaitForSingleObject(lpExecInfo.hProcess, 10);
        } while (waitresult == WAIT_TIMEOUT);
        GetExitCodeProcess(lpExecInfo.hProcess, &retval);
        CloseHandle(lpExecInfo.hProcess);

        if(retval == 0) {
            // launched and finished without errors
        }
    } else {
       // failed to launch
    }

I think you may also need to link to shell32.lib in your PRO file, not sure.

LIBS += -lshell32

Upvotes: 3

Ferenc Deak
Ferenc Deak

Reputation: 35448

Since you specified that you are running under Windows, I think the simplest is to use the windows messaging system. A description of those: http://msdn.microsoft.com/en-us/library/windows/desktop/ms632590%28v=vs.85%29.aspx

Now, in the Qt application you will need to work with QWidget's winEvent: http://qt-project.org/doc/qt-4.8/qwidget.html#winEvent.

The page http://doc.qt.digia.com/solutions/4/qtwinmigrate/winmigrate-win32-in-qt-example.html has a good example on how to make a Windows aware Qt application.

However if you really want only to check that an application finished, then just start the "Updater.exe" via the runas command (http://qt-project.org/forums/viewthread/19060) to run as an Administrator then wait for it to finish (QProcess::waitForFinished (http://qt-project.org/doc/qt-4.8/qprocess.html#waitForFinished))

Upvotes: 1

Related Questions