1.

Solve : Can't read data from USB device?

Answer»

Hello,

I have a strange problem, which might be caused by some hardware limitation, or
by my ignorance in USB protocol (I have no advanced knowledge in USB).

I need to read keys from a USB device (some kind of keyboard). When doing it
under Windows 2000/XP, everything is fine. When doing it under GNU/Linux though,
I always get a timeout, even though by ignoring the timeout I get the data
right (but it doesn't always work, it VARIES according to the kernels and
architectures used). After trying everything I could think of, I finally
decided to dive into intimate USB protocol by snooping over raw USB
communications. For that, I used the snoop feature in usbcore [1].
I wrote a simple program that initializes the USB device, read keys for 10
seconds, and terminates. I first ran the program on a Windows virtual machine,
and as expected the keys were right. I then compiled and ran the same program
on GNU/Linux, and as expected, I got nothing else than timeouts. Then I went to
compare the logs: the working one, and the non-working one. Codes don't seem to
be tampered with in any way; the only real difference seems to lie in a subtle
difference at the beginning (interrupt urb instead of urb complete).
From this point I'm stuck: I have no idea whether they are correct regarding to
the standard. I have no way to force some kind of trick to simulate the working
one from GNU/Linux, as it would probably mean tampering with the kernel (even
for testing purpose, I am not exactly CONFIDENT). Therefore I have no choice
but to try my luck at finding SOMEONE who would be willing to dive into the
gory details below and hint me about what's hapenning :-P

Configuration on Windows (virtual machine):
- Windows XP (no service pack)
- AMD Athlon(tm) 64 X2 Dual (only 1 core used, virtual machine)   2.51 GHz
- 256 Mb of RAM

Configuration on GNU/Linux (real machine):
- OpenSuse 10.2, kernel 2.6.24.2 (last version, not PATCHED, downloaded from kernel.org)
- AMD Athlon(tm) 64 X2 Dual (2 cores used)   2.51 GHz
- 1 Gb of RAM
- USB chipset: USB Controller: nVidia Corporation MCP51 USB Controller (rev a3)

The above configurations are the ones I used for testing, but the timeouts
problem occurs on other machines and other FLAVOURS of GNU/Linux (including a
2.4 kernel on an arm processor). Windows seems to always work though (2000 and
XP tested).

Log obtained from Windows: http://wotan.homelinux.com/vbremaud/usb_win32.log

Log obtained from GNU/Linux (truncated in the middle): http://wotan.homelinux.com/vbremaud/usb_linux.log

[1] http://www.linuxjournal.com/node/7582The problem is solved: it was a difference of behavior between Linux and Windows kernels.
If a buffer of 32 bytes is provided for reading and only 8 bytes are available, the Windows kernel will provide the 8 bytes and return 8 as the number of bytes read. The Linux kernel will wait for aditional data, won't get any, and therefore return a timeout. Plain and simple...

Thanks to people who read



Discussion

No Comment Found