Linux USB
 help / color / mirror / Atom feed
From: Michal Pecio <michal.pecio@gmail.com>
To: Julian Oes <julian@oes.ch>
Cc: oneukum@suse.com, gregkh@linuxfoundation.org, johan@kernel.org,
	linux-kernel@vger.kernel.org, linux-usb@vger.kernel.org
Subject: Re: [PATCH v2] USB: serial: generic: recover from a stalled bulk-in endpoint
Date: Wed, 2 Sep 2026 06:42:04 +0200	[thread overview]
Message-ID: <20260902064204.1a47cd73.michal.pecio@gmail.com> (raw)
In-Reply-To: <20260901231355.114733-1-julian@oes.ch>

On Wed,  2 Sep 2026 11:13:53 +1200, Julian Oes wrote:
> On Tue, Sep 01, 2026 at 10:28:08AM +0200, Oliver Neukum wrote:
> > But why do you get a port stalling?
> > It seems your hardware is quite broken.  
> 
> Maybe, yes, but as I wrote to Greg, I believe I have seen this (or
> similar stalls) over the years in the past with various hardware.
> Maybe it's just me but if it is not, it would be nice to fix it for
> others too.

What you are probably seeing is USB 2.0 hub(s) returning STALL
handshake when a transaction attempt with downstream low/full-speed
device fails three times. See USB 2.0 section 11.17.1 page 364.

If that's the case, the device endpoint isn't actually halted and you
would see the traffic resume if you simply ignored the error and kept
resubmitting until communication is restored.

That being said, calling usb_clear_halt() is indeed the only recovery
supported by USB specs, both for -EPIPE and -EPROTO or similar. Linux
has traditionally ignored this and things are quite broken sometimes,
particularly with xhci-hcd, even if you call usb_clear_halt().

I suppose you can try this and see how it works, and if you run into
xhci-hcd bugs we could try to fix them too. The -EPIPE case is easier
because drivers don't rely on out of spec behavior of the USB stack.

Related discussion: (gonna need *a lot* of popcorn for that one)
https://lore.kernel.org/linux-usb/261996a8-7ad4-4df2-a469-f6602da71255@suse.com/

Alan Stern tried to come up with some solution in USB core, but not sure
how far that got.

It seems there is only one risk of usb_clear_halt() in such cases:
- you send a packet to an OUT endpoint
- and the device accepts it but you never receive the ACK
- even after re-sending three times
- you call usb_clear_halt() and queue the same packet again
- the device may accept the packet twice

The recommended solution is to query the device by class-defined means
to determine whether it has received the apparently lost packet or not,
or to put it into some known and desired state. Common problem: nobody
knows how to do that with given device.

(And the same could happen in IN direction if you usb_clear_halt() after
a successful transfer, but drivers are unlikely to do that).

> > Your conceptual mistake is seeing the recovery from stall
> > as an indivisible process. It is not, as it has two parts.
> > Once your port is in a stall, you should send the feature
> > request to unblock the halt. There is no reason to cancel the
> > feature request if you close a port. You just need to refrain
> > from resubmitting the read URB.  
> 
> That makes sense. I'll try to fix that for v3.

Yes, if you are going there, just clear the halt and reset everything
unconditionally. Then the pipe will be ready for new transfers.

One note about rate limiting: it would perhaps make sense to perform
the first attempt ASAP and only slow down for retries. But arguably
anything at all is better than just giving up like now.

Regards,
Michal

  reply	other threads:[~2026-09-02  4:42 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-09-01  3:49 [PATCH v2] USB: serial: generic: recover from a stalled bulk-in endpoint Julian Oes
2026-09-01  4:33 ` Greg Kroah-Hartman
2026-09-01 22:44   ` Julian Oes
2026-09-01  8:28 ` Oliver Neukum
2026-09-01 23:13   ` Julian Oes
2026-09-02  4:42     ` Michal Pecio [this message]
2026-09-02  8:40       ` Oliver Neukum
2026-09-02 14:33       ` Alan Stern

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260902064204.1a47cd73.michal.pecio@gmail.com \
    --to=michal.pecio@gmail.com \
    --cc=gregkh@linuxfoundation.org \
    --cc=johan@kernel.org \
    --cc=julian@oes.ch \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-usb@vger.kernel.org \
    --cc=oneukum@suse.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox