Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 55bcdce8 authored by Alan Stern's avatar Alan Stern Committed by Greg Kroah-Hartman
Browse files

USB: EHCI: remove ASS/PSS polling timeout



This patch (as1647) attempts to work around a problem that seems to
affect some nVidia EHCI controllers.  They sometimes take a very long
time to turn off their async or periodic schedules.  I don't know if
this is a result of other problems, but in any case it seems wise not
to depend on schedule enables or disables taking effect in any
specific length of time.

The patch removes the existing 20-ms timeout for enabling and
disabling the schedules.  The driver will now continue to poll the
schedule state at 1-ms intervals until the controller finally decides
to obey the most recent command issued by the driver.  Just in case
this hides a problem, a debugging message will be logged if the
controller takes longer than 20 polls.

I don't know if this will actually fix anything, but it can't hurt.

Signed-off-by: default avatarAlan Stern <stern@rowland.harvard.edu>
Tested-by: default avatarPiergiorgio Sartor <piergiorgio.sartor@nexgo.de>
CC: <stable@vger.kernel.org>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent a28dde61
Loading
Loading
Loading
Loading
+15 −14
Original line number Diff line number Diff line
@@ -113,14 +113,15 @@ static void ehci_poll_ASS(struct ehci_hcd *ehci)

	if (want != actual) {

		/* Poll again later, but give up after about 20 ms */
		if (ehci->ASS_poll_count++ < 20) {
		/* Poll again later */
		ehci_enable_event(ehci, EHCI_HRTIMER_POLL_ASS, true);
		++ehci->ASS_poll_count;
		return;
	}
		ehci_dbg(ehci, "Waited too long for the async schedule status (%x/%x), giving up\n",
				want, actual);
	}

	if (ehci->ASS_poll_count > 20)
		ehci_dbg(ehci, "ASS poll count reached %d\n",
				ehci->ASS_poll_count);
	ehci->ASS_poll_count = 0;

	/* The status is up-to-date; restart or stop the schedule as needed */
@@ -159,14 +160,14 @@ static void ehci_poll_PSS(struct ehci_hcd *ehci)

	if (want != actual) {

		/* Poll again later, but give up after about 20 ms */
		if (ehci->PSS_poll_count++ < 20) {
		/* Poll again later */
		ehci_enable_event(ehci, EHCI_HRTIMER_POLL_PSS, true);
		return;
	}
		ehci_dbg(ehci, "Waited too long for the periodic schedule status (%x/%x), giving up\n",
				want, actual);
	}

	if (ehci->PSS_poll_count > 20)
		ehci_dbg(ehci, "PSS poll count reached %d\n",
				ehci->PSS_poll_count);
	ehci->PSS_poll_count = 0;

	/* The status is up-to-date; restart or stop the schedule as needed */