我正在使用 Qt 在 Visual C++ (2015) 中创建自配置软件工具,该工具根据需要运行其他几个第 3 方安装程序。当软件发现它需要一个不可用的库或驱动程序时,它将使用 ShellExecuteEx 调用相应的安装程序来打开相应的可执行文件。
如果只需要安装一件事(ShellExecuteEx 只运行一次),一切都会正常运行。如果需要同时安装两件东西,那么大约 25% 的情况下,安装程序将正确运行,而另一个将打开包含可执行文件的文件夹,而不是运行可执行文件。对于正确运行的是第一个操作还是第二个操作没有一致性。
ShellExecuteEx 声称在这两种情况下都正确运行(返回 true)。我已经验证每次都提供了可执行文件(和工作目录)的正确路径。我尝试在 ShellExecuteEx 中同时使用动词“open”和“NULL”,但行为没有改变。
如果重要,两个可执行文件都请求管理权限。当一切正常时,他们都会按预期进行。当一个失败时,它不会要求管理员权限。
我找不到任何有类似问题的人的记录,这可能意味着我以某种基本方式滥用 ShellExecuteEx,但我没有看到它。提前感谢您的任何建议或意见。
这是代码:
if(dummy1Required && !dummy1Present){
SHELLEXECUTEINFOA execinfo = {};
execinfo.cbSize = sizeof(SHELLEXECUTEINFOA);
execinfo.fMask = NULL;
execinfo.hwnd = NULL;
execinfo.lpVerb = NULL;
execinfo.lpFile = QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy1/install.bat").toLocal8Bit().data();
execinfo.lpParameters = NULL;
execinfo.lpDirectory = QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy1").toLocal8Bit().data();
printf("Dummy1 Executing: %s\n In directory:%s\n", QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy1/install.bat").toLocal8Bit().data(), QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy1").toLocal8Bit().data());
fflush(stdout);
execinfo.nShow = SW_SHOW;
execinfo.hInstApp = NULL;
execinfo.fMask = execinfo.fMask | SEE_MASK_NOCLOSEPROCESS;
if(ShellExecuteExA(&execinfo)){
WaitForSingleObject(execinfo.hProcess,INFINITE);
CloseHandle(execinfo.hProcess);
}else{
printf("Failed to launch dummy1 installer because...%lu\n", GetLastError());
fflush(stdout);
}
}
if(dummy2Required && !dummy2Present){
SHELLEXECUTEINFOA execinfo = {};
execinfo.cbSize = sizeof(SHELLEXECUTEINFOA);
execinfo.fMask = NULL;
execinfo.hwnd = NULL;
execinfo.lpVerb = NULL;
execinfo.lpFile = QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy2/setup.exe").toLocal8Bit().data();
execinfo.lpParameters = "setupParamters.ini /qb /acceptlicenses y /norestart";
execinfo.lpDirectory = QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy2").toLocal8Bit().data();
printf("Dummy2 Executing: %s\n In directory:%s\n", QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy2/setup.exe").toLocal8Bit().data(), QDir::toNativeSeparators(QCoreApplication::applicationDirPath() + "/Drivers/dummy2").toLocal8Bit().data());
fflush(stdout);
execinfo.nShow = SW_SHOW;
execinfo.hInstApp = NULL;
execinfo.fMask = execinfo.fMask | SEE_MASK_NOCLOSEPROCESS;
if(ShellExecuteExA(&execinfo)){
WaitForSingleObject(execinfo.hProcess,INFINITE);
CloseHandle(execinfo.hProcess);
}else{
printf("Failed to launch dummy2 installer because...%lu\n", GetLastError());
fflush(stdout);
}
}
编辑:我不正确。如果只运行一个可执行文件,我会观察到这种行为的频率要低得多,因此它与运行两个操作没有内在联系。
编辑 2: PaulMckenzie 指出我没有正确初始化结构,这很尴尬。不幸的是,修复它并没有改变行为。不过谢谢!