summaryrefslogtreecommitdiff
path: root/drivers/usb/host/ehci.h
diff options
context:
space:
mode:
authorIngo Molnar <mingo@elte.hu>2008-07-11 10:46:50 +0200
committerIngo Molnar <mingo@elte.hu>2008-07-11 10:46:50 +0200
commit0c81b2a1448bc6a2a9b2d6469fb0669fb4b25e5b (patch)
tree6f82579cae6d6e39fa9f837a3c349ded51e19d14 /drivers/usb/host/ehci.h
parent0729fbf3bc70870370b4f43d652f05a468dc68b8 (diff)
parent70ff05554f91a1edda1f11684da1dbde09e2feea (diff)
Merge branch 'linus' into core/rcu
Conflicts: include/linux/rculist.h kernel/rcupreempt.c Signed-off-by: Ingo Molnar <mingo@elte.hu>
Diffstat (limited to 'drivers/usb/host/ehci.h')
-rw-r--r--drivers/usb/host/ehci.h19
1 files changed, 10 insertions, 9 deletions
diff --git a/drivers/usb/host/ehci.h b/drivers/usb/host/ehci.h
index 35a03095757e..90245fd8bac4 100644
--- a/drivers/usb/host/ehci.h
+++ b/drivers/usb/host/ehci.h
@@ -177,6 +177,15 @@ timer_action_done (struct ehci_hcd *ehci, enum ehci_timer_action action)
static inline void
timer_action (struct ehci_hcd *ehci, enum ehci_timer_action action)
{
+ /* Don't override timeouts which shrink or (later) disable
+ * the async ring; just the I/O watchdog. Note that if a
+ * SHRINK were pending, OFF would never be requested.
+ */
+ if (timer_pending(&ehci->watchdog)
+ && ((BIT(TIMER_ASYNC_SHRINK) | BIT(TIMER_ASYNC_OFF))
+ & ehci->actions))
+ return;
+
if (!test_and_set_bit (action, &ehci->actions)) {
unsigned long t;
@@ -192,15 +201,7 @@ timer_action (struct ehci_hcd *ehci, enum ehci_timer_action action)
t = EHCI_SHRINK_JIFFIES;
break;
}
- t += jiffies;
- // all timings except IAA watchdog can be overridden.
- // async queue SHRINK often precedes IAA. while it's ready
- // to go OFF neither can matter, and afterwards the IO
- // watchdog stops unless there's still periodic traffic.
- if (time_before_eq(t, ehci->watchdog.expires)
- && timer_pending (&ehci->watchdog))
- return;
- mod_timer (&ehci->watchdog, t);
+ mod_timer(&ehci->watchdog, t + jiffies);
}
}