简体   繁体   English

CreateProcessAsUser创建空白/黑色窗口

[英]CreateProcessAsUser creates blank/black window

I'm using CreateProcessAsUser to create a process under user-specified credentials. 我正在使用CreateProcessAsUser在用户指定的凭据下创建一个进程。

I'm posting what are hopefully the relevant parts of the code. 我希望发布代码的相关部分。 Let me know if you want to see anything more. 让我知道您是否想看更多。

First LogonUser to get the token: 第一个LogonUser获得令牌:

result = LogonUser(
        username,
        wcschr(username, '@') ? NULL : (domain ? domain : L"."),
        password,
        LOGON32_LOGON_INTERACTIVE,
        LOGON32_PROVIDER_DEFAULT,
        &hrunastoken);

I then load the profile, set the lpDesktop value of the STARTUPINFO structure to NULL (which makes it use the desktop of the calling process), and call CreateProcessAsUser: 然后,我加载配置文件,将STARTUPINFO结构的lpDesktop值设置为NULL(这使其使用调用进程的桌面),然后调用CreateProcessAsUser:

result = CreateProcessAsUser(
        hrunastoken,
        NULL,
        apptorun,
        NULL,
        NULL,
        FALSE,
        CREATE_UNICODE_ENVIRONMENT,
        envblock ? envblock : NULL,
        NULL,
        &si,
        &pi);

This works fine - it logs in and creates the process successfully, and the process "works". 这可以正常工作-登录并成功创建进程,然后进程“运行”。 The problem is that the windows it creates are black, as in this screenshot of a notepad process started with my program: 问题在于它创建的窗口是黑色的,如以下以我的程序开始的记事本过程的屏幕截图所示:

记事本屏幕截图

Possibly relevant context: 可能相关的上下文:

My account is a local account on a Windows 7 machine with full admin rights, and I am logged on with that account. 我的帐户是具有完全管理员权限的Windows 7计算机上的本地帐户,并且已使用该帐户登录。 I used psexec (Sysinternals utility) to open a command prompt running interactively under the local system account. 我使用psexec(Sysinternals实用程序)打开在本地系统帐户下交互运行的命令提示符。 I am launching my program from that command prompt. 我正在从该命令提示符启动程序。 The credentials I am passing to it are from my account. 我要传递给它的凭据来自我的帐户。

I have not done anything with permissions to windowstations/desktops; 我没有对windowstations / desktop进行任何权限; I assume the process I create should have rights to those as the process is being created in my session and using the same account I'm already logged in with - albeit going through the SYSTEM account first. 我假设我创建的进程应具有这些权限,因为该进程是在会话中创建的,并且使用与我已经登录的帐户相同的权限-尽管首先要通过SYSTEM帐户。 Using Process Explorer, I don't see any difference in the permissions on the values and handles to windowstation/desktop by the process opened via my program vs opened normally. 使用Process Explorer,我看不到通过程序打开或正常打开的进程对windowstation / desktop的值和句柄的权限的任何区别。 Maybe that's completely irrelevant. 也许这是完全不相关的。

I also cannot use CreateProcessWithLogonW function because it must work when run from the SYSTEM account - that function as well as the "runas" program that comes with Windows don't work under SYSTEM. 我也不能使用CreateProcessWithLogonW函数,因为它必须在从SYSTEM帐户运行时必须可以工作-该函数以及Windows附带的“ runas”程序在SYSTEM下不能工作。

Funnily enough, I can't use my current method to open processes unless I'm running it under the SYSTEM account, as "a required privilege is not held by the client", so I can't compare the windows created when starting my program under my account vs the SYSTEM account... 有趣的是,除非我在SYSTEM帐户下运行它,否则无法使用当前方法打开进程,因为“客户端未拥有所需的特权”,因此无法比较启动我的窗口时创建的窗口。我的帐户与SYSTEM帐户下的程序...

The default DACL for window stations and desktops grant full access to the logon SID (which is unique to the current logon session ) rather than to the user's SID. 窗口站和桌面的默认DACL授予对登录SID(对于当前登录会话是唯一的)的完全访问权限,而不是对用户的SID的完全访问权限。 (The user's SID also appears in the DACL for the window station but has only limited permissions. It does not appear in the desktop DACL.) (用户的SID也出现在窗口站的DACL中,但只有有限的权限。它没有出现在桌面DACL中。)

The call to LogonUser generates a new session (and associated logon SID) rather than reusing the existing one, so your process does not have access to the desktop, and only has minimal access to the window station. LogonUser的调用将生成一个新会话(和关联的登录SID),而不是重用现有会话,因此您的进程无权访问桌面,而对Window Station的访问却很少。 (Actually I'm slightly puzzled as to how the process manages to run at all; when I tried to reproduce your results the process exited immediately with exit code 0xC0000142, as expected.) (实际上,我对进程如何管理完全有些困惑;当我尝试重现您的结果时,该进程立即退出,退出代码为0xC0000142,如预期的那样。)

The second piece of code in this answer shows how to change the DACL on the window station and desktop to allow the process to run properly. 此答案中的第二段代码显示了如何更改窗口站和桌面上的DACL,以使进程正常运行。 (This may not be the best solution, however, depending on your specific goals.) (但是,这可能不是最佳解决方案,具体取决于您的特定目标。)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM