一些功能比如sendmessage、截屏等等在SYSTEM权限下会不工作,以前没有碰到过这个情况所以一直没去处理,前两天做模拟点击的时候必须处理这个情况,于是有了个这个传说中的降权的代码。SYSTEM权限的进程建立普通权限的进程第一反应就是CreateProcessAsUser函数。于是有了下面的代码:
Option Explicit Private Type ProcessEntry dwSize As Long peUsage As Long peProcessID As Long peDefaultHeapID As Long peModuleID As Long peThreads As Long peParentProcessID As Long pePriority As Long dwFlags As Long szExeFile As String * 260 End Type Private Type PROCESS_INFORMATION hProcess As Long hThread As Long dwProcessId As Long dwThreadID As Long End Type Private Type STARTUPINFO cb As Long lpReserved As String lpDesktop As String lpTitle As String dwX As Long dwY As Long dwXSize As Long dwYSize As Long dwXCountChars As Long dwYCountChars As Long dwFillAttribute As Long dwFlags As Long wShowWindow As Integer cbReserved2 As Integer lpReserved2 As Long hStdInput As Long hStdOutput As Long hStdError As Long End Type Private Declare Function CreateToolhelp32Snapshot _ Lib "kernel32" (ByVal dwFlags As Long, _ ByVal dwIdProc As Long) As Long Private Declare Function Process32First _ Lib "kernel32" (ByVal hndl As Long, _ ByRef pstru As ProcessEntry) As Boolean Private Declare Function Process32Next _ Lib "kernel32" (ByVal hndl As Long, _ ByRef pstru As ProcessEntry) As Boolean Private Declare Function OpenProcess _ Lib "kernel32" (ByVal dwDesiredAccess As Long, _ ByVal bInheritHandle As Long, _ ByVal dwProcessId As Long) As Long Private Declare Function CloseHandle Lib "kernel32" (ByVal hnd As Long) As Boolean Private Declare Function OpenProcessToken _ Lib "advapi32.dll" (ByVal ProcessHandle As Long, _ ByVal DesiredAccess As Long, _ TokenHandle As Long) As Long Private Declare Function CreateProcessAsUser _ Lib "advapi32.dll" _ Alias "CreateProcessAsUserA" (ByVal hToken As Long, _ ByVal lpApplicationName As String, _ ByVal lpCommandLine As String, _ lpProcessAttributes As Long, _ lpThreadAttributes As Long, _ ByVal bInheritHandles As Long, _ ByVal dwCreationFlags As Long, _ ByVal lpEnvironment As String, _ ByVal lpCurrentDirectory As String, _ lpStartupInfo As STARTUPINFO, _ lpProcessInformation As PROCESS_INFORMATION) As Long Private Const STANDARD_RIGHTS_REQUIRED As Long = &HF0000 Private Const SYNCHRONIZE As Long = &H100000 Private Const PROCESS_ALL_ACCESS As Long = (STANDARD_RIGHTS_REQUIRED Or SYNCHRONIZE Or &HFFF) Private Const TOKEN_ALL_ACCESS = 983551 Private Sub RunAsUser(ByVal strRun As String) Dim lSnapShot As Long, hProcess As Long, hToken As Long Dim tmpPE As ProcessEntry Dim bRet As Long Dim tmpProcName As String Dim strPath As String Dim si As STARTUPINFO, pi As PROCESS_INFORMATION lSnapShot = CreateToolhelp32Snapshot(&H2, 0) tmpPE.dwSize = Len(tmpPE) bRet = Process32First(lSnapShot, tmpPE) Do Until bRet = False tmpProcName = Left(tmpPE.szExeFile, InStr(1, tmpPE.szExeFile, Chr(0)) - 1) If LCase(tmpProcName) = "explorer.exe" Then hProcess = OpenProcess(PROCESS_ALL_ACCESS, 0, tmpPE.peProcessID) If OpenProcessToken(hProcess, TOKEN_ALL_ACCESS, hToken) Then strPath = Replace$(App.Path & "\", "\\", "\") si.cb = Len(si) 'CreateProcessAsUser hToken, vbNullString, strPath & App.EXEName & ".exe start", ByVal 0&, ByVal 0, False, ByVal 0&, vbNullString, vbNullString, si, pi CreateProcessAsUser hToken, vbNullString, strRun, ByVal 0&, ByVal 0, False, ByVal 0&, vbNullString, vbNullString, si, pi End If CloseHandle hProcess Exit Do End If bRet = Process32Next(lSnapShot, tmpPE) Loop bRet = CloseHandle(lSnapShot) End Sub Private Sub Form_Load() RunAsUser "c:\a.exe" End End Sub
遍历进程找到explorer.exe进程,获取它的权限后用他的权限建立新进程。一般情况下explorer都是登陆用户的权限,除非你中毒了。。。这个问题暂时不考虑了。。。
使用方法就是RunAsUser "c:\a.exe" ,strRun参数就是你要运行的程序。
大家多来顶起我的博客!~