⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 kbfiltr.c

📁 Advance(LOVEHINA-AVC) 的kbFiltr WDM驱动源码
💻 C
📖 第 1 页 / 共 2 页
字号:

                break;
            }

            ((PVERSION_DATA)bufferPointer)->MajorVersion =            VER_MAJOR;
            ((PVERSION_DATA)bufferPointer)->MinorVersion =            VER_MINOR;
            irpStack->Parameters.DeviceIoControl.OutputBufferLength = sizeof(VERSION_DATA);

            Irp->IoStatus.Information = sizeof(VERSION_DATA);

            break;

        case IOCTL_KBMHOOK_HOOK_SWITCH:

            if (irpStack->Parameters.DeviceIoControl.InputBufferLength < sizeof(HOOK_SWITCH_DATA))
            {
                status = STATUS_BUFFER_TOO_SMALL;

                break;
            }
            
            kbmDevExt->HookSwitch = ((PHOOK_SWITCH_DATA)bufferPointer)->HookSwitch;

            if ((kbmDevExt->HookSwitch == TRUE) && (kbmDevExt->DeviceCounter == 0))
                status = STATUS_INVALID_DEVICE_REQUEST;

            Irp->IoStatus.Information = 0;

            break;

        case IOCTL_KBMHOOK_QUERY_KEYDOWN:

            if (irpStack->Parameters.DeviceIoControl.OutputBufferLength < sizeof(KEYDOWN_DATA))
            {
                status = STATUS_BUFFER_TOO_SMALL;

                break;
            }
            
            *(PKEYDOWN_DATA)bufferPointer =                           kbmDevExt->KeyDown;
            irpStack->Parameters.DeviceIoControl.OutputBufferLength = sizeof(KEYDOWN_DATA);

            Irp->IoStatus.Information = sizeof(KEYDOWN_DATA);

            break;

        case IOCTL_KBMHOOK_QUERY_DEVICE:

            if (irpStack->Parameters.DeviceIoControl.OutputBufferLength < sizeof(DEVICE_COUNTER_DATA))
            {
                status = STATUS_BUFFER_TOO_SMALL;

                break;
            }
            
            ((PDEVICE_COUNTER_DATA)bufferPointer)->DeviceCounter =    kbmDevExt->DeviceCounter;
            irpStack->Parameters.DeviceIoControl.OutputBufferLength = sizeof(DEVICE_COUNTER_DATA);

            Irp->IoStatus.Information = sizeof(DEVICE_COUNTER_DATA);

            break;

        case IOCTL_KBMHOOK_MAPPING_KEYS:

            if (irpStack->Parameters.DeviceIoControl.InputBufferLength < kbmDevExt->DeviceCounter)
            {
                status = STATUS_BUFFER_TOO_SMALL;

                break;
            }

            copysize =    kbmDevExt->DeviceCounter;
            sizePointer = (PCHAR)bufferPointer;
            dataPointer = sizePointer + copysize;

            for (i = 0 ; i < kbmDevExt->DeviceCounter ; i++)
            {
                copysize += *(sizePointer + i) * sizeof(KEYMAP_DATA);
            }

            if (irpStack->Parameters.DeviceIoControl.InputBufferLength < copysize)
            {
                status = STATUS_BUFFER_TOO_SMALL;

                break;
            }

            RtlZeroMemory(kbmDevExt->KeyStore, sizeof(kbmDevExt->KeyStore));

            for (i = 0 ; i < kbmDevExt->DeviceCounter ; i++)
            {
                fltDevExt = (PFILTER_DEVICE_EXTENSION)kbmDevExt->FltDevExtPointer[i];

                RtlZeroMemory(fltDevExt->KeyStore, sizeof(fltDevExt->KeyStore));
                RtlZeroMemory(fltDevExt->KeyIndex, sizeof(fltDevExt->KeyIndex));

                copysize = *sizePointer++;

                for (j = 0 ; j < copysize ; j++)
                {
                     keyCode =      *dataPointer++;
                     keyFlags =     *dataPointer++;
                     keyCodeIndex = 0;

                     if (keyFlags & KEY_E0)
                     {
                         keyCodeIndex = 1;
                     } else if (keyFlags & KEY_E1)
                     {
                         keyCodeIndex = 2;
                     }

                     if ((keyCode != 0) && (keyCode < 128))
                     {
                         keyMapping =      *dataPointer++;
                         keyFlags =        *dataPointer++;
                         keyMappingIndex = 0;

                         if (keyFlags & KEY_E0)
                         {
                             keyMappingIndex = 1;
                         } else if (keyFlags & KEY_E1)
                         {
                             keyMappingIndex = 2;
                         }

                         if (keyMapping < 128)
                         {
                             if (keyMapping == 0)
                             {
                                 kbmDevExt->KeyStore[keyCodeIndex][keyCode] = 1;
                             } else {
                                 fltDevExt->KeyStore[keyCodeIndex][keyCode] =       keyMapping;
                                 fltDevExt->KeyIndex[keyCodeIndex][keyCode] =       keyMappingIndex;
                                 //kbmDevExt->KeyStore[keyMappingIndex][keyMapping] = 1;
                             }
                         }
                     }
                 }
            }

            Irp->IoStatus.Information = 0;

            break;
    }

    Irp->IoStatus.Status = status;
    IoCompleteRequest(Irp, IO_NO_INCREMENT);

    return (status);
}

