# HG changeset patch # User Andre Heinecke # Date 1396446357 0 # Node ID f23e0ccd5d144bbd2d57c1dfe885d84d1eade7f9 # Parent a0c5eba8eb412acd71d9df6e471d85bd37d75ea9 Fix call to windows process. This now uses the correct parameters, emits the signals correctly as errors and waits for the process to finish instead of relying on NOASYNC which did not work for runas and also made it impossible to get the return code diff -r a0c5eba8eb41 -r f23e0ccd5d14 ui/installwrapper.cpp --- a/ui/installwrapper.cpp Wed Apr 02 15:31:42 2014 +0200 +++ b/ui/installwrapper.cpp Wed Apr 02 13:45:57 2014 +0000 @@ -8,6 +8,8 @@ #include "logging.h" +#define INSTALL_TIMEOUT 3600000 /* Wait up to an hour */ + InstallWrapper::InstallWrapper(QObject* parent, const QString& path, const QStringList& instructions): QThread(parent), @@ -27,32 +29,26 @@ } #ifdef WIN32 -extern Q_CORE_EXPORT int qt_ntfs_permission_lookup; - void InstallWrapper::run() { + /* TODO: We need errorcodes here so that we can see if a user + * cancled the UAC elevation */ QTemporaryFile instructionsFile; QFileInfo cinstProcInfo = getCinstProcInfo(); + DWORD retval = 0; + SHELLEXECUTEINFOW shExecInfo; + memset (&shExecInfo, 0, sizeof(SHELLEXECUTEINFOW)); QString cinstFileName = QDir::toNativeSeparators( getCinstProcInfo().absoluteFilePath()); if (!cinstProcInfo.isExecutable()) { - emit error (tr("Could not find certificate installation process.")); + emit error(tr("Could not find certificate installation process.")); return; } instructionsFile.open(); - qt_ntfs_permission_lookup++; - if (instructionsFile.permissions() ^ ( - QFileDevice::ReadUser | - QFileDevice::WriteUser | - QFileDevice::ReadOwner | - QFileDevice::WriteOwner)) { - emit error (tr("Invalid permissions on temporary file.")); - } - foreach (const QString &b64data, mInstructions) { instructionsFile.write(b64data.toLatin1()); instructionsFile.write("\n"); @@ -60,25 +56,56 @@ instructionsFile.close(); - QString parameters = "\"" + mCertListFile + "\" \"" +instructionsFile.fileName() + "\""; + QString parameters = "\"list=" + mCertListFile + + "\" \"instructions=" +instructionsFile.fileName() + "\""; - memset (&mExecInfo, 0, sizeof(SHELLEXECUTEINFOW)); - mExecInfo.cbSize = sizeof(SHELLEXECUTEINFOW); - mExecInfo.fMask = SEE_MASK_FLAG_NO_UI | - SEE_MASK_NOASYNC; - mExecInfo.lpVerb = L"runas"; - mExecInfo.lpFile = reinterpret_cast (cinstFileName.utf16()); - mExecInfo.lpParameters = reinterpret_cast (parameters.utf16()); + shExecInfo.cbSize = sizeof(SHELLEXECUTEINFOW); + shExecInfo.fMask = SEE_MASK_NOCLOSEPROCESS; + shExecInfo.lpVerb = L"runas"; + shExecInfo.lpFile = reinterpret_cast (cinstFileName.utf16()); + shExecInfo.lpParameters = reinterpret_cast (parameters.utf16()); qDebug() << "Starting process " << cinstFileName <<" params: " << parameters; - if (!ShellExecuteExW(&mExecInfo)) { + if (!ShellExecuteExW(&shExecInfo)) { char* errmsg = getLastErrorMsg(); QString qerrmsg = QString::fromUtf8(errmsg); free(errmsg); - emit(tr("Error executing process: %1").arg(qerrmsg)); + emit error(tr("Error executing process: %1").arg(qerrmsg)); + return; } - qt_ntfs_permission_lookup--; + + retval = WaitForSingleObject(shExecInfo.hProcess, INSTALL_TIMEOUT); + + if (retval != WAIT_OBJECT_0) { + if (retval == WAIT_FAILED) { + char* errmsg = getLastErrorMsg(); + QString qerrmsg = QString::fromUtf8(errmsg); + free(errmsg); + emit error (tr("Error monitoring process: %1").arg(qerrmsg)); + return; + } else { + emit error (tr("Certificate installation timed out.")); + return; + } + } + + if (GetExitCodeProcess(shExecInfo.hProcess, &retval)) { + if (retval == STILL_ACTIVE) { + qDebug() << "Process still running, huh.."; + } + } else { + char* errmsg = getLastErrorMsg(); + QString qerrmsg = QString::fromUtf8(errmsg); + free(errmsg); + emit error (tr("Failed to check process status: %1").arg(qerrmsg)); + } + CloseHandle(shExecInfo.hProcess); + + if (retval != 0) { + /* TODO make this nicer */ + emit error (tr("The process failed with return code. %1").arg(retval)); + } } #else void InstallWrapper::run() diff -r a0c5eba8eb41 -r f23e0ccd5d14 ui/installwrapper.h --- a/ui/installwrapper.h Wed Apr 02 15:31:42 2014 +0200 +++ b/ui/installwrapper.h Wed Apr 02 13:45:57 2014 +0000 @@ -3,7 +3,6 @@ #include #include -#include #include #include "certificate.h" @@ -45,11 +44,6 @@ private: const QString mCertListFile; const QStringList mInstructions; -#ifdef WIN32 - SHELLEXECUTEINFOW mExecInfo; -#else - QProcess cinstProc; -#endif protected: void run();