虚拟鼠标驱动的实现

news/2024/11/7 10:37:57/

虚拟鼠标驱动的实现
好久以前的东西了,发出来给感兴趣的朋友参考一下。
虚拟鼠标驱动就是通过驱动虚拟一个mouse,然后通过上层应用程序控制其发码,可以模拟硬件级的发码。
下面来看一下代码,主要的函数如下:
NTSTATUS
DriverEntry (
    IN  PDRIVER_OBJECT  DriverObject,
    IN  PUNICODE_STRING RegistryPath
    )
/*++
Routine Description:

    Initialize the entry points of the driver.

--*/
{
    ULONG i;

   
 NTSTATUS status = STATUS_SUCCESS;
 UNICODE_STRING      deviceLinkUnicodeString;
 UNICODE_STRING         deviceNameUnicodeString;
 RtlInitUnicodeString(&deviceNameUnicodeString, L"//Device//VMouse");
 
 UNREFERENCED_PARAMETER (RegistryPath);
 status = IoCreateDevice(DriverObject, 0,
  &deviceNameUnicodeString,FILE_DEVICE_UNKNOWN,
  0, FALSE, &g_DeviceObject);
 
 if (!NT_SUCCESS(status))
 {
  return status;
 }
 
 
 RtlInitUnicodeString(&deviceLinkUnicodeString, L"//DosDevices//VMouse");
 status = IoCreateSymbolicLink(&deviceLinkUnicodeString, &deviceNameUnicodeString);
 if (!NT_SUCCESS(status))
 {
  if (g_DeviceObject)
  {
   IoDeleteDevice(g_DeviceObject);
   return status;
  }
 }
 g_DeviceObject->Flags |= DO_BUFFERED_IO|DO_POWER_PAGABLE;
 g_DeviceObject->Flags &= ~DO_DEVICE_INITIALIZING;
    //
    // Fill in all the dispatch entry points with the pass through function
    // and the explicitly fill in the functions we are going to intercept
    //
//     for (i = 0; i <= IRP_MJ_MAXIMUM_FUNCTION; i++) {
//         DriverObject->MajorFunction[i] = MouFilter_DispatchPassThrough;
//     }

    DriverObject->MajorFunction [IRP_MJ_CREATE] =
    DriverObject->MajorFunction [IRP_MJ_CLOSE] =        MouFilter_CreateClose;
    DriverObject->MajorFunction [IRP_MJ_PNP] =          MouFilter_PnP;
    DriverObject->MajorFunction [IRP_MJ_POWER] =        MouFilter_Power;
    DriverObject->MajorFunction [IRP_MJ_INTERNAL_DEVICE_CONTROL] =
                                                        MouFilter_InternIoCtl;
 DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL         ] = DeviceControl;
    //
    // If you are planning on using this function, you must create another
    // device object to send the requests to.  Please see the considerations
    // comments for MouFilter_DispatchPassThrough for implementation details.
    //
    // DriverObject->MajorFunction [IRP_MJ_DEVICE_CONTROL];

    DriverObject->DriverUnload = MouFilter_Unload;
    DriverObject->DriverExtension->AddDevice = MouFilter_AddDevice;

    return STATUS_SUCCESS;
}
虚拟鼠标最主要的就是下面的部分,告诉OS你的设备属性:
NTSTATUS
MouFilter_InternIoCtl(
    __in PDEVICE_OBJECT DeviceObject,
    __in PIRP Irp
    )
