I call this the "turn time" problem.. I've known about it for a while, and
it's much bigger than just this.
I've been waiting for URB queuing to be done and stable (and for more time
and broadband internet service) before I look at this -- but I consider it
a future enhancement, which is less important than bug fixes.
Matt
On Tue, Apr 10, 2001 at 10:43:11PM +0200, Sancho Dauskardt wrote:
>
> I had major performance problems reading the SSFDC mapping table: that
> involed to usb_stor_bulk_msg() for each of the 4096 blocks and took around
> 17 sek (and only around 6 sek same device under Win98 ).. I guessed that
> this could possibly be a schedluing issue, and tried following:
>
> master_XXX is supposed to be the 'Command URB'
> slave_XXX is supposed to be the 'Data URB' which results out of the command
> urb.
>
> int usb_stor_bulk_combo_msg(
> struct us_data *us,
>
> void *master_data,
> int master_pipe,
> unsigned int master_len,
> unsigned int *master_act_len,
>
> void *slave_data,
> int slave_pipe,
> unsigned int slave_len,
> unsigned int *slave_act_len
> )
> {
> wait_queue_head_t wqh;
> wait_queue_t wait;
> int status;
>
> // set up data structures for the wakeup system
> //
> init_waitqueue_head(&wqh);
> init_waitqueue_entry(&wait, current);
> add_wait_queue(&wqh, &wait);
>
> // lock the URB
> //
> down(&(us->current_urb_sem));
>
> // fill both URB's
> //
> FILL_BULK_URB(us->current_urb, us->pusb_dev, master_pipe, master_data,
> master_len,
> usb_stor_blocking_completion, &wqh);
> us->current_urb->actual_length = 0;
> us->current_urb->error_count = 0;
> us->current_urb->transfer_flags = USB_ASYNC_UNLINK;
>
> FILL_BULK_URB(us->slave_urb, us->pusb_dev, slave_pipe, slave_data, slave_len,
> usb_stor_blocking_completion, &wqh);
> us->slave_urb->actual_length = 0;
> us->slave_urb->error_count = 0;
> us->slave_urb->transfer_flags = USB_ASYNC_UNLINK;
>
>
> /* submit the URB */
> set_current_state(TASK_UNINTERRUPTIBLE);
>
> status = usb_submit_urb(us->current_urb);
> if (status) {
> /* something went wrong */
> up(&(us->current_urb_sem));
> set_current_state(TASK_RUNNING);
> remove_wait_queue(&wqh, &wait);
> return status;
> }
>
> // Submit the other urb.
> //
> status = usb_submit_urb(us->slave_urb);
> if (status) {
> /* something went wrong */
> up(&(us->current_urb_sem));
> set_current_state(TASK_RUNNING);
> remove_wait_queue(&wqh, &wait);
> return status;
> }
>
>
> /* wait for the completion of the URB */
> up(&(us->current_urb_sem));
>
> while (us->current_urb->status == -EINPROGRESS)
> schedule();
>
> while (us->slave_urb->status == -EINPROGRESS)
> schedule();
>
> down(&(us->current_urb_sem));
>
> /* we either timed out or got woken up -- clean up either way */
> set_current_state(TASK_RUNNING);
> remove_wait_queue(&wqh, &wait);
>
> /* return the actual length of the data transferred */
> *master_act_len = us->current_urb->actual_length;
> *slave_act_len = us->current_urb->actual_length;
>
> /* release the lock and return status */
> up(&(us->current_urb_sem));
> return us->current_urb->status;
> }
>
>
>
> And is got a speedup factor 2 (same device now only takes around 8 sek to
> read mapping table). I still dont quite understand why this ist faster ?
> Does it do one schedule() less, due to the second URB already being finished ?
>
> I guess all devices using plain bulk interface will suffer from this
> problem, only with no so large impact;
> How should usb_stor_bulk_combo_msg() react, when the first fails ?
>
> If we can make this reliable, then it should be used in
> usb_stor_Bulk_transport() ?
>
> - sda
>
>
>
> _______________________________________________
> [EMAIL PROTECTED]
> To unsubscribe, use the last form field at:
> http://lists.sourceforge.net/lists/listinfo/linux-usb-devel
--
Matthew Dharm Home: [EMAIL PROTECTED]
Maintainer, Linux USB Mass Storage Driver
SP: I sell software for Microsoft. Can you set me free?
DP: Natural Selection says I shouldn't.
-- MS Salesman and Dust Puppy
User Friendly, 4/2/1998
PGP signature