aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/usb
diff options
context:
space:
mode:
authorMing Lei <tom.leiming@gmail.com>2010-09-20 03:32:02 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2010-09-24 14:05:00 -0400
commiteeb1b2a4a9112bcd05d0ce53b99bbd5404abe060 (patch)
tree9049a7a9a333b29dc5a463650450f2fcea5cdafe /drivers/usb
parentbd2e74d657fc7d514881cc2117e323790b257914 (diff)
usb: musb: gadget: fix bulk IN infinit hangs in double buffer case
This patch fixes one infinite hang of bulk IN transfer in double buffer case, the hang can be observed easily by test #6 of usbtest if musb is configured as g_zero and fifo mode 3 is taken to enable double fifo. In fact, the patch only removes the check for non-empty fifo before loading data from new request into fifo since the check is not correct: -in double buffer case, fifo may accommodate more than one packet, even though it has contained one packet already and is non-empty -since last DMA is completed before calling musb_g_tx, it is sure that fifo may accommodate at least one packet Without applying the patch, new requst enqueued from .complte may not have a chance to be loaded into fifo, then will never be completed and cause infinite hangs. With the patch, on my beagle B5, test#6(queued bulk in) can be passed and test result may go beyond 33Mbyte/s if musb is configured as g_zero and fifo mode 3 is taken, follows the test command: #testusb -D DEV_NAME -c 1024 -t 6 -s 32768 -g 8 [1] [1], -source of testusb : tools/usb/testusb.c under linux kernel; Signed-off-by: Ming Lei <tom.leiming@gmail.com> Acked-by: Anand Gadiyar <gadiyar@ti.com> Cc: David Brownell <dbrownell@users.sourceforge.net> Cc: Anand Gadiyar <gadiyar@ti.com> Cc: Mike Frysinger <vapier@gentoo.org> Cc: Sergei Shtylyov <sshtylyov@ru.mvista.com> Signed-off-by: Felipe Balbi <balbi@ti.com> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/usb')
-rw-r--r--drivers/usb/musb/musb_gadget.c12
1 files changed, 0 insertions, 12 deletions
diff --git a/drivers/usb/musb/musb_gadget.c b/drivers/usb/musb/musb_gadget.c
index de0ca90ceb9b..f206c94b8b1c 100644
--- a/drivers/usb/musb/musb_gadget.c
+++ b/drivers/usb/musb/musb_gadget.c
@@ -504,18 +504,6 @@ void musb_g_tx(struct musb *musb, u8 epnum)
504 /* ... or if not, then complete it. */ 504 /* ... or if not, then complete it. */
505 musb_g_giveback(musb_ep, request, 0); 505 musb_g_giveback(musb_ep, request, 0);
506 506
507 /*
508 * Kickstart next transfer if appropriate;
509 * the packet that just completed might not
510 * be transmitted for hours or days.
511 * REVISIT for double buffering...
512 * FIXME revisit for stalls too...
513 */
514 musb_ep_select(mbase, epnum);
515 csr = musb_readw(epio, MUSB_TXCSR);
516 if (csr & MUSB_TXCSR_FIFONOTEMPTY)
517 return;
518
519 request = musb_ep->desc ? next_request(musb_ep) : NULL; 507 request = musb_ep->desc ? next_request(musb_ep) : NULL;
520 if (!request) { 508 if (!request) {
521 DBG(4, "%s idle now\n", 509 DBG(4, "%s idle now\n",