diff options
author | Felipe Balbi <felipe.balbi@linux.intel.com> | 2016-10-04 15:14:43 +0300 |
---|---|---|
committer | Sasha Levin <alexander.levin@verizon.com> | 2016-11-01 15:17:22 -0400 |
commit | 517052446f36f78b13502ccafc8884b6339643d2 (patch) | |
tree | 710b4dbb93e8513fc0a1089fcc216f046ec5a846 /drivers/usb | |
parent | 66f38bf99faa0b30d7486906738da66b56fb7d80 (diff) |
usb: gadget: function: u_ether: don't starve tx request queue
[ Upstream commit 6c83f77278f17a7679001027e9231291c20f0d8a ]
If we don't guarantee that we will always get an
interrupt at least when we're queueing our very last
request, we could fall into situation where we queue
every request with 'no_interrupt' set. This will
cause the link to get stuck.
The behavior above has been triggered with g_ether
and dwc3.
Cc: <stable@vger.kernel.org>
Reported-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Signed-off-by: Felipe Balbi <felipe.balbi@linux.intel.com>
Signed-off-by: Sasha Levin <alexander.levin@verizon.com>
Diffstat (limited to 'drivers/usb')
-rw-r--r-- | drivers/usb/gadget/function/u_ether.c | 5 |
1 files changed, 3 insertions, 2 deletions
diff --git a/drivers/usb/gadget/function/u_ether.c b/drivers/usb/gadget/function/u_ether.c index f1fd777ef4ec..82e63f73bfd5 100644 --- a/drivers/usb/gadget/function/u_ether.c +++ b/drivers/usb/gadget/function/u_ether.c @@ -591,8 +591,9 @@ static netdev_tx_t eth_start_xmit(struct sk_buff *skb, /* throttle high/super speed IRQ rate back slightly */ if (gadget_is_dualspeed(dev->gadget)) - req->no_interrupt = (dev->gadget->speed == USB_SPEED_HIGH || - dev->gadget->speed == USB_SPEED_SUPER) + req->no_interrupt = (((dev->gadget->speed == USB_SPEED_HIGH || + dev->gadget->speed == USB_SPEED_SUPER)) && + !list_empty(&dev->tx_reqs)) ? ((atomic_read(&dev->tx_qlen) % dev->qmult) != 0) : 0; |