服务程序中如何以当前登陆用户身份运行程序

开发中有时会遇到这样的问题,当服务程序需要使用某些功能时,由于用户的关系而受到限制,比如访问注册表的HKEY_CURRENT_USER键,使用网络等等,这时候就需要以当前登陆用户的身份去进行操作,通常会创建一个进程来完成需要的功能。
如果使用CreateProcess来创建进程的话,新创建的进程和服务程序依然是相同的用户身份,还是无法达到目的,只有使用CreateProcessAsUser了。但CreateProcessAsUser的第一个参数是HANDLE hToken该参数通常应该用LogonUser来获得,但是LogonUser又需要用户名和用户密码,这样就很不现实。那应该怎么办呢?我想到了一个方法可以绕过LogonUser直接获得hToken。因为用户已经登陆,那么肯定有Shell(就是EXPLORER.EXE)运行了,我们可以通过遍历进程来取得Shell的hToken来运行进程。下面就是示例代码:

BOOL GetTokenByName(HANDLE &hToken,LPSTR lpName)
{
 if(!lpName)
 {
  return FALSE;
 }
 HANDLE         hProcessSnap = NULL;
    BOOL           bRet      = FALSE;
    PROCESSENTRY32 pe32      = {0};
 
    hProcessSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); 
    if (hProcessSnap == INVALID_HANDLE_VALUE)
        return (FALSE);
 
    pe32.dwSize = sizeof(PROCESSENTRY32);
 
    if (Process32First(hProcessSnap, &pe32))
    {  
        do
        {
   if(!strcmp(_strupr(pe32.szExeFile),_strupr(lpName)))
   {
    HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION,
     FALSE,pe32.th32ProcessID);
    bRet = OpenProcessToken(hProcess,TOKEN_ALL_ACCESS,&hToken);
    CloseHandle (hProcessSnap);
    return (bRet);
   }
        }
        while (Process32Next(hProcessSnap, &pe32));
        bRet = TRUE;
    }
    else
        bRet = FALSE;
 
    CloseHandle (hProcessSnap);
    return (bRet);
}

BOOL RunProcess(LPCSTR lpImage)
{
 if(!lpImage)
 {
  return FALSE;
 }
 HANDLE hToken;
 if(!GetTokenByName(hToken,"EXPLORER.EXE"))
 {
  return FALSE;
 }
 STARTUPINFO si;
 PROCESS_INFORMATION pi;
 
 ZeroMemory(&si, sizeof(STARTUPINFO));
 si.cb= sizeof(STARTUPINFO);
 si.lpDesktop = TEXT("winsta0//default");
 
 BOOL bResult = CreateProcessAsUser(hToken,lpImage,NULL,NULL,NULL,
  FALSE,NORMAL_PRIORITY_CLASS,NULL,NULL,&si,&pi);
 CloseHandle(hToken);
 if(bResult)
 {
  OutputDebugString("CreateProcessAsUser ok!/r/n");
 }
 else
 {
  OutputDebugString("CreateProcessAsUser false!/r/n");
 }
 return bResult;
}

这样就可以以登陆用户的身份来运行程序了.

你可能感兴趣的:(shell,null,query,Class,Access,token)