如:升级进程具有管理员权限,但是,希望该进程启动一个以当前用户登录的普通进程。
有木有方法啊

解决方案 »

  1.   

    //提升权限
    void CxxxDlg::EnableDebugPriv()
    {
    HANDLE hToken;
    TOKEN_PRIVILEGES tkp; //打开进程的令牌,提升权限
    OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken);
    //查询进程的权限
    LookupPrivilegeValue(NULL, SE_SHUTDOWN_NAME, &tkp.Privileges[0].Luid);
    //赋给本进程特权
    tkp.PrivilegeCount = 1;
    tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
    //将进程的权限提升到支持调试(Debug),也就是通知Windows NT修改本进程的权利
    AdjustTokenPrivileges(hToken, FALSE, &tkp, 0, (PTOKEN_PRIVILEGES)NULL, 0);
    CloseHandle(hToken);
    }
      

  2.   

    使用指定用户启动子程序入口函数 StartInteractiveClientProcess#define DESKTOP_ALL (DESKTOP_READOBJECTS | DESKTOP_CREATEWINDOW | \
    DESKTOP_CREATEMENU | DESKTOP_HOOKCONTROL | DESKTOP_JOURNALRECORD | \
    DESKTOP_JOURNALPLAYBACK | DESKTOP_ENUMERATE | DESKTOP_WRITEOBJECTS | \
    DESKTOP_SWITCHDESKTOP | STANDARD_RIGHTS_REQUIRED)#define WINSTA_ALL (WINSTA_ENUMDESKTOPS | WINSTA_READATTRIBUTES | \
    WINSTA_ACCESSCLIPBOARD | WINSTA_CREATEDESKTOP | \
    WINSTA_WRITEATTRIBUTES | WINSTA_ACCESSGLOBALATOMS | \
    WINSTA_EXITWINDOWS | WINSTA_ENUMERATE | WINSTA_READSCREEN | \
    STANDARD_RIGHTS_REQUIRED)#define GENERIC_ACCESS (GENERIC_READ | GENERIC_WRITE | \
    GENERIC_EXECUTE | GENERIC_ALL)BOOL AddAceToWindowStation(HWINSTA hwinsta, PSID psid);BOOL AddAceToDesktop(HDESK hdesk, PSID psid);
    VOID FreeLogonSID (PSID *ppsid);
    BOOL GetLogonSID (HANDLE hToken, PSID *ppsid);BOOL StartInteractiveClientProcess (
        LPTSTR lpszUsername,    // client to log on
        LPTSTR lpszDomain,      // domain of client's account
        LPTSTR lpszPassword,    // client's password
        LPTSTR lpCommandLine    // command line to execute

    {
       HANDLE      hToken;
       HDESK       hdesk = NULL;
       HWINSTA     hwinsta = NULL, hwinstaSave = NULL;
       PROCESS_INFORMATION pi;
       PSID pSid = NULL;
       STARTUPINFO si;
       BOOL bResult = FALSE;// Log the client on to the local computer.   if (!LogonUser(
               lpszUsername,
               lpszDomain,
               lpszPassword,
               LOGON32_LOGON_INTERACTIVE,
               LOGON32_PROVIDER_DEFAULT,
               &hToken) ) 
       {
          goto Cleanup;
       }// Save a handle to the caller's current window station.   if ( (hwinstaSave = GetProcessWindowStation() ) == NULL)
          goto Cleanup;// Get a handle to the interactive window station.   hwinsta = OpenWindowStation(
           "winsta0",                   // the interactive window station 
           FALSE,                       // handle is not inheritable
           READ_CONTROL | WRITE_DAC);   // rights to read/write the DACL   if (hwinsta == NULL) 
          goto Cleanup;// To get the correct default desktop, set the caller's 
    // window station to the interactive window station.   if (!SetProcessWindowStation(hwinsta))
          goto Cleanup;// Get a handle to the interactive desktop.   hdesk = OpenDesktop(
          "default",     // the interactive window station 
          0,             // no interaction with other desktop processes
          FALSE,         // handle is not inheritable
          READ_CONTROL | // request the rights to read and write the DACL
          WRITE_DAC | 
          DESKTOP_WRITEOBJECTS | 
          DESKTOP_READOBJECTS);// Restore the caller's window station.   if (!SetProcessWindowStation(hwinstaSave)) 
          goto Cleanup;   if (hdesk == NULL) 
          goto Cleanup;// Get the SID for the client's logon session.   if (!GetLogonSID(hToken, &pSid)) 
          goto Cleanup;// Allow logon SID full access to interactive window station.   if (! AddAceToWindowStation(hwinsta, pSid) ) 
          goto Cleanup;// Allow logon SID full access to interactive desktop.   if (! AddAceToDesktop(hdesk, pSid) ) 
          goto Cleanup;// Impersonate client to ensure access to executable file.   if (! ImpersonateLoggedOnUser(hToken) ) 
          goto Cleanup;// Initialize the STARTUPINFO structure.
    // Specify that the process runs in the interactive desktop.   ZeroMemory(&si, sizeof(STARTUPINFO));
       si.cb= sizeof(STARTUPINFO);
       si.lpDesktop = TEXT("winsta0\\default");// Launch the process in the client's logon session.   int iNum = 0;
    for (int i=0; i< strlen(lpCommandLine); i++)
    {
    if (lpCommandLine[i] == '\\')
    {
    iNum = i;
    }
    } char* lpstrAppPath = new char[iNum + 2];
    memcpy(lpstrAppPath, lpCommandLine, iNum + 1);
    lpstrAppPath[iNum+1] = '\0';   bResult = CreateProcessAsUser(
          hToken,            // client's access token
          NULL,              // file to execute
          lpCommandLine,     // 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,   // creation flags
          NULL,              // pointer to new environment block 
          lpstrAppPath,              // name of current directory 
          &si,               // pointer to STARTUPINFO structure
          &pi                // receives information about new process
       );    delete lpstrAppPath;
    // End impersonation of client.   RevertToSelf();
    /*
       if (bResult && pi.hProcess != INVALID_HANDLE_VALUE) 
       { 
          WaitForSingleObject(pi.hProcess, INFINITE); 
          CloseHandle(pi.hProcess); 
       }    if (pi.hThread != INVALID_HANDLE_VALUE)
          CloseHandle(pi.hThread);  
    */
    Cleanup:    if (hwinstaSave != NULL)
          SetProcessWindowStation (hwinstaSave);// Free the buffer for the logon SID.   if (pSid)
          FreeLogonSID(&pSid);// Close the handles to the interactive window station and desktop.   if (hwinsta)
          CloseWindowStation(hwinsta);   if (hdesk)
          CloseDesktop(hdesk);// Close the handle to the client's access token.   if (hToken != INVALID_HANDLE_VALUE)
          CloseHandle(hToken);     return bResult;
    }
      

  3.   

    BOOL AddAceToWindowStation(HWINSTA hwinsta, PSID psid)
    {
       ACCESS_ALLOWED_ACE   *pace;
       ACL_SIZE_INFORMATION aclSizeInfo;
       BOOL                 bDaclExist;
       BOOL                 bDaclPresent;
       BOOL                 bSuccess = FALSE;
       DWORD                dwNewAclSize;
       DWORD                dwSidSize = 0;
       DWORD                dwSdSizeNeeded;
       PACL                 pacl;
       PACL                 pNewAcl;
       PSECURITY_DESCRIPTOR psd = NULL;
       PSECURITY_DESCRIPTOR psdNew = NULL;
       PVOID                pTempAce;
       SECURITY_INFORMATION si = DACL_SECURITY_INFORMATION;
       unsigned int         i;   __try
       {
          // Obtain the DACL for the window station.      if (!GetUserObjectSecurity(
                 hwinsta,
                 &si,
                 psd,
                 dwSidSize,
                 &dwSdSizeNeeded)
          )
          if (GetLastError() == ERROR_INSUFFICIENT_BUFFER)
          {
             psd = (PSECURITY_DESCRIPTOR)HeapAlloc(
                   GetProcessHeap(),
                   HEAP_ZERO_MEMORY,
                   dwSdSizeNeeded);         if (psd == NULL)
                __leave;         psdNew = (PSECURITY_DESCRIPTOR)HeapAlloc(
                   GetProcessHeap(),
                   HEAP_ZERO_MEMORY,
                   dwSdSizeNeeded);         if (psdNew == NULL)
                __leave;         dwSidSize = dwSdSizeNeeded;         if (!GetUserObjectSecurity(
                   hwinsta,
                   &si,
                   psd,
                   dwSidSize,
                   &dwSdSizeNeeded)
             )
                __leave;
          }
          else
             __leave;      // Create a new DACL.      if (!InitializeSecurityDescriptor(
                psdNew,
                SECURITY_DESCRIPTOR_REVISION)
          )
             __leave;      // Get the DACL from the security descriptor.      if (!GetSecurityDescriptorDacl(
                psd,
                &bDaclPresent,
                &pacl,
                &bDaclExist)
          )
             __leave;      // Initialize the ACL.      ZeroMemory(&aclSizeInfo, sizeof(ACL_SIZE_INFORMATION));
          aclSizeInfo.AclBytesInUse = sizeof(ACL);      // Call only if the DACL is not NULL.      if (pacl != NULL)
          {
             // get the file ACL size info
             if (!GetAclInformation(
                   pacl,
                   (LPVOID)&aclSizeInfo,
                   sizeof(ACL_SIZE_INFORMATION),
                   AclSizeInformation)
             )
                __leave;
          }      // Compute the size of the new ACL.      dwNewAclSize = aclSizeInfo.AclBytesInUse +
                (2*sizeof(ACCESS_ALLOWED_ACE)) + (2*GetLengthSid(psid)) -
                (2*sizeof(DWORD));      // Allocate memory for the new ACL.      pNewAcl = (PACL)HeapAlloc(
                GetProcessHeap(),
                HEAP_ZERO_MEMORY,
                dwNewAclSize);      if (pNewAcl == NULL)
             __leave;      // Initialize the new DACL.      if (!InitializeAcl(pNewAcl, dwNewAclSize, ACL_REVISION))
             __leave;      // If DACL is present, copy it to a new DACL.      if (bDaclPresent)
          {
             // Copy the ACEs to the new ACL.
             if (aclSizeInfo.AceCount)
             {
                for (i=0; i < aclSizeInfo.AceCount; i++)
                {
                   // Get an ACE.
                   if (!GetAce(pacl, i, &pTempAce))
                      __leave;               // Add the ACE to the new ACL.
                   if (!AddAce(
                         pNewAcl,
                         ACL_REVISION,
                         MAXDWORD,
                         pTempAce,
                        ((PACE_HEADER)pTempAce)->AceSize)
                   )
                      __leave;
                }
             }
          }      // Add the first ACE to the window station.      pace = (ACCESS_ALLOWED_ACE *)HeapAlloc(
                GetProcessHeap(),
                HEAP_ZERO_MEMORY,
                sizeof(ACCESS_ALLOWED_ACE) + GetLengthSid(psid) -
                      sizeof(DWORD));      if (pace == NULL)
             __leave;      pace->Header.AceType  = ACCESS_ALLOWED_ACE_TYPE;
          pace->Header.AceFlags = CONTAINER_INHERIT_ACE |
                       INHERIT_ONLY_ACE | OBJECT_INHERIT_ACE;
          pace->Header.AceSize  = sizeof(ACCESS_ALLOWED_ACE) +
                       GetLengthSid(psid) - sizeof(DWORD);
          pace->Mask            = GENERIC_ACCESS;      if (!CopySid(GetLengthSid(psid), &pace->SidStart, psid))
             __leave;      if (!AddAce(
                pNewAcl,
                ACL_REVISION,
                MAXDWORD,
                (LPVOID)pace,
                pace->Header.AceSize)
          )
             __leave;      // Add the second ACE to the window station.      pace->Header.AceFlags = NO_PROPAGATE_INHERIT_ACE;
          pace->Mask            = WINSTA_ALL;      if (!AddAce(
                pNewAcl,
                ACL_REVISION,
                MAXDWORD,
                (LPVOID)pace,
                pace->Header.AceSize)
          )
             __leave;      // Set a new DACL for the security descriptor.      if (!SetSecurityDescriptorDacl(
                psdNew,
                TRUE,
                pNewAcl,
                FALSE)
          )
             __leave;      // Set the new security descriptor for the window station.      if (!SetUserObjectSecurity(hwinsta, &si, psdNew))
             __leave;      // Indicate success.      bSuccess = TRUE;
       }
       __finally
       {
          // Free the allocated buffers.      if (pace != NULL)
             HeapFree(GetProcessHeap(), 0, (LPVOID)pace);      if (pNewAcl != NULL)
             HeapFree(GetProcessHeap(), 0, (LPVOID)pNewAcl);      if (psd != NULL)
             HeapFree(GetProcessHeap(), 0, (LPVOID)psd);      if (psdNew != NULL)
             HeapFree(GetProcessHeap(), 0, (LPVOID)psdNew);
       }   return bSuccess;}
      

  4.   

    BOOL AddAceToDesktop(HDESK hdesk, PSID psid)
    {
       ACL_SIZE_INFORMATION aclSizeInfo;
       BOOL                 bDaclExist;
       BOOL                 bDaclPresent;
       BOOL                 bSuccess = FALSE;
       DWORD                dwNewAclSize;
       DWORD                dwSidSize = 0;
       DWORD                dwSdSizeNeeded;
       PACL                 pacl;
       PACL                 pNewAcl;
       PSECURITY_DESCRIPTOR psd = NULL;
       PSECURITY_DESCRIPTOR psdNew = NULL;
       PVOID                pTempAce;
       SECURITY_INFORMATION si = DACL_SECURITY_INFORMATION;
       unsigned int         i;   __try
       {
          // Obtain the security descriptor for the desktop object.      if (!GetUserObjectSecurity(
                hdesk,
                &si,
                psd,
                dwSidSize,
                &dwSdSizeNeeded))
          {
             if (GetLastError() == ERROR_INSUFFICIENT_BUFFER)
             {
                psd = (PSECURITY_DESCRIPTOR)HeapAlloc(
                      GetProcessHeap(),
                      HEAP_ZERO_MEMORY,
                      dwSdSizeNeeded );            if (psd == NULL)
                   __leave;            psdNew = (PSECURITY_DESCRIPTOR)HeapAlloc(
                      GetProcessHeap(),
                      HEAP_ZERO_MEMORY,
                      dwSdSizeNeeded);            if (psdNew == NULL)
                   __leave;            dwSidSize = dwSdSizeNeeded;            if (!GetUserObjectSecurity(
                      hdesk,
                      &si,
                      psd,
                      dwSidSize,
                      &dwSdSizeNeeded)
                )
                   __leave;
             }
             else
                __leave;
          }      // Create a new security descriptor.      if (!InitializeSecurityDescriptor(
                psdNew,
                SECURITY_DESCRIPTOR_REVISION)
          )
             __leave;      // Obtain the DACL from the security descriptor.      if (!GetSecurityDescriptorDacl(
                psd,
                &bDaclPresent,
                &pacl,
                &bDaclExist)
          )
             __leave;      // Initialize.      ZeroMemory(&aclSizeInfo, sizeof(ACL_SIZE_INFORMATION));
          aclSizeInfo.AclBytesInUse = sizeof(ACL);      // Call only if NULL DACL.      if (pacl != NULL)
          {
             // Determine the size of the ACL information.         if (!GetAclInformation(
                   pacl,
                   (LPVOID)&aclSizeInfo,
                   sizeof(ACL_SIZE_INFORMATION),
                   AclSizeInformation)
             )
                __leave;
          }      // Compute the size of the new ACL.      dwNewAclSize = aclSizeInfo.AclBytesInUse +
                sizeof(ACCESS_ALLOWED_ACE) +
                GetLengthSid(psid) - sizeof(DWORD);      // Allocate buffer for the new ACL.      pNewAcl = (PACL)HeapAlloc(
                GetProcessHeap(),
                HEAP_ZERO_MEMORY,
                dwNewAclSize);      if (pNewAcl == NULL)
             __leave;      // Initialize the new ACL.      if (!InitializeAcl(pNewAcl, dwNewAclSize, ACL_REVISION))
             __leave;      // If DACL is present, copy it to a new DACL.      if (bDaclPresent)
          {
             // Copy the ACEs to the new ACL.
             if (aclSizeInfo.AceCount)
             {
                for (i=0; i < aclSizeInfo.AceCount; i++)
                {
                   // Get an ACE.
                   if (!GetAce(pacl, i, &pTempAce))
                      __leave;               // Add the ACE to the new ACL.
                   if (!AddAce(
                      pNewAcl,
                      ACL_REVISION,
                      MAXDWORD,
                      pTempAce,
                      ((PACE_HEADER)pTempAce)->AceSize)
                   )
                      __leave;
                }
             }
          }      // Add ACE to the DACL.      if (!AddAccessAllowedAce(
                pNewAcl,
                ACL_REVISION,
                DESKTOP_ALL,
                psid)
          )
             __leave;      // Set new DACL to the new security descriptor.      if (!SetSecurityDescriptorDacl(
                psdNew,
                TRUE,
                pNewAcl,
                FALSE)
          )
             __leave;      // Set the new security descriptor for the desktop object.      if (!SetUserObjectSecurity(hdesk, &si, psdNew))
             __leave;      // Indicate success.      bSuccess = TRUE;
       }
       __finally
       {
          // Free buffers.      if (pNewAcl != NULL)
             HeapFree(GetProcessHeap(), 0, (LPVOID)pNewAcl);      if (psd != NULL)
             HeapFree(GetProcessHeap(), 0, (LPVOID)psd);      if (psdNew != NULL)
             HeapFree(GetProcessHeap(), 0, (LPVOID)psdNew);
       }   return bSuccess;
    }BOOL GetLogonSID (HANDLE hToken, PSID *ppsid) 
    {
       BOOL bSuccess = FALSE;
       DWORD dwIndex;
       DWORD dwLength = 0;
       PTOKEN_GROUPS ptg = NULL;// Verify the parameter passed in is not NULL.
        if (NULL == ppsid)
            goto Cleanup;// Get required buffer size and allocate the TOKEN_GROUPS buffer.   if (!GetTokenInformation(
             hToken,         // handle to the access token
             TokenGroups,    // get information about the token's groups 
             (LPVOID) ptg,   // pointer to TOKEN_GROUPS buffer
             0,              // size of buffer
             &dwLength       // receives required buffer size
          )) 
       {
          if (GetLastError() != ERROR_INSUFFICIENT_BUFFER) 
             goto Cleanup;      ptg = (PTOKEN_GROUPS)HeapAlloc(GetProcessHeap(),
             HEAP_ZERO_MEMORY, dwLength);      if (ptg == NULL)
             goto Cleanup;
       }// Get the token group information from the access token.   if (!GetTokenInformation(
             hToken,         // handle to the access token
             TokenGroups,    // get information about the token's groups 
             (LPVOID) ptg,   // pointer to TOKEN_GROUPS buffer
             dwLength,       // size of buffer
             &dwLength       // receives required buffer size
             )) 
       {
          goto Cleanup;
       }// Loop through the groups to find the logon SID.   for (dwIndex = 0; dwIndex < ptg->GroupCount; dwIndex++) 
          if ((ptg->Groups[dwIndex].Attributes & SE_GROUP_LOGON_ID)
                 ==  SE_GROUP_LOGON_ID) 
          {
          // Found the logon SID; make a copy of it.         dwLength = GetLengthSid(ptg->Groups[dwIndex].Sid);
             *ppsid = (PSID) HeapAlloc(GetProcessHeap(),
                         HEAP_ZERO_MEMORY, dwLength);
             if (*ppsid == NULL)
                 goto Cleanup;
             if (!CopySid(dwLength, *ppsid, ptg->Groups[dwIndex].Sid)) 
             {
                 HeapFree(GetProcessHeap(), 0, (LPVOID)*ppsid);
                 goto Cleanup;
             }
             break;
          }   bSuccess = TRUE;Cleanup: // Free the buffer for the token groups.   if (ptg != NULL)
          HeapFree(GetProcessHeap(), 0, (LPVOID)ptg);   return bSuccess;
    }//The following function frees the buffer allocated by the GetLogonSID example function.
    VOID FreeLogonSID (PSID *ppsid) 
    {
        HeapFree(GetProcessHeap(), 0, (LPVOID)*ppsid);
    }
      

  5.   

    尝试这个int wmain()
    {
    HANDLE hToken,hNewToken;unsigned long Length;static STARTUPINFOW SI={sizeof(STARTUPINFOW)};PROCESS_INFORMATION PI;SID_AND_ATTRIBUTES SidAttrib;static SID_IDENTIFIER_AUTHORITY ia={{0,0,0,0,0,5}};
    static LUID_AND_ATTRIBUTES Privileges[26]={{{2}},{{3}},{{4}},{{5}},{{6}},{{7}},{{8}},{{9}},{{10}},{{11}},{{12}},{{13}},{{14}},{{15}},{{16}},{{17}},{{18}},{{20}},{{21}},{{22}},{{24}},{{26}},{{27}},{{28}},{{29}},{{30}}};
    static wchar_t CmdLine[]=L"cmd.exe";
    if(OpenProcessToken((HANDLE)-1,TOKEN_ALL_ACCESS,&hToken))
    {
    if(AllocateAndInitializeSid(&ia,2,SECURITY_BUILTIN_DOMAIN_RID,DOMAIN_ALIAS_RID_ADMINS,0,0,0,0,0,0,&SidAttrib.Sid))
    {
    SidAttrib.Attributes=0;
    if(CreateRestrictedToken(hToken,0,1,&SidAttrib,26,Privileges,0,0,&hNewToken))
    {
    if(CreateProcessAsUserW(hNewToken,0,CmdLine,0,0,0,0,0,0,&SI,&PI))
    {
    CloseHandle(PI.hProcess);
    CloseHandle(PI.hThread);
    }
    CloseHandle(hNewToken);
    }
    FreeSid(SidAttrib.Sid);
    }
    CloseHandle(hToken);
    }
    }
      

  6.   

    你的管理员权限怎么得到的,你指的普通用户是什么。UAC的受保护管理员就是通过这种方法得到的。