1 From f59dcab176293b646e1358144c93c58c3cda2813 Mon Sep 17 00:00:00 2001
2 From: Felipe Balbi <felipe.balbi@linux.intel.com>
3 Date: Fri, 11 Mar 2016 10:51:52 +0200
4 Subject: usb: dwc3: core: improve reset sequence
6 According to Synopsys Databook, we shouldn't be
7 relying on GCTL.CORESOFTRESET bit as that's only for
8 debugging purposes. Instead, let's use DCTL.CSFTRST
9 if we're OTG or PERIPHERAL mode.
11 Host side block will be reset by XHCI driver if
12 necessary. Note that this reduces amount of time
13 spent on dwc3_probe() by a long margin.
15 We're still gonna wait for reset to finish for a
16 long time (default to 1ms max), but tests show that
17 the reset polling loop executed at most 19 times
18 (modprobe dwc3 && modprobe -r dwc3 executed 1000
21 Suggested-by: Mian Yousaf Kaukab <yousaf.kaukab@intel.com>
22 Signed-off-by: Felipe Balbi <felipe.balbi@linux.intel.com>
24 drivers/usb/dwc3/core.c | 48 ++++++++++++++++++------------------------------
25 1 file changed, 18 insertions(+), 30 deletions(-)
27 --- a/drivers/usb/dwc3/core.c
28 +++ b/drivers/usb/dwc3/core.c
29 @@ -67,23 +67,9 @@ void dwc3_set_mode(struct dwc3 *dwc, u32
30 static int dwc3_core_soft_reset(struct dwc3 *dwc)
36 - /* Before Resetting PHY, put Core in Reset */
37 - reg = dwc3_readl(dwc->regs, DWC3_GCTL);
38 - reg |= DWC3_GCTL_CORESOFTRESET;
39 - dwc3_writel(dwc->regs, DWC3_GCTL, reg);
41 - /* Assert USB3 PHY reset */
42 - reg = dwc3_readl(dwc->regs, DWC3_GUSB3PIPECTL(0));
43 - reg |= DWC3_GUSB3PIPECTL_PHYSOFTRST;
44 - dwc3_writel(dwc->regs, DWC3_GUSB3PIPECTL(0), reg);
46 - /* Assert USB2 PHY reset */
47 - reg = dwc3_readl(dwc->regs, DWC3_GUSB2PHYCFG(0));
48 - reg |= DWC3_GUSB2PHYCFG_PHYSOFTRST;
49 - dwc3_writel(dwc->regs, DWC3_GUSB2PHYCFG(0), reg);
51 usb_phy_init(dwc->usb2_phy);
52 usb_phy_init(dwc->usb3_phy);
53 ret = phy_init(dwc->usb2_generic_phy);
54 @@ -95,26 +81,28 @@ static int dwc3_core_soft_reset(struct d
55 phy_exit(dwc->usb2_generic_phy);
60 - /* Clear USB3 PHY reset */
61 - reg = dwc3_readl(dwc->regs, DWC3_GUSB3PIPECTL(0));
62 - reg &= ~DWC3_GUSB3PIPECTL_PHYSOFTRST;
63 - dwc3_writel(dwc->regs, DWC3_GUSB3PIPECTL(0), reg);
65 - /* Clear USB2 PHY reset */
66 - reg = dwc3_readl(dwc->regs, DWC3_GUSB2PHYCFG(0));
67 - reg &= ~DWC3_GUSB2PHYCFG_PHYSOFTRST;
68 - dwc3_writel(dwc->regs, DWC3_GUSB2PHYCFG(0), reg);
72 - /* After PHYs are stable we can take Core out of reset state */
73 - reg = dwc3_readl(dwc->regs, DWC3_GCTL);
74 - reg &= ~DWC3_GCTL_CORESOFTRESET;
75 - dwc3_writel(dwc->regs, DWC3_GCTL, reg);
77 + * We're resetting only the device side because, if we're in host mode,
78 + * XHCI driver will reset the host block. If dwc3 was configured for
79 + * host-only mode, then we can return early.
81 + if (dwc->dr_mode == USB_DR_MODE_HOST)
84 + reg = dwc3_readl(dwc->regs, DWC3_DCTL);
85 + reg |= DWC3_DCTL_CSFTRST;
86 + dwc3_writel(dwc->regs, DWC3_DCTL, reg);
89 + reg = dwc3_readl(dwc->regs, DWC3_DCTL);
90 + if (!(reg & DWC3_DCTL_CSFTRST))
94 + } while (--retries);