/*++

Routine Description:

    This routine is the dispatch routine for internal device control requests.
    There are two specific control codes that are of interest:
   
    IOCTL_INTERNAL_MOUSE_CONNECT:
        Store the old context and function pointer and replace it with our own.
        This makes life much simpler than intercepting IRPs sent by the RIT and
        modifying them on the way back up.
                                     
    IOCTL_INTERNAL_I8042_HOOK_MOUSE:
        Add in the necessary function pointers and context values so that we can
        alter how the ps/2 MOUSE is initialized. 
                                           
    NOTE:  Handling IOCTL_INTERNAL_I8042_HOOK_MOUSE is *NOT* necessary if
           all you want to do is filter MOUSE_INPUT_DATAs.  You can remove
           the handling code and all related device extension fields and
           functions to conserve space.
                                        
Arguments:

    DeviceObject - Pointer to the device object.

    Irp - Pointer to the request packet.

Return Value:

    Status is returned.

--*/
{
    /*省略*/
    case IOCTL_MOUSE_QUERY_ATTRIBUTES:
  if(irpStack->Parameters.DeviceIoControl.InputBufferLength>=sizeof(MOUSE_UNIT_ID_PARAMETER))
  {
   
   
  }
  
  
  if (irpStack->Parameters.DeviceIoControl.OutputBufferLength <sizeof(MOUSE_ATTRIBUTES))
  {
   Irp->IoStatus.Status = STATUS_BUFFER_TOO_SMALL;
   Irp->IoStatus.Information = 0;
   IoCompleteRequest(Irp,IO_NO_INCREMENT);
   return status;
  }
  else
  {
   PMOUSE_ATTRIBUTES pka = (PMOUSE_ATTRIBUTES) Irp->AssociatedIrp.SystemBuffer ;
   pka->MouseIdentifier=WHEELMOUSE_HID_HARDWARE;
   pka->NumberOfButtons=3;
   pka->SampleRate=100;
   pka->InputDataQueueLength=256;
            Irp->IoStatus.Status = STATUS_SUCCESS;
   Irp->IoStatus.Information = sizeof(MOUSE_ATTRIBUTES);
   IoCompleteRequest(Irp,IO_NO_INCREMENT);
   
   return status;
   break;
  }
        break;
 }

 

    IoSkipCurrentIrpStackLocation(Irp);
 return IoCallDriver( devExt->TopOfStack, Irp);
}
和上层通信模拟按键
NTSTATUS DeviceControl(IN PDEVICE_OBJECT DeviceObject,IN PIRP Irp)
{
 PIO_STACK_LOCATION IrpStack = IoGetCurrentIrpStackLocation(Irp);
 
 NTSTATUS status = STATUS_INVALID_DEVICE_REQUEST;
 //ULONG OutputLength   = IrpStack->Parameters.DeviceIoControl.OutputBufferLength;
 PDEVICE_EXTENSION DevExt = (PDEVICE_EXTENSION)DeviceObject->DeviceExtension;
 if(g_DeviceObject != DeviceObject)
 {
  
  IrpStack = IoGetCurrentIrpStackLocation(Irp);
  IoSkipCurrentIrpStackLocation(Irp);
  return IoCallDriver( DevExt->TopOfStack, Irp);
 }

 switch( IrpStack->Parameters.DeviceIoControl.IoControlCode)
 {
 case IOCTL_SENDBUTTON:
  {
   int i;
   ULONG nSend = 0;
   MOUSE_INPUT_DATA Data[10];
   PVMOUSEBUFF Buffer = (PVMOUSEBUFF)Irp->AssociatedIrp.SystemBuffer;
   ULONG InputLength    = IrpStack->Parameters.DeviceIoControl.InputBufferLength;
   if( (Buffer==0) || (InputLength < sizeof(VMOUSEBUFF)) || (Buffer->nCount > 10) )
   {
    status = STATUS_INVALID_PARAMETER;
    break;
   }
   RtlZeroMemory(Data,sizeof(MOUSE_INPUT_DATA)*10);
   for(i =0 ; i< Buffer->nCount ; i++)
   {
    if (Buffer->nBtns[i].Pressed==1)// key down
    {
     Data[i].ButtonFlags = MouseFlag[Buffer->nBtns[i].ButtonNo-1].dwDn;
    }
    else if( !Buffer->nBtns[i].Pressed )//key up
    {
     Data[i].ButtonFlags= MouseFlag[Buffer->nBtns[i].ButtonNo-1].dwUp;
    }
    Data[i].UnitId   = UnitId ;
   
   }
   
   SeviceCallback(MouseDev,Data,&Data[i],&nSend);
   
   
   status = STATUS_SUCCESS;
   break;
  }
 default:
  status = STATUS_INVALID_DEVICE_REQUEST;
 }

  Irp->IoStatus.Status = STATUS_SUCCESS;
  Irp->IoStatus.Information = 0;
  IoCompleteRequest(Irp,IO_NO_INCREMENT);
  return status;

}


http://www.ppmy.cn/news/211212.html

相关文章

USB设备驱动之鼠标

USB设备驱动之鼠标 1. 概述 USB鼠标驱动程序大致分为两大部分&#xff1a;USB设备驱动部分和输入设备驱动部分&#xff0c;USB设备驱动只起了挂接总线和传输数据的作用&#xff0c;而具体的设备类型的驱动仍然是工作的主体。 USB设备驱动部分&#xff1a;负责注册USB设备驱动…

usb键鼠驱动分析

一、鼠标 linux下的usb鼠标驱动在/drivers/hid/usbhid/usbmouse.c中实现 1.加载初始化过程 1.1模块入口 module_init(usb_mouse_init); 1.2初始化函数 static int __init usb_mouse_init(void) //初始化{int retval usb_register(&usb_mouse_driver); //注册usb鼠标…

USB鼠标设备驱动程序简单实现(一)

一、Linux下的USB驱动程序 分离和分层是Linux下驱动程序开发采用的最基本的形式&#xff0c;USB驱动开发在主机端主要涉及两个部分&#xff1a;主机控制器驱动和设备驱动。 主机控制器驱动主要是和具体的Soc相关的&#xff0c;它来识别USB设备&#xff0c;安装对应的设备驱动…

USB鼠标驱动

仿照drivers/hid/usbhid/usbmouse.c系统自带的USB鼠标驱动实现的USB鼠标驱动。 一、usb/usbmouse_as_key.c #include <linux/kernel.h> #include <linux/slab.h> #include <linux/module.h> #include <linux/init.h> #include <linux/usb/input.h…

编写USB鼠标驱动程序,并测试

转载自&#xff1a;https://www.cnblogs.com/lxl-lennie/p/10189188.html 8.1 编写USB鼠标驱动程序&#xff0c;并测试 学习目标&#xff1a;编写USB鼠标驱动程序&#xff0c;并测试&#xff08;将USB鼠标的左键当作L按键,将USB鼠标的右键当作S按键,中键当作回车按键&#x…

USB鼠标驱动开发流程

USB驱动开发&#xff0c;针对某一个USB设备的某个功能&#xff08;接口&#xff09;构建的驱动程序。USB驱动并不直接和USB设备进行数据交互&#xff0c;而是通过USB总线驱动程序&#xff08;USB Core和USB HCD&#xff09;来操作USB设备的。一般构建USB设备驱动的流程为&#…

USB驱动之Android usb鼠标驱动

1. 前言 HID是Human Interface Devices的缩写&#xff0c;翻译成中文即为人机交互设备。这里的人机交互设备是一个宏观上面的概念&#xff0c;任何设备只要符合HID spec都可以称之为HID设备&#xff0c;常见的HID设备有鼠标键盘&#xff0c;游戏操纵杆等等。 usb鼠标在android代…

编写USB鼠标驱动程序

编写USB鼠标驱动程序 文章目录 编写USB鼠标驱动程序参考资料&#xff1a;1. 目标2. 编程2.1 驱动框架2.2 实现usb_driver2.2.1 id_table2.2.2 probe函数 2.3 实现输入设备2.4 实现数据传输 3. 上机实验 致谢 参考资料&#xff1a; Linux内核源码&#xff1a;include\linux\usb.…