| From 8cfac9a6744fcb143cb3e94ce002f09fd17fadbb Mon Sep 17 00:00:00 2001 |
| From: Li Jun <jun.li@nxp.com> |
| Date: Wed, 8 Sep 2021 10:28:19 +0800 |
| Subject: [PATCH] usb: dwc3: core: balance phy init and exit |
| Git-commit: 8cfac9a6744fcb143cb3e94ce002f09fd17fadbb |
| References: git-fixes stable-5.14.9 |
| Patch-mainline: v5.15-rc3 |
| |
| After we start to do core soft reset while usb role switch, |
| the phy init is invoked at every switch to device mode, but |
| its counter part de-init is missing, this causes the actual |
| phy init can not be done when we really want to re-init phy |
| like system resume, because the counter maintained by phy |
| core is not 0. considering phy init is actually redundant for |
| role switch, so move out the phy init from core soft reset to |
| dwc3 core init where is the only place required. |
| |
| Fixes: f88359e1588b ("usb: dwc3: core: Do core softreset when switch mode") |
| Cc: <stable@vger.kernel.org> |
| Tested-by: faqiang.zhu <faqiang.zhu@nxp.com> |
| Tested-by: John Stultz <john.stultz@linaro.org> #HiKey960 |
| Acked-by: Felipe Balbi <balbi@kernel.org> |
| Signed-off-by: Li Jun <jun.li@nxp.com> |
| Link: https://lore.kernel.org/r/1631068099-13559-1-git-send-email-jun.li@nxp.com |
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |
| Signed-off-by: Oliver Neukum <oneukum@suse.com> |
| |
| drivers/usb/dwc3/core.c | 30 +++++++++++++----------------- |
| 1 file changed, 13 insertions(+), 17 deletions(-) |
| |
| diff --git a/drivers/usb/dwc3/core.c b/drivers/usb/dwc3/core.c |
| index 01866dcb953b..0104a80b185e 100644 |
| |
| |
| @@ -264,19 +264,6 @@ static int dwc3_core_soft_reset(struct dwc3 *dwc) |
| { |
| u32 reg; |
| int retries = 1000; |
| - int ret; |
| - |
| - usb_phy_init(dwc->usb2_phy); |
| - usb_phy_init(dwc->usb3_phy); |
| - ret = phy_init(dwc->usb2_generic_phy); |
| - if (ret < 0) |
| - return ret; |
| - |
| - ret = phy_init(dwc->usb3_generic_phy); |
| - if (ret < 0) { |
| - phy_exit(dwc->usb2_generic_phy); |
| - return ret; |
| - } |
| |
| /* |
| * We're resetting only the device side because, if we're in host mode, |
| @@ -310,9 +297,6 @@ static int dwc3_core_soft_reset(struct dwc3 *dwc) |
| udelay(1); |
| } while (--retries); |
| |
| - phy_exit(dwc->usb3_generic_phy); |
| - phy_exit(dwc->usb2_generic_phy); |
| - |
| return -ETIMEDOUT; |
| |
| done: |
| @@ -982,9 +966,21 @@ static int dwc3_core_init(struct dwc3 *dwc) |
| dwc->phys_ready = true; |
| } |
| |
| + usb_phy_init(dwc->usb2_phy); |
| + usb_phy_init(dwc->usb3_phy); |
| + ret = phy_init(dwc->usb2_generic_phy); |
| + if (ret < 0) |
| + goto err0a; |
| + |
| + ret = phy_init(dwc->usb3_generic_phy); |
| + if (ret < 0) { |
| + phy_exit(dwc->usb2_generic_phy); |
| + goto err0a; |
| + } |
| + |
| ret = dwc3_core_soft_reset(dwc); |
| if (ret) |
| - goto err0a; |
| + goto err1; |
| |
| if (hw_mode == DWC3_GHWPARAMS0_MODE_DRD && |
| !DWC3_VER_IS_WITHIN(DWC3, ANY, 194A)) { |
| -- |
| 2.26.2 |
| |