[Nut-upsuser] lost USB comms under FreeBSD
clepple at gmail.com
Thu Aug 23 03:34:00 UTC 2007
On 8/22/07, Daniel O'Connor <doconnor at gsoft.com.au> wrote:
> On Wed, 22 Aug 2007, Charles Lepple wrote:
> > NUT drivers poll the UPS every so often, which works fine on systems
> > where a single libusb call results in a single USB transaction. In
> > FreeBSD (and probably other BSD systems as well), interrupt transfers
> > are scheduled periodically, even if the calling program is not
> > requesting interrupt transfers at the same rate.
> I had a look through the USB code and it seems that ugen uses the
> default value which means that it obtains the value from the end point
Right. IIRC, Linux and Windows only poll the device as often as the
userspace program or kernel driver request an interrupt transfer.
> > What I saw with tripplite_usb (where the USB descriptor for the
> > device tells the OS to poll 10-100 times a second) is that the driver
> > does not poll frequently enough, and an interrupt transfer buffer
> > fills up in the OS. Due to the way that libusb and the kernel USB
> > stack interact, this could cause the symptoms you are seeing.
> Hmm, which buffer?
If you dig into the way libusb interfaces with ugen, it is basically
reading from a file descriptor tied to the interrupt endpoint. The
kernel is filling the buffer behind this file descriptor faster than
tripplite_usb could empty it (although I think that is fixed now), and
there is a chance that the same overrun is affecting usbhid-ups.
> It would be nice if it could recover gracefully from this situation
> though (since a number of things could cause missed interrupts anyway)
Probably the best thing would be to have the kernel driver only commit
to the buffer in multiples of the interrupt transfer size. The
OMNIVS1000 sends 8-byte packets over the interrupt IN pipe, and stuff
would occasionally get misaligned by 4 bytes (in a test program that
repeatedly read 8 bytes from the interrupt endpoint via libusb).
- Charles Lepple
More information about the Nut-upsuser