2010-04-25 13:11:58 阅读6 评论0 字号:大中小
发代码高亮太占字数....
#include <ntifs.h>
#include <ntddkbd.h>
#include "kbdfilter.h"
ULONG KeyCount = 0;
UNICODE_STRING mDeviceName,symbolic;
PDRIVER_OBJECT mDriverObject = NULL;
PDEVICE_OBJECT mDevice = NULL;
PDEVICE_LIST DeviceList = NULL;//过滤设备表
KSPIN_LOCK DLSpinLock;
USHORT KbdMap[100];
void InsertDevice(PDEVICE_LIST *Head,PDEVICE_OBJECT obj)
{
PDEVICE_LIST tmp;
KIRQL irql;
KeAcquireSpinLock(&DLSpinLock,&irql);
tmp = (PDEVICE_LIST)ExAllocatePoolWithTag(NonPagedPool,sizeof(DEVICE_LIST),MEM_TAG);
tmp->DeviceObj = obj;
tmp->Next = *Head;
*Head = tmp;
KeReleaseSpinLock(&DLSpinLock,irql);
}
void kfDetach(PDEVICE_OBJECT DeviceObject)
{
PMDEV_EXT devExt;
devExt = (PMDEV_EXT)(DeviceObject->DeviceExtension);
__try
{
IoDetachDevice(devExt->TargetDeviceObject);
IoDeleteDevice(DeviceObject);
devExt->TargetDeviceObject = NULL;
devExt->pFilterDeviceObject = NULL;
KdPrint(("KbdFilter: Device:%X has been delete\n",DeviceObject));
}
__except(EXCEPTION_EXECUTE_HANDLER){}
return;
}
void mUnload(PDRIVER_OBJECT DriverObject)
{
PDEVICE_OBJECT DeviceObject;
PDEVICE_LIST tmp;
LARGE_INTEGER lDelay;
PRKTHREAD CurrentThread;
KIRQL irql;
KdPrint(("KbdFilter: Driver Unloading\n"));
lDelay.QuadPart = (__int64)-10*1000*200;//200毫秒
CurrentThread = KeGetCurrentThread();
//当前线程设置为低实时模式
KeSetPriorityThread(CurrentThread,LOW_REALTIME_PRIORITY);
UNREFERENCED_PARAMETER(DriverObject);
//卸载mDevice
IoDeleteSymbolicLink(&symbolic);
IoDeleteDevice(mDevice);
//卸载过滤设备
KeAcquireSpinLock(&DLSpinLock,&irql);
while(DeviceList)
{
tmp = DeviceList->Next;
kfDetach(DeviceList->DeviceObj);
ExFreePool(DeviceList);//释放
DeviceList = tmp;
}
ASSERT(DriverObject->DeviceObject == NULL);
KeReleaseSpinLock(&DLSpinLock,irql);
while(KeyCount)
{
KeDelayExecutionThread(KernelMode, FALSE, &lDelay);
}
KdPrint(("KbdFilter: Unload Successful\n"));
return;
}
NTSTATUS kfAttachDevice(IN PDRIVER_OBJECT DriverObject,
IN PUNICODE_STRING RegistryPath)
{
NTSTATUS status = STATUS_SUCCESS;
UNICODE_STRING DrvName;
PMDEV_EXT devExt;
PDEVICE_OBJECT pFilterDeviceObject = NULL;
PDEVICE_OBJECT pTargetDeviceObject = NULL;
PDEVICE_OBJECT pLowerDeviceObject = NULL;
PDRIVER_OBJECT KbdDriverObject = NULL;
KdPrint(("KbdFilter: Attaching Keyboard Device\n"));
RtlInitUnicodeString(&DrvName,KBD_DRIVER_NAME);
status = ObReferenceObjectByName ( &DrvName,
OBJ_CASE_INSENSITIVE,
NULL,
0,
*IoDriverObjectType,
KernelMode,
NULL,
(PVOID *)&KbdDriverObject);
if(!NT_SUCCESS(status))
{
KdPrint(("KbdFilter: [ObReferenceObjectByName]Failed\n"));
return status;
}
ObDereferenceObject(KbdDriverObject);
pTargetDeviceObject = KbdDriverObject->DeviceObject;
while(pTargetDeviceObject) //遍历设备链
{
status = IoCreateDevice(DriverObject,
sizeof(MDEV_EXT),
NULL,
pTargetDeviceObject->DeviceType,
pTargetDeviceObject->Characteristics,
FALSE,
&pFilterDeviceObject);
if(!NT_SUCCESS(status))
{
KdPrint(("KbdFilter: Cannot create filter device!\n"));
return status;
}
pLowerDeviceObject = IoAttachDeviceToDeviceStack(pFilterDeviceObject,pTargetDeviceObject);
if(!pLowerDeviceObject)
{
KdPrint(("KbdFilter: Attach device failed!\n"));
IoDeleteDevice(pFilterDeviceObject);
return STATUS_SUCCESS;
}
devExt = (PMDEV_EXT)(pFilterDeviceObject->DeviceExtension);
//修改设备属性
pFilterDeviceObject->StackSize=pLowerDeviceObject->StackSize+1;
pFilterDeviceObject->Flags |= pLowerDeviceObject->Flags & (DO_BUFFERED_IO | DO_DIRECT_IO | DO_POWER_PAGABLE);
//完成设备扩展
memset(devExt,0,sizeof(MDEV_EXT));
devExt->NodeSize = sizeof(MDEV_EXT);
devExt->LowerDeviceObject = pLowerDeviceObject;
devExt->pFilterDeviceObject = pFilterDeviceObject;
devExt->TargetDeviceObject = pTargetDeviceObject;
KeInitializeSpinLock(&(devExt->IoRequestsSpinLock));
KeInitializeEvent(&(devExt->IoInProgressEvent), NotificationEvent, FALSE);
//将新建的过滤设备插入链表
InsertDevice(&DeviceList,pFilterDeviceObject);
pTargetDeviceObject = pTargetDeviceObject->NextDevice;
}
return status;
}
void InitKbdMap()
{
USHORT i;
for(i=0;i<100;i++) KbdMap[i]=i;
}
NTSTATUS kfDispatchGeneral(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
PDEVICE_LIST tmp = DeviceList;
KIRQL irql;
PIO_STACK_LOCATION isl;
PKBD_MAP_CONFIG buf;
ULONG buflen;
KeAcquireSpinLock(&DLSpinLock,&irql);
KeReleaseSpinLock(&DLSpinLock,irql);
while(tmp)
{
if(tmp->DeviceObj == DeviceObject)
{
KdPrint(("KbdFilter: OtherDispatch\n"));
IoSkipCurrentIrpStackLocation(Irp);
return IoCallDriver(((PMDEV_EXT)(DeviceObject->DeviceExtension))->LowerDeviceObject,Irp);
}
tmp = tmp->Next;
}
isl = IoGetCurrentIrpStackLocation(Irp);
if (DeviceObject == mDevice)
{
switch(isl->MajorFunction)
{
case IRP_MJ_CREATE:
case IRP_MJ_CLOSE:
Irp->IoStatus.Information=0;
Irp->IoStatus.Status = STATUS_SUCCESS;
break;
case IRP_MJ_DEVICE_CONTROL:
Irp->IoStatus.Information=0;
if(isl->Parameters.DeviceIoControl.IoControlCode == MAP_CONFIG_CO
{
buflen = isl->Parameters.DeviceIoControl.InputBufferLength;
buf = (PKBD_MAP_CONFIG)Irp->AssociatedIrp.SystemBuffer;
if ((buf != NULL)&&(buflen>=sizeof(KBD_MAP_CONFIG)))
{
KdPrint(("KbdFilter: SetMapConfig %X --> %X",buf->source,buf->target));
if((buf->source<100)&&(buf->source>=0)) KbdMap[buf->source]=buf->target;
Irp->IoStatus.Status = STATUS_SUCCESS;
}
}
else
{
Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
}
break;
default:
Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
Irp->IoStatus.Information = 0;
}
IoCompleteRequest(Irp,IO_NO_INCREMENT);
return Irp->IoStatus.Status;
}
Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
Irp->IoStatus.Information = 0;
IoCompleteRequest(Irp,IO_NO_INCREMENT);
return STATUS_INVALID_DEVICE_REQUEST;
}
NTSTATUS kfPnP(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
NTSTATUS status;
KIRQL irql;
PMDEV_EXT devExt;
PIO_STACK_LOCATION irpStack;
PDEVICE_LIST tmp,last;
KeAcquireSpinLock(&DLSpinLock,&irql);
tmp = DeviceList;
last = NULL;
while(tmp)
{
if (tmp->DeviceObj == DeviceObject)
{
irpStack = IoGetCurrentIrpStackLocation(Irp);
devExt = (PMDEV_EXT)tmp->DeviceObj->DeviceExtension;
if (irpStack->MinorFunction == IRP_MN_REMOVE_DEVICE)
{
KdPrint(("KbdFilter: IRP_MN_REMOVE_DEVICE\n"));
IoSkipCurrentIrpStackLocation(Irp);
IoCallDriver(devExt->LowerDeviceObject, Irp);
status = STATUS_SUCCESS;
//解除绑定,删除过滤设备
IoDetachDevice(devExt->TargetDeviceObject);
IoDeleteDevice(DeviceObject);
//从列表中移除
if (tmp == DeviceList) //是否在链表的头部?
{
DeviceList = tmp->Next;
ExFreePool(tmp);
}
else
{
last->Next = tmp->Next;
ExFreePool(tmp);
}
}
else
{
//对于其他类型的IRP,全部都直接下发
IoSkipCurrentIrpStackLocation(Irp);
status = IoCallDriver(devExt->LowerDeviceObject, Irp);
}
return status;
}
last = tmp;
tmp = tmp->Next;
}
KeReleaseSpinLock(&DLSpinLock,irql);
Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
Irp->IoStatus.Information = 0;
IoCompleteRequest(Irp,IO_NO_INCREMENT);
return STATUS_INVALID_DEVICE_REQUEST;
}
NTSTATUS kfPower(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
PMDEV_EXT devExt;
PDEVICE_LIST tmp;
KIRQL irql;
KeAcquireSpinLock(&DLSpinLock,&irql);
KeReleaseSpinLock(&DLSpinLock,irql);
tmp = DeviceList;
while(tmp)
{
if(tmp->DeviceObj == DeviceObject)
{
devExt = (PMDEV_EXT)DeviceObject->DeviceExtension;
PoStartNextPowerIrp( Irp );
IoSkipCurrentIrpStackLocation( Irp );
return PoCallDriver(devExt->LowerDeviceObject, Irp );
}
tmp = tmp->Next;
}
Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
Irp->IoStatus.Information = 0;
IoCompleteRequest(Irp,IO_NO_INCREMENT);
return STATUS_INVALID_DEVICE_REQUEST;
}
NTSTATUS kfCompletionRead(IN PDEVICE_OBJECT DeviceObject,
IN PIRP Irp,
IN PVOID Context)
{
PIO_STACK_LOCATION IrpSp;
ULONG buf_len;
PKEYBOARD_INPUT_DA
ULONG i;
IrpSp = IoGetCurrentIrpStackLocation(Irp);
if(NT_SUCCESS(Irp->IoStatus.Status))
{
buf = Irp->AssociatedIrp.SystemBuffer;
buf_len = (ULONG)Irp->IoStatus.Information;
for(i=0;i<(buf_len/sizeof(KEYBOARD_INPUT_DA
{
if(!(buf->Flags&KEY_BREAK))
{
KdPrint(("KbdFilter: MakeCode:%d Flags:%4X\n",buf->MakeCode,buf->Flags));
}
buf->MakeCode = KbdMap[buf->MakeCode];
buf++;
}
}
KeyCount--;
if (Irp->PendingReturned)
{
IoMarkIrpPending(Irp);
}
return Irp->IoStatus.Status;
}
NTSTATUS kfRead(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
NTSTATUS status = STATUS_SUCCESS;
PMDEV_EXT devExt;
PDEVICE_LIST tmp;
KIRQL irql;
if (Irp->CurrentLocation == 1)
{
ULONG ReturnedInformation = 0;
KdPrint(("KbdFilter: Dispatch encountered bogus current location\n"));
status = STATUS_INVALID_DEVICE_REQUEST;
Irp->IoStatus.Status = status;
Irp->IoStatus.Information = ReturnedInformation;
IoCompleteRequest(Irp, IO_NO_INCREMENT);
return(status);
}
KeAcquireSpinLock(&DLSpinLock,&irql);
KeReleaseSpinLock(&DLSpinLock,irql);
tmp = DeviceList;
while(tmp)
{
if (tmp->DeviceObj == DeviceObject)
{
KeyCount++;
devExt = (PMDEV_EXT)DeviceObject->DeviceExtension;
IoCopyCurrentIrpStackLocationToNext(Irp);
IoSetCompletionRoutine(Irp,kfCompletionRead,DeviceObject,TRUE,TRUE,TRUE);
status = IoCallDriver( devExt->LowerDeviceObject, Irp );
return status;
}
tmp = tmp->Next;
}
Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST;
Irp->IoStatus.Information = 0;
IoCompleteRequest(Irp,IO_NO_INCREMENT);
return STATUS_INVALID_DEVICE_REQUEST;
}
NTSTATUS DriverEntry(PDRIVER_OBJECT DriverObject,PUNICODE_STRING RegPath)
{
NTSTATUS status = STATUS_SUCCESS;
ULONG i;
mDriverObject=DriverObject;
KdPrint(("KbdFilter: Entering DriverEntry\n"));
//__asm int 3
KeInitializeSpinLock(&DLSpinLock);
for(i = 0;i<IRP_MJ_MAXIMUM_FUNCTION;i++)
{
DriverObject->MajorFunction[i] = kfDispatchGeneral;
}
DriverObject->MajorFunction[IRP_MJ_PNP] = kfPnP;
DriverObject->MajorFunction[IRP_MJ_POWER] = kfPower;
DriverObject->MajorFunction[IRP_MJ_READ] = kfRead;
DriverObject->DriverUnload = mUnload;
//建立设备以完成与用户层通讯
RtlInitUnicodeString(&mDeviceName,MDEVICE_NAME);
status = IoCreateDevice(DriverObject,
0,
&mDeviceName,
FILE_DEVICE_UNKNOWN,
0,
FALSE,
&mDevice);
if(!NT_SUCCESS(status))
{
KdPrint(("KbdFilter: Cannot create device!"));
return status;
}
RtlInitUnicodeString(&symbolic,MDEVICE_SYMB);
status = IoCreateSymbolicLink(&symbolic,&mDeviceName);
if(!NT_SUCCESS(status))
{
KdPrint(("KbdFilter: Cannot create device!"));
IoDeleteDevice(mDevice);
return status;
}
mDevice->Flags &= ~DO_DEVICE_INITIALIZING;
InitKbdMap();
//绑定键盘设备
status = kfAttachDevice(DriverObject,RegPath);
return status;
}