Discussion:
[libhid-discuss] unable to get input report
stdht.inbox
2009-01-13 08:44:23 UTC
Permalink
Hello

My device is an usb barcode scanner. It works in 2 modes: simulates
usb keyboard or acts like usb2serial device (general hid). I use it in mode 2 as
general hid device.
I used raw hid under linux and was able to read interrupt reports and
used function ioctl(HIDIOCGUSAGES,...) to retrieve all the array of
usages (about 63 values)...

Now I am using libhid. I receive interrupt reports without problems
but how to get array of usages????

hid_get_input_report with path 0xff03c00, 0xff030d03, 0xff030022
or 0xff03c00, 0xff030d03, 0xff030050 with lengths (1,63,64) fails
with code 20.

My hidtrace and related info:

Device Descriptor:
bLength 18
bDescriptorType 1
bcdUSB 2.00
bDeviceClass 0 (Defined at Interface level)
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 16
idVendor 0x05e0 Symbol Technologies
idProduct 0x0600
bcdDevice 2.01
iManufacturer 1 ?Symbol Technologies, Inc, 2002
iProduct 2 Symbol Bar Code Scanner
iSerial 3 S/N:1BBFACCB09D4 Rev:NBRMIAAU5
bNumConfigurations 1
Configuration Descriptor:
bLength 9
bDescriptorType 2
wTotalLength 34
bNumInterfaces 1
bConfigurationValue 1
iConfiguration 4 Bus Powered
bmAttributes 0x80
(Bus Powered)
MaxPower 400mA
Interface Descriptor:
bLength 9
bDescriptorType 4
bInterfaceNumber 0
bAlternateSetting 0
bNumEndpoints 1
bInterfaceClass 3 Human Interface Devices
bInterfaceSubClass 1 Boot Interface Subclass
bInterfaceProtocol 1 Keyboard
iInterface 0
HID Device Descriptor:
bLength 9
bDescriptorType 33
bcdHID 1.10
bCountryCode 0 Not supported
bNumDescriptors 1
bDescriptorType 34 Report
wDescriptorLength 40
Report Descriptor: (length is 40)
Item(Global): Usage Page, data= [ 0x03 0xff ] 65283
(null)
Item(Local ): Usage, data= [ 0x00 0x0c ] 3072
(null)
Item(Main ): Collection, data= [ 0x01 ] 1
Application
Item(Local ): Usage, data= [ 0x03 0x0d ] 3331
(null)
Item(Main ): Collection, data= [ 0x02 ] 2
Logical
Item(Global): Report Size, data= [ 0x08 ] 8
Item(Global): Report Count, data= [ 0x01 ] 1
Item(Global): Logical Minimum, data= [ 0x00 ] 0
Item(Global): Logical Maximum, data= [ 0x3f ] 63
Item(Local ): Usage, data= [ 0x50 ] 80
(null)
Item(Main ): Input, data= [ 0x02 ] 2
Data Variable Absolute No_Wrap Linear
Preferred_State No_Null_Position Non_Volatile Bitfield
Item(Global): Report Size, data= [ 0x08 ] 8
Item(Global): Report Count, data= [ 0x3f ] 63
Item(Global): Logical Minimum, data= [ 0x00 ] 0
Item(Global): Logical Maximum, data= [ 0xff 0x00 ] 255
Item(Local ): Usage, data= [ 0x22 ] 34
(null)
Item(Main ): Input, data= [ 0x00 ] 0
Data Array Absolute No_Wrap Linear
Preferred_State No_Null_Position Non_Volatile Bitfield
Item(Main ): End Collection, data=none
Item(Main ): End Collection, data=none
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x82 EP 2 IN
bmAttributes 3
Transfer Type Interrupt
Synch Type None
Usage Type Data
wMaxPacketSize 0x0040 1x 64 bytes
bInterval 10
Device Status: 0x0000
(Bus Powered)

TRACE: hid_dump_tree(): iterating the parse tree for USB device 003/030[0]...
parse tree of HIDInterface 003/030[0]:
path: 0xff030c00.0xff030d03.0xff030050; type: 0x80
path: 0xff030c00.0xff030d03.0xff030022; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80




-----------------------------------------------------