NTSTATUS
KbFilter_Read(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP Irp
    )

{
    PFILTER_DEVICE_EXTENSION  fltDevExt = (PFILTER_DEVICE_EXTENSION)DeviceObject->DeviceExtension;

    if (fltDevExt->IsFilterDevice == FALSE)
    {
        Irp->IoStatus.Information = 0;
        Irp->IoStatus.Status =      STATUS_NOT_IMPLEMENTED;
        IoCompleteRequest(Irp, IO_NO_INCREMENT);

        return STATUS_NOT_IMPLEMENTED;
    }

    //
    // 读取请求来自Win32k,在此挂接我们的完成例程。
    //
    IoCopyCurrentIrpStackLocationToNext(Irp);
    IoSetCompletionRoutine(Irp,
                           (PIO_COMPLETION_ROUTINE)KbFilter_Complete,
                           NULL,
                           TRUE,
                           FALSE,
                           FALSE);

    return IoCallDriver(fltDevExt->LowerDeviceObject, Irp);
}

NTSTATUS
KbFilter_PnP(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP Irp
    )

{
    PKBMHOOK_DEVICE_EXTENSION   kbmDevExt;
    PFILTER_DEVICE_EXTENSION    fltDevExt;
    PIO_STACK_LOCATION          irpStack;
    UCHAR                       i,j,index;
    NTSTATUS                    status = STATUS_SUCCESS;

    irpStack =  IoGetCurrentIrpStackLocation(Irp);

    switch(irpStack->MinorFunction)
    {
        //
        // 得到移除设备的IRP之后必须分离并删除我们的过滤设备对象
        //
        case IRP_MN_REMOVE_DEVICE:

            fltDevExt = (PFILTER_DEVICE_EXTENSION)DeviceObject->DeviceExtension;
            kbmDevExt = (PKBMHOOK_DEVICE_EXTENSION)fltDevExt->KbmDevExtPointer;
            index =     fltDevExt->DeviceID;

            Irp->IoStatus.Status = STATUS_SUCCESS;
        
            IoSkipCurrentIrpStackLocation(Irp);
            status = IoCallDriver(fltDevExt->LowerDeviceObject, Irp);

            IoDetachDevice(fltDevExt->LowerDeviceObject); 
            IoDeleteDevice(DeviceObject);

            //
            // 对设备扩展指针进行重排序
            //
            for (i = 0 ; i < 16 ; i++)
            {
                if (fltDevExt == kbmDevExt->FltDevExtPointer[i])
                {
                    if (i < 15)
                    {
                        for (j = i ; j < 15 ; j++)
                        {
                            kbmDevExt->FltDevExtPointer[j] = kbmDevExt->FltDevExtPointer[j + 1];
                        }
                    }
                    break;
                }
            }

            kbmDevExt->DeviceCounter--;
            kbmDevExt->KbdClassDevice[index] = NULL;

            break;

        default:

            status = KbFilter_DispatchPassThrough(DeviceObject, Irp);
            break;
    }

    return status;
}

NTSTATUS
KbFilter_HookDevice(
    IN PDEVICE_OBJECT DeviceObject,
    IN PKBMHOOK_DEVICE_EXTENSION KbmDevExt
    )

{
    PDEVICE_OBJECT            fltDevice,kbdcDevice;
    PFILTER_DEVICE_EXTENSION  fltDevExt;
    BOOLEAN                   flag;
    UCHAR                     i,index;
    NTSTATUS                  status = STATUS_SUCCESS;

    //
    // 位于链表顶端的设备对象指针,也就是键盘类驱动的最后一个设备。
    //
    kbdcDevice = KbmDevExt->KbdClassDriver->DeviceObject;

    goto EnumNewDevice;

CreateFidoForPdo:

    //
    // 为每块物理键盘创建一个键盘类驱动钩子设备
    //
    status = IoCreateDevice(DeviceObject->DriverObject,                   
                            sizeof(FILTER_DEVICE_EXTENSION), 
                            NULL,                    
                            FILE_DEVICE_UNKNOWN,   
                            0,                     
                            FALSE,                
                            &fltDevice              
                            );

    if (!NT_SUCCESS(status))
        goto CompleteCreateProc;

    fltDevExt = (PFILTER_DEVICE_EXTENSION)fltDevice->DeviceExtension;

    RtlZeroMemory(fltDevice->DeviceExtension, sizeof(FILTER_DEVICE_EXTENSION));

    //
    // 附加到设备栈上,该例程返回位于设备栈顶层的设备对象(KbdClass)指针。
    //
    fltDevExt->LowerDeviceObject = IoAttachDeviceToDeviceStack(fltDevice, kbdcDevice);

    if (fltDevExt->LowerDeviceObject == NULL)
    {
        IoDeleteDevice(fltDevice);
        goto SkipCreateProc;
    }

    fltDevExt->KbmDevExtPointer = KbmDevExt;
    fltDevExt->DeviceID =         index;
    fltDevExt->IsFilterDevice =   TRUE;
    fltDevice->Flags |= (DO_BUFFERED_IO | DO_POWER_PAGABLE);

    KbmDevExt->KbdClassDevice[index] =                      kbdcDevice;
    KbmDevExt->FltDevExtPointer[KbmDevExt->DeviceCounter] = fltDevExt;
    KbmDevExt->DeviceCounter++;

    //
    // 16个已经足够了……
    //
    if (KbmDevExt->DeviceCounter == 16)
        goto CompleteCreateProc;

SkipCreateProc:

    if (kbdcDevice->NextDevice == NULL)
        goto CompleteCreateProc;

    kbdcDevice = kbdcDevice->NextDevice;

EnumNewDevice:

    flag = FALSE;
    for (i = 0 ; i < 16 ; i++)
    {
        if (kbdcDevice == KbmDevExt->KbdClassDevice[i])
        {
            flag = TRUE;
            break;
        }
    }

    if (flag == TRUE)
        goto SkipCreateProc;

    index = -1;
    for (i = 0 ; i < 16 ; i++)
    {
        if (KbmDevExt->KbdClassDevice[i] == NULL)
        {
            index = i;
            break;
        }
    }

    ASSERT(index >= 0);

    goto CreateFidoForPdo;

CompleteCreateProc:

    //
    // 如果没有成功附加到任何物理设备,就返回STATUS_DEVICE_NOT_CONNECTED。
    //
    if ((KbmDevExt->DeviceCounter == 0) && (status == STATUS_SUCCESS))
        status = STATUS_DEVICE_NOT_CONNECTED;

    return (status);
}

VOID
KbFilter_Unload(
   IN PDRIVER_OBJECT DriverObject
   )

{

		return;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -