tech-kern archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: Potential problem with reading data from usb devices with ugen(4)



On 09/24/15 08:07, Brian Buhrow wrote:
	hello folks.   Perhaps someone on this list can enlighten me as to
where I'm going wrong, but I think there may be an issue with ugen(4) when
using the bulk read ahead and write behind code in conjunction with file
descriptors which are in O_NONBLOCK mode.  This is with NetBSD/i386 5.2
with the UGEN_BULK_RA_WB code ifdef'd into the ugen(4) code.  I've looked
at -current and it looks like the problem is still there.  Let me explain:

	I'm trying to get the usbmuxd and libimobiledevice code working under
NetBSD using the libusb1-1.0.19 package.  The usbmuxd code scans the
available ugen devices, identifies which ones are Apple devices, and then
rescans the devices it identified as being of interest.  With the default
libusb1 code, this functionality doesn't work because the usbmuxd code
expects to be able to do this over and over again but the ugen(4) driver
locks the process in "ugenrb" when it checks to see if a given  device has
the proper bulk endpoints.  I modified the libusb1 NetBSD backend module to
enable the read ahead code  and write behind code, as well as to put the
file descriptor associated with each of the endpoints into non-blocking
mode with fcntl(2).    Now, the first pass usbmuxd makes works, but it doesn't
generate any requests of the Apple devices which cause them to respond with
data on the bulk endpoints.  That's fine, but when usbmuxd comes around to
begin conversing with the "interesting" devices again, it's told there's
nothing to read because the ugen(4) driver, which has read ahead enabled
already, doesn't check for new input from the USB device when read requests
are made and there's no data available.  Specifically, when this code is
enabled, I think data is read from the bulk end points of a device using
the function ugen_bulkra_intr().  In theory it's supposed to be a self
perpetuating function that keeps checking for input, but it seems to only
get called from itself or when the read ahead  code is enabled via the
ioctl(2) call.  The scenario looks like this to me:

1.  Enable the read ahead code with the ioctl(2) on a device bulk endpoint
and also set the file descriptor into non-blocking mode.  The function
ugen_bulkra_intr() gets called once, but there's nothing to read so
the function doesn't set things up to call itself again.

2.  The next call to read(2) by the user process doesn't rigger a call to
ugen_bulkra_intr() because the file descriptor is in non-blocking mode and
there's no data to pass to the process so the driver just returnes and
EWOULDBLOCK.

3.  This repeats over and over again without ever actually querying the
device to see if it has anything to say.

Are you sure about this? I'm not sure why ugen_bulkra_intr doesn't start a new transfer, but see below.

I wonder if

        http://nxr.netbsd.org/xref/src/sys/dev/usb/ugen.c#697
        http://nxr.netbsd.org/xref/src/sys/dev/usb/ugen.c#1221

needs USBD_SHORT_XFER_OK adding to the flags arg.

UGEN_DEBUG output will help?

Nick


Home | Main Index | Thread Index | Old Index