// hook一ZwCreateSection.cpp : Defines the entry point for the console application.
//
#include <ntddk.h>
#include <wdm.h>
extern "C" typedef struct _SERVICE_DESCRIPTOR_TABLE
{
PVOID ServiceTableBase;
PULONG ServiceCounterTableBase;
ULONG NumberOfService;
ULONG ParamTableBase;
}SERVICE_DESCRIPTOR_TABLE,*PSERVICE_DESCRIPTOR_TABLE;
extern "C" PSERVICE_DESCRIPTOR_TABLE KeServiceDescriptorTable;
VOID Hook();
VOID Unhook();
VOID OnUnload(IN PDRIVER_OBJECT DriverObject);
ULONG JmpAddress;
ULONG OldServiceAddress;
NTSTATUS extern "C" NtCreateSection(OUT PHANDLE SectionHandle,IN ACCESS_MASK DesiredAccess,IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL,
IN PLARGE_INTEGER MaximumSize OPTIONAL,
IN ULONG SectionPageProtection,
IN ULONG AllocationAttributes,
IN HANDLE FileHandle OPTIONAL
);
__declspec(naked) NTSTATUS __stdcall MyNtCreateSection( OUT PHANDLE SectionHandle,
IN ACCESS_MASK DesiredAccess,
IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL,
IN PLARGE_INTEGER MaximumSize OPTIONAL,
IN ULONG SectionPageProtection,
IN ULONG AllocationAttributes,IN HANDLE FileHandle OPTIONAL)
{
DbgPrint(("NtCreateSection is called/n"));
__asm{
//push 2Ch
//push 804da308h
jmp [JmpAddress];
//jmp JmpAddress;
}
}
extern "C" NTSTATUS DriverEntry(IN PDRIVER_OBJECT DriverObject,PUNICODE_STRING RegistryPath)
{
DriverObject->DriverUnload=OnUnload;
Hook();
return STATUS_SUCCESS;
}
VOID OnUnload(IN PDRIVER_OBJECT DriverObject)
{
DbgPrint("Unhooker unload!");
Unhook();
}
VOID Hook()
{
DbgPrint(("START HOOKING!/n"));
ULONG Address;
KIRQL irql;
Address=(ULONG) KeServiceDescriptorTable->ServiceTableBase + 0x32 * 4;
KdPrint(("Address:0x%08X",Address));
OldServiceAddress=*(ULONG *)Address;//sdt表中原来zwCreateSection的
DbgPrint("OldServiceAddress:0x%08X",OldServiceAddress);
DbgPrint("MyNtOpenProcess:0x%08X",MyNtCreateSection);
JmpAddress=(ULONG)NtCreateSection;
//怪不得,有重入问题,调用ZwCreateSection时又从sdt表中查找,从而。。。。。
//JmpAddress=OldServiceAddress+7;
DbgPrint("JmpAddress:0x%08X",JmpAddress);
irql=KeRaiseIrqlToDpcLevel();
__asm{
cli
mov eax,cr0
and eax,not 10000h
mov cr0,eax
}
*((ULONG*)Address)=(ULONG)MyNtCreateSection;
__asm{
mov eax,cr0
or eax,10000h
mov cr0,eax
sti
}
KeLowerIrql(irql);
}
VOID Unhook()
{
KIRQL irql;
ULONG Address;
Address = (ULONG)KeServiceDescriptorTable->ServiceTableBase + 0x7A * 4;//查找SSDT
irql=KeRaiseIrqlToDpcLevel();
__asm{
cli
mov eax,cr0
and eax,not 10000h
mov cr0,eax
}
*((ULONG*)Address) = (ULONG)OldServiceAddress;//还原SSDT
__asm{
mov eax,cr0
or eax,10000h
mov cr0,eax
sti
}
KeLowerIrql(irql);
DbgPrint("Unhook");
DbgPrint(("CANCEL HOOING/n"));
}