C++ CreateProcessAsUser失败,错误为“UIAccess=”的进程需要“U高程”;“真的”;
我正在尝试使用以下代码从我的服务应用程序运行用户模式进程(作为C++ CreateProcessAsUser失败,错误为“UIAccess=”的进程需要“U高程”;“真的”;,c++,c,winapi,service,uac,C++,C,Winapi,Service,Uac,我正在尝试使用以下代码从我的服务应用程序运行用户模式进程(作为本地系统运行) 用户模式流程的要求是运行而不进行提升,但在其清单中包含UIAccess=“true”,以便能够进行提升 因此,我这样做(从我的服务)是为了运行我的用户模式进程: //NOTE: Error checking is omitted for readability //'dwSessionID' = user session ID to run user-mode process in //'pUserProcPath'
本地系统运行)
用户模式流程的要求是运行而不进行提升,但在其清单中包含UIAccess=“true”
,以便能够进行提升
因此,我这样做(从我的服务)是为了运行我的用户模式进程:
//NOTE: Error checking is omitted for readability
//'dwSessionID' = user session ID to run user-mode process in
//'pUserProcPath' = L"C:\\Program Files (x86)\\Company\\Software\\user_process.exe"
HANDLE hToken = NULL;
WTSQueryUserToken(dwSessionID, &hToken);
HANDLE hToken2;
DuplicateTokenEx(hToken, MAXIMUM_ALLOWED, NULL, SecurityIdentification, TokenPrimary, &hToken2);
LPVOID pEnvBlock = NULL;
CreateEnvironmentBlock(&pEnvBlock, hToken2, FALSE);
STARTUPINFO si;
ZeroMemory(&si, sizeof(STARTUPINFO));
si.cb = sizeof(STARTUPINFO);
si.lpDesktop = L"winsta0\\default";
PROCESS_INFORMATION pi;
ZeroMemory(&pi, sizeof(pi));
//ImpersonateLoggedOnUser(hToken2); //Not necessary as suggested below
PVOID OldRedir;
Wow64DisableWow64FsRedirection(&OldRedir);
BOOL bSuccess = CreateProcessAsUser(
hToken2, // client's access token
pUserProcPath, // file to execute
NULL, // command line
NULL, // pointer to process SECURITY_ATTRIBUTES
NULL, // pointer to thread SECURITY_ATTRIBUTES
FALSE, // handles are not inheritable
NORMAL_PRIORITY_CLASS | CREATE_NEW_CONSOLE | CREATE_UNICODE_ENVIRONMENT, // creation flags
pEnvBlock, // pointer to new environment block
NULL, // name of current directory
&si, // pointer to STARTUPINFO structure
&pi // receives information about new process
);
int nOSError = ::GetLastError();
Wow64RevertWow64FsRedirection(OldRedir);
//RevertToSelf(); //Not necessary as suggested below
CloseHandle(pi.hProcess);
CloseHandle(pi.hThread);
DestroyEnvironmentBlock(pEnvBlock);
CloseHandle(hToken2);
CloseHandle(hToken);
如果user\u process.exe
的清单中有UIAccess=“false”
,则运行正常
但如果我做了以下事情:
- 为
启用user\u process.exe
:UIAccess=“true”
- 用我的代码签名证书和
- 将其放入
文件夹中“C:\Program Files(x86)\Company\Software”
CreateProcessAsUser
失败,出现错误error\u ELEVATION\u REQUIRED
有人能建议怎么做吗
另外,我尝试调整我的服务权限以启用SE_DEBUG_NAME
和SE_TCB_NAME
,但都没有效果
PS2。如果我只需双击我的
user\u process.exe
进程,该进程使用UIAccess=“true”
编译,代码签名,并放置在C:\Program Files(x86)\Company\Software
文件夹中,它将正常启动和运行(未提升)。我找到了答案。这是给遇到它的人的:
在DuplicateTokenEx
调用后添加此项:
HANDLE hToken2;
DuplicateTokenEx(hToken, MAXIMUM_ALLOWED, NULL, SecurityIdentification, TokenPrimary, &hToken2);
//ONLY if requiring UIAccess!
DWORD dwUIAccess = 1;
::SetTokenInformation(hToken2, TokenUIAccess, &dwUIAccess, sizeof(dwUIAccess));
在调用
CreateProcessAsUser(hToken2,…)
之前,您不需要调用ImpersonalLoggeDonUser(hToken2)
@RemyLebeau:谢谢。这是一个不同的主题,但我很好奇。当需要调用ImpersonalLoggeDonUser
时,是否有说明?我一直不清楚这一点。当您希望调用一个API,该API代表当前与调用线程关联的用户,但您的线程与希望API看到的用户不同时,您进行模拟。您将用户令牌传递给他们的API,如CreateProcessAsUser()
,不具备该要求,因为令牌拥有他们所需的一切。@RemyLebeau:谢谢。我感谢你的解释。@RemyLebeau:根据MSDN文档,如果您希望系统在目标用户的安全上下文而不是调用方的安全上下文中打开可执行文件,则需要使用CreateProcessAsUser的模拟。非常感谢您的分享!帮我省去了很多痛苦。