标签:
#include <ntddk.h> #include <windef.h> #include <stdlib.h> typedef struct _ServiceDescriptorTable { PVOID ServiceTableBase; //System Service Dispatch Table 的基地址 PVOID ServiceCounterTable; //包含着 SSDT 中每个服务被调用次数的计数器。这个计数器一般由sysenter 更新。 unsigned int NumberOfServices; //由 ServiceTableBase 描述的服务的数目。 PVOID ParamTableBase; //包含每个系统服务参数字节数表的基地址-系统服务参数表 }*PServiceDescriptorTable; extern "C" PServiceDescriptorTable KeServiceDescriptorTable; VOID UnHOOKNtOpenProcess(); ULONG Old_NtOpProAddress; ULONG New_NtOpProAddress; ULONG Address_KiFastCallEntry; ULONG OldJmpKeFastCallEntry; typedef NTSTATUS (*NTOPENPROCESS)( OUT PHANDLE ProcessHandle, IN ACCESS_MASK DesiredAccess, IN POBJECT_ATTRIBUTES ObjectAttributes, IN PCLIENT_ID ClientId OPTIONAL ); VOID OutPut() { DbgPrint("Success\n"); } VOID UnHookKiFastCallEntry() { // 2B E1 C1 E9 02 UCHAR HookKiFastMyAddress[5] = {0x2B,0xE1,0xC1,0xE9,0x02}; _asm { cli mov eax,cr0 and eax,not 10000h mov cr0,eax } RtlCopyMemory((PVOID)(OldJmpKeFastCallEntry-5),HookKiFastMyAddress,5); _asm { mov eax,cr0 or eax,10000h mov cr0,eax sti } } _declspec(naked)VOID MyKiFaseCallEntry() { _asm { pushad //一定要保存这个 pushfd call OutPut popfd popad sub esp,ecx shr ecx,2 jmp OldJmpKeFastCallEntry } } VOID HOOKMYKIFASTCALLENTRY(ULONG Address) { ULONG HOOKFUNTIONADDRESS = (ULONG)MyKiFaseCallEntry; UCHAR HOOKADDRESS[5] = {0xe9,0,0,0,0}; ULONG NTHOOKADDRESS_KIFASTCALLENTRY = HOOKFUNTIONADDRESS - Address - 5; *(ULONG*)&HOOKADDRESS[1] = NTHOOKADDRESS_KIFASTCALLENTRY; OldJmpKeFastCallEntry = (Address+5); _asm { cli mov eax,cr0 and eax,not 10000h mov cr0,eax } RtlCopyMemory((PVOID)Address,HOOKADDRESS,5); _asm { mov eax,cr0 or eax,10000h mov cr0,eax sti } } ULONG HookKiFastCallEntry(ULONG KiFastCallEntryAddress) { KiFastCallEntryAddress-=50; BYTE* P; for (ULONG i=0;i<50;i++) { // 2B E1 C1 E9 02 P = (BYTE*)(KiFastCallEntryAddress+i); if (*P==0x2b && *(P+1)== 0xe1 && *(P+2)==0xc1 && *(P+3)== 0xE9 && *(P+4)==0x02) { //============================================ DbgPrint("OldJmpKeFastCallEntry:%X\n",P); UnHOOKNtOpenProcess(); //============================================ return (ULONG)P; break; } } return 0; } NTSTATUS MyNtOpenProcess( OUT PHANDLE ProcessHandle, IN ACCESS_MASK DesiredAccess, IN POBJECT_ATTRIBUTES ObjectAttributes, IN PCLIENT_ID ClientId OPTIONAL ) { //获取调用 KiFastCallEntry 中代码的地址 _asm { pushfd mov eax,[ebp+4] mov Address_KiFastCallEntry,eax popfd } ULONG Address = HookKiFastCallEntry(Address_KiFastCallEntry); if (Address != 0) { HOOKMYKIFASTCALLENTRY(Address); } return ((NTOPENPROCESS)Old_NtOpProAddress)(ProcessHandle,DesiredAccess,ObjectAttributes,ClientId); } VOID HOOKNtOpenProcess() { _asm { push ebx push eax push ecx mov ebx,122 mov eax,KeServiceDescriptorTable mov eax,[eax] mov ecx,[eax+ebx*4] mov Old_NtOpProAddress,ecx pop ecx pop eax pop ebx } New_NtOpProAddress = (ULONG)MyNtOpenProcess; _asm //关闭保护 { cli mov eax,CR0 and eax,not 10000h mov CR0,eax } _asm { push ebx push eax push ecx mov ebx,122 mov eax,KeServiceDescriptorTable mov eax,[eax] mov ecx,MyNtOpenProcess mov [eax+ebx*4],ecx pop ecx pop eax pop ebx } _asm //开启保护 { mov eax,CR0 or eax,10000h mov CR0,eax sti } } VOID UnHOOKNtOpenProcess() { _asm //关闭保护 { cli mov eax,CR0 and eax,not 10000h mov CR0,eax } _asm { push ebx push eax push ecx mov ebx,122 mov eax,KeServiceDescriptorTable mov eax,[eax] mov ecx,Old_NtOpProAddress mov [eax+ebx*4],ecx pop ecx pop eax pop ebx } _asm //开启保护 { mov eax,CR0 or eax,10000h mov CR0,eax sti } } VOID DriverUnload(PDRIVER_OBJECT pDriverObj) { UnHookKiFastCallEntry(); DbgPrint("++++驱动卸载++++\n"); } NTSTATUS DriverEntry(PDRIVER_OBJECT pDriverObj, PUNICODE_STRING pRegistryString) { pDriverObj->DriverUnload = DriverUnload; DbgPrint("++++驱动加载++++\n"); HOOKNtOpenProcess(); return STATUS_SUCCESS; }
标签:
原文地址:http://www.cnblogs.com/cxys/p/4970235.html