RE: [PATCH 7/7 v2] usb: dwc3: add the hibernation code itself

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

 



> From: linux-usb-owner@xxxxxxxxxxxxxxx [mailto:linux-usb-owner@xxxxxxxxxxxxxxx] On Behalf Of Felipe Balbi
> Sent: Monday, February 27, 2012 12:14 AM
> 
> On Fri, Feb 24, 2012 at 11:16:00AM -0800, Paul Zimmerman wrote:
> > > From: Felipe Balbi [mailto:balbi@xxxxxx]
> > > Sent: Friday, February 24, 2012 1:58 AM
> > >
> > > On Thu, Feb 23, 2012 at 01:17:13PM -0800, Paul Zimmerman wrote:
> > > >
> > > > Unfortunately, I don't see a way to make that work. The way the
> > > > interface between the modules is designed, dwc3-pci does not have
> > > > access to the DWC3 registers. Plus, dwc3-pci does not have access to
> > > > the 'struct dwc3' pointer either, so it has no way to see the software
> > > > state of the dwc3 driver.
> > > >
> > > > We could redesign that, so the register space is mapped and the
> > > > 'struct dwc3' is allocated in the glue layer instead of in dwc3.
> > > > Would you be up for that? If so, I could prepare an RFC patch for
> > > > that.
> > >
> > > no no, that'll cause problems when removing modules. If you remove
> > > dwc3-pci.ko before dwc3.ko, the latter could try to access already freed
> > > memory.
> >
> > No, I was thinking that dwc3 would export an init() and exit() function.
> > When dwc3-pci was removed, it would call the exit() function, and after
> > that dwc3 would no longer be active.
> 
> That would look like a violation of the driver core. Well, it would look
> a lot like MUSB and that frightens me to death ;-)
> 
> > > You could split the PCI address space into DWC USB3 IP specific and the
> > > rest (which is HAPS specific), unless you're mapping your HAPS-specific
> > > part on an unused area of the DWC USB3 IP address space, then, well, we
> > > need to think how to handle it.
> >
> > I played around with that, but it was really ugly, and there were still
> > problems because 'struct dwc3' was not accessible from dwc3-pci.
> >
> > Let me cook up an RFC patch for the modifications I have in mind. Code
> > talks, after all :) It might take me a few days, I have some higher-
> > priority stuff going on right now.
> 
> Sure, go ahead ;-) I'll go over the other patches you sent meanwhile.

Hi Felipe,

I think I found a less invasive way to do what I need, by defining a
platform_data struct for the dwc3 device, so that it can share function
pointers and the dwc3 context with the bus glue. Below is a POC patch
to show roughly what I plan to do. Is this an acceptable use of platform
data?

If so, maybe we could also remove the dwc3_{get|put}_device_id functions
and just have dwc3_probe write the devid into the platform_data? Then we
could get rid of those two exported functions.


diff --git a/drivers/usb/dwc3/core.h b/drivers/usb/dwc3/core.h
index 6c7945b..3f5d0dc 100644
--- a/drivers/usb/dwc3/core.h
+++ b/drivers/usb/dwc3/core.h
@@ -529,6 +529,18 @@ struct dwc3_request {
 	unsigned		queued:1;
 };
 
+/*
+ * Platform data (used for hibernation control)
+ */
+struct dwc3_pdata {
+	/* set by dwc3 module */
+	struct dwc3	*dwc;
+
+	/* set by bus glue module */
+	void		(*power_control)(struct dwc3 *, int);
+	int		(*interrupt_hook)(struct dwc3 *);
+};
+
 /**
  * struct dwc3 - representation of our controller
  * @ctrl_req: usb control request which is used for ep0
@@ -584,6 +596,7 @@ struct dwc3 {
 
 	struct platform_device	*xhci;
 	struct resource		*res;
+	struct dwc3_pdata		*pdata;
 
 	struct dwc3_event_buffer **ev_buffs;
 	struct dwc3_ep		*eps[DWC3_ENDPOINTS_NUM];

diff --git a/drivers/usb/dwc3/dwc3-pci.c b/drivers/usb/dwc3/dwc3-pci.c
index a81b30e..e647570 100644
--- a/drivers/usb/dwc3/dwc3-pci.c
+++ b/drivers/usb/dwc3/dwc3-pci.c
@@ -51,8 +51,38 @@
 struct dwc3_pci {
 	struct device		*dev;
 	struct platform_device	*dwc3;
+	struct dwc3_pdata		pdata;
 };
 
+/**
+ * dwc3_haps_power_ctl - platform-specific power control routine, for HAPS board
+ *
+ * @dwc: pointer to our controller context structure
+ * @on: 1 to turn the power on, 0 to turn it off
+ */
+static void dwc3_haps_power_ctl(struct dwc3 *dwc, int on)
+{
+	/* ... */
+}
+
+/**
+ * dwc3_haps_intr_hook - platform-specific interrupt handling, for HAPS board
+ *
+ * If this routine returns false, the caller should handle the interrupt
+ * as usual.
+ *
+ * If this routine returns true, the caller should exit the interrupt handler
+ * immediately, without touching the dwc3 registers.
+ *
+ * @dwc: pointer to our controller context structure
+ */
+static int dwc3_haps_intr_hook(struct dwc3 *dwc)
+{
+	/* ... */
+
+	return 0;
+}
+
 static int __devinit dwc3_pci_probe(struct pci_dev *pci,
 		const struct pci_device_id *id)
 {
@@ -109,12 +139,16 @@ static int __devinit dwc3_pci_probe(struct pci_dev *pci,
 		goto err2;
 	}
 
+	glue->pdata.power_control = dwc3_haps_power_ctl;
+	glue->pdata.interrupt_hook = dwc3_haps_intr_hook;
+
 	pci_set_drvdata(pci, glue);
 
 	dma_set_coherent_mask(&dwc3->dev, dev->coherent_dma_mask);
 
 	dwc3->dev.dma_mask = dev->dma_mask;
 	dwc3->dev.dma_parms = dev->dma_parms;
+	dwc3->dev.platform_data = &glue->pdata;
 	dwc3->dev.parent = dev;
 	glue->dwc3 = dwc3;
 

diff --git a/drivers/usb/dwc3/core.c b/drivers/usb/dwc3/core.c
index fd6917b..ad8529a 100644
--- a/drivers/usb/dwc3/core.c
+++ b/drivers/usb/dwc3/core.c
@@ -405,6 +405,7 @@ static void dwc3_core_exit(struct dwc3 *dwc)
 static int __devinit dwc3_probe(struct platform_device *pdev)
 {
 	struct device_node	*node = pdev->dev.of_node;
+	struct dwc3_pdata		*pdata = pdev->dev.platform_data;
 	struct resource		*res;
 	struct dwc3		*dwc;
 	struct device		*dev = &pdev->dev;
@@ -459,6 +460,10 @@ static int __devinit dwc3_probe(struct platform_device *pdev)
 	dwc->regs_size	= resource_size(res);
 	dwc->dev	= dev;
 	dwc->irq	= irq;
+	dwc->pdata	= pdata;
+
+	if (pdata)
+		pdata->dwc = dwc;
 
 	if (!strncmp("super", maximum_speed, 5))
 		dwc->maximum_speed = DWC3_DCFG_SUPERSPEED;

-- 
Paul

--
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