最近在看 Linux Kernel module: hid-multitouch 的問題,在這裡將相關用到的 debug 技巧紀錄下來。
(內容會有點零亂不全,畢竟相關資料小弟沒看幾天)
USB 裝置連線問題
舉凡 USB 插上後沒預期反應可先確認裝置是否有被 USB Hub 偵測到,可用 lsusb 或 dmesg 查看 log。如下
$ dmesg | tail [ 1589.450251] usb 2-1.2: new full-speed USB device number 5 using ehci_hcd [ 1589.547043] input: Logitech USB Receiver as /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.0/input/input14 [ 1589.547234] generic-usb 0003:046D:C52E.0009: input,hidraw1: USB HID v1.11 Keyboard [Logitech USB Receiver] on usb-0000:00:1d.0-1.2/input0 [ 1589.549531] input: Logitech USB Receiver as /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.2/2-1.2:1.1/input/input15 [ 1589.549852] generic-usb 0003:046D:C52E.000A: input,hiddev0,hidraw2: USB HID v1.11 Mouse [Logitech USB Receiver] on usb-0000:00:1d.0-1.2/input1
看起來有被偵測到。再用 lsusb 看一下 USB 列表,有時會再下 -vv 看一些 USB 的參數,像 USB 3.0 or 2.1(參數 bcdUSB)。
$ lsusb Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub Bus 002 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub Bus 001 Device 002: ID 8087:0024 Intel Corp. Integrated Rate Matching Hub Bus 002 Device 002: ID 8087:0024 Intel Corp. Integrated Rate Matching Hub Bus 001 Device 003: ID 0a5c:21d7 Broadcom Corp. Bus 001 Device 006: ID 2149:2003 Bus 001 Device 005: ID 0c45:649c Microdia Bus 002 Device 005: ID 046d:c52e Logitech, Inc.
USB 封包監聽
如果很不幸的,問題是發生在 driver/kernel 或更底層的問題,以及大大們有能力弄懂 USB protocol 的話,可以用 wireshark and usbmon 來監聽 USB traffic。安裝/打開 wireshark 之前,要先做一些前置動作
$ # 掛 usbmon $ sudo modprobe usbmomn $ # 掛 debugfs, 如果已掛上了就不用做 $ mount -t debugfs / /sys/kernel/debug
接著打開 wireshark,就會看到多了幾個可監聽的 USB hubs 可以選,如第一張圖。
driver 沒上(熱插拔)
請先自己想辦法找到對應的 driver,再手動 insmod 即可。要找的方法很多,而且因裝置而異,我這裡就不提了。
通常最常遇到的只是 driver 內沒包含裝置的 vendor and product ID,可以先用 sysfs 內的 new_id 來先做測試,如下
$ # 先把 driver 掛上 $ sudo modprobe hid-multitouch $ # 接著用 lsusb 確認 vendor and product id Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub Bus 002 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub Bus 001 Device 002: ID 8087:0024 Intel Corp. Integrated Rate Matching Hub Bus 002 Device 002: ID 8087:0024 Intel Corp. Integrated Rate Matching Hub Bus 001 Device 003: ID 0a5c:21d7 Broadcom Corp. Bus 001 Device 006: ID 2149:2003 Bus 001 Device 005: ID 0c45:649c Microdia Bus 002 Device 005: ID 046d:c52e Logitech, Inc. $ # 看到了觸控裝置 2149:2003 $ echo 2149 2003 > /sys/module/hid_multitouch/drivers/hid\:hid-multitouch/new_id
到這裡這隻 driver 應該就起作用了。緊接著,若想以後能自動插入 driver 可修改 udev 的 rules,如下:
$ cat /etc/udev/rules.d/41-hid-multitouch.rules SUBSYSTEM=="usb", ATTRS{idVendor}=="2149", ATTRS{idProduct}=="2003", RUN+="/bin/sh /etc/udev/load_hid_multitouch.sh $env{ID_VENDOR_ID} $env{ID_MODEL_ID}"
input event 監聽
若是 driver 掛上了,行為有點不如預期,可能是有些 input event 會自動消失或是不準的,可以用 evtest 來監看所有的 input event。
$ sudo evtest /dev/input/event11 Input driver version is 1.0.1 Input device ID: bus 0x3 vendor 0x2149 product 0x2003 version 0x110 Input device name: "Advanced Silicon S.A. CoolTouch(TM) System" Supported events: Event type 0 (EV_SYN) Event type 1 (EV_KEY) Event code 330 (BTN_TOUCH) Event type 3 (EV_ABS) Event code 0 (ABS_X) Value 9104 Min 0 Max 32767 Event code 1 (ABS_Y) Value 18364 Min 0 Max 32767 Event code 47 (ABS_MT_SLOT) Value 0 Min 0 Max 9 Event code 53 (ABS_MT_POSITION_X) Value 0 Min 0 Max 32767 Event code 54 (ABS_MT_POSITION_Y) Value 0 Min 0 Max 32767 Event code 57 (ABS_MT_TRACKING_ID) Value 0 Min 0 Max 65535 Testing ... (interrupt to exit) Event: time 1367477844.348301, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value 50 Event: time 1367477844.348303, type 3 (EV_ABS), code 53 (ABS_MT_POSITION_X), value 9655 Event: time 1367477844.348303, type 3 (EV_ABS), code 54 (ABS_MT_POSITION_Y), value 10190 Event: time 1367477844.348313, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 1 Event: time 1367477844.348315, type 3 (EV_ABS), code 0 (ABS_X), value 9655 Event: time 1367477844.348315, type 3 (EV_ABS), code 1 (ABS_Y), value 10190 Event: time 1367477844.348316, -------------- SYN_REPORT ------------ Event: time 1367477844.493292, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value -1 Event: time 1367477844.493301, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 0 Event: time 1367477844.493302, -------------- SYN_REPORT ------------
最後的問題有可能是出現在 driver or application,這就看自己的造化了。小弟我遇到的問題是都有,還好 upstream 都解了。最後提一下,在看 driver 前除了有基本的知識外,舉例來說在解 USB HID multitouch driver 時,最好可以從 USB protocol 到 hid-multitouch 都有基本的了解,USB protocol 網上資料一堆,hid-multitouch 則看 kernel 裡的 Documentation/input/multi-touch-protocol.txt 即可。
(唉,解 bug 花的時間沒寫文章的多)
Reference
- USB HID information, http://www.usb.org/developers/hidpage/
- HID Usage Tables, http://www.usb.org/developers/devclass_docs/Hut1_12v2.pdf
- Wireshark USB capture setup, http://wiki.wireshark.org/CaptureSetup/USB
No comments:
Post a Comment