Message ID | d56e95e0e6e7d9ad5d1f3d8d659ab3f572dc9df3.1537280238.git.hminas@synopsys.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | usb: dwc2: Disable all EP's on disconnect | expand |
Hi Minas, I love your patch! Perhaps something to improve: [auto build test WARNING on balbi-usb/next] [also build test WARNING on v4.19-rc4 next-20180918] [if your patch is applied to the wrong git tree, please drop us a note to help improve the system] url: https://github.com/0day-ci/linux/commits/Minas-Harutyunyan/usb-dwc2-Disable-all-EP-s-on-disconnect/20180919-104259 base: https://git.kernel.org/pub/scm/linux/kernel/git/balbi/usb.git next config: x86_64-allmodconfig (attached as .config) compiler: gcc-7 (Debian 7.3.0-1) 7.3.0 reproduce: # save the attached .config to linux build tree make ARCH=x86_64 All warnings (new ones prefixed by >>): >> drivers/usb/dwc2/gadget.c:4053:9: warning: context imbalance in 'dwc2_hsotg_ep_disable' - different lock contexts for basic block >> drivers/usb/dwc2/gadget.c:4361:28: warning: context imbalance in 'dwc2_hsotg_udc_stop' - different lock contexts for basic block vim +/dwc2_hsotg_ep_disable +4053 drivers/usb/dwc2/gadget.c 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 3993 8b9bc4608 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 3994 /** 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 3995 * dwc2_hsotg_ep_disable - disable given endpoint 8b9bc4608 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 3996 * @ep: The endpoint to disable. 8b9bc4608 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 3997 */ 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 3998 static int dwc2_hsotg_ep_disable(struct usb_ep *ep) 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 3999 { 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 4000 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); 941fcce4f drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-11-11 4001 struct dwc2_hsotg *hsotg = hs_ep->parent; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4002 int dir_in = hs_ep->dir_in; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4003 int index = hs_ep->index; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4004 unsigned long flags; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4005 u32 epctrl_reg; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4006 u32 ctrl; a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4007 int locked; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4008 1e0112937 drivers/usb/dwc2/gadget.c Marek Szyprowski 2014-09-09 4009 dev_dbg(hsotg->dev, "%s(ep %p)\n", __func__, ep); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4010 c6f5c050e drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4011 if (ep == &hsotg->eps_out[0]->ep) { 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4012 dev_err(hsotg->dev, "%s: called for ep0\n", __func__); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4013 return -EINVAL; 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4014 } 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4015 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4016 if (hsotg->op_state != OTG_STATE_B_PERIPHERAL) { 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4017 dev_err(hsotg->dev, "%s: called in host mode?\n", __func__); 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4018 return -EINVAL; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4019 } 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4020 94cb8fd63 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 4021 epctrl_reg = dir_in ? DIEPCTL(index) : DOEPCTL(index); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4022 a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4023 locked = spin_trylock(&hsotg->lock); a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4024 spin_unlock(&hsotg->lock); 5ad1d3160 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-06-14 4025 spin_lock_irqsave(&hsotg->lock, flags); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4026 f25c42b8d drivers/usb/dwc2/gadget.c Gevorg Sahakyan 2018-07-26 4027 ctrl = dwc2_readl(hsotg, epctrl_reg); a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4028 a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4029 if (ctrl & DXEPCTL_EPENA) a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4030 dwc2_hsotg_ep_stop_xfr(hsotg, hs_ep); a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4031 47a1685f1 drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-04-14 4032 ctrl &= ~DXEPCTL_EPENA; 47a1685f1 drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-04-14 4033 ctrl &= ~DXEPCTL_USBACTEP; 47a1685f1 drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-04-14 4034 ctrl |= DXEPCTL_SNAK; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4035 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4036 dev_dbg(hsotg->dev, "%s: DxEPCTL=0x%08x\n", __func__, ctrl); f25c42b8d drivers/usb/dwc2/gadget.c Gevorg Sahakyan 2018-07-26 4037 dwc2_writel(hsotg, ctrl, epctrl_reg); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4038 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4039 /* disable endpoint interrupts */ 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 4040 dwc2_hsotg_ctrl_epint(hsotg, hs_ep->index, hs_ep->dir_in, 0); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4041 1141ea01d drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4042 /* terminate all requests with shutdown */ 1141ea01d drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4043 kill_all_requests(hsotg, hs_ep, -ESHUTDOWN); 1141ea01d drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4044 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4045 hsotg->fifo_map &= ~(1 << hs_ep->fifo_index); 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4046 hs_ep->fifo_index = 0; 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4047 hs_ep->fifo_size = 0; 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4048 22258f490 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-06-14 4049 spin_unlock_irqrestore(&hsotg->lock, flags); a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4050 if (!locked) a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4051 spin_lock(&hsotg->lock); a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4052 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 @4053 return 0; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4054 } 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4055 :::::: The code at line 4053 was first introduced by commit :::::: 5b7d70c6dbf2db786395cbd21750a1a4ce222f84 USB: Gadget driver for Samsung HS/OtG block :::::: TO: Ben Dooks <ben@simtec.co.uk> :::::: CC: Greg Kroah-Hartman <gregkh@suse.de> --- 0-DAY kernel test infrastructure Open Source Technology Center https://lists.01.org/pipermail/kbuild-all Intel Corporation
Hi Minas, url: https://github.com/0day-ci/linux/commits/Minas-Harutyunyan/usb-dwc2-Disable-all-EP-s-on-disconnect/20180919-104259 base: https://git.kernel.org/pub/scm/linux/kernel/git/balbi/usb.git next smatch warnings: drivers/usb/dwc2/gadget.c:4024 dwc2_hsotg_ep_disable() error: double unlock 'spin_lock:&hsotg->lock' drivers/usb/dwc2/gadget.c:4350 dwc2_hsotg_udc_stop() error: double unlock 'spin_lock:&hsotg->lock' # https://github.com/0day-ci/linux/commit/a4705c3fee2053e95791210eb435a04b665f6dc3 git remote add linux-review https://github.com/0day-ci/linux git remote update linux-review git checkout a4705c3fee2053e95791210eb435a04b665f6dc3 vim +4024 drivers/usb/dwc2/gadget.c 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 3993 8b9bc4608 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 3994 /** 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 3995 * dwc2_hsotg_ep_disable - disable given endpoint 8b9bc4608 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 3996 * @ep: The endpoint to disable. 8b9bc4608 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 3997 */ 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 3998 static int dwc2_hsotg_ep_disable(struct usb_ep *ep) 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 3999 { 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 4000 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); 941fcce4f drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-11-11 4001 struct dwc2_hsotg *hsotg = hs_ep->parent; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4002 int dir_in = hs_ep->dir_in; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4003 int index = hs_ep->index; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4004 unsigned long flags; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4005 u32 epctrl_reg; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4006 u32 ctrl; a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4007 int locked; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4008 1e0112937 drivers/usb/dwc2/gadget.c Marek Szyprowski 2014-09-09 4009 dev_dbg(hsotg->dev, "%s(ep %p)\n", __func__, ep); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4010 c6f5c050e drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4011 if (ep == &hsotg->eps_out[0]->ep) { 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4012 dev_err(hsotg->dev, "%s: called for ep0\n", __func__); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4013 return -EINVAL; 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4014 } 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4015 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4016 if (hsotg->op_state != OTG_STATE_B_PERIPHERAL) { 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4017 dev_err(hsotg->dev, "%s: called in host mode?\n", __func__); 9b481092c drivers/usb/dwc2/gadget.c John Stultz 2017-10-23 4018 return -EINVAL; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4019 } 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4020 94cb8fd63 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-05-04 4021 epctrl_reg = dir_in ? DIEPCTL(index) : DOEPCTL(index); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4022 a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4023 locked = spin_trylock(&hsotg->lock); a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 @4024 spin_unlock(&hsotg->lock); 5ad1d3160 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-06-14 4025 spin_lock_irqsave(&hsotg->lock, flags); This is obviously deliberate that we drop the other thread's lock and then take it ourselves. But I don't think that can be right at all. How do we know that it's safe for the other thread to drop the lock? There should at least be a long comment in front of the code explaining why it's safe to steal the lock like this. 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4026 f25c42b8d drivers/usb/dwc2/gadget.c Gevorg Sahakyan 2018-07-26 4027 ctrl = dwc2_readl(hsotg, epctrl_reg); a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4028 a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4029 if (ctrl & DXEPCTL_EPENA) a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4030 dwc2_hsotg_ep_stop_xfr(hsotg, hs_ep); a4f827714 drivers/usb/dwc2/gadget.c Vahram Aharonyan 2016-11-14 4031 47a1685f1 drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-04-14 4032 ctrl &= ~DXEPCTL_EPENA; 47a1685f1 drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-04-14 4033 ctrl &= ~DXEPCTL_USBACTEP; 47a1685f1 drivers/usb/dwc2/gadget.c Dinh Nguyen 2014-04-14 4034 ctrl |= DXEPCTL_SNAK; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4035 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4036 dev_dbg(hsotg->dev, "%s: DxEPCTL=0x%08x\n", __func__, ctrl); f25c42b8d drivers/usb/dwc2/gadget.c Gevorg Sahakyan 2018-07-26 4037 dwc2_writel(hsotg, ctrl, epctrl_reg); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4038 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4039 /* disable endpoint interrupts */ 1f91b4cc0 drivers/usb/dwc2/gadget.c Felipe Balbi 2015-08-06 4040 dwc2_hsotg_ctrl_epint(hsotg, hs_ep->index, hs_ep->dir_in, 0); 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4041 1141ea01d drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4042 /* terminate all requests with shutdown */ 1141ea01d drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4043 kill_all_requests(hsotg, hs_ep, -ESHUTDOWN); 1141ea01d drivers/usb/dwc2/gadget.c Mian Yousaf Kaukab 2015-01-09 4044 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4045 hsotg->fifo_map &= ~(1 << hs_ep->fifo_index); 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4046 hs_ep->fifo_index = 0; 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4047 hs_ep->fifo_size = 0; 1c07b20ea drivers/usb/dwc2/gadget.c Robert Baldyga 2016-08-29 4048 22258f490 drivers/usb/gadget/s3c-hsotg.c Lukasz Majewski 2012-06-14 4049 spin_unlock_irqrestore(&hsotg->lock, flags); a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4050 if (!locked) a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4051 spin_lock(&hsotg->lock); a4705c3fe drivers/usb/dwc2/gadget.c Minas Harutyunyan 2018-09-18 4052 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4053 return 0; 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4054 } 5b7d70c6d drivers/usb/gadget/s3c-hsotg.c Ben Dooks 2009-06-02 4055 --- 0-DAY kernel test infrastructure Open Source Technology Center https://lists.01.org/pipermail/kbuild-all Intel Corporation
Hi Dan, On 9/20/2018 1:49 PM, Dan Carpenter wrote: > is is obviously deliberate that we drop the other thread's lock and > then take it ourselves. But I don't think that can be right at all. > How do we know that it's safe for the other thread to drop the lock? > > There should at least be a long comment in front of the code explaining > why it's safe to steal the lock like this. Please review patch version 2: "[PATCH v2] usb: dwc2: Disable all EP's on disconnect" Thanks, Minas
On Thu, Sep 20, 2018 at 10:21:26AM +0000, Minas Harutyunyan wrote: > Hi Dan, > > On 9/20/2018 1:49 PM, Dan Carpenter wrote: > > is is obviously deliberate that we drop the other thread's lock and > > then take it ourselves. But I don't think that can be right at all. > > How do we know that it's safe for the other thread to drop the lock? > > > > There should at least be a long comment in front of the code explaining > > why it's safe to steal the lock like this. > > Please review patch version 2: "[PATCH v2] usb: dwc2: Disable all EP's > on disconnect" These are automated emails from the kbuild bot. I just review them and forward them. I'm not on the list. I'm going to trust that you fixed it in an appropriate way. :) regards, dan carpenter
diff --git a/drivers/usb/dwc2/gadget.c b/drivers/usb/dwc2/gadget.c index 220c0f9b89b0..30975731812e 100644 --- a/drivers/usb/dwc2/gadget.c +++ b/drivers/usb/dwc2/gadget.c @@ -3109,6 +3109,8 @@ static void kill_all_requests(struct dwc2_hsotg *hsotg, dwc2_hsotg_txfifo_flush(hsotg, ep->fifo_index); } +static int dwc2_hsotg_ep_disable(struct usb_ep *ep); + /** * dwc2_hsotg_disconnect - disconnect service * @hsotg: The device state. @@ -3127,13 +3129,12 @@ void dwc2_hsotg_disconnect(struct dwc2_hsotg *hsotg) hsotg->connected = 0; hsotg->test_mode = 0; + /* all endpoints should be shutdown */ for (ep = 0; ep < hsotg->num_of_eps; ep++) { if (hsotg->eps_in[ep]) - kill_all_requests(hsotg, hsotg->eps_in[ep], - -ESHUTDOWN); + dwc2_hsotg_ep_disable(&hsotg->eps_in[ep]->ep); if (hsotg->eps_out[ep]) - kill_all_requests(hsotg, hsotg->eps_out[ep], - -ESHUTDOWN); + dwc2_hsotg_ep_disable(&hsotg->eps_out[ep]->ep); } call_gadget(hsotg, disconnect); @@ -3191,13 +3192,23 @@ void dwc2_hsotg_core_init_disconnected(struct dwc2_hsotg *hsotg, u32 val; u32 usbcfg; u32 dcfg = 0; + int ep; /* Kill any ep0 requests as controller will be reinitialized */ kill_all_requests(hsotg, hsotg->eps_out[0], -ECONNRESET); - if (!is_usb_reset) + if (!is_usb_reset) { if (dwc2_core_reset(hsotg, true)) return; + } else { + /* all endpoints should be shutdown */ + for (ep = 1; ep < hsotg->num_of_eps; ep++) { + if (hsotg->eps_in[ep]) + dwc2_hsotg_ep_disable(&hsotg->eps_in[ep]->ep); + if (hsotg->eps_out[ep]) + dwc2_hsotg_ep_disable(&hsotg->eps_out[ep]->ep); + } + } /* * we must now enable ep0 ready for host detection and then @@ -3993,6 +4004,7 @@ static int dwc2_hsotg_ep_disable(struct usb_ep *ep) unsigned long flags; u32 epctrl_reg; u32 ctrl; + int locked; dev_dbg(hsotg->dev, "%s(ep %p)\n", __func__, ep); @@ -4008,6 +4020,8 @@ static int dwc2_hsotg_ep_disable(struct usb_ep *ep) epctrl_reg = dir_in ? DIEPCTL(index) : DOEPCTL(index); + locked = spin_trylock(&hsotg->lock); + spin_unlock(&hsotg->lock); spin_lock_irqsave(&hsotg->lock, flags); ctrl = dwc2_readl(hsotg, epctrl_reg); @@ -4033,6 +4047,9 @@ static int dwc2_hsotg_ep_disable(struct usb_ep *ep) hs_ep->fifo_size = 0; spin_unlock_irqrestore(&hsotg->lock, flags); + if (!locked) + spin_lock(&hsotg->lock); + return 0; } @@ -4316,6 +4333,7 @@ static int dwc2_hsotg_udc_stop(struct usb_gadget *gadget) struct dwc2_hsotg *hsotg = to_hsotg(gadget); unsigned long flags = 0; int ep; + int locked; if (!hsotg) return -ENODEV; @@ -4328,6 +4346,8 @@ static int dwc2_hsotg_udc_stop(struct usb_gadget *gadget) dwc2_hsotg_ep_disable(&hsotg->eps_out[ep]->ep); } + locked = spin_trylock(&hsotg->lock); + spin_unlock(&hsotg->lock); spin_lock_irqsave(&hsotg->lock, flags); hsotg->driver = NULL; @@ -4335,6 +4355,8 @@ static int dwc2_hsotg_udc_stop(struct usb_gadget *gadget) hsotg->enabled = 0; spin_unlock_irqrestore(&hsotg->lock, flags); + if (!locked) + spin_lock(&hsotg->lock); if (!IS_ERR_OR_NULL(hsotg->uphy)) otg_set_peripheral(hsotg->uphy->otg, NULL);
Disabling all EP's allow to reset EP's to initial state. On disconnect disable all EP's instead of just killing all requests. Because of some platform didn't catch disconnect event, same stuff added to dwc2_hsotg_core_init_disconnected() function when USB reset detected on the bus. In dwc2_hsotg_ep_disable() function before locking hsotg->lock, check if it locked by calling functions then unlock. Lock again on exit if it was locked. Same lock checking flow added to dwc2_hsotg_udc_stop() function. Signed-off-by: Minas Harutyunyan <hminas@synopsys.com> --- drivers/usb/dwc2/gadget.c | 32 +++++++++++++++++++++++++++----- 1 file changed, 27 insertions(+), 5 deletions(-)