UPSTREAM: usb: dwc3: gadget: fix gadget suspend/resume
authorFelipe Balbi <felipe.balbi@linux.intel.com>
Wed, 4 May 2016 12:50:27 +0000 (15:50 +0300)
committerHuang, Tao <huangtao@rock-chips.com>
Tue, 16 Aug 2016 12:48:19 +0000 (20:48 +0800)
Instead of trying hard to stay connected to the
host, it's best (and far easier) to disconnect from
the host already.

Anything relying on KEEP_CONNECT will just have that
ignored, but we don't have proper hibernation
implementation yet, so there are no regressions.

In any case, hibernation is only useful for runtime
PM, not system sleep.

While at that, also remove dwc3.dcfg which has been
rendered unnecessary.

Change-Id: I605a452a416b3a2e2b98b6b6505ecc545846d5dd
Signed-off-by: Felipe Balbi <felipe.balbi@linux.intel.com>
Signed-off-by: Wu Liang feng <wulf@rock-chips.com>
(cherry picked from commit 9f8a67b65a49d0e35c6ca782136c84541d948a64)

drivers/usb/dwc3/core.h
drivers/usb/dwc3/gadget.c

index 222b0150713af22eeb17d5ba36b653fdd6d399a1..8098d31f116dcbc128ad726dcbed8b9bfe13a7cf 100644 (file)
@@ -817,7 +817,6 @@ struct dwc3 {
        enum usb_dr_mode        dr_mode;
 
        /* used for suspend/resume */
-       u32                     dcfg;
        u32                     gctl;
 
        u32                     nr_scratch;
index b26eaa91a68e0ddc4a51130c6df68eac228267d8..2119fa521922f03dbe21850697cc901f6a76f2c9 100644 (file)
@@ -2940,60 +2940,40 @@ void dwc3_gadget_exit(struct dwc3 *dwc)
 
 int dwc3_gadget_suspend(struct dwc3 *dwc)
 {
+       int ret;
+
        if (!dwc->gadget_driver)
                return 0;
 
-       if (dwc->pullups_connected) {
-               dwc3_gadget_disable_irq(dwc);
-               dwc3_gadget_run_stop(dwc, true, true);
-       }
-
-       __dwc3_gadget_ep_disable(dwc->eps[0]);
-       __dwc3_gadget_ep_disable(dwc->eps[1]);
+       ret = dwc3_gadget_run_stop(dwc, false, false);
+       if (ret < 0)
+               return ret;
 
-       dwc->dcfg = dwc3_readl(dwc->regs, DWC3_DCFG);
+       dwc3_disconnect_gadget(dwc);
+       __dwc3_gadget_stop(dwc);
 
        return 0;
 }
 
 int dwc3_gadget_resume(struct dwc3 *dwc)
 {
-       struct dwc3_ep          *dep;
        int                     ret;
 
        if (!dwc->gadget_driver)
                return 0;
 
-       /* Start with SuperSpeed Default */
-       dwc3_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(512);
-
-       dep = dwc->eps[0];
-       ret = __dwc3_gadget_ep_enable(dep, &dwc3_gadget_ep0_desc, NULL, false,
-                       false);
-       if (ret)
+       ret = __dwc3_gadget_start(dwc);
+       if (ret < 0)
                goto err0;
 
-       dep = dwc->eps[1];
-       ret = __dwc3_gadget_ep_enable(dep, &dwc3_gadget_ep0_desc, NULL, false,
-                       false);
-       if (ret)
+       ret = dwc3_gadget_run_stop(dwc, true, false);
+       if (ret < 0)
                goto err1;
 
-       /* begin to receive SETUP packets */
-       dwc->ep0state = EP0_SETUP_PHASE;
-       dwc3_ep0_out_start(dwc);
-
-       dwc3_writel(dwc->regs, DWC3_DCFG, dwc->dcfg);
-
-       if (dwc->pullups_connected) {
-               dwc3_gadget_enable_irq(dwc);
-               dwc3_gadget_run_stop(dwc, true, false);
-       }
-
        return 0;
 
 err1:
-       __dwc3_gadget_ep_disable(dwc->eps[0]);
+       __dwc3_gadget_stop(dwc);
 
 err0:
        return ret;