SwitchDesktop可以暂时工作,但过了一会儿就会切换回来

Gra*_* H. 5 c++ windows winapi

我有一些代码来创建一个新的桌面并在该桌面上启动一个进程.

一些选择的Windows XP机器,当这段代码运行时,我可以看到它切换到新桌面并启动过程,但几乎立即,桌面切换回普通桌面.

这个代码在大约98%的机器上工作正常,我似乎无法隔离任何原因导致其他机器无法工作.

应该SwitchDesktop可靠吗?我可以挂钩SwitchDesktop可能从另一个应用程序调用的调用吗?

我的代码:

int DLL_EXP_IMP WINAPI Process_Desktop(char *szDesktopName, char *szPath)
{
    HDESK   hOriginalThread;
    HDESK   hOriginalInput;
    HDESK   hNewDesktop;
    int procSuccess;
    // Save original ...
    hOriginalThread = GetThreadDesktop(GetCurrentThreadId());
    hOriginalInput = OpenInputDesktop(0, FALSE, DESKTOP_SWITCHDESKTOP);

    // Create a new Desktop and switch to it
    hNewDesktop = CreateDesktop(szDesktopName, NULL, NULL, DF_ALLOWOTHERACCOUNTHOOK, GENERIC_ALL, NULL);
    SetThreadDesktop(hNewDesktop);
    SwitchDesktop(hNewDesktop);

    // This call blocks until the process exits, and is confirmed to work on the affected machines
    procSuccess = StartProcess(szDesktopName, szPath);

    // Restore original ...
    SwitchDesktop(hOriginalInput);
    SetThreadDesktop(hOriginalThread);

    // Close the Desktop
    CloseDesktop(hNewDesktop);

    if (procSuccess != 0)
    {
        return procSuccess;
    }
    else
    {
        return 0;
    }
}
Run Code Online (Sandbox Code Playgroud)

小智 1

我的猜测是 SetThreadDesktop() 失败。

来自 MSDN:“如果调用线程在其当前桌面上有任何窗口或挂钩,则 SetThreadDesktop 函数将失败(除非 hDesktop 参数是当前桌面的句柄)。”

您提到 StartProcess() 会阻塞,直到进程终止。这样就没有人引用新桌面,因此桌面将消失。

您可能需要考虑用 C++ 包装易出错的系统调用——在失败时抛出异常。当然,CreateDesktop/CloseDesktop 对属于 C++ 资源包装器。这是2013年了!