CreateProcessAsUser与ShellExecute

时间:2020-03-05 18:44:44  来源:igfitidea点击:

我需要以另一个用户的身份执行ShellExecute的操作,目前,我使用CreateProcessAsUser启动了一个调用ShellExecute的帮助程序,但这似乎太过分了(错误的父进程等等)。这?

@PabloG:ImpersonateLoggedOnUser不起作用:

HANDLE hTok;
VERIFY(LogonUser("otheruser",0,"password",LOGON32_LOGON_INTERACTIVE,LOGON32_PROVIDER_DEFAULT,&hTok));
VERIFY(ImpersonateLoggedOnUser(hTok));
ShellExecute(0,0,"calc.exe",0,0,SW_SHOW);
RevertToSelf();
CloseHandle(hTok);

只会以登录用户身份而不是" otheruser"身份启动calc

@ 1800信息:CreateProcess/CreateProcessAsUserShellExecute不同,在Vista上使用UAC时,如果我们无法控制用户正在执行的程序,则CreateProcess是没有用的(CreateProcess将返回如果我们给它一个带有清单文件的exe文件,并且带有标记为requireAdmin的文件,则会出现错误)

@Brian R. Bondy:我已经知道了这个信息(不要误会我,这是很好的东西),但是这不是主题(恕我直言),我要求的是ShellExecuteAsUser,而不是有关以另一个用户身份启动进程的信息,我已经知道该怎么做。

解决方案

回答

我们可以在ImpersonateLoggedOnUser / RevertToSelf之间包装ShellExecute

链接:
ImpersonateLoggedOnUser:http://msdn.microsoft.com/en-us/library/aa378612(VS.85).aspx

RevertToSelf:http://msdn.microsoft.com/en-us/library/aa379317.aspx

回答

抱歉,无法使用"()"超链接URL

我们为什么不只创建要运行的进程的CreateProcessAsUser?

回答

我们也许也可以使用SHCreateProcessAsUserW。

  • 如果我们不需要使用GUI运行该过程并且不需要提升
  • 如果我们要运行的用户已经登录到会话中
  • 如果我们需要使用GUI运行该过程,则用户可能会或者可能不会登录
  • 如果我们需要使用海拔高度运行流程

该解决方案实际上取决于需求,并且可能非常复杂(完全感谢Windows Vista)。这可能超出了需求,但这其他通过搜索找到此页面的人。

关于1:
在Windows Vista中,存在一种称为会话0隔离的东西。所有服务均以会话0运行,并且我们不应在会话0中使用GUI。第一个登录的用户已登录到会话1. 在早期版本的Windows(Vista之前的版本)中,第一个登录的用户也已在该版本中完全运行。会话0。

我们可以在同一会话中使用不同的用户名运行多个不同的进程。我们可以在此处找到有关会话0隔离的良好文档。

由于我们正在处理选项1),因此我们不需要GUI。因此,我们可以在会话0中启动过程。

我们将需要这样的调用序列:
LogonUser,ExpandEnvironmentStringsForUser,GetLogonSID,LoadUserProfile,CreateEnvironmentBlock,CreateProcessAsUser。

可以通过任何搜索引擎或者Google代码搜索找到示例代码

关于2:如果我们想以已经登录的身份运行该进程的用户,则可以简单地使用:WTSEnumerateSessions和WTSQuerySessionInformation来获取会话ID,然后使用WTSQueryUserToken来获取用户令牌。从那里我们可以在CreateProcessAsUser Win32 API中使用用户令牌。

这是一个很好的方法,因为我们甚至不需要以用户身份登录,也不知道用户的用户名/密码。我相信,尽管以本地系统帐户身份运行,但这只能通过服务来实现。

我们可以通过WTSGetActiveConsoleSessionId获取当前会话。

关于3:
我们将按照与#1相同的步骤进行操作,但除此之外,还将使用STARTUPINFO的lpDesktop字段。将此设置为winsta0 \ Default。我们还需要尝试使用OpenDesktop Win32 API,如果失败,则可以使用CreateDesktop。在使用工作站和桌面句柄之前,应在SE_WINDOW_OBJECT和GROUP_SECURITY_INFORMATION | |上分别使用SetSecurityInfo。 DACL_SECURITY_INFORMATION。

如果有问题的用户以后尝试登录,那么他实际上将看到正在运行的进程。

关于4:
也可以完成此操作,但是它要求我们已经在运行提升的流程。以本地系统帐户运行的服务确实以提升的身份运行。我还只能通过让我想启动的Authenticode签名过程来使其正常工作。我们要启动的进程还必须具有一个清单文件,该清单文件与所请求的ExecutionLevel level =" requireAdministrator"关联。

  • 我们可以通过SetTokenInformation和TokenSessionId设置令牌的会话
  • 我们无法更改已经运行的进程的会话ID。
  • 如果Vista不在考虑范围之内,那么整个过程将大大简化。

回答

其他说明:

如果我们需要ShellExecute语义,则可以提供以下内容:

段落数量不匹配