Best regards,
Serge.
Charles Lepple
2009-01-13 16:05:58 UTC
Permalink
Post by stdht.inbox
Hello
My device is an usb barcode scanner. It works in 2 modes: simulates
usb keyboard or acts like usb2serial device (general hid). I use it in mode 2 as
general hid device.
I used raw hid under linux and was able to read interrupt reports and
used function ioctl(HIDIOCGUSAGES,...) to retrieve all the array of
usages (about 63 values)...
If you send me some pointers to the "raw hid" API, I will take a look
at it. I am in the process of rewriting the libhid backend to not be
tied to just raw libusb calls.
Post by stdht.inbox
Now I am using libhid. I receive interrupt reports without problems
but how to get array of usages????
hid_get_input_report with path 0xff03c00, 0xff030d03, 0xff030022
or 0xff03c00, 0xff030d03, 0xff030050 with lengths (1,63,64) fails
with code 20.
The error code is meant to be somewhat generic. (You can look up the
message name with hid_strerror(), by the way). What is usually more
interesting is the trace messages, as they tell you what operations
succeeded and failed.
Post by stdht.inbox
bLength 18
bDescriptorType 1
bcdUSB 2.00
bDeviceClass 0 (Defined at Interface level)
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 16
idVendor 0x05e0 Symbol Technologies
idProduct 0x0600
bcdDevice 2.01
iManufacturer 1 ?Symbol Technologies, Inc, 2002
iProduct 2 Symbol Bar Code Scanner
iSerial 3 S/N:1BBFACCB09D4 Rev:NBRMIAAU5
bNumConfigurations 1
bLength 9
bDescriptorType 2
wTotalLength 34
bNumInterfaces 1
bConfigurationValue 1
iConfiguration 4 Bus Powered
bmAttributes 0x80
(Bus Powered)
MaxPower 400mA
bLength 9
bDescriptorType 4
bInterfaceNumber 0
bAlternateSetting 0
bNumEndpoints 1
bInterfaceClass 3 Human Interface Devices
bInterfaceSubClass 1 Boot Interface Subclass
bInterfaceProtocol 1 Keyboard
iInterface 0
bLength 9
bDescriptorType 33
bcdHID 1.10
bCountryCode 0 Not supported
bNumDescriptors 1
bDescriptorType 34 Report
wDescriptorLength 40
Report Descriptor: (length is 40)
Item(Global): Usage Page, data= [ 0x03 0xff ] 65283
(null)
Item(Local ): Usage, data= [ 0x00 0x0c ] 3072
(null)
Item(Main ): Collection, data= [ 0x01 ] 1
Application
Item(Local ): Usage, data= [ 0x03 0x0d ] 3331
(null)
Item(Main ): Collection, data= [ 0x02 ] 2
Logical
Item(Global): Report Size, data= [ 0x08 ] 8
Item(Global): Report Count, data= [ 0x01 ] 1
Item(Global): Logical Minimum, data= [ 0x00 ] 0
Item(Global): Logical Maximum, data= [ 0x3f ] 63
Item(Local ): Usage, data= [ 0x50 ] 80
(null)
Item(Main ): Input, data= [ 0x02 ] 2
Data Variable Absolute No_Wrap Linear
Preferred_State No_Null_Position
Non_Volatile Bitfield
Item(Global): Report Size, data= [ 0x08 ] 8
Item(Global): Report Count, data= [ 0x3f ] 63
Item(Global): Logical Minimum, data= [ 0x00 ] 0
Item(Global): Logical Maximum, data= [ 0xff 0x00 ] 255
Item(Local ): Usage, data= [ 0x22 ] 34
(null)
Item(Main ): Input, data= [ 0x00 ] 0
Data Array Absolute No_Wrap Linear
Preferred_State No_Null_Position
Non_Volatile Bitfield
Item(Main ): End Collection, data=none
Item(Main ): End Collection, data=none
bLength 7
bDescriptorType 5
bEndpointAddress 0x82 EP 2 IN
bmAttributes 3
Transfer Type Interrupt
Synch Type None
Usage Type Data
wMaxPacketSize 0x0040 1x 64 bytes
bInterval 10
Device Status: 0x0000
(Bus Powered)
TRACE: hid_dump_tree(): iterating the parse tree for USB device 003/030[0]...
path: 0xff030c00.0xff030d03.0xff030050; type: 0x80
path: 0xff030c00.0xff030d03.0xff030022; type: 0x80
It looks like you would use 0xff030c00.0xff030d03.0xff030022 with
length 63.

