usb_get_from_anchor() hands over a reference to the URB, which the caller has to release. atusb_work_urbs() never does, so every URB collected from the idle anchor keeps an extra reference: the reference count grows on each retry cycle and the URBs are never freed on disconnect. Drop the reference after a successful submission, and after the URB has been put back on the idle anchor when submission failed, as the HCD holds its own reference while the URB is in flight. Fixes: 7490b008d123 ("ieee802154: add support for atusb transceiver") Cc: stable@vger.kernel.org Signed-off-by: Wentao Liang --- drivers/net/ieee802154/atusb.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/net/ieee802154/atusb.c b/drivers/net/ieee802154/atusb.c index 5f7fc4ee7a07..3dbb142eccb2 100644 --- a/drivers/net/ieee802154/atusb.c +++ b/drivers/net/ieee802154/atusb.c @@ -180,9 +180,15 @@ static void atusb_work_urbs(struct work_struct *work) if (!urb) return; ret = atusb_submit_rx_urb(atusb, urb); + if (!ret) + usb_put_urb(urb); } while (!ret); + /* The reference obtained above is dropped once the URB is back + * on the idle anchor. + */ usb_anchor_urb(urb, &atusb->idle_urbs); + usb_put_urb(urb); dev_warn_ratelimited(&usb_dev->dev, "atusb_in: can't allocate/submit URB (%d)\n", ret); schedule_delayed_work(&atusb->work, -- 2.34.1