usb/110855: ugen: interrupt in msgs are truncated when buffer is full

Hans Petter Selasky hselasky at c2i.net
Tue Mar 27 19:40:10 UTC 2007


The following reply was made to PR usb/110855; it has been noted by GNATS.

From: Hans Petter Selasky <hselasky at c2i.net>
To: Markus Henschel <m.henschel at bally-wulff.de>
Cc: freebsd-usb at freebsd.org,
 freebsd-gnats-submit at freebsd.org
Subject: Re: usb/110855: ugen: interrupt in msgs are truncated when buffer is full
Date: Tue, 27 Mar 2007 21:33:37 +0200

 On Tuesday 27 March 2007 18:55, Markus Henschel wrote:
 > Hans Petter Selasky schrieb:
 > > On Tuesday 27 March 2007 11:30, Markus Henschel wrote:
 > >> Hans Petter Selasky schrieb:
 > >>> On Monday 26 March 2007 16:13, Markus Henschel wrote:
 > >>>>> Number:         110855
 > >>>>> Category:       usb
 > >>>>> Synopsis:       ugen: interrupt in msgs are truncated when buffer is
 > >>>>> full Confidential:   no
 > >>>>> Severity:       serious
 > >>>>> Priority:       medium
 > >>>>> Responsible:    freebsd-usb
 > >>>>> State:          open
 > >>>>> Quarter:
 > >>>>> Keywords:
 > >>>>> Date-Required:
 > >>>>> Class:          change-request
 > >>>>> Submitter-Id:   current-users
 > >>>>> Arrival-Date:   Mon Mar 26 14:20:04 GMT 2007
 > >>>>> Closed-Date:
 > >>>>> Last-Modified:
 > >>>>> Originator:     Markus Henschel
 > >>>>> Release:        6.2 custom kernel
 > >>>>> Organization:
 > >>>>
 > >>>> Bally Wulff Automaten GmbH
 > >>>>
 > >>>>> Environment:
 > >>>>
 > >>>> FreeBSD freebsd-1.bally.de 6.2-RELEASE FreeBSD 6.2-RELEASE #11: Fri
 > >>>> Mar 23 21:28:38 CET 2007
 > >>>> prog at freebsd-1.bally.de:/usr/obj/usr/src/sys/BALLYWULFF  i386
 > >>>>
 > >>>>> Description:
 > >>>>
 > >>>> We use ugen for some user space drivers. When an interrupt in endpoint
 > >>>> is used ugen creates a queue that is filled by the kernel. The user
 > >>>> space driver is responsible for reading data from the device file. If
 > >>>> this happens too slow the queue is full and new msgs arriving from the
 > >>>> usb device are lost. This behavior is OK.
 > >>>>
 > >>>> The problem is that the queue is not a multiple of the interrupt in
 > >>>> endpoints msgs size. So it is possible that the last msg in the queue
 > >>>> is truncated. This is very hard to detect for a user space driver. The
 > >>>> data stream seen by the user space driver will contain an incomplete
 > >>>> msgs directly followed by the next message without knowing truncation
 > >>>> happened (except when using some data corruption detection mechanism).
 > >>>>
 > >>>> It would be much better if ugen would fill the queues of interrupt in
 > >>>> endpoints until there is no more space for a complete msg. This way
 > >>>> the user space driver will not loose sync with the incoming msgs.
 > >>>
 > >>> The new USB stack has this fixed already. What I do is that the USB
 > >>> driver stops polling the interrupt endpoint when the user-land
 > >>> application does not read data. When the user-land application has read
 > >>> a packet, the interrupt endpoint is started again. The only problem is
 > >>> that some devices, like a Microsoft mouse I have, stops working
 > >>> immediately when its internal buffer overflows. Bad hardware design.
 > >>> But if your hardware is not like that, the new ugen, which is part of
 > >>> the new USB driver, will work great for you.
 > >>>
 > >>> Also packet alignment is kept between reads: Only one packet per read.
 > >>>
 > >>> See:
 > >>>
 > >>> http://www.turbocat.net/~hselasky/usb4bsd
 > >>>
 > >>> --HPS
 > >>
 > >> Thanks,
 > >>
 > >> I gave it a try and it seems to work fine :-). Could you please explain
 > >> how reading an interrupt in endpoint works internally with the new ugen?
 > >> Is there still a buffer that recieves data from the endpoint or is each
 > >> read request from user land synchronously triggering a read data request
 > >> on the interrupt endpoint?
 > >
 > > Yes, there is a buffer, but the buffer is packet-based, and not a "ring"
 > > based, so you will never get problem with packet alignment.
 > >
 > >> Why isn't O_NONBLOCK working anymore?
 > >
 > > It is implemented, and it should work. Can you explain more what is not
 > > working?
 > >
 > > --HPS
 >
 > With the old ugen I did something like:
 >
 > int iDevice=open("/dev/ugen0.4", O_RDONLY);
 > fcntl(iDevice, F_SETFL, O_NONBLOCK);
 
 I've just committed a patch for that to the P4 tree. It will be in SVN in not 
 too long. It was just the matter of a missing IOCTL that F_SETFL uses. 
 Usually the following works when you want to set/clear non-blocking mode:
 
 int t = 1;
 fcntl(iDevice, FIONBIO, &t)
 
 >
 > Now the fcntl call fails. But instead this works and does the same:
 >
 > int iDevice=open("/dev/ugen0.4", O_RDONLY|O_NONBLOCK);
 >
 >
 > I thought the O_NONBLOCK flag was just for the open call itself?!?
 > Whatever, it does what I need :-)
 >
 > The only thing that keeps me from using the new usb stack is umass now.
 > When inserting an usb flash memory stick it is detected and says umass
 > attached to ii but then it takes ages (more that 30s) for the device
 > files to become available. A "camcontrol rescan all" hangs during this
 > time too.Is it possible to use the old umass with the new stack or just
 > revert umass to an older version from you like 1.6.1?
 
 If you use the SVN version, reverting won't help much. Could you turn on 
 debugging: sysctl hw.usb.umass.debug=-1
 
 And see what is going on when you plug your umass device.
 
 >
 > BTW: The performance of the new usb stack is great. umass throughput
 > with the memory stick nearly increased by 50%!!
 
 Cool.
 
 --HPS


More information about the freebsd-usb mailing list