I haven't checked recently, but I think libhid discards the rest of
the buffer if you only request one item from a report.

You could also try hid_get_input_report(), passing in the length of
the whole report (looks to be 64) if you know you need both items.
Post by stdht.inbox
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
path: 0xff030c00.0xff030d03.0x00000000; type: 0x80
-----------------------------------------------------
Best regards,
Serge.
_______________________________________________
libhid-discuss mailing list
libhid-discuss at lists.alioth.debian.org
http://lists.alioth.debian.org/mailman/listinfo/libhid-discuss
http://libhid.alioth.debian.org/
stdht.inbox
2009-01-13 16:47:25 UTC
Permalink
Hello, Charles.

rawhid = linux/hiddev.h

besides, I overworked..
So my devices sends me scanned info in each interrupt report.
I call hid_interrupt_read in loop (timeout=5000)
I works ok! it works good at 2.6.x and 2.4.31 kernel...
BUT!!! I tried my utility under linux 2.4.25 (my target
embedded device). The result is bad. In the loop after the first
hid_interrup_read timeouts and after that moment all subsequent calls
to hid_interrup_read fail!!

TRACE: hid_interrupt_read(): retrieving interrupt report from device 002/002[0] ...
WARNING: hid_interrupt_read(): timeout on interrupt read from device 002/002[0]
hid_interrupt_read failed with return code 23
// ALL OK IT'S JUST TIMEOUT device sends nothing...

TRACE: hid_interrupt_read(): retrieving interrupt report from device 002/002[0] ...
NOTICE: hid_interrupt_read(): successfully got interrupt report from device 002/002[0]
TRACE: hid_interrupt_read(): retrieving interrupt report from device 002/002[0] ...
host/usb-uhci.c : ENXIO 40010280, flags 0, urb c71e2d70, burb c54ee800
USB error: error submitting URB: No such device or address
WARNING: hid_interrupt_read(): failed to get interrupt read from device 002/002[0]: error submitting URB: No such device or address
hid_interrupt_read failed with return code 21
TRACE: hid_interrupt_read(): retrieving interrupt report from device 002/002[0] ...
host/usb-uhci.c : ENXIO 40010280, flags 0, urb c71e2d70, burb c54ee800
USB error: error submitting URB: No such device or address
WARNING: hid_interrupt_read(): failed to get interrupt read from device 002/002[0]: error submitting URB: No such device or address
TRACE: hid_interrupt_read(): retrieving interrupt report from device 002/002[0] ...
host/usb-uhci.c : ENXIO 40010280, flags 0, urb c71e2d70, burb c54ee800
USB error: error submitting URB: No such device or address
WARNING: hid_interrupt_read(): failed to get interrupt read from device 002/002[0]: error submitting URB: No such device or address
hid_interrupt_read failed with return code 21
TRACE: hid_interrupt_read(): retrieving interrupt report from device 002/002[0] ...

