Module Name: src Committed By: skrll Date: Sat Mar 16 12:05:03 UTC 2013
Modified Files: src/sys/dev/usb: dwc_otg.c Log Message: Fix misunderstanding of how to handle wMaxPacketSize. The *_host_{setup,data}_[tr]x routines already split transfers into < mps units, so there no reason to do it in *_setup_{ctrl,data}_chain. Fix short_pkt handling in the process. This gives urtwn a fighting change to Tx large packets. To generate a diff of this commit: cvs rdiff -u -r1.47 -r1.48 src/sys/dev/usb/dwc_otg.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/dev/usb/dwc_otg.c diff -u src/sys/dev/usb/dwc_otg.c:1.47 src/sys/dev/usb/dwc_otg.c:1.48 --- src/sys/dev/usb/dwc_otg.c:1.47 Sat Feb 23 08:22:05 2013 +++ src/sys/dev/usb/dwc_otg.c Sat Mar 16 12:05:02 2013 @@ -1,4 +1,4 @@ -/* $NetBSD: dwc_otg.c,v 1.47 2013/02/23 08:22:05 skrll Exp $ */ +/* $NetBSD: dwc_otg.c,v 1.48 2013/03/16 12:05:02 skrll Exp $ */ /*- * Copyright (c) 2012 Hans Petter Selasky. All rights reserved. @@ -60,7 +60,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: dwc_otg.c,v 1.47 2013/02/23 08:22:05 skrll Exp $"); +__KERNEL_RCSID(0, "$NetBSD: dwc_otg.c,v 1.48 2013/03/16 12:05:02 skrll Exp $"); #include <sys/param.h> #include <sys/systm.h> @@ -2987,7 +2987,7 @@ dwc_otg_host_data_tx(struct dwc_otg_td * return 0; /* complete */ /* - * Else we need to transmit a short + * Else we need to transmit a 0 length * packet: */ } @@ -3682,7 +3682,6 @@ dwc_otg_setup_ctrl_chain(usbd_xfer_handl uint32_t len = UGETW(req->wLength); struct dwc_otg_std_temp temp; /* XXX */ struct dwc_otg_td *td; - int done; DPRINTFN(3, "type=0x%02x, request=0x%02x, wValue=0x%04x," "wIndex=0x%04x len=%d, addr=%d, endpt=%d, dir=%s, speed=%d\n", @@ -3712,11 +3711,8 @@ dwc_otg_setup_ctrl_chain(usbd_xfer_handl temp.short_pkt = 1; /* We're 8 bytes this is short for HS */ temp.setup_alt_next = 0; /* XXXNH */ - DPRINTF("SE temp.len %d temp.pc %p\n", temp.len, temp.buf); - dwc_otg_setup_standard_chain_sub(&temp); - done = 0; KASSERT((temp.buf == NULL) == (temp.len == 0)); if (dir == UT_READ) { temp.func = &dwc_otg_host_data_rx; @@ -3725,22 +3721,15 @@ dwc_otg_setup_ctrl_chain(usbd_xfer_handl } /* Optional Data stage */ - while (done != len) { + if (len != 0) { /* DATA0 / DATA1 message */ - temp.buf = len ? KERNADDR(&xfer->dmabuf, done) : NULL; - temp.len = len - done; + temp.buf = KERNADDR(&xfer->dmabuf, 0); + temp.len = len; temp.short_pkt = ( (xfer->flags & USBD_FORCE_SHORT_XFER) ? 0 : 1); - if (temp.len > UGETW(ed->wMaxPacketSize)) - temp.len = UGETW(ed->wMaxPacketSize); - dwc_otg_setup_standard_chain_sub(&temp); - - done += temp.len; - if (temp.len) - temp.buf = (char *)KERNADDR(&xfer->dmabuf, 0) + done; } /* Status Stage */ @@ -3783,9 +3772,6 @@ dwc_otg_setup_data_chain(usbd_xfer_handl uint8_t dir = UE_GET_DIR(ed->bEndpointAddress); struct dwc_otg_std_temp temp; /* XXX */ struct dwc_otg_td *td; - int off; - int done; - int len; DPRINTFN(3, "xfer=%p, len=%d, flags=%d, addr=%d, endpt=%d, dir %s\n", xfer, xfer->length, xfer->flags, dev->address, @@ -3806,30 +3792,27 @@ dwc_otg_setup_data_chain(usbd_xfer_handl temp.did_stall = 0; /* !xfer->flags_int.control_stall; */ temp.func = NULL; - done = 0; if (dir == UE_DIR_IN) { temp.func = &dwc_otg_host_data_rx; } else { temp.func = &dwc_otg_host_data_tx; } - /* Data stage */ - off = 0; - len = xfer->length; - while (len > 0) { - /* DATA0 / DATA1 message */ - temp.buf = KERNADDR(&xfer->dmabuf, off); - temp.len = MIN(len, UGETW(ed->wMaxPacketSize)); - temp.short_pkt = (xfer->flags & USBD_FORCE_SHORT_XFER) ? 0 : 1; - if (len <= UGETW(ed->wMaxPacketSize)) - temp.setup_alt_next = 0; + /* DATA0 / DATA1 message */ + temp.buf = KERNADDR(&xfer->dmabuf, 0); + temp.len = xfer->length; + if (temp.len == 0) { - dwc_otg_setup_standard_chain_sub(&temp); + /* make sure that we send an USB packet */ - len -= temp.len; - off += temp.len; + temp.short_pkt = 0; + + } else { + temp.short_pkt = (xfer->flags & USBD_FORCE_SHORT_XFER) ? 0 : 1; } + dwc_otg_setup_standard_chain_sub(&temp); + /* must have at least one frame! */ td = temp.td; dxfer->td_transfer_last = td;