summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGregory Nutt <gnutt@nuttx.org>2013-08-26 14:28:13 -0600
committerGregory Nutt <gnutt@nuttx.org>2013-08-26 14:28:13 -0600
commit260405d60666ea266e72f56484e56ef37b591851 (patch)
tree5163985a643b2fc19bfc41091b9d5096460137e2
parent7f18b02e9ce6872998169cd849def297a76435b2 (diff)
downloadnuttx-260405d60666ea266e72f56484e56ef37b591851.tar.gz
nuttx-260405d60666ea266e72f56484e56ef37b591851.tar.bz2
nuttx-260405d60666ea266e72f56484e56ef37b591851.zip
SAMA5 EHCI: Status phase is the opposite direction as the data phase
-rwxr-xr-xnuttx/arch/arm/src/sama5/sam_ehci.c33
1 files changed, 26 insertions, 7 deletions
diff --git a/nuttx/arch/arm/src/sama5/sam_ehci.c b/nuttx/arch/arm/src/sama5/sam_ehci.c
index 0076563d7..1889f9783 100755
--- a/nuttx/arch/arm/src/sama5/sam_ehci.c
+++ b/nuttx/arch/arm/src/sama5/sam_ehci.c
@@ -982,8 +982,8 @@ static int sam_qtd_foreach(struct sam_qh_s *qh, foreach_qtd_t handler, void *arg
/* Handle the special case where the queue is empty */
- bp = &qh->fqp; /* Start of qTDs in original list */
- physaddr = sam_swap32(*bp); /* Physical address of first qTD in CPU order */
+ bp = &qh->fqp; /* Start of qTDs in original list */
+ physaddr = sam_swap32(*bp); /* Physical address of first qTD in CPU order */
if ((physaddr & QTD_NQP_T) != 0)
{
@@ -1608,7 +1608,7 @@ static struct sam_qtd_s *sam_qtd_setupphase(struct sam_epinfo_s *epinfo,
}
/* Mark this as the end of the list (this will be overwritten if another
- * qTD is added after this one.
+ * qTD is added after this one).
*/
qtd->hw.nqp = sam_swap32(QTD_NQP_T);
@@ -1676,7 +1676,7 @@ static struct sam_qtd_s *sam_qtd_dataphase(struct sam_epinfo_s *epinfo,
}
/* Mark this as the end of the list (this will be overwritten if another
- * qTD is added after this one.
+ * qTD is added after this one).
*/
qtd->hw.nqp = sam_swap32(QTD_NQP_T);
@@ -1741,7 +1741,7 @@ static struct sam_qtd_s *sam_qtd_statusphase(uint32_t tokenbits)
}
/* Mark this as the end of the list (this will be overwritten if another
- * qTD is added after this one.
+ * qTD is added after this one).
*/
qtd->hw.nqp = sam_swap32(QTD_NQP_T);
@@ -1936,9 +1936,28 @@ static ssize_t sam_async_transfer(struct sam_rhport_s *rhport,
if (req != NULL)
{
- /* Extra TOKEN bits include the data toggle and the data PID. */
+ /* Extra TOKEN bits include the data toggle and the correct data PID. */
- uint32_t tokenbits = toggle | datapid;
+ uint32_t tokenbits = toggle;
+
+ /* The status phase direction is the opposite of the data phase. If
+ * this is an IN request, then we received the buffer and we will send
+ * the zero length packet handshake.
+ */
+
+ if ((req->type & USB_REQ_DIR_MASK) == USB_REQ_DIR_IN)
+ {
+ tokenbits |= QTD_TOKEN_PID_OUT;
+ }
+
+ /* Otherwise, this in an OUT request. We send the buffer and we expect
+ * to receive the NULL packet handshake.
+ */
+
+ else
+ {
+ tokenbits |= QTD_TOKEN_PID_IN;
+ }
/* Allocate a new Queue Element Transfer Descriptor (qTD) for the status */