流沙团
[驱动开发]Hook KiFastCallEntry
2018-11-18 流沙团


很多知识点可以学习







完整代码










#include <ntddk.h>

#pragma pack(1)
typedef struct ServiceDescriptorEntry {
unsigned int *ServiceTableBase;
unsigned int *ServiceCounterTableBase; //仅适用于checked build版本
unsigned int NumberOfServices;
unsigned char *ParamTableBase;
} ServiceDescriptorTableEntry_t, *PServiceDescriptorTableEntry_t;
#pragma pack()

__declspec(dllimport) ServiceDescriptorTableEntry_t KeServiceDescriptorTable;

ULONG Old_NtCreateFile = 0;

ULONG Address1 = 0;
ULONG Address2 = 0;

typedef NTSTATUS (*PNEWNTCREATEFILE)(
OUT PHANDLE FileHandle,
IN ACCESS_MASK DesiredAccess,
IN POBJECT_ATTRIBUTES ObjectAttributes,
OUT PIO_STATUS_BLOCK IoStatusBlock,
IN PLARGE_INTEGER AllocationSize OPTIONAL,
IN ULONG FileAttributes,
IN ULONG ShareAccess,
IN ULONG CreateDisposition,
IN ULONG CreateOptions,
IN PVOID EaBuffer OPTIONAL,
IN ULONG EaLength
);

void PageProtectOn()
{
__asm{//恢复内存保护
mov eax, cr0
or eax, 10000h
mov cr0, eax
sti
}
}

void PageProtectOff()
{
__asm{//去掉内存保护
cli
mov eax, cr0
and eax, not 10000h
mov cr0, eax
}
}

ULONG SearchAddress()
{
int i = 0;
UCHAR *p = (UCHAR *)Address1;

for (i = 0; i < 100; i++)
{
if (*p == 0x2b && *(p + 1) == 0xe1 && *(p + 2) == 0xc1 && *(p + 3) == 0xe9 && *(p + 4) == 0x02)
{
//KdPrint(("找到地址kifastcallentry的hook点地址 %x\n",(ULONG)p));
Address2 = (ULONG)p;
return (ULONG)p;
}
p--;
}
return 0;
}


VOID File_HOOKAPI(ULONG ServiceTableBase, ULONG NumberOfServices)
{
if (ServiceTableBase == (ULONG)KeServiceDescriptorTable.ServiceTableBase)
{
if (NumberOfServices == 119)
{
KdPrint(("看那些进入KiFasetCallEntry调用ntopenkey进程名是%s\n", (char*)PsGetCurrentProcess() + 0x174));
}
}
}




__declspec(naked)
VOID NewKiFastCallEntry()
{
__asm{
pushad
pushfd
push eax
push edi
call File_HOOKAPI //调用我们的过滤函数
popfd
popad
pop eax
sub esp, ecx //call lisaisaide_KiFasetCallEntry 替换掉的5个字节的代码
shr ecx, 2
jmp eax
}
}

VOID Hook_KiFastCallEntry()
{
ULONG AwayAddress = 0;
UCHAR TraitCode[5];
TraitCode[0] = 0xE8;
AwayAddress = (ULONG)NewKiFastCallEntry - 5 - Address2;
*(ULONG*)&TraitCode[1] = AwayAddress;

PageProtectOff();
RtlCopyMemory((PVOID)Address2, TraitCode, 5);
PageProtectOn();

}



NTSTATUS NewCreateFile(
OUT PHANDLE FileHandle,
IN ACCESS_MASK DesiredAccess,
IN POBJECT_ATTRIBUTES ObjectAttributes,
OUT PIO_STATUS_BLOCK IoStatusBlock,
IN PLARGE_INTEGER AllocationSize OPTIONAL,
IN ULONG FileAttributes,
IN ULONG ShareAccess,
IN ULONG CreateDisposition,
IN ULONG CreateOptions,
IN PVOID EaBuffer OPTIONAL,
IN ULONG EaLength
)
{
__asm{
pushad
mov eax, [ebp + 0x4]
mov Address1, eax
popad
}

SearchAddress();

Hook_KiFastCallEntry();

return (((PNEWNTCREATEFILE)Old_NtCreateFile)(FileHandle, DesiredAccess, ObjectAttributes,
IoStatusBlock, AllocationSize, FileAttributes, ShareAccess, CreateDisposition, CreateOptions,
EaBuffer, EaLength));


}



VOID DriverUnload(IN PDRIVER_OBJECT pDriverObject)
{
UCHAR tezhengma[5] = { 0x2b, 0xe1, 0xc1, 0xe9, 0x02 };
PageProtectOff();//页保护关闭
KeServiceDescriptorTable.ServiceTableBase[37] = (unsigned int)Old_NtCreateFile;//还原ntcreatefile
PageProtectOn();//页保护开启
PageProtectOff();//页保护关闭
RtlCopyMemory((PVOID)Address2, tezhengma, 5);//还原kifastcallentry
PageProtectOn();//页保护开启
KdPrint(("已经执行到驱动卸载历程\n"));
}

NTSTATUS DriverEntry(IN PDRIVER_OBJECT pDriverObject, IN PUNICODE_STRING RegistryPath)
{
Old_NtCreateFile = KeServiceDescriptorTable.ServiceTableBase[37];

PageProtectOff();
KeServiceDescriptorTable.ServiceTableBase[37] = (unsigned int)NewCreateFile;
PageProtectOn();

pDriverObject->DriverUnload = DriverUnload;
DbgPrint("DriverEntry");

return STATUS_SUCCESS;
}




发表评论:
昵称

邮件地址 (选填)

个人主页 (选填)

内容