• SSDT Hook


    一、效果图

    二、分析

    这里对NtCreateProcessEx做拦截,用WinDbg来定位该函数在SSDT中的记录地址:

    0: kd> dd KeServiceDescriptorTable
    8055d700  80505450 00000000 0000011c 805058c4
    8055d710  00000000 00000000 00000000 00000000
    8055d720  00000000 00000000 00000000 00000000
    8055d730  00000000 00000000 00000000 00000000
    8055d740  00000002 00002710 bf80c0b6 00000000
    8055d750  f8399a80 f82ffb60 820f06b0 806f70c0
    8055d760  071d8498 00000000 0b14f8a6 00000000
    8055d770  13460466 01cf525a 00000000 00000000
    0: kd> dd 80505450 + 0x30 * 4
    80505510  805d2136 80618172 805ac3ae 80615702
    80505520  805c49b6 805d1fd4 80617622 805fa0e6
    80505530  805a60f4 80643f58 806440a8 80617026
    80505540  80616858 806170d6 80577c2c 80624c16
    80505550  805f5958 80624de6 8057a24a 80613680
    80505560  805befc4 805edd88 806170e4 80624fc6
    80505570  806170c8 80625230 805b4c9e 805edf34
    80505580  8061660c 80577cf8 805b7806 8062549a
    0: kd> u 805d2136
    nt!NtCreateProcessEx:
    805d2136 6a0c            push    0Ch
    805d2138 68e0b84d80      push    offset nt!ObWatchHandles+0x684 (804db8e0)
    805d213d e83eaaf6ff      call    nt!_SEH_prolog (8053cb80)
    805d2142 64a124010000    mov     eax,dword ptr fs:[00000124h]
    805d2148 33d2            xor     edx,edx
    805d214a 389040010000    cmp     byte ptr [eax+140h],dl
    805d2150 7435            je      nt!NtCreateProcessEx+0x51 (805d2187)
    805d2152 8955fc          mov     dword ptr [ebp-4],edx

    三、源代码

    #include <ntddk.h>
    
    typedef struct _SERVICE_DESCRIPTOR_TABLE 
    {
        PULONG    ServiceTableBase;
        PULONG    ServiceCounterTableBase;
        ULONG    NumberOfServices;
        PUCHAR    ParamTableBase;
    }SERVICE_DESCRIPTOR_TABLE, *PSERVICE_DESCRIPTOR_TALBLE;
    
    extern PSERVICE_DESCRIPTOR_TALBLE KeServiceDescriptorTable;
    
    typedef NTSTATUS (*NTCREATEPROCESSEX)(PHANDLE, ACCESS_MASK, POBJECT_ATTRIBUTES, HANDLE, ULONG, HANDLE, HANDLE, HANDLE, ULONG);
    
    //保存NtCreateProcessEx函数的地址
    NTCREATEPROCESSEX ulNtCreateProcessEx = 0;
    //在指针数组中NtCreateProcessEx的地址
    ULONG ulNtCreateProcessExAddr = 0;
    
    
    
    VOID UN_PROTECT()
    {
        _asm
        {
            push    eax
            mov        eax,0FFFEFFFFh
            mov        CR0,eax
            pop        eax
        }
    }
    
    
    
    VOID RE_PROTECT()
    {
        _asm
        {
            push    eax
            mov        eax,CR0
            or        eax,0FFFEFFFFh
            mov        CR0,eax
            pop        eax
        }
    }
    
    
    
    
    VOID DriverUnload(PDRIVER_OBJECT pDriverObject)
    {
        UN_PROTECT();
    
        //替换NtCreateProcessEx的地址为MyNtCreateProcessEx
        *(PULONG)ulNtCreateProcessExAddr = (ULONG)ulNtCreateProcessEx;
    
        RE_PROTECT();
    }
    
    
    
    
    NTSTATUS MyNtCreateProcessEx
    (
        __out        PHANDLE                ProcessHandle,
        __in        ACCESS_MASK            DesiredAccess,
        __in_opt    POBJECT_ATTRIBUTES    ObjectAttributes,
        __in        HANDLE                ParentProcess,
        __in        ULONG                Flags,
        __in_opt    HANDLE                SectionHandle,
        __in_opt    HANDLE                DebugPort,
        __in_opt    HANDLE                ExceptionPort,
        __in        ULONG                JobMemberLevel
    )
    {
        NTSTATUS Status = STATUS_SUCCESS;
        KdPrint(("Enter MyNtCreateProcessEx! 
    "));
    
        Status = ulNtCreateProcessEx(ProcessHandle,
            DesiredAccess, ObjectAttributes, ParentProcess,
            Flags, SectionHandle, DebugPort, ExceptionPort, JobMemberLevel);
    
        return Status;
    }
    
    
    
    VOID HookCreateProcess()
    {
        ULONG ulSsdt = 0;
    
    
        //获取SSDT
        ulSsdt = (ULONG)KeServiceDescriptorTable->ServiceTableBase;
    
        //获取NtCreateProcessEx地址的指针
        ulNtCreateProcessExAddr = ulSsdt + 0x30 * 4;
    
        //备份NtCreateProcessEx的原始地址
        ulNtCreateProcessEx = (NTCREATEPROCESSEX)*(PULONG)ulNtCreateProcessExAddr;
    
        UN_PROTECT();
    
        //替换NtCreateProcessEx的地址为MyNtCreateProcessEx
        *(PULONG)ulNtCreateProcessExAddr = (ULONG)MyNtCreateProcessEx;
    
        RE_PROTECT();
    }
    
    
    
    NTSTATUS DriverEntry(PDRIVER_OBJECT pDriverObject, PUNICODE_STRING pRegistryPath)
    {
        NTSTATUS Status = STATUS_SUCCESS;
        pDriverObject->DriverUnload = DriverUnload;
    
        HookCreateProcess();
    
        return Status;
    }
  • 相关阅读:
    每天读一下,你就会改变
    C++ 反转字符串(原创)
    C++ string学习
    18种常见室内花卉的功效 (转自网络)
    UML建模教程
    孙鑫视频VC++深入详解学习笔记
    visual C++ 6.0开发工具与调试
    C++ typeid typename使用
    C++模板学习
    Working classes Code complete reading notes(6)
  • 原文地址:https://www.cnblogs.com/qiyueliuguang/p/3650630.html
Copyright © 2020-2023  润新知