I try to patch external DRIVER_OBJECT structure by replacing
MajorFunction handlers addresses. I use this code:
KeRaiseIrql(HIGH_LEVEL, &OldIrql);
InterceptFunction(IRP_MJ_CREATE, DriverObject, &HookedDevices[
HookedDevicesCount ].fnCreate, HookRoutine);
InterceptFunction(IRP_MJ_PNP, DriverObject, &HookedDevices[
HookedDevicesCount ].fnPnP, HookRoutine);
InterceptFunction(IRP_MJ_POWER, DriverObject, &HookedDevices[
HookedDevicesCount ].fnPower, HookRoutine);
InterceptFunction(IRP_MJ_READ, DriverObject, &HookedDevices[
HookedDevicesCount ].fnRead, HookRoutine);
InterceptFunction(IRP_MJ_WRITE, DriverObject, &HookedDevices[
HookedDevicesCount ].fnWrite, HookRoutine);
InterceptFunction(IRP_MJ_FLUSH_BUFFERS, DriverObject,
&HookedDevices[HookedDevicesCount].fnFlushBuffers, HookRoutine);
InterceptFunction(IRP_MJ_QUERY_INFORMATION, DriverObject,
&HookedDevices[HookedDevicesCount].fnQueryInformation, HookRoutine);
InterceptFunction(IRP_MJ_SET_INFORMATION, DriverObject,
&HookedDevices[HookedDevicesCount].fnSetInformation, HookRoutine);
InterceptFunction(IRP_MJ_DEVICE_CONTROL, DriverObject,
&HookedDevices[HookedDevicesCount].fnDeviceControl, HookRoutine);
InterceptFunction(IRP_MJ_INTERNAL_DEVICE_CONTROL, DriverObject,
&HookedDevices[HookedDevicesCount].fnInternalDeviceControl, HookRoutine);
InterceptFunction(IRP_MJ_SYSTEM_CONTROL, DriverObject,
&HookedDevices[HookedDevicesCount].fnSystemControl, HookRoutine);
InterceptFunction(IRP_MJ_CLEANUP, DriverObject, &HookedDevices[
HookedDevicesCount ].fnCleanup, HookRoutine);
InterceptFunction(IRP_MJ_CLOSE, DriverObject, &HookedDevices[
HookedDevicesCount ].fnClose, HookRoutine);
InterceptFunction(IRP_MJ_SHUTDOWN, DriverObject, &HookedDevices[
HookedDevicesCount ].fnShutdown, HookRoutine);
HookedDevices[HookedDevicesCount].FastIoDispatch =
DriverObject->FastIoDispatch;
if (DriverObject->FastIoDispatch)
DriverObject->FastIoDispatch = HookedFastIo;
HookedDevices[HookedDevicesCount].DriverObject = DriverObject;
HookedDevicesCount++;
KeLowerIrql(OldIrql);
where InterceptFunction is:
VOID
InterceptFunction(
UCHAR MajorFunction,
PDRIVER_OBJECT DriverObject,
PDRIVER_DISPATCH* pfnOldDispatch,
PDRIVER_DISPATCH fnNewDispatch)
{
PDRIVER_DISPATCH* fnTarget;
fnTarget = &(DriverObject->MajorFunction[MajorFunction]);
//hook only if handler exists
if (*fnTarget)
{
if (pfnOldDispatch)
*pfnOldDispatch = *fnTarget;
if (fnNewDispatch)
*fnTarget = fnNewDispatch;
}
For simplicity I realize HookRoutine as:
DbgPrint((“HookRoutine\n”));
Irp->IoStatus.Information = 0;
Irp->IoStatus.Status = STATUS_SUCCESS;
IoCompleteRequest(Irp, IO_NO_INCREMENT);
return STATUS_SUCCESS;
}
Using this code I hooked DRIVER_OBJECT controlling USB mouse. After
moving mouse system hangs for some time (from 10 seconds to several
minutes). Only after this time delay I can watch a lof of log records in
DbgView. If I restore back original MajorFunction handlers there is no
any time delays.
Why do time delays take place? What should I do to correct this bug?