linux-omap.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: George Cherian <george.cherian@ti.com>
To: linux-arm-kernel@lists.infradead.org,
	linux-kernel@vger.kernel.org, linux-samsung-soc@vger.kernel.org,
	linux-omap@vger.kernel.org, linux-usb@vger.kernel.org
Cc: peter.chen@freescale.com, sojka@merica.cz,
	mathias.nyman@intel.com, balbi@ti.com,
	gregkh@linuxfoundation.org, tony@atomide.com,
	bcousson@baylibre.com, kgene.kim@samsung.com,
	ben-linux@fluff.org, linux@arm.linux.org.uk,
	galak@codeaurora.org, ijc+devicetree@hellion.org.uk,
	mark.rutland@arm.com, pawel.moll@arm.com, robh+dt@kernel.org,
	George Cherian <george.cherian@ti.com>
Subject: [PATCH 12/19] usb: dwc3: gadget: Adapt gadget to drd library
Date: Tue, 25 Nov 2014 18:41:48 +0530	[thread overview]
Message-ID: <1416921115-10467-13-git-send-email-george.cherian@ti.com> (raw)
In-Reply-To: <1416921115-10467-1-git-send-email-george.cherian@ti.com>

Adapt the dwc3 gadget to use drd library functions.
In prepration to support DRD on dwc3.

Signed-off-by: George Cherian <george.cherian@ti.com>
---
 drivers/usb/dwc3/gadget.c | 128 ++++++++++++++++++++++++++++++++++++----------
 1 file changed, 100 insertions(+), 28 deletions(-)

diff --git a/drivers/usb/dwc3/gadget.c b/drivers/usb/dwc3/gadget.c
index 2c54d45..a75fae5 100644
--- a/drivers/usb/dwc3/gadget.c
+++ b/drivers/usb/dwc3/gadget.c
@@ -29,6 +29,7 @@
 
 #include <linux/usb/ch9.h>
 #include <linux/usb/gadget.h>
+#include <linux/usb/drd.h>
 
 #include "debug.h"
 #include "core.h"
@@ -2681,6 +2682,89 @@ static irqreturn_t dwc3_interrupt(int irq, void *_dwc)
 	return ret;
 }
 
