[PATCH 2/4 v3] EHCI: split ehci_qh - ehci-mem.c and echi-hcd,c changes

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



>From b7f2d5d11bbccd0dcf3b05ed7c5123583753874d Mon Sep 17 00:00:00 2001
From: Alek Du <alek.du@xxxxxxxxx>
Date: Wed, 24 Jun 2009 18:57:28 +0800
Subject: [PATCH] EHCI: Spilt ehci_qh - ehci-mem.c and echi-hcd,c changes

The ehci_qh allocation and free changed.
Also the dma pool item size changed.
The ehci_qh items in ehci_hcd initialization changed.

Signed-off-by: Alek Du <alek.du@xxxxxxxxx>
---
 drivers/usb/host/ehci-hcd.c |   21 +++++++++++----------
 drivers/usb/host/ehci-mem.c |   27 ++++++++++++++++++---------
 2 files changed, 29 insertions(+), 19 deletions(-)

diff --git a/drivers/usb/host/ehci-hcd.c b/drivers/usb/host/ehci-hcd.c
index 2b72473..f406c9f 100644
--- a/drivers/usb/host/ehci-hcd.c
+++ b/drivers/usb/host/ehci-hcd.c
@@ -543,13 +543,14 @@ static int ehci_init(struct usb_hcd *hcd)
 	 * its dummy is used in hw_alt_next of many tds, to prevent the qh
 	 * from automatically advancing to the next td after short reads.
 	 */
-	ehci->async->qh_next.qh = NULL;
-	ehci->async->hw_next = QH_NEXT(ehci, ehci->async->qh_dma);
-	ehci->async->hw_info1 = cpu_to_hc32(ehci, QH_HEAD);
-	ehci->async->hw_token = cpu_to_hc32(ehci, QTD_STS_HALT);
-	ehci->async->hw_qtd_next = EHCI_LIST_END(ehci);
+	SH_HW(&ehci->async->qh_next) = NULL;
+	HW(ehci->async)->hw_next = QH_NEXT(ehci, ehci->async->qh_dma);
+	HW(ehci->async)->hw_info1 = cpu_to_hc32(ehci, QH_HEAD);
+	HW(ehci->async)->hw_token = cpu_to_hc32(ehci, QTD_STS_HALT);
+	HW(ehci->async)->hw_qtd_next = EHCI_LIST_END(ehci);
 	ehci->async->qh_state = QH_STATE_LINKED;
-	ehci->async->hw_alt_next = QTD_NEXT(ehci, ehci->async->dummy->qtd_dma);
+	HW(ehci->async)->hw_alt_next =
+				QTD_NEXT(ehci, ehci->async->dummy->qtd_dma);
 
 	/* clear interrupt enables, set irq latency */
 	if (log2_irq_thresh < 0 || log2_irq_thresh > 6)
@@ -978,7 +979,7 @@ rescan:
 	/* endpoints can be iso streams.  for now, we don't
 	 * accelerate iso completions ... so spin a while.
 	 */
-	if (qh->hw_info1 == 0) {
+	if (HW(qh)->hw_info1 == 0) {
 		ehci_vdbg (ehci, "iso delay\n");
 		goto idle_timeout;
 	}
@@ -987,9 +988,9 @@ rescan:
 		qh->qh_state = QH_STATE_IDLE;
 	switch (qh->qh_state) {
 	case QH_STATE_LINKED:
-		for (tmp = ehci->async->qh_next.qh;
+		for (tmp = SH_QH(&ehci->async->qh_next);
 				tmp && tmp != qh;
-				tmp = tmp->qh_next.qh)
+				tmp = SH_QH(&tmp->qh_next))
 			continue;
 		/* periodic qh self-unlinks on empty */
 		if (!tmp)
@@ -1047,7 +1048,7 @@ ehci_endpoint_reset(struct usb_hcd *hcd, struct usb_host_endpoint *ep)
 		if (!list_empty(&qh->qtd_list)) {
 			WARN_ONCE(1, "clear_halt for a busy endpoint\n");
 		} else if (qh->qh_state == QH_STATE_IDLE) {
-			qh->hw_token &= ~cpu_to_hc32(ehci, QTD_TOGGLE);
+			HW(qh)->hw_token &= ~cpu_to_hc32(ehci, QTD_TOGGLE);
 		} else {
 			/* It's not safe to write into the overlay area
 			 * while the QH is active.  Unlink it first and
diff --git a/drivers/usb/host/ehci-mem.c b/drivers/usb/host/ehci-mem.c
index 10d5291..7e5548a 100644
--- a/drivers/usb/host/ehci-mem.c
+++ b/drivers/usb/host/ehci-mem.c
@@ -75,7 +75,8 @@ static void qh_destroy(struct ehci_qh *qh)
 	}
 	if (qh->dummy)
 		ehci_qtd_free (ehci, qh->dummy);
-	dma_pool_free (ehci->qh_pool, qh, qh->qh_dma);
+	dma_pool_free(ehci->qh_pool, HW(qh), qh->qh_dma);
+	kfree(qh);
 }
 
 static struct ehci_qh *ehci_qh_alloc (struct ehci_hcd *ehci, gfp_t flags)
@@ -83,15 +84,18 @@ static struct ehci_qh *ehci_qh_alloc (struct ehci_hcd *ehci, gfp_t flags)
 	struct ehci_qh		*qh;
 	dma_addr_t		dma;
 
-	qh = (struct ehci_qh *)
-		dma_pool_alloc (ehci->qh_pool, flags, &dma);
+	qh = kzalloc(sizeof *qh, GFP_ATOMIC);
 	if (!qh)
-		return qh;
-
-	memset (qh, 0, sizeof *qh);
+		goto done;
+	HW(qh) = (struct ehci_qh_hw *)
+		dma_pool_alloc(ehci->qh_pool, flags, &dma);
+	if (!HW(qh))
+		goto fail;
+	memset(HW(qh), 0, sizeof *HW(qh));
 	qh->refcount = 1;
 	qh->ehci = ehci;
 	qh->qh_dma = dma;
+	QH(HW(qh)) = qh;
 	// INIT_LIST_HEAD (&qh->qh_list);
 	INIT_LIST_HEAD (&qh->qtd_list);
 
@@ -99,10 +103,15 @@ static struct ehci_qh *ehci_qh_alloc (struct ehci_hcd *ehci, gfp_t flags)
 	qh->dummy = ehci_qtd_alloc (ehci, flags);
 	if (qh->dummy == NULL) {
 		ehci_dbg (ehci, "no dummy td\n");
-		dma_pool_free (ehci->qh_pool, qh, qh->qh_dma);
-		qh = NULL;
+		goto fail1;
 	}
+done:
 	return qh;
+fail1:
+	dma_pool_free(ehci->qh_pool, HW(qh), qh->qh_dma);
+fail:
+	kfree(qh);
+	return NULL;
 }
 
 /* to share a qh (cpu threads, or hc) */
@@ -180,7 +189,7 @@ static int ehci_mem_init (struct ehci_hcd *ehci, gfp_t flags)
 	/* QHs for control/bulk/intr transfers */
 	ehci->qh_pool = dma_pool_create ("ehci_qh",
 			ehci_to_hcd(ehci)->self.controller,
-			sizeof (struct ehci_qh),
+			sizeof(struct ehci_qh_hw),
 			32 /* byte alignment (for hw parts) */,
 			4096 /* can't cross 4K */);
 	if (!ehci->qh_pool) {
-- 
1.6.0.4
--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux Media]     [Linux Input]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Old Linux USB Devel Archive]

  Powered by Linux