一.USB HID设备简介
USB HID设备主要用于和计算机进行交互通信,典型的USB HID类设备包括USB键盘、USB鼠标、USB游戏手柄等等,这些都是日常生活中常见的设备。以USB接口的鼠标为例,打开计算机的“设备管理器”,可以在“鼠标和其他指针设备”中找到USBHID接口的鼠标,其名称一般为“HID-Compliantmouse”,如图9.1所示。双击该设备,在打开的“HID-Compliantmouse属性”对话框中查看设备类信息,如图9.2所示。这里显示了当前设备属于Mouse类,也就是鼠标类。
二.配置HID
在内核中,配置USB键盘、鼠标、触摸屏驱动有多种方式,我们采用其中一种即可。
(1) 通用HID驱动程序
如果要使用USB接口的keyboards(键盘)、mice(鼠标)、joysticks(摇杆)、graphic tablets(绘图板)等其他的HID设备,那么就需要配置USB HID Transport layer(USB人机接口设备传输层)。
USB HID transport layer此选项对应配置项就是CONFIG_USB_HID,也就是通用HID驱动程序。
Device Drivers --->HID support --->[*] HID bus support-*- HID bus core support<*> Generic HID driverUSB HID support ---><*> USB HID transport layer[*] PID device support[*] /dev/hiddev raw HID device support
USB HID Transport Layer是USB协议栈中的一个组件,用于支持 HID类型的设备与计算机之间的通信。USB HID传输层负责解析来自HID设备的数据,并将其转换为适当的格式,以便应用程序可以理解和使用。
通用HID驱动程序在内核源码的/kernel-5.10/drivers/hid/usbhid目录下。
三.HID设备调试
lsubs:
插入usb hid设备后,新生成的pid vid 093a:2510。
ls /dev/hid*会发现新生成的hid设备的dev节点。
console:/ # ls /dev/hid*
/dev/hidraw0
ls /dev/input/event* 发现新生成/dev/input/event2。
cat /dev/input/event2会收到设备发送过来的数据。
在终端cat出现的是乱码,因为终端的数据格式不一样,没有解析好usb hid设备发过来的数据,但是可以看到乱码就说明有数据发送过来。
通过usbmon抓取usb hid设备数据包
在menuconfig中选取:
确认内核支持usbmon模块:
ls /sys/module/usbmon
这个我使用的是android13的GKI版本,选择后还是不支持usbmon,后续研究。
代码实现读取usbhid设备触摸框的版本号:
#define HID_DEV_PATH "/dev/hidraw"
#define TOUCH_F_VID (0x093a)
#define TOUCH_F_PID (0x2510)static IMW_U8 usb_version[64] = {0};int nRet = -1;
int nIndex = 0;
int nCount = 0;
int nHidDevHandle = -1;
int ret = 0;
IMW_U8 ist[64]={0xa1,0x55,0xc1,0x01};char devPath[HID_PATH_SIZE];
struct hidraw_devinfo info;for(nIndex = 0; nIndex < HID_PATH_COUNT; nIndex++)
{memset(devPath,0x00,sizeof(devPath));memset(&info,0x00,sizeof(info));snprintf(devPath, sizeof(devPath), "%s%d", HID_DEV_PATH, nIndex);nHidDevHandle = open(devPath , O_RDWR);if(nHidDevHandle < 0){close(nHidDevHandle);continue;}nRet = ioctl(nHidDevHandle, HIDIOCGRAWINFO , &info);if(nRet < 0){close(nHidDevHandle);continue;}if(TOUCH_F_VID == info.vendor && TOUCH_F_PID == (info.product & 0xFFFF) && (nCount < 2)){if(usb_version[0] != 0x00){return -1;}if (nHidDevHandle > 0) {ret = write(nHidDevHandle,ist,64);if(ret > 0){IMW_U8 buf[64];nret = read(nHidDevHandle, buf, 64);if(nret > 0){if(buf[0] == 0xa1 && buf[1] == 0x55 && buf[2] == 0xc1 && buf[3] == 0x01){memcpy(usb_version,&buf[0],BUFF_MAX);}}}}else{return -1;}}
}