培训
模块
通过使用 Power Automate 桌面版模拟鼠标和键盘操作 - Training
了解如何在 Power Automate 中自动模拟鼠标移动、单击、键入和按键。 此外,还将了解如何在屏幕上选择和定位图像或区域。
本文讨论键盘和鼠标 HID 客户端驱动程序。 键盘和鼠标表示在 HID 使用情况表中标准化并在 Windows 操作系统中实现的第一组 HID 客户端。
键盘和鼠标 HID 客户端驱动程序以 HID 映射器驱动程序的形式实现。 HID 映射器驱动程序是内核模式 WDM 筛选器驱动程序,它为非 HID 类驱动程序和 HID 类驱动程序之间的 I/O 请求提供双向接口。 映射器驱动程序将一个请求和数据协议映射到另一个请求和数据协议。
Windows 为 HID 键盘和 HID 鼠标设备提供系统提供的 HID 映射器驱动程序。
下图演示了 USB 键盘、鼠标和触摸板设备的系统提供的驱动程序堆栈。
下图显示了以下组件:
系统生成驱动程序堆栈,如下所示:
Microsoft为编写驱动程序的 IHV 提供本指南:
允许驱动程序开发人员以筛选器驱动程序或新的 HID 客户端驱动程序的形式添加更多驱动程序。
筛选器驱动程序:驱动程序开发人员应确保其增值驱动程序是筛选器驱动程序,不会替换(或代替)输入堆栈中的现有 Windows HID 驱动程序。
函数驱动程序:或者供应商可以创建函数驱动程序(而不是筛选器驱动程序),但仅适用于供应商特定的 HID PDO(必要时使用用户模式服务)。
在这些方案中允许函数驱动程序:
传输驱动程序:Windows 团队不建议创建更复杂的 HID 传输微型驱动程序来编写和维护。 如果合作伙伴正在创建新的 HID 传输微型驱动程序,尤其是在 SoC 系统上,我们建议进行详细的体系结构评审,以了解推理并确保正确开发驱动程序。
驱动程序开发人员应使用驱动程序框架(KMDF 或 UMDF),而不依赖 WDM 来获取筛选器驱动程序。
驱动程序开发人员应减少其服务与驱动程序堆栈之间的内核用户转换数。
驱动程序开发人员应确保能够通过键盘和触摸板功能(最终用户(设备管理器)或电脑制造商调整)唤醒系统。 此外,在 SoC 系统上,这些设备必须能够在系统处于工作 S0 状态时从低功率状态唤醒自己。
驱动程序开发人员应确保其硬件高效管理。
键盘布局完全描述了Microsoft Windows 2000 及更高版本的键盘输入特征。 例如,键盘布局指定语言、键盘类型和版本、修饰符、扫描代码等。
有关键盘布局的信息,请参阅以下资源:
Windows 驱动程序开发工具包 (DDK)中的键盘头文件 kdb.h,其中记录了有关键盘布局的一般信息。
示例键盘 布局。
若要可视化特定键盘的布局,请参阅 Windows 键盘布局。
有关键盘布局的更多详细信息,请访问 控制面板\Clock、Language 和 Region\Language。
下表标识了 Windows 操作系统的不同客户端版本支持的功能。
功能 | Windows XP | Windows Vista | Windows 7 | Windows 8 及更高版本 |
---|---|---|---|---|
按钮 1-5 | 支持 (P/2 和 HID) | 支持 (PS/2 和 HID) | 支持 (PS/2 和 HID) | 支持 (PS/2 和 HID) |
垂直滚轮 | 支持 (PS/2 和 HID) | 支持 (PS/2 和 HID) | 支持 (PS/2 和 HID) | 支持 (PS/2 和 HID) |
水平滚轮 | 不支持 | 支持(仅 HID) | 支持(仅 HID) | 支持(仅 HID) |
平滑滚轮支持(水平和垂直) | 不支持 | 部分支持 | 支持 (仅 HID) | 支持 (仅 HID) |
Windows 用于激活新的四个和五个按钮和滚轮模式的方法是用于激活 IntelliMouse 兼容鼠标中的第三个按钮和滚轮的方法的扩展:
通过将报表速率设置为每秒 200 个报表,然后将鼠标设置为三个按钮滚轮模式,然后将每秒 100 个报表设置为 80 个报表。 然后,从鼠标读取 ID。 完成此序列后,鼠标应报告 ID 为 3。
然后将鼠标设置为五个按钮滚轮模式,方法是将报表速率设置为每秒 200 个报表,然后再次设置为每秒 200 个报表,再设置为每秒 80 个报表。 然后,从鼠标读取 ID。 完成序列后,五按钮滚轮鼠标应报告 ID 为 4(而 IntelliMouse 兼容的三按钮滚轮鼠标仍报告 ID 为 3)。
此方法仅适用于 PS/2 老鼠,不适用于 HID 老鼠。 HID 鼠标必须在报表描述符中报告准确的使用情况。
Byte | D7 | D6 | D5 | D4 | D3 | D2 | D1 | D0 | 注释 |
---|---|---|---|---|---|---|---|---|---|
1 | Yover | Xover | Ysign | Xsign | 标记 | M | R | L | X/Y 溢出和标志、按钮 |
2 | X7 | X6 | X5 | X4 | X3 | X2 | X1 | X0 | X 数据字节 |
3 | Y7 | Y6 | Y5 | Y4 | Y3 | Y2 | 是1 | Y0 | Y 数据字节 |
备注
Windows 鼠标驱动程序不检查溢出位。 如果溢出,鼠标应只发送最大有符号排量值。
Byte | D7 | D6 | D5 | D4 | D3 | D2 | D1 | D0 | 注释 |
---|---|---|---|---|---|---|---|---|---|
1 | 0 | 0 | Ysign | Xsign | 1 | M | R | L | X/Y 符号和 R/L/M 按钮 |
2 | X7 | X6 | X5 | X4 | X3 | X2 | X1 | X0 | X 数据字节 |
3 | Y7 | Y6 | Y5 | Y4 | Y3 | Y2 | 是1 | Y0 | Y 数据字节 |
4 | Z7 | Z6 | Z5 | Z4 | Z3 | Z2 | Z1 | Z0 | Z/wheel 数据字节 |
Byte | D7 | D6 | D5 | D4 | D3 | D2 | D1 | D0 | 注释 |
---|---|---|---|---|---|---|---|---|---|
1 | 0 | 0 | Ysign | Xsign | 1 | M | R | L | X/Y 符号和 R/L/M 按钮 |
2 | X7 | X6 | X5 | X4 | X3 | X2 | X1 | X0 | X 数据字节 |
3 | Y7 | Y6 | Y5 | Y4 | Y3 | Y2 | 是1 | Y0 | Y 数据字节 |
4 | 0 | 0 | B5 | B4 | Z3 | Z2 | Z1 | Z0 | Z/wheel 数据和按钮 4 和 5 |
重要
请注意,五按钮滚轮鼠标的 Z/wheel 数据已减少到四位,而不是 IntelliMouse 兼容的三按钮滚轮模式中使用的 8 位。 这种减少是可以实现的,因为轮通常不能在任何给定中断期间产生超出范围 +7/-8 的值。 当鼠标处于五按钮滚轮模式时,Windows 鼠标驱动程序将签署扩展四个 Z/wheel 数据位,当鼠标在三按钮滚轮模式下操作时,完整的 Z/wheel 数据字节。
按钮 4 和 5 映射到WM_APPCOMMAND消息,对应于App_Back和App_Forward。
以下设备不需要供应商驱动程序:
Kbfiltr 用于 Kbdclass、键盘设备的系统类驱动程序和 I8042prt(PS/2 样式键盘的函数驱动程序)。 Kbfiltr 演示如何筛选 I/O 请求以及如何添加修改 Kbdclass 和 I8042prt 操作的回调例程。
有关 Kbfiltr 操作的详细信息,请参阅:
Kbfiltr 使用以下 IOCTL。
IOCTL_INTERNAL_I8042_HOOK_KEYBOARD请求:
初始化和 ISR 回调是可选的,由 PS/2 样式键盘设备的高级筛选器驱动程序提供。
I8042prt 收到 IOCTL_INTERNAL_KEYBOARD_CONNECT 请求后,它会向键盘设备堆栈顶部发送同步 IOCTL_INTERNAL_I8042_HOOK_KEYBOARD 请求。
Kbfiltr 收到挂钩键盘请求后,Kbfiltr 将按以下方式筛选请求:
IOCTL_INTERNAL_KEYBOARD_CONNECT请求将 Kbdclass 服务连接到键盘设备。 Kbdclass 在打开键盘设备之前,将此请求发送到键盘设备堆栈。
Kbfiltr 收到键盘连接请求后,Kbfiltr 将按以下方式筛选连接请求:
如果请求未成功,Kbfiltr 会以适当的错误状态完成请求。
Kbfiltr 为筛选器服务回调例程提供了一个模板,该例程可以补充 KeyboardClassServiceCallback(Kbdclass 类服务回调例程)的操作。 筛选器服务回调可以筛选从设备输入缓冲区传输到类数据队列的输入数据。
IOCTL_INTERNAL_KEYBOARD_DISCONNECT请求已完成,状态为STATUS_NOT_IMPLEMENTED。 即插即用管理器可以添加或删除即插即用键盘。
对于所有其他设备控制请求,Kbfiltr 会跳过当前的 IRP 堆栈,并在设备堆栈中发送请求,而无需进一步处理。
Kbfiltr 实现以下回调例程。
请参阅 PI8042_KEYBOARD_INITIALIZATION_ROUTINE
如果键盘的 I8042prt 默认初始化已足够,则不需要KbFilter_InitializationRoutine。
初始化键盘时,I8042prt 调用KbFilter_InitializationRoutine 。 默认键盘初始化包括以下操作:
/*
Parameters
DeviceObject [in]
Pointer to the device object that is the context for this callback.
SynchFuncContext [in]
Pointer to the context for the routines pointed to by ReadPort and Writeport.
ReadPort [in]
Pointer to the system-supplied PI8042_SYNCH_READ_PORT callback that reads from the port.
WritePort [in]
Pointer to the system-supplied PI8042_SYNCH_WRITE_PORT callback that writes to the port.
TurnTranslationOn [out]
Specifies, if TRUE, to turn translation on. Otherwise, translation is turned off.
Return value
KbFilter_InitializationRoutine returns an appropriate NTSTATUS code.
*/
NTSTATUS KbFilter_InitializationRoutine(
In PDEVICE_OBJECT DeviceObject,
In PVOID SynchFuncContext,
In PI8042_SYNCH_READ_PORT ReadPort,
In PI8042_SYNCH_WRITE_PORT WritePort,
Out PBOOLEAN TurnTranslationOn
);
请参阅 PI8042_KEYBOARD_ISR。 如果 I8042prt 的默认操作足够,则不需要此回调。
I8042prt 键盘 ISR 在验证中断并读取扫描代码后调用KbFilter_IsrHook 。
KbFilter_IsrHook在 I8042prt 键盘的 IRQL 的内核模式下运行。
/*
Parameters
DeviceObject [in]
Pointer to the filter device object of the driver that supplies this callback.
CurrentInput [in]
Pointer to the input KEYBOARD_INPUT_DATA structure that is being constructed by the ISR.
CurrentOutput [in]
Pointer to an OUTPUT_PACKET structure that specifies the bytes that are being written to the hardware device.
StatusByte [in, out]
Specifies the status byte that is read from I/O port 60 when an interrupt occurs.
DataByte [in]
Specifies the data byte that is read from I/O port 64 when an interrupt occurs.
ContinueProcessing [out]
Specifies, if TRUE, to continue processing in the I8042prt keyboard ISR after this callback returns; otherwise, processing is not continued.
ScanState [in]
Pointer to a KEYBOARD_SCAN_STATE structure that specifies the keyboard scan state.
Return value
KbFilter_IsrHook returns TRUE if the interrupt service routine should continue; otherwise it returns FALSE.
*/
KbFilter_IsrHook KbFilter_IsrHook(
In PDEVICE_OBJECT DeviceObject,
In PKEYBOARD_INPUT_DATA CurrentInput,
In POUTPUT_PACKET CurrentOutput,
Inout UCHAR StatusByte,
In PUCHAR DataByte,
Out PBOOLEAN ContinueProcessing,
In PKEYBOARD_SCAN_STATE ScanState
);
请参阅 PSERVICE_CALLBACK_ROUTINE。
函数驱动程序 调用的 ISR 调度完成例程KbFilter_ServiceCallback,然后调用键盘类驱动程序的 PSERVICE_CALLBACK_ROUTINE实现。 供应商可以实现筛选器服务回调,以修改从设备的输入缓冲区传输到类数据队列的输入数据。 例如,回调可以删除、转换或插入数据。
/*
Parameters
DeviceObject [in]
Pointer to the class device object.
InputDataStart [in]
Pointer to the first keyboard input data packet in the input data buffer of the port device.
InputDataEnd [in]
Pointer to the keyboard input data packet that immediately follows the last data packet in the input data buffer of the port device.
InputDataConsumed [in, out]
Pointer to the number of keyboard input data packets that are transferred by the routine.
Return value
None
*/
VOID KbFilter_ServiceCallback(
In PDEVICE_OBJECT DeviceObject,
In PKEYBOARD_INPUT_DATA InputDataStart,
In PKEYBOARD_INPUT_DATA InputDataEnd,
Inout PULONG InputDataConsumed
);
Moufiltr 与 Mouclass 一起使用,这是用于 Windows 2000 及更高版本的鼠标设备的系统类驱动程序,I8042prt 是用于 Windows 2000 及更高版本的 PS/2 样式鼠标的函数驱动程序。 Moufiltr 演示如何筛选 I/O 请求并添加修改 Mouclass 和 I8042prt 操作的回调例程。
有关 Moufiltr 操作的详细信息,请参阅以下资源:
Moufiltr 使用以下 IOCTL。
IOCTL_INTERNAL_I8042_HOOK_MOUSE请求将 ISR 回调例程添加到 I8042prt 鼠标 ISR。 ISR 回调是可选的,由高级鼠标筛选器驱动程序提供。
I8042prt 在收到 IOCTL_INTERNAL_MOUSE_CONNECT 请求后发送此请求。 I8042prt 向鼠标设备堆栈顶部发送同步 IOCTL_INTERNAL_I8042_HOOK_MOUSE 请求。
在 Moufiltr 收到挂钩鼠标请求后,它会按以下方式筛选请求:
IOCTL_INTERNAL_MOUSE_CONNECT请求将 Mouclass 服务连接到鼠标设备。
Moufiltr 完成IOCTL_INTERNAL_MOUSE_DISCONNECT请求,错误状态为STATUS_NOT_IMPLEMENTED。
对于所有其他请求,Moufiltr 会跳过当前的 IRP 堆栈,并在不进一步处理的情况下将请求发送到设备堆栈。
MouFiltr 实现以下回调例程。
请参阅 PI8042_MOUSE_ISR。
/*
Parameters
DeviceObject
Pointer to the filter device object of the driver that supplies this callback.
CurrentInput
Pointer to the input MOUSE_INPUT_DATA structure being constructed by the ISR.
CurrentOutput
Pointer to the OUTPUT_PACKET structure that specifies the bytes being written to the hardware device.
StatusByte
Specifies a status byte that is read from I/O port 60 when the interrupt occurs.
DataByte
Specifies a data byte that is read from I/O port 64 when the interrupt occurs.
ContinueProcessing
Specifies, if TRUE, that the I8042prt mouse ISR continues processing after this callback returns. Otherwise, processing is not continued.
MouseState
Pointer to a MOUSE_STATE enumeration value, which identifies the state of mouse input.
ResetSubState
Pointer to MOUSE_RESET_SUBSTATE enumeration value, which identifies the mouse reset substate. See the Remarks section.
Return value
MouFilter_IsrHook returns TRUE if the interrupt service routine should continue; otherwise it returns FALSE.
*/
BOOLEAN MouFilter_IsrHook(
PDEVICE_OBJECT DeviceObject,
PMOUSE_INPUT_DATA CurrentInput,
POUTPUT_PACKET CurrentOutput,
UCHAR StatusByte,
PUCHAR DataByte,
PBOOLEAN ContinueProcessing,
PMOUSE_STATE MouseState,
PMOUSE_RESET_SUBSTATE ResetSubState
);
如果 I8042prt 的默认操作足够,则不需要MouFilter_IsrHook回调。
I8042prt 鼠标 ISR 在验证中断后调用MouFilter_IsrHook 。
若要重置鼠标,I8042prt 会经历一系列操作子状态。 MOUSE_RESET_SUBSTATE枚举值标识每个子州。 有关如何 I8042prt 重置鼠标和相应的鼠标重置子状态的详细信息,请参阅 ntdd8042.h 中MOUSE_RESET_SUBSTATE的文档。
MouFilter_IsrHook在 I8042prt 鼠标 ISR 的 IRQL 的内核模式下运行。
请参阅 PSERVICE_CALLBACK_ROUTINE
/*
Parameters
DeviceObject [in]
Pointer to the class device object.
InputDataStart [in]
Pointer to the first mouse input data packet in the input data buffer of the port device.
InputDataEnd [in]
Pointer to the mouse input data packet immediately following the last data packet in the port device's input data buffer.
InputDataConsumed [in, out]
Pointer to the number of mouse input data packets that are transferred by the routine.
Return value
None
*/
VOID MouFilter_ServiceCallback(
_In_ PDEVICE_OBJECT DeviceObject,
_In_ PMOUSE_INPUT_DATA InputDataStart,
_In_ PMOUSE_INPUT_DATA InputDataEnd,
_Inout_ PULONG InputDataConsumed
);
I8042prt 的 ISR DPC 调用MouFilter_ServiceCallback,然后调用 MouseClassServiceCallback。 可以将筛选器服务回调配置为修改从设备的输入缓冲区传输到类数据队列的输入数据。 例如,回调可以删除、转换或插入数据。
培训
模块
通过使用 Power Automate 桌面版模拟鼠标和键盘操作 - Training
了解如何在 Power Automate 中自动模拟鼠标移动、单击、键入和按键。 此外,还将了解如何在屏幕上选择和定位图像或区域。
文档
传感器 HID 类驱动程序 - Windows drivers
Windows 操作系统包括内置传感器 HID 类驱动程序 (SensorsHIDClassDriver.dll) 。
如果系统提供的 HID 微型驱动程序不支持设备的端口或总线,则需要供应商提供的微型驱动程序。
顶级集合的 HIDClass 硬件 ID - Windows drivers
本部分指定 HID 类驱动程序为顶级集合生成的硬件 ID。
PSERVICE_CALLBACK_ROUTINE (kbdmou.h) - Windows drivers
函数驱动程序在其 ISR 调度完成例程中调用类服务回调。 类服务回调将输入数据从设备的输入数据缓冲区传输到类数据队列。