On 10/5/06, Alan Stern <[EMAIL PROTECTED]> wrote: > > The question is, how does a stream get disabled?
ehci_endpoint_disable(). As patched, that will perform the final refcount decrement and reap the ehci_iso_stream, which will also release the budget. > No, that's not what I said. The way it's supposed to work is like this: > The bandwidth is released as soon as the last completion handler callback > returns, which has nothing to do with whether or not an overrun occurred. Are overrun and underrun synonyms here? What happens when, eg, an application does not submit more audio to the usbaudio layer in time to avoid an underrun in playback? In that case, all the completion handlers would return and the stream would be released. > An overrun occurs when the completion handler fails to submit an URB in > time for its slot. But as long as the completion handler submits any URB > at all, it isn't the _last_ callback and so the bandwidth is not released. Ah, so if, eg, usbaudio has no more playback data to submit, blank URBs are supposed to get filled in? I'm trying to understand what is supposed to happen, and how that differs from what previously and currently happens. > I don't know the details of how ehci-hcd used to implement this. But > waiting until endpoint_disable is wrong. endpoint_disable is where the budget is released, which has little/nothing to do with the hardware schedule itself. Once a USB periodic endpoint is open()ed, it must be guaranteed to be schedulable until it is close()d. > > In the new scheduler, the budget is unaffected. When an underrun > > occurs, the hardware scheduler merely skips over the schedule slots > > that got missed, but does not drop the 'late' transactions when > > they're submitted. Perhaps you are arguing that this is broken? > > Not at all; that's what it _should_ do. Oh, OK. > However, if an > URB is submitted so late that it has already missed _all_ of its slots, > the submission should not return an error. I never suggested that it > should. But the completion handler should quickly be called and all the > frames should have an error status. OK, I think here may be a point of confusion. A URB has no specific slot[s] until it is submitted. The endpoint, as a whole, has a circular, infinite set of guaranteed available slots URBs can be dropped into, therefore it is not possible to miss 'all the slots' (in the old scheduler, bandwidth allocation was not circular). A URB is associated with no specific point[s] in time (or the schedule) until ehci_urb_enqueue, but so long as there's a budget, enqueue is guaranteed availability of slots. Unless, of course, the URB is so large as to overflow the entire schedule, in which case it is refused. But that's not what we're talking about. > I get the feeling that neither the old way (as you describe it) nor your > new way is correct. I think I don't yet understand your concern fully... > Missing schedule slots because an URB was submitted too late should not be > enough to release the bandwidth reservation. That should happen if and > only if the stream is broken, that is, if no more URBs are queued for the > endpoint when a completion handler returns. OK, this makes clear another point of confusion. What exactly do you mean by 'completion handler'? sitd_complete et al? And by 'the completion handler submitting a new URB', you mean draining the internal queue of a higher level driver, eg, usb-audio? What if the source of latency is the application, not the driver? > Then so long as the completion handler submits a new URB, the bandwidth > will remain reserved -- even if things run slow and a few slots are > missed. And when the driver stops submitting URBs and the queue drains, > then the bandwidth can be released right away. No need to wait for > endpoint_disable; that might not happen until the device is unplugged. The intent is that endpoint_disable is called upon close(); in my testing (and from the code I read), close would in fact always result in an endpoint_disable. I do not want any possibility of bandwidth being released prior to close() in the event that the source of the underrun is the application, not just latency internal to the kernel. Monty ------------------------------------------------------------------------- Take Surveys. Earn Cash. Influence the Future of IT Join SourceForge.net's Techsay panel and you'll get the chance to share your opinions on IT & business topics through brief surveys -- and earn cash http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV _______________________________________________ linux-usb-devel@lists.sourceforge.net To unsubscribe, use the last form field at: https://lists.sourceforge.net/lists/listinfo/linux-usb-devel