Open JoergAtGithub opened 3 years ago
Application level work-around from probe-rs
Also here from Microchip (hard-coded table) https://github.com/microchip-pic-avr-tools/pyedbglib/blob/main/pyedbglib/hidtransport/toolinfo.py
{'pid': USB_TOOL_DEVICE_PRODUCT_ID_JTAGICE3, 'default_report_size': 512},
{'pid': USB_TOOL_DEVICE_PRODUCT_ID_ATMELICE, 'default_report_size': 512},
{'pid': USB_TOOL_DEVICE_PRODUCT_ID_POWERDEBUGGER, 'default_report_size': 512},
{'pid': USB_TOOL_DEVICE_PRODUCT_ID_EDBG_A, 'default_report_size': 512},
{'pid': USB_TOOL_DEVICE_PRODUCT_ID_MSD, 'default_report_size': 512},
Alan Ott mentioned about VRPN application side work-around. I believe it is here (512 Bytest report) https://github.com/vrpn/vrpn/blob/master/vrpn_HumanInterface.C
So yes there are quite some devices with >64 Bytes HID report size. I need to find one of them and check if they still use wMaxPacketSize=64 bytest or if any of them use higher one.
@MCUdude
Hi Hans, would you please do me a favor to dump the USB Prober output of your Atmel-ICE or Power Debuger if you still have them. Thanks.
Something like this:
Or you can post the output from lsusb -vvv
under macOS or Linux. You can install usbutils under macOS Homebrew.
brew install usbutils
And also the outout of hidapi hidtest or mac-hid-dump. https://github.com/todbot/mac-hid-dump
[To be confimred] It seems to me because Windows inbox HID driver most likely does not really support Interrupt IN/OUT Endpoint with wMaxPacketSize greater than 64 bytes, so for the High Speed USB HID device out in the market, the Interrupt IN/OUT Endpoint will still have wMaxPacketSize at 64Bytes.
Can not confirm. I own the laptop with USB touchscreen which input report is greater than 100 bytes. It had Windows 8.0 preinstalled.
[To be confimred] It seems to me because Windows inbox HID driver most likely does not really support Interrupt IN/OUT Endpoint with wMaxPacketSize greater than 64 bytes, so for the High Speed USB HID device out in the market, the Interrupt IN/OUT Endpoint will still have wMaxPacketSize at 64Bytes.
Can not confirm. I own the laptop with USB touchscreen which input report is greater than 100 bytes. It had Windows 8.0 preinstalled.
There are certainly devices with input report size greater than 64 Bytes as mentioned in the above (like 512 Bytes or even 1024 Bytes). However, please check the wMaxPacketSize of the Interupt IN endpoint of your USB touch deviice. I bet it is still 64 Bytes.
wMaxPacketSize is 64 as it is USB 2.0 LowSpeed device
wMaxPacketSize is 64 as it is USB 2.0 LowSpeed device
I think you mean to say USB 2.0 Full Speed Device.
It is good that you have such device, probably you can use it to test the current HIDAPI FreeBSD implementation which use libusb. And if you would like to work on FreeBSD hidraw backend for HIDAPI, it can be useful as a comparison.
[To be confimred --> confirmed to be wrong]
It seems to me because Windows inbox HID driver most likely does not really support Interrupt IN/OUT Endpoint with wMaxPacketSize greater than 64 bytes, so for the High Speed USB HID device out in the market, the Interrupt IN/OUT Endpoint will still have wMaxPacketSize at 64Bytes.
Later version of Windows may or may not have such limitations but the device out in the market have to support older version of Windows.
[/To be confirmed --> confirmed to be wrong]
Hopefully some people will have some High Speed USB HID device to check if their HID interrupt Endpoint have greater than 64 Bytest wMaxPacketSize or not. So far I have only seen High Speed USB HID Devices with their Interrupt Endpoint having only 64 Bytes wMaxPacketSize.
Hi Hans, would you please do me a favor to dump the USB Prober output of your Atmel-ICE or Power Debuger if you still have them. Thanks.
I really need a picture, but this is what I've got:
Bus /dev/usb Device /dev/ugen0.3: ID 03eb:2103 Atmel Corp. JTAG ICE mkII
Device Descriptor:
bLength 18
bDescriptorType 1
bcdUSB 1.10
bDeviceClass 255 Vendor Specific Class
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 16
idVendor 0x03eb Atmel Corp.
idProduct 0x2103 JTAG ICE mkII
bcdDevice 2.00
iManufacturer 1 ATMEL
iProduct 2 JTAGICE mkII
iSerial 3 (redacted)
bNumConfigurations 1
Configuration Descriptor:
bLength 9
bDescriptorType 2
wTotalLength 32
bNumInterfaces 1
bConfigurationValue 1
iConfiguration 0
bmAttributes 0x80
(Bus Powered)
MaxPower 500mA
Interface Descriptor:
bLength 9
bDescriptorType 4
bInterfaceNumber 0
bAlternateSetting 0
bNumEndpoints 2
bInterfaceClass 255 Vendor Specific Class
bInterfaceSubClass 0
bInterfaceProtocol 0
iInterface 0
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x82 EP 2 IN
bmAttributes 2
Transfer Type Bulk
Synch Type None
Usage Type Data
wMaxPacketSize 0x0040 1x 64 bytes
bInterval 10
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x02 EP 2 OUT
bmAttributes 2
Transfer Type Bulk
Synch Type None
Usage Type Data
wMaxPacketSize 0x0040 1x 64 bytes
bInterval 10
Device Status: 0x0001
Self Powered
Bus /dev/usb Device /dev/ugen0.3: ID 03eb:2104 Atmel Corp. AVR ISP mkII
Device Descriptor:
bLength 18
bDescriptorType 1
bcdUSB 1.10
bDeviceClass 255 Vendor Specific Class
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 16
idVendor 0x03eb Atmel Corp.
idProduct 0x2104 AVR ISP mkII
bcdDevice 2.00
iManufacturer 1 ATMEL
iProduct 2 AVRISP mkII
iSerial 3 (redacted)
bNumConfigurations 1
Configuration Descriptor:
bLength 9
bDescriptorType 2
wTotalLength 32
bNumInterfaces 1
bConfigurationValue 1
iConfiguration 0
bmAttributes 0xc0
Self Powered
MaxPower 100mA
Interface Descriptor:
bLength 9
bDescriptorType 4
bInterfaceNumber 0
bAlternateSetting 0
bNumEndpoints 2
bInterfaceClass 255 Vendor Specific Class
bInterfaceSubClass 0
bInterfaceProtocol 0
iInterface 0
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x82 EP 2 IN
bmAttributes 2
Transfer Type Bulk
Synch Type None
Usage Type Data
wMaxPacketSize 0x0040 1x 64 bytes
bInterval 10
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x02 EP 2 OUT
bmAttributes 2
Transfer Type Bulk
Synch Type None
Usage Type Data
wMaxPacketSize 0x0040 1x 64 bytes
bInterval 10
Device Status: 0x0001
Self Powered
I'm confused about the discussion regarding Windows. Why does it matter? Is there some use case for using the libusb backend on Windows instead of Windows' HID API?
Hi Hans, would you please do me a favor to dump the USB Prober output of your Atmel-ICE or Power Debugger if you still have them. Thanks.
I really need a picture, but this is what I've got:
Hi HPS, Sorry the request is to @MCUdude (another Hans) who has the access to the two High Speed USB Composite devices with an HID interface (Atmel-ICE and Atmel Power Debugger). What you have (Jtag ICE mkII and AVR ISP mkII) are not HID devices.
I'm confused about the discussion regarding Windows. Why does it matter? Is there some use case for using the libusb backend on Windows instead of Windows' HID API?
Ahh, it is a side topic -- I am trying to understand why High Speed USB HID device developers would not choose to have the Interrupt IN endpoint's wMaxPacketSize to be higher value (up to 1024 Bytes). From what I read the HID report size is usually less than 1024 Bytes. In that case they can simplify their Firmware development efforts (send the report in one packet and no need to deal with multiple packets on the device side). Of course the issue is not as bad as this one since the device firmware developer only needs to deal with one paticular device or a group of similar devices.
As for hidapi Windows libusb backend, in fact there are some use cases.
Interestingly I see a similar issue from the libfido2 project. But they do not use libusb backend. I see they have platfrom specific backend and even one hidapi backend.
Issue:
Fixes:
@wulf7 and @hselasky
FYI as well. libfido2 uses FreeBSD hidraw on FreeBSD13+. I think it is also good for hidapi to move to FreeBSD hidraw for newer version of FreeBSD. https://github.com/Yubico/libfido2/blob/main/src/hid_freebsd.c
#include <dev/usb/usb_ioctl.h>
#include <dev/usb/usbhid.h>
#if __FreeBSD_version >= 1300500
#include <dev/hid/hidraw.h>
#define USE_HIDRAW /* see usbhid(4) and hidraw(4) on FreeBSD 13+ */
#endif
@mcuee I've only borrowed an Atmel ICE, so I cant test with this at the moment, but here are the Power Debugger dump, which is very similar hardware vice:
@MCUdude
Great. So we can see that the HID report size is 512 Bytes and the Interrupt IN/OUT Endpoint's wMaxPacketSize is 512 Bytes.
Since the Power Debugger works well under Windows, so this confirms that Windows does support HID interface with the Interrupt IN/OUT Endpoint's wMaxPacketSize greater than 64 Bytes.
Interface Descriptor:
bLength 9
bDescriptorType 4
bInterfaceNumber 0
bAlternateSetting 0
bNumEndpoints 2
bInterfaceClass 3
bInterfaceSubClass 0
bInterfaceProtocol 0
iInterface 4 Power Debugger CMSIS-DAP
HID Device Descriptor:
bLength 9
bDescriptorType 33
bcdHID 1.11
bCountryCode 0 Not supported
bNumDescriptors 1
bDescriptorType 34 Report
wDescriptorLength 35
Report Descriptors:
** UNAVAILABLE **
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x01 EP 1 OUT
bmAttributes 3
Transfer Type Interrupt
Synch Type None
Usage Type Data
wMaxPacketSize 0x0200 1x 512 bytes
bInterval 1
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x82 EP 2 IN
bmAttributes 3
Transfer Type Interrupt
Synch Type None
Usage Type Data
wMaxPacketSize 0x0200 1x 512 bytes
bInterval 1
The hid report parser output. https://eleccelerator.com/usbdescreqparser/
0x06, 0x00, 0xFF, // Usage Page (Vendor Defined 0xFF00)
0x09, 0x01, // Usage (0x01)
0xA1, 0x01, // Collection (Application)
0x15, 0x00, // Logical Minimum (0)
0x26, 0xFF, 0x00, // Logical Maximum (255)
0x75, 0x08, // Report Size (8)
0x96, 0x00, 0x02, // Report Count (512)
0x09, 0x01, // Usage (0x01)
0x81, 0x02, // Input (Data,Var,Abs,No Wrap,Linear,Preferred State,No Null Position)
0x96, 0x00, 0x02, // Report Count (512)
0x09, 0x01, // Usage (0x01)
0x91, 0x02, // Output (Data,Var,Abs,No Wrap,Linear,Preferred State,No Null Position,Non-volatile)
0x95, 0x04, // Report Count (4)
0x09, 0x01, // Usage (0x01)
0xB1, 0x02, // Feature (Data,Var,Abs,No Wrap,Linear,Preferred State,No Null Position,Non-volatile)
0xC0, // End Collection
// 35 bytes
I hope my modification to Jan Axelson's FX2HID FW is correct. In that case, I can probably carry out some tests for this issue in different OS.
INPUT/OUTPUT report size 128 bytes, loop back, no report ID. (wMaxPacketSize = 64, high speed or full speed).
PS C:\work\hid\hidapitester> .\hidapitester --vidpid 0925:1234 --open --buflen 256 -l 129 --send-output 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128 --read-input
Opening device, vid/pid: 0x0925/0x1234
Writing output report of 129-bytes...wrote 129 bytes:
00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F
20 21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F
40 41 42 43 44 45 46 47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56 57 58 59 5A 5B 5C 5D 5E 5F
60 61 62 63 64 65 66 67 68 69 6A 6B 6C 6D 6E 6F 70 71 72 73 74 75 76 77 78 79 7A 7B 7C 7D 7E 7F
80
Reading 129-byte input report 0, 250 msec timeout...read 128 bytes:
01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F 20
21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F 40
41 42 43 44 45 46 47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56 57 58 59 5A 5B 5C 5D 5E 5F 60
61 62 63 64 65 66 67 68 69 6A 6B 6C 6D 6E 6F 70 71 72 73 74 75 76 77 78 79 7A 7B 7C 7D 7E 7F 80
00
Closing device
I hope https://github.com/libusb/hidapi/issues/478#issuecomment-1547963784 is correct. In that case, I can probably carry out some tests for this issue in different OS.
Indeed I can reproduce the issue using hidapitester under Linux.
1) using hidapitester with hidraw -- no issue
mcuee@UbuntuSwift3:~/build/hid/hidapitester$ /hidapitester_libusb --vidpid 0925:1234 --open --buflen 256 -l 129 --send-output 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128 --read-input
Opening device, vid/pid: 0x0925/0x1234
Writing output report of 129-bytes...wrote 129 bytes:
00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F
20 21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F
40 41 42 43 44 45 46 47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56 57 58 59 5A 5B 5C 5D 5E 5F
60 61 62 63 64 65 66 67 68 69 6A 6B 6C 6D 6E 6F 70 71 72 73 74 75 76 77 78 79 7A 7B 7C 7D 7E 7F
80
Reading 129-byte input report 0, 250 msec timeout...read 128 bytes:
01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F 20
21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F 40
41 42 43 44 45 46 47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56 57 58 59 5A 5B 5C 5D 5E 5F 60
61 62 63 64 65 66 67 68 69 6A 6B 6C 6D 6E 6F 70 71 72 73 74 75 76 77 78 79 7A 7B 7C 7D 7E 7F 80
00
Closing device
Using libusb backend, I can reproduce the issue under Linux. You can see that it only reads back 64 Bytes.
mcuee@UbuntuSwift3:~/build/hid/hidapitester$ ./hidapitester_libusb --vidpid 0925:1234 --open --buflen 256 -l 129 --send-output 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128 --read-input
Opening device, vid/pid: 0x0925/0x1234
Writing output report of 129-bytes...wrote 129 bytes:
00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F
20 21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F
40 41 42 43 44 45 46 47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56 57 58 59 5A 5B 5C 5D 5E 5F
60 61 62 63 64 65 66 67 68 69 6A 6B 6C 6D 6E 6F 70 71 72 73 74 75 76 77 78 79 7A 7B 7C 7D 7E 7F
80
Reading 129-byte input report 0, 250 msec timeout...read 64 bytes:
01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F 20
21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F 40
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00
Closing device
The documentation of libusb_interrupt_transfer()
states: "You should also check the transferred parameter for interrupt writes. Not all of the data may have been written."
https://libusb.sourceforge.io/api-1.0/group__libusb__syncio.html#ga0f171a72904a552fc43e6e6564d108a3
@JoergAtGithub and @Youw
Just wondering if you are still looking at this issue or not. Thanks.
This is clearly a bug in hidapi libusb backend, confirmed by several affected users. But I'm not working on a fix curently.
Agree. I don't have capacity for this either.
At Mixxx, users reported problems with USB 2.0 High-Speed devices, which are limited to Full-Speed mode for some reasons. Under MacOS and Windows they operate as High-Speed device.
This is not only a performance limitation, but it has functional implications for the HID communication, because USB Full-Speed is limited to a package size of 64 Bytes instead of 1024 in High-Speed mode. The result is, that HIDAP returns a 79Byte input report correct on Windows and MacOS, but two reports on Linux (libusb backend), the first with correct report ID, the second with report ID 0x00.
How could a cross platform application using HIDAPI handle this:
Linux-Output (libusb): Debug [Controller]: Traktor Kontrol S4 MK3 A79A_3: t:15558 ms, 64 bytes: 02 6E 08 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
Debug [Controller]: Traktor Kontrol S4 MK3 A79A_3: t:15559 ms, 15 bytes: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
This is the lsusb output: Interface Descriptor: bLength 9 bDescriptorType 4 bInterfaceNumber 3 bAlternateSetting 0 bNumEndpoints 2 bInterfaceClass 3 Human Interface Device bInterfaceSubClass 0 bInterfaceProtocol 0 iInterface 11 Traktor Kontrol S4 MK3 HID HID Device Descriptor: bLength 9 bDescriptorType 33 bcdHID 1.10 bCountryCode 0 Not supported bNumDescriptors 1 bDescriptorType 34 Report wDescriptorLength 673 Report Descriptors: UNAVAILABLE Endpoint Descriptor: bLength 7 bDescriptorType 5 bEndpointAddress 0x83 EP 3 IN bmAttributes 3 Transfer Type Interrupt Synch Type None Usage Type Data wMaxPacketSize 0x0040 1x 64 bytes bInterval 1 Endpoint Descriptor: bLength 7 bDescriptorType 5 bEndpointAddress 0x02 EP 2 OUT bmAttributes 3 Transfer Type Interrupt Synch Type None Usage Type Data wMaxPacketSize 0x0040 1x 64 bytes bInterval 2 Interface Descriptor: bLength 9 bDescriptorType 4 bInterfaceNumber 4 bAlternateSetting 0 bNumEndpoints 1 bInterfaceClass 255 Vendor Specific Class bInterfaceSubClass 189 bInterfaceProtocol 0 iInterface 12 Traktor Kontrol S4 MK3 BD Endpoint Descriptor: bLength 7 bDescriptorType 5 bEndpointAddress 0x03 EP 3 OUT bmAttributes 2 Transfer Type Bulk Synch Type None Usage Type Data wMaxPacketSize 0x0200 1x 512 bytes bInterval 1 Interface Descriptor: bLength 9 bDescriptorType 4 bInterfaceNumber 5 bAlternateSetting 0 bNumEndpoints 0 bInterfaceClass 254 Application Specific Interface bInterfaceSubClass 1 Device Firmware Update bInterfaceProtocol 1 iInterface 10 Traktor Kontrol S4 MK3 DFU Device Firmware Upgrade Interface Descriptor: bLength 9 bDescriptorType 33 bmAttributes 7 Will Not Detach Manifestation Tolerant Upload Supported Download Supported wDetachTimeout 250 milliseconds wTransferSize 64 bytes bcdDFUVersion 1.10 Device Qualifier (for other device speed): bLength 10 bDescriptorType 6 bcdUSB 2.00 bDeviceClass 0 bDeviceSubClass 0 bDeviceProtocol 0 bMaxPacketSize0 64 bNumConfigurations 1