HID复合设备(键盘、鼠标)的实现
在使用一些USB键盘或鼠标的时候,特别是一些电竟高档HID设备时,经常发现这些设备会额外定义一些特别的快捷键,使得这些设备不仅有基础设备(如键盘,鼠标)的功能,也有一些特别的快捷功能(如系统声音的放大放小)。甚至更有一些复杂的设备,只需要一个USB接口,就同时支持鼠标键盘功能或在键盘的额外区域支持触模板功能。对于这种复杂的HID设备,是怎么实现的呢?这里有两种方法:
- 第一种方法是使用多个接口多个报表描述符来实现。
- 第二种方法是使用一个接口一个报表描述符实现,这个报表描述符中包括多个应用功能集合。
我们知道,对于USB设设接口描述符的定义,其实就是设备的功能。一个普通的USB设备一般有几个接口描述符,它就有几个功能。不同的接口对应着不同的接口描述符。对于HID设备,这个接口中描述符也有一个与之对应的报表描述符。这样我们可以在一个USB设备中实现多个接口,每个接口对应的报表描述符实现不同的HID设备功能,如对于这些报表描述符实现与之对应的键盘功能,鼠标功能,触摸屏功功能。通过这种方法实现的设备在windows中的设备管理器中的硬件ID会到MI处。如对于PID,VID分别为0x1234,0x5678,bcdDevice为0xabcd的USB设备,,供如接口0实现键盘功能,接口1实现鼠标功能。那么这些特定的HID设备对应的硬件设备树如下:
- USB通用驱动usbccgp.sys(USB\VID_1234&PID_5678&REV_ABCD)
- USB 输入设备 (USB\VID_1234&PID_5678&REV_ABCD&MI_00)
- USB键盘(HID\VID_1234&PID_5678&REV_ABCD&MI_00)
- USB 输入设备 (USB\VID_1234&PID_5678&REV_ABCD&MI_01)
- USB鼠标(HID\VID_1234&PID_5678&REV_ABCD&MI_01)
- USB 输入设备 (USB\VID_1234&PID_5678&REV_ABCD&MI_00)
第一种的方式比较和普通的USB HID设备类似,只是多了一套接口描述符和HID报表描述符而已。关于接口描述符与HID报表描述符之间枚举的对应关系可见本站文章 USB复合HID设备报告描述符的区分 http://www.usbzh.com/article/detail-381.html
第二种方法是使用一个报表描述符包含多个应用集合实现。这样在windows系统中枚举出来的设备硬件设备树关系如下:
- USB 输入设备 (USB\VID_1234&PID_5678&REV_ABCD)
- USB鼠标(HID\VID_1234&PID_5678&REV_ABCD&Col_00)
- USB键盘(HID\VID_1234&PID_5678&REV_ABCD&Col_01)
其对应的报表描述符结构构如下:
05 01 //USAGE_PAGE (Generic Desktop)
09 02 //USAGE (MOUSE)
a1 01 //COLLECTION (Application)
85 01 //REPORTID 01
...
0xc0 //END_COLLECTION
05 01 //USAGE_PAGE (Generic Desktop)
09 06 //USAGE (Keyboard)
a1 01 //COLLECTION (Application)
85 02 //REPORTID 02
...
0xc0 //END_COLLECTION
这里需要使用ReportId来区分数据来源。