123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596 |
- From patchwork Tue Mar 12 09:51:42 2019
- Content-Type: text/plain; charset="utf-8"
- MIME-Version: 1.0
- Content-Transfer-Encoding: 7bit
- X-Patchwork-Submitter: Stanislaw Gruszka <[email protected]>
- X-Patchwork-Id: 10848961
- X-Patchwork-Delegate: [email protected]
- From: Stanislaw Gruszka <[email protected]>
- To: [email protected]
- Cc: =?utf-8?q?Tomislav_Po=C5=BEega?= <[email protected]>,
- Daniel Golle <[email protected]>, Felix Fietkau <[email protected]>,
- Mathias Kresin <[email protected]>
- Subject: [PATCH v3 3/4] rt2x00: check number of EPROTO errors
- Date: Tue, 12 Mar 2019 10:51:42 +0100
- Message-Id: <[email protected]>
- In-Reply-To: <[email protected]>
- References: <[email protected]>
- Some USB host devices/drivers on some conditions can always return
- EPROTO error on submitted URBs. That can cause infinity loop in the
- rt2x00 driver.
- Since we can have single EPROTO errors we can not mark as device as
- removed to avoid infinity loop. However we can count consecutive
- EPROTO errors and mark device as removed if get lot of it.
- I choose number 10 as threshold.
- Reported-and-tested-by: Randy Oostdyk <[email protected]>
- Signed-off-by: Stanislaw Gruszka <[email protected]>
- ---
- drivers/net/wireless/ralink/rt2x00/rt2x00.h | 1 +
- drivers/net/wireless/ralink/rt2x00/rt2x00usb.c | 22 +++++++++++++++++++---
- 2 files changed, 20 insertions(+), 3 deletions(-)
- --- a/drivers/net/wireless/ralink/rt2x00/rt2x00.h
- +++ b/drivers/net/wireless/ralink/rt2x00/rt2x00.h
- @@ -1017,6 +1017,7 @@ struct rt2x00_dev {
- unsigned int extra_tx_headroom;
-
- struct usb_anchor *anchor;
- + unsigned int num_proto_errs;
-
- /* Clock for System On Chip devices. */
- struct clk *clk;
- --- a/drivers/net/wireless/ralink/rt2x00/rt2x00usb.c
- +++ b/drivers/net/wireless/ralink/rt2x00/rt2x00usb.c
- @@ -31,6 +31,22 @@
- #include "rt2x00.h"
- #include "rt2x00usb.h"
-
- +static bool rt2x00usb_check_usb_error(struct rt2x00_dev *rt2x00dev, int status)
- +{
- + if (status == -ENODEV || status == -ENOENT)
- + return true;
- +
- + if (status == -EPROTO || status == -ETIMEDOUT)
- + rt2x00dev->num_proto_errs++;
- + else
- + rt2x00dev->num_proto_errs = 0;
- +
- + if (rt2x00dev->num_proto_errs > 3)
- + return true;
- +
- + return false;
- +}
- +
- /*
- * Interfacing with the HW.
- */
- @@ -57,7 +73,7 @@ int rt2x00usb_vendor_request(struct rt2x
- if (status >= 0)
- return 0;
-
- - if (status == -ENODEV || status == -ENOENT) {
- + if (rt2x00usb_check_usb_error(rt2x00dev, status)) {
- /* Device has disappeared. */
- clear_bit(DEVICE_STATE_PRESENT, &rt2x00dev->flags);
- break;
- @@ -321,7 +337,7 @@ static bool rt2x00usb_kick_tx_entry(stru
-
- status = usb_submit_urb(entry_priv->urb, GFP_ATOMIC);
- if (status) {
- - if (status == -ENODEV || status == -ENOENT)
- + if (rt2x00usb_check_usb_error(rt2x00dev, status))
- clear_bit(DEVICE_STATE_PRESENT, &rt2x00dev->flags);
- set_bit(ENTRY_DATA_IO_FAILED, &entry->flags);
- rt2x00lib_dmadone(entry);
- @@ -410,7 +426,7 @@ static bool rt2x00usb_kick_rx_entry(stru
-
- status = usb_submit_urb(entry_priv->urb, GFP_ATOMIC);
- if (status) {
- - if (status == -ENODEV || status == -ENOENT)
- + if (rt2x00usb_check_usb_error(rt2x00dev, status))
- clear_bit(DEVICE_STATE_PRESENT, &rt2x00dev->flags);
- set_bit(ENTRY_DATA_IO_FAILED, &entry->flags);
- rt2x00lib_dmadone(entry);
|