BOOL GetProcessIntegrityLevel( DWORD PID, PDWORD pIntegrityLevel, PDWORD pPolicy, PDWORD pResourceIntegrityLevel, PDWORD pResourcePolicy) { /* Sanity checks */ if ((PID <= 0) || (pIntegrityLevel == NULL)) return(FALSE); /* Check if we can get information for this process */ HANDLE hProcess = OpenProcess( READ_CONTROL | PROCESS_QUERY_INFORMATION, FALSE, PID); if (hProcess == NULL) return(FALSE); BOOL bReturn = GetProcessIntegrityLevel( hProcess, pIntegrityLevel, pPolicy, pResourceIntegrityLevel, pResourcePolicy); // Don't forget to release the process handle CloseHandle(hProcess); return(bReturn); }
BOOL OnInitDialog(HWND hWnd, HWND hwndFocus, LPARAM lParam) { // 获取并显示即使在还没有为当前用户提升权限的前提下,拥有此进程的主访 // 问令牌的用户是否是本地管理员组的成员。(IsUserInAdminGroup)。 HWND hInAdminGroupLabel = GetDlgItem(hWnd, IDC_INADMINGROUP_STATIC); try { BOOL const fInAdminGroup = IsUserInAdminGroup(); SetWindowText(hInAdminGroupLabel, fInAdminGroup ? L"是" : L"否"); } catch (DWORD dwError) { SetWindowText(hInAdminGroupLabel, L"N/A"); ReportError(L"IsUserInAdminGroup", dwError); } // 获取并显示是否此进程以管理员身份运行。(IsRunAsAdmin)。 HWND hIsRunAsAdminLabel = GetDlgItem(hWnd, IDC_ISRUNASADMIN_STATIC); try { BOOL const fIsRunAsAdmin = IsRunAsAdmin(); SetWindowText(hIsRunAsAdminLabel, fIsRunAsAdmin ? L"是" : L"否"); } catch (DWORD dwError) { SetWindowText(hIsRunAsAdminLabel, L"N/A"); ReportError(L"IsRunAsAdmin", dwError); } // 获取并显示进程权限提升信息(IsProcessElevated)和完整性级别(GetProcessIntegrityLevel) // 注意:这些信息在Windows Vista之前的Windows中不存在。 HWND hIsElevatedLabel = GetDlgItem(hWnd, IDC_ISELEVATED_STATIC); HWND hILLabel = GetDlgItem(hWnd, IDC_IL_STATIC); OSVERSIONINFO osver = { sizeof(osver) }; if (GetVersionEx(&osver) && osver.dwMajorVersion >= 6) { // 运行于Windows Vista或后续版本(主版本号 >= 6)。 try { // 获取并显示进程权限提升信息 BOOL const fIsElevated = IsProcessElevated(); SetWindowText(hIsElevatedLabel, fIsElevated ? L"是" : L"否"); // 如果进程尚未被提升,更新“自我提升权限”按钮以在UI中显示UAC盾形 // 图标。宏Button_SetElevationRequiredState(在Commctrl.h中定义)用 // 于显示或隐藏按钮上的盾形图标。你也可以通过调用SHGetStockIconInfo // (参量SIID_SHIELD)来获取此图标。 HWND hElevateBtn = GetDlgItem(hWnd, IDC_ELEVATE_BN); Button_SetElevationRequiredState(hElevateBtn, !fIsElevated); } catch (DWORD dwError) { SetWindowText(hIsElevatedLabel, L"N/A"); ReportError(L"IsProcessElevated", dwError); } try { // 获取并显示进程的完整性级别 DWORD const dwIntegrityLevel = GetProcessIntegrityLevel(); switch (dwIntegrityLevel) { case SECURITY_MANDATORY_UNTRUSTED_RID: SetWindowText(hILLabel, L"不信任"); break; case SECURITY_MANDATORY_LOW_RID: SetWindowText(hILLabel, L"低"); break; case SECURITY_MANDATORY_MEDIUM_RID: SetWindowText(hILLabel, L"中"); break; case SECURITY_MANDATORY_HIGH_RID: SetWindowText(hILLabel, L"高"); break; case SECURITY_MANDATORY_SYSTEM_RID: SetWindowText(hILLabel, L"系统"); break; default: SetWindowText(hILLabel, L"未知"); break; } } catch (DWORD dwError) { SetWindowText(hILLabel, L"N/A"); ReportError(L"GetProcessIntegrityLevel", dwError); } } else { SetWindowText(hIsElevatedLabel, L"N/A"); SetWindowText(hILLabel, L"N/A"); } return TRUE; }
VOID Dlg_PopulateProcessList(HWND hwnd) { HWND hwndList = GetDlgItem(hwnd, IDC_PROCESSMODULELIST); SetWindowRedraw(hwndList, FALSE); ComboBox_ResetContent(hwndList); CToolhelp thProcesses(TH32CS_SNAPPROCESS); PROCESSENTRY32 pe = { sizeof(pe) }; BOOL fOk = thProcesses.ProcessFirst(&pe); /* Call function Process32Next for each process in the system */ for (; fOk; fOk = thProcesses.ProcessNext(&pe)) { TCHAR sz[1024]; /* Place the process name (without its path) & ID in the list */ PCTSTR pszExeFile = _tcsrchr(pe.szExeFile, TEXT('\\')); if (pszExeFile == NULL) { pszExeFile = pe.szExeFile; } else { /* Skip over the slash */ pszExeFile++; } /* Append the code/resource integrity level and policy */ DWORD dwCodeIntegrityLevel = 0; DWORD dwCodePolicy = TOKEN_MANDATORY_POLICY_OFF; DWORD dwResourcePolicy = 0; DWORD dwResourceIntegrityLevel = 0; TCHAR szCodeDetails[256]; szCodeDetails[0] = TEXT('\0'); TCHAR szResourceDetails[256]; szResourceDetails[0] = TEXT('\0'); if (GetProcessIntegrityLevel(pe.th32ProcessID, &dwCodeIntegrityLevel, &dwCodePolicy, &dwResourceIntegrityLevel, &dwResourcePolicy)) { switch (dwCodeIntegrityLevel) { case SECURITY_MANDATORY_LOW_RID: _tcscpy_s(szCodeDetails, _countof(szCodeDetails), TEXT("- Low ")); break; case SECURITY_MANDATORY_MEDIUM_RID: _tcscpy_s(szCodeDetails, _countof(szCodeDetails), TEXT("- Medium ")); break; case SECURITY_MANDATORY_HIGH_RID: _tcscpy_s(szCodeDetails, _countof(szCodeDetails), TEXT("- High ")); break; case SECURITY_MANDATORY_SYSTEM_RID: _tcscpy_s(szCodeDetails, _countof(szCodeDetails), TEXT("- System ")); break; default: _tcscpy_s(szCodeDetails, _countof(szCodeDetails), TEXT("- ??? ")); } if (dwCodePolicy == TOKEN_MANDATORY_POLICY_OFF) { // = 0 _tcscat_s(szCodeDetails, _countof(szCodeDetails), TEXT(" + no policy")); } else { if ((dwCodePolicy & TOKEN_MANDATORY_POLICY_VALID_MASK) == 0) { _tcscat_s(szCodeDetails, _countof(szCodeDetails), TEXT(" + ???")); } else { if ((dwCodePolicy & TOKEN_MANDATORY_POLICY_NO_WRITE_UP) == TOKEN_MANDATORY_POLICY_NO_WRITE_UP) { _tcscat_s(szCodeDetails, _countof(szCodeDetails), TEXT(" + no write-up")); } if ((dwCodePolicy & TOKEN_MANDATORY_POLICY_NEW_PROCESS_MIN) == TOKEN_MANDATORY_POLICY_NEW_PROCESS_MIN) { _tcscat_s(szCodeDetails, _countof(szCodeDetails), TEXT(" + new process min")); } } } switch (dwResourceIntegrityLevel) { case SECURITY_MANDATORY_LOW_RID: _tcscpy_s(szResourceDetails, _countof(szResourceDetails), TEXT("Low")); break; case SECURITY_MANDATORY_MEDIUM_RID: _tcscpy_s(szResourceDetails, _countof(szResourceDetails), TEXT("Medium")); break; case SECURITY_MANDATORY_HIGH_RID: _tcscpy_s(szResourceDetails, _countof(szResourceDetails), TEXT("High")); break; case SECURITY_MANDATORY_SYSTEM_RID: _tcscpy_s(szResourceDetails, _countof(szResourceDetails), TEXT("System")); break; case 0: _tcscpy_s(szResourceDetails, _countof(szResourceDetails), TEXT("Not set")); break; default: _tcscpy_s(szResourceDetails, _countof(szResourceDetails), TEXT("???")); } if (dwResourcePolicy == 0) { // = 0 _tcscat_s(szResourceDetails, _countof(szResourceDetails), TEXT(" + 0 policy")); } else { if ((dwResourcePolicy & TOKEN_MANDATORY_POLICY_VALID_MASK) == 0) { _tcscat_s(szResourceDetails, _countof(szResourceDetails), TEXT(" + ???")); } else { if ((dwResourcePolicy & SYSTEM_MANDATORY_LABEL_NO_WRITE_UP) == SYSTEM_MANDATORY_LABEL_NO_WRITE_UP) { _tcscat_s(szResourceDetails, _countof(szResourceDetails), TEXT(" + no write-up")); } if ((dwResourcePolicy & SYSTEM_MANDATORY_LABEL_NO_READ_UP) == SYSTEM_MANDATORY_LABEL_NO_READ_UP) { _tcscat_s(szResourceDetails, _countof(szResourceDetails), TEXT(" + no read-up")); } if ((dwResourcePolicy & SYSTEM_MANDATORY_LABEL_NO_EXECUTE_UP) == SYSTEM_MANDATORY_LABEL_NO_EXECUTE_UP) { _tcscat_s(szResourceDetails, _countof(szResourceDetails), TEXT(" + no execute-up")); } } } } StringCchPrintf(sz, _countof(sz), TEXT("%s (0x%08X) %s [%s]"), pszExeFile, pe.th32ProcessID, szCodeDetails, szResourceDetails); int n = ComboBox_AddString(hwndList, sz); // Associate the process ID with the added item ComboBox_SetItemData(hwndList, n, pe.th32ProcessID); } ComboBox_SetCurSel(hwndList, 0); // Select the first entry // Simulate the user selecting this first item so that the // results pane shows something interesting FORWARD_WM_COMMAND(hwnd, IDC_PROCESSMODULELIST, hwndList, CBN_SELCHANGE, SendMessage); SetWindowRedraw(hwndList, TRUE); InvalidateRect(hwndList, NULL, FALSE); }
bool CRemoteCacheLink::GetStatusFromRemoteCache(const CTGitPath& Path, TGITCacheResponse* pReturnedStatus, bool bRecursive) { if(!EnsurePipeOpen()) { // We've failed to open the pipe - try and start the cache // but only if the last try to start the cache was a certain time // ago. If we just try over and over again without a small pause // in between, the explorer is rendered unusable! // Failing to start the cache can have different reasons: missing exe, // missing registry key, corrupt exe, ... if (((long)GetTickCount() - m_lastTimeout) < 0) return false; // if we're in protected mode, don't try to start the cache: since we're // here, we know we can't access it anyway and starting a new process will // trigger a warning dialog in IE7+ on Vista - we don't want that. if (GetProcessIntegrityLevel() < SECURITY_MANDATORY_MEDIUM_RID) return false; if (!RunTGitCacheProcess()) return false; // Wait for the cache to open long endTime = (long)GetTickCount()+1000; while(!EnsurePipeOpen()) { if(((long)GetTickCount() - endTime) > 0) { m_lastTimeout = (long)GetTickCount()+10000; return false; } } m_lastTimeout = (long)GetTickCount()+10000; } AutoLocker lock(m_critSec); DWORD nBytesRead; TGITCacheRequest request; request.flags = TGITCACHE_FLAGS_NONOTIFICATIONS; if(bRecursive) { request.flags |= TGITCACHE_FLAGS_RECUSIVE_STATUS; } wcsncpy_s(request.path, Path.GetWinPath(), _countof(request.path) - 1); SecureZeroMemory(&m_Overlapped, sizeof(OVERLAPPED)); m_Overlapped.hEvent = m_hEvent; // Do the transaction in overlapped mode. // That way, if anything happens which might block this call // we still can get out of it. We NEVER MUST BLOCK THE SHELL! // A blocked shell is a very bad user impression, because users // who don't know why it's blocked might find the only solution // to such a problem is a reboot and therefore they might loose // valuable data. // One particular situation where the shell could hang is when // the cache crashes and our crash report dialog comes up. // Sure, it would be better to have no situations where the shell // even can get blocked, but the timeout of 10 seconds is long enough // so that users still recognize that something might be wrong and // report back to us so we can investigate further. BOOL fSuccess = TransactNamedPipe(m_hPipe, &request, sizeof(request), pReturnedStatus, sizeof(*pReturnedStatus), &nBytesRead, &m_Overlapped); if (!fSuccess) { if (GetLastError()!=ERROR_IO_PENDING) { //OutputDebugStringA("TortoiseShell: TransactNamedPipe failed\n"); ClosePipe(); return false; } // TransactNamedPipe is working in an overlapped operation. // Wait for it to finish DWORD dwWait = WaitForSingleObject(m_hEvent, 10000); if (dwWait == WAIT_OBJECT_0) { fSuccess = GetOverlappedResult(m_hPipe, &m_Overlapped, &nBytesRead, FALSE); } else { // the cache didn't respond! fSuccess = FALSE; } } if (fSuccess) { return true; } ClosePipe(); return false; }