+void dwc3_gadget_release(struct device *dev)
+{
+	struct usb_gadget *gadget = container_of(dev, struct usb_gadget, dev);
+	struct dwc3_gadget *dwc_gadget = gadget_to_dwc_gadget(gadget);
+	struct dwc3 *dwc = dwc_gadget->dwc;
+
+	dev_dbg(dev, "releasing '%s'\n", dev_name(dev));
+	dwc3_gadget_free_endpoints(dwc);
+	dma_free_coherent(dwc->dev, DWC3_EP0_BOUNCE_SIZE,
+			  dwc->ep0_bounce, dwc->ep0_bounce_addr);
+	kfree(dwc->setup_buf);
+	dma_free_coherent(dwc->dev, sizeof(*dwc->ep0_trb),
+			  dwc->ep0_trb, dwc->ep0_trb_addr);
+	dma_free_coherent(dwc->dev, sizeof(*dwc->ctrl_req),
+			  dwc->ctrl_req, dwc->ctrl_req_addr);
+	usb_drd_unregister_udc(dwc->dev);
+	kfree(dwc_gadget);
+}
+
+int dwc3_gadget_setup(void *data)
+{
+	struct dwc3 *dwc = data;
+	struct dwc3_gadget *dwc_gadget;
+	struct usb_drd_gadget *drd_gadget;
+	struct usb_drd_setup *gadget_setup;
+	int ret;
+
+	drd_gadget = kzalloc(sizeof(*drd_gadget), GFP_KERNEL);
+	if (!drd_gadget) {
+		ret = -ENOMEM;
+		goto err1;
+	}
+
+	gadget_setup = kzalloc(sizeof(*gadget_setup), GFP_KERNEL);
+	if (!gadget_setup) {
+		ret = -ENOMEM;
+		goto err2;
+	}
+
+	dwc_gadget = kzalloc(sizeof(*dwc_gadget), GFP_KERNEL);
+	if (!dwc_gadget) {
+		ret = -ENOMEM;
+		goto err3;
+	}
+
+	drd_gadget->g_driver = dwc->gadget_driver;
+
+	/*
+	 * Pass the DWC3 specific routines for
+	 * switching roles to the drd library
+	 */
+	gadget_setup->ll_start = NULL;
+	gadget_setup->ll_stop = NULL;
+	gadget_setup->ll_release = dwc3_gadget_release;
+	gadget_setup->data =  (void *)dwc;
+	drd_gadget->gadget_setup = gadget_setup;
+
+	dwc_gadget->gadget.ops			= &dwc3_gadget_ops;
+	dwc_gadget->gadget.max_speed		= USB_SPEED_SUPER;
+	dwc_gadget->gadget.speed		= USB_SPEED_UNKNOWN;
+	dwc_gadget->gadget.sg_supported		= true;
+	dwc_gadget->gadget.name			= "dwc3-gadget";
+	dwc_gadget->dwc				= dwc;
+	drd_gadget->gadget = &dwc_gadget->gadget;
+
+	/*
+	 * Per databook, DWC3 needs buffer size to be aligned to MaxPacketSize
+	 * on ep out.
+	 */
+	dwc_gadget->gadget.quirk_ep_out_aligned_size = true;
+	dwc->dwc_gadget = dwc_gadget;
+	usb_drd_register_udc(dwc->dev, drd_gadget);
+
+	return 0;
+
+err3:
+	kfree(gadget_setup);
+err2:
+	kfree(drd_gadget);
+err1:
+	return ret;
+}
+
 /**
  * dwc3_gadget_init - Initializes gadget related registers
  * @dwc: pointer to our controller context structure
@@ -2690,7 +2774,6 @@ static irqreturn_t dwc3_interrupt(int irq, void *_dwc)
 int dwc3_gadget_init(struct dwc3 *dwc)
 {
 	int					ret;
-	struct dwc3_gadget			*dwc_gadget;
 
 	dwc->ctrl_req = dma_alloc_coherent(dwc->dev, sizeof(*dwc->ctrl_req),
 			&dwc->ctrl_req_addr, GFP_KERNEL);
@@ -2723,24 +2806,9 @@ int dwc3_gadget_init(struct dwc3 *dwc)
 		goto err3;
 	}
 
-	dwc_gadget = kzalloc(sizeof(*dwc_gadget), GFP_KERNEL);
-	if (!dwc_gadget) {
-		ret = -ENOMEM;
+	ret = dwc3_gadget_setup(dwc);
+	if (ret)
 		goto err3;
-	}
-
-	dwc_gadget->gadget.ops			= &dwc3_gadget_ops;
-	dwc_gadget->gadget.max_speed		= USB_SPEED_SUPER;
-	dwc_gadget->gadget.speed		= USB_SPEED_UNKNOWN;
-	dwc_gadget->gadget.sg_supported	= true;
-	dwc_gadget->gadget.name		= "dwc3-gadget";
-	dwc_gadget->dwc = dwc;
-
-	/*
-	 * Per databook, DWC3 needs buffer size to be aligned to MaxPacketSize
-	 * on ep out.
-	 */
-	dwc_gadget->gadget.quirk_ep_out_aligned_size = true;
 
 	/*
 	 * REVISIT: Here we should clear all pending IRQs to be
@@ -2751,7 +2819,8 @@ int dwc3_gadget_init(struct dwc3 *dwc)
 	if (ret)
 		goto err4;
 
-	ret = usb_add_gadget_udc(dwc->dev, &dwc_gadget->gadget);
+	ret = usb_add_gadget_udc_release(dwc->dev, &dwc->dwc_gadget->gadget,
+					 dwc3_gadget_release);
 	if (ret) {
 		dev_err(dwc->dev, "failed to register udc\n");
 		goto err4;
@@ -2760,6 +2829,7 @@ int dwc3_gadget_init(struct dwc3 *dwc)
 	return 0;
 
 err4:
+	usb_drd_unregister_udc(dwc->dev);
 	dwc3_gadget_free_endpoints(dwc);
 	dma_free_coherent(dwc->dev, DWC3_EP0_BOUNCE_SIZE,
 			dwc->ep0_bounce, dwc->ep0_bounce_addr);
@@ -2785,20 +2855,22 @@ void dwc3_gadget_exit(struct dwc3 *dwc)
 {
 	struct dwc3_gadget *dwc_gadget = dwc->dwc_gadget;
 
-	usb_del_gadget_udc(&dwc_gadget->gadget);
+	if (usb_drd_get_state(dwc->dev) & DRD_DEVICE_REGISTERED) {
+		usb_del_gadget_udc(&dwc_gadget->gadget);
 
-	dwc3_gadget_free_endpoints(dwc);
+		dwc3_gadget_free_endpoints(dwc);
 
-	dma_free_coherent(dwc->dev, DWC3_EP0_BOUNCE_SIZE,
-			dwc->ep0_bounce, dwc->ep0_bounce_addr);
+		dma_free_coherent(dwc->dev, DWC3_EP0_BOUNCE_SIZE,
+				  dwc->ep0_bounce, dwc->ep0_bounce_addr);
 
-	kfree(dwc->setup_buf);
+		kfree(dwc->setup_buf);
 
-	dma_free_coherent(dwc->dev, sizeof(*dwc->ep0_trb),
-			dwc->ep0_trb, dwc->ep0_trb_addr);
+		dma_free_coherent(dwc->dev, sizeof(*dwc->ep0_trb),
+				  dwc->ep0_trb, dwc->ep0_trb_addr);
 
-	dma_free_coherent(dwc->dev, sizeof(*dwc->ctrl_req),
-			dwc->ctrl_req, dwc->ctrl_req_addr);
+		dma_free_coherent(dwc->dev, sizeof(*dwc->ctrl_req),
+				  dwc->ctrl_req, dwc->ctrl_req_addr);
+	}
 }
 
 int dwc3_gadget_suspend(struct dwc3 *dwc)
-- 
1.8.3.1

  parent reply	other threads:[~2014-11-25 13:11 UTC|newest]

Thread overview: 22+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2014-11-25 13:11 [PATCH 00/19] Add Support for USB DRD in AM437x George Cherian
2014-11-25 13:11 ` [PATCH 01/19] usb: common: drd-lib: Add DRD lib for USB George Cherian
2014-11-26  5:14   ` Peter Chen
2014-11-25 13:11 ` [PATCH 02/19] usb: host xhci: fix up deallocation code George Cherian
2014-11-25 13:11 ` [PATCH 03/19] usb: host: xhci-plat: Add support to pass XHCI_DRD_SUPPORT quirk George Cherian
2014-11-25 13:11 ` [PATCH 04/19] usb: host xhci: Add XHCI_NEEDS_LHC_RESET quirk George Cherian
2014-11-25 13:11 ` [PATCH 05/19] usb: host: xhci-plat: Add support to pass " George Cherian
2014-11-25 13:11 ` [PATCH 06/19] usb: dwc3: host: Pass the XHCI_DRD_SUPPORT and " George Cherian
2014-11-27  2:00   ` Lu, Baolu
2014-11-25 13:11 ` [PATCH 07/19] usb: host: xhci: Adapt xhci to use usb drd library George Cherian
2014-11-25 13:11 ` [PATCH 08/19] usb: dwc3: core: Add dwc3_drd_helper function George Cherian
2014-11-25 13:11 ` [PATCH 09/19] usb: dwc3: dwc3-omap: Make the wrapper interrupt shared George Cherian
2014-11-25 13:11 ` [PATCH 10/19] usb: dwc3: core: Adapt to named interrupts George Cherian
2014-11-25 13:11 ` [PATCH 11/19] usb: dwc3: Add seperate dwc3_gadget object to support gadget release George Cherian
2014-11-25 13:11 ` George Cherian [this message]
2014-11-25 13:11 ` [PATCH 13/19] usb: dwc3: core: Add DWC3 OTG specific register defines George Cherian
2014-11-25 13:11 ` [PATCH 14/19] usb: dwc3: otg: Add the initial otg driver for dwc3 George Cherian
2014-11-25 13:11 ` [PATCH 15/19] arm: dts: am4372: Add named interrupt property " George Cherian
2014-11-25 13:11 ` [PATCH 16/19] arm: dts: omap5: " George Cherian
2014-11-25 13:11 ` [PATCH 17/19] arm: dts: dra7: " George Cherian
2014-11-25 13:11 ` [PATCH 18/19] arm: dts: exynos5250: " George Cherian
2014-11-25 13:11 ` [PATCH 19/19] arm: dts: am43x evms: Make usb1 as OTG George Cherian

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1416921115-10467-13-git-send-email-george.cherian@ti.com \
    --to=george.cherian@ti.com \
    --cc=balbi@ti.com \
    --cc=bcousson@baylibre.com \
    --cc=ben-linux@fluff.org \
    --cc=galak@codeaurora.org \
    --cc=gregkh@linuxfoundation.org \
    --cc=ijc+devicetree@hellion.org.uk \
    --cc=kgene.kim@samsung.com \
    --cc=linux-arm-kernel@lists.infradead.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-omap@vger.kernel.org \
    --cc=linux-samsung-soc@vger.kernel.org \
    --cc=linux-usb@vger.kernel.org \
    --cc=linux@arm.linux.org.uk \
    --cc=mark.rutland@arm.com \
    --cc=mathias.nyman@intel.com \
    --cc=pawel.moll@arm.com \
    --cc=peter.chen@freescale.com \
    --cc=robh+dt@kernel.org \
    --cc=sojka@merica.cz \
    --cc=tony@atomide.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).