mirror of
https://github.com/Ysurac/openmptcprouter.git
synced 2025-02-15 04:42:02 +00:00
112 lines
3.3 KiB
Diff
112 lines
3.3 KiB
Diff
From 84251d27a9fbcae8aa9dbbb0cecc0ea1599dd23a Mon Sep 17 00:00:00 2001
|
|
From: Minas Harutyunyan <Minas.Harutyunyan@synopsys.com>
|
|
Date: Wed, 19 Sep 2018 18:13:52 +0400
|
|
Subject: [PATCH 312/432] usb: dwc2: Disable all EP's on disconnect
|
|
|
|
commit dccf1bad4be7eaa096c1f3697bd37883f9a08ecb upstream.
|
|
|
|
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.
|
|
|
|
Changed from version 1:
|
|
Changed lock acquire flow in dwc2_hsotg_ep_disable()
|
|
function.
|
|
|
|
Signed-off-by: Minas Harutyunyan <hminas@synopsys.com>
|
|
Signed-off-by: Felipe Balbi <felipe.balbi@linux.intel.com>
|
|
---
|
|
drivers/usb/dwc2/gadget.c | 30 +++++++++++++++++++++++-------
|
|
1 file changed, 23 insertions(+), 7 deletions(-)
|
|
|
|
diff --git a/drivers/usb/dwc2/gadget.c b/drivers/usb/dwc2/gadget.c
|
|
index 220c0f9b89b0..79189db4bf17 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,7 +4020,9 @@ static int dwc2_hsotg_ep_disable(struct usb_ep *ep)
|
|
|
|
epctrl_reg = dir_in ? DIEPCTL(index) : DOEPCTL(index);
|
|
|
|
- spin_lock_irqsave(&hsotg->lock, flags);
|
|
+ locked = spin_is_locked(&hsotg->lock);
|
|
+ if (!locked)
|
|
+ spin_lock_irqsave(&hsotg->lock, flags);
|
|
|
|
ctrl = dwc2_readl(hsotg, epctrl_reg);
|
|
|
|
@@ -4032,7 +4046,9 @@ static int dwc2_hsotg_ep_disable(struct usb_ep *ep)
|
|
hs_ep->fifo_index = 0;
|
|
hs_ep->fifo_size = 0;
|
|
|
|
- spin_unlock_irqrestore(&hsotg->lock, flags);
|
|
+ if (!locked)
|
|
+ spin_unlock_irqrestore(&hsotg->lock, flags);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
--
|
|
2.19.1
|
|
|