--------------
code:
while(1) {
ret = hid_interrupt_read(hid, 0x82, buf, 64, 5000);
if (ret != HID_RET_SUCCESS) {
printf( "hid_interrupt_read failed with return code %d\n", ret);
} else {
//printf( "interrupt\n" );
for (i=0;i<64; i++) printf( "%u ", buf[i] );
printf( "\n" );
}
}
Post by Charles Lepple
Post by stdht.inbox
Hello
My device is an usb barcode scanner. It works in 2 modes: simulates
usb keyboard or acts like usb2serial device (general hid). I use it in mode 2 as
general hid device.
I used raw hid under linux and was able to read interrupt reports and
used function ioctl(HIDIOCGUSAGES,...) to retrieve all the array of
usages (about 63 values)...
If you send me some pointers to the "raw hid" API, I will take a look
at it. I am in the process of rewriting the libhid backend to not be
tied to just raw libusb calls.
Post by stdht.inbox
Now I am using libhid. I receive interrupt reports without problems
but how to get array of usages????
hid_get_input_report with path 0xff03c00, 0xff030d03, 0xff030022
or 0xff03c00, 0xff030d03, 0xff030050 with lengths (1,63,64) fails
with code 20.
The error code is meant to be somewhat generic. (You can look up the
message name with hid_strerror(), by the way). What is usually more
interesting is the trace messages, as they tell you what operations
succeeded and failed.
--
? ?????????,
stdht mailto:stdht.inbox at gmail.com
Charles Lepple
2009-01-13 22:44:18 UTC
Permalink
Post by stdht.inbox
Hello, Charles.
rawhid = linux/hiddev.h
Oh, OK. When we first started writing libhid, the hiddev interface
did not handle the nested collections necessary to read information
from USB UPSes. It has changed since then, but some UPSes are still
blacklisted as a result.
Post by stdht.inbox
besides, I overworked..
So my devices sends me scanned info in each interrupt report.
I call hid_interrupt_read in loop (timeout=5000)
I works ok! it works good at 2.6.x and 2.4.31 kernel...
BUT!!! I tried my utility under linux 2.4.25 (my target
embedded device). The result is bad. In the loop after the first
hid_interrup_read timeouts and after that moment all subsequent calls
to hid_interrup_read fail!!
Sounds like something specific to your platform. Have you checked to
see how long it waits before declaring a timeout?
Post by stdht.inbox
WARNING: hid_interrupt_read(): failed to get interrupt read from
device 002/002[0]: error submitting URB: No such device or address
hid_interrupt_read failed with return code 21
TRACE: hid_interrupt_read(): retrieving interrupt report from device 002/002[0] ...
host/usb-uhci.c : ENXIO 40010280, flags 0, urb c71e2d70, burb c54ee800
USB error: error submitting URB: No such device or address
This error does not sound good - it's like the device disconnected
itself. Check to see if it still has the same device address in
'lsusb' (or /proc/bus/usb/devices)
Post by stdht.inbox
while(1) {
ret = hid_interrupt_read(hid, 0x82, buf, 64, 5000);
if (ret != HID_RET_SUCCESS) {
printf( "hid_interrupt_read failed with return code %d\n", ret);
You should be able to do the following:

printf( "hid_interrupt_read failed with return code %d (%s)\n",
ret, hid_strerror(ret));
--
Charles Lepple
stdht.inbox
2009-01-14 09:20:47 UTC
Permalink
Hello
Post by Charles Lepple
Sounds like something specific to your platform. Have you checked to
see how long it waits before declaring a timeout?
It waits about 5 secs (timeout=5secs) seems like all is ok.
Post by Charles Lepple
This error does not sound good - it's like the device disconnected
itself. Check to see if it still has the same device address in
'lsusb' (or /proc/bus/usb/devices)
after I press CTRL+C device is present //// in devices file..
if I rerun the prog it start again with one timeout and subsequent
errors (libhid: interrrupt read failed)...

As a notice: sometimes device really reinitializes especially after
calls to hid_get_input_report or feature report (which it doesn't
support) with bad params...
Post by Charles Lepple
printf( "hid_interrupt_read failed with return code %d (%s)\n",
ret, hid_strerror(ret));
I receive at first (libhid: timeout)
after: libhid: interrrupt read failed.

Besides I have:

hid_set_debug(HID_DEBUG_ALL);
hid_set_usb_debug(5);
hid_set_debug_stream(stdout);

so all of the errors I've already mailed...

Best regards, Serg.
stdht.inbox
2009-01-14 20:18:46 UTC
Permalink
Hello, Charles.

I've made some new experiments. I make hid_interrupt_read in a loop
as before:

while(1) {
ret = hid_interrupt_read(hid, 0x82, buf, 64, 100);
usleep(1000*300);
if (ret != HID_RET_SUCCESS) {
printf( "hid_interrupt_read failed with return code %d (%s)\n", ret, hid_strerror(ret));
} else {

//printf( "interrupt\n" );
printf( "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n" );
for (i=0;i<20; i++) printf( "%u ", buf[i] );
printf( "\n" );
printf( "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n" );

}
}

It's surprising but device returns correct information!
What I receive:

hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
14 49 50 51 52 53 54 55 56 57 48 49 50 56 13 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
9 49 50 51 52 53 54 55 48 13 0 0 0 0 0 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
13 49 50 51 52 53 54 55 56 57 48 49 50 13 0 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
13 49 50 51 52 53 54 55 56 57 48 49 50 13 0 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)


PS. may be my mistake is that I build my prog and libusb and libhid under 2.4.31
and try it under 2.4.25?? Or in other case there is something in
usb-uhci...

Best regards,
Serg.
Charles Lepple
2009-01-14 20:42:37 UTC
Permalink
Post by stdht.inbox
Hello, Charles.
I've made some new experiments. I make hid_interrupt_read in a loop
while(1) {
ret = hid_interrupt_read(hid, 0x82, buf, 64, 100);
usleep(1000*300);
^ you shouldn't need the usleep() here - all libhid calls are
currently synchronous.
Post by stdht.inbox
if (ret != HID_RET_SUCCESS) {
printf( "hid_interrupt_read failed with return code %d (%s)
\n", ret, hid_strerror(ret));
} else {
//printf( "interrupt\n" );
printf
( "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n" );
for (i=0;i<20; i++) printf( "%u ", buf[i] );
printf( "\n" );
printf
( "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n" );
}
}
It's surprising but device returns correct information!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
14 49 50 51 52 53 54 55 56 57 48 49 50 56 13 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
9 49 50 51 52 53 54 55 48 13 0 0 0 0 0 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
13 49 50 51 52 53 54 55 56 57 48 49 50 13 0 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
13 49 50 51 52 53 54 55 56 57 48 49 50 13 0 0 0 0 0 0
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
hid_interrupt_read failed with return code 21 (libhid: interrupt read failed)
PS. may be my mistake is that I build my prog and libusb and libhid under 2.4.31
and try it under 2.4.25?? Or in other case there is something in
usb-uhci...
The kernel version should not matter for building versus running,
because a given combination of libhid and libusb versions will use
the same kernel interfaces.

However, it could be a difference at the UHCI driver level. I would
not be surprised if the timeouts were not working correctly in the
platform-specific code.
stdht.inbox
2009-01-14 21:17:26 UTC
Permalink
Hello, Charles.
Post by Charles Lepple
^ you shouldn't need the usleep() here - all libhid calls are
currently synchronous.
I use it because of errors with timeout... I think I have no other
overcome:(
Post by Charles Lepple
The kernel version should not matter for building versus running,
because a given combination of libhid and libusb versions will use
the same kernel interfaces.
However, it could be a difference at the UHCI driver level. I would
not be surprised if the timeouts were not working correctly in the
platform-specific code.
I do not understand all details but is it possible to build my prog
under 2.4.31 for use without timeout problems under 2.4.25? I have the
sources of 2.4.25 kernel.


Best regards,
Serg

Peter Stuge
2009-01-13 22:48:00 UTC
Permalink
Post by Charles Lepple
If you send me some pointers to the "raw hid" API, I will take a
look at it. I am in the process of rewriting the libhid backend to
not be tied to just raw libusb calls.
/usr/src/linux/Documentation/usb/hiddev.txt

I would like to request that the backend becomes a separate library
(almost) as simple as the Windows HID API. libhidio may be a good
name? I don't know how much sense it really makes, but I think it
would be nice to have.


//Peter
Charles Lepple
2009-01-14 20:53:09 UTC
Permalink
Post by Peter Stuge
Post by Charles Lepple
If you send me some pointers to the "raw hid" API, I will take a
look at it. I am in the process of rewriting the libhid backend to
not be tied to just raw libusb calls.
/usr/src/linux/Documentation/usb/hiddev.txt
I would like to request that the backend becomes a separate library
(almost) as simple as the Windows HID API. libhidio may be a good
name? I don't know how much sense it really makes, but I think it
would be nice to have.
Peter,

I'm not sure I understand your suggestion here. What are you
proposing to separate? When I say "backend", I mean the glue code to
a platform's native HID API (or to libusb, for "legacy" libhid
operation). The "frontend", in my mind, is the generic API that hides
platform-specific details.

I know that the Windows HID API automates finding the first input and
output report, and finding which endpoint to use, but to me that
sounds like a maintenance nightmare, with the new #1 FAQ becoming
"why doesn't my Windows code work on Linux?". To me, that also sounds
like a convenience function on top of the frontend described in the
previous paragraph (for platforms other than Windows), since it
builds on the more generic libhid API.

Do you have a sketch of your proposed architecture?
Loading...