Commit bccbefaa authored by Alan Stern's avatar Alan Stern Committed by Greg Kroah-Hartman

USB: EHCI: simplify remainder computations

This patch (as1406) adds a micro-optimization to ehci-hcd's scheduling
code.  Instead of computing remainders with respect to the schedule
length, use bitwise-and (which is quicker).  We know that the schedule
length will always be a power of two, but the compiler doesn't have
this information.
Signed-off-by: default avatarAlan Stern <stern@rowland.harvard.edu>
CC: David Brownell <david-b@pacbell.net>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@suse.de>
parent ae68a83b
...@@ -1417,7 +1417,7 @@ iso_stream_schedule ( ...@@ -1417,7 +1417,7 @@ iso_stream_schedule (
if (!stream->highspeed) if (!stream->highspeed)
period <<= 3; period <<= 3;
now = ehci_readl(ehci, &ehci->regs->frame_index) % mod; now = ehci_readl(ehci, &ehci->regs->frame_index) & (mod - 1);
/* Typical case: reuse current schedule, stream is still active. /* Typical case: reuse current schedule, stream is still active.
* Hopefully there are no gaps from the host falling behind * Hopefully there are no gaps from the host falling behind
...@@ -1461,7 +1461,7 @@ iso_stream_schedule ( ...@@ -1461,7 +1461,7 @@ iso_stream_schedule (
* jump until after the queue is primed. * jump until after the queue is primed.
*/ */
start = SCHEDULE_SLOP + (now & ~0x07); start = SCHEDULE_SLOP + (now & ~0x07);
start %= mod; start &= mod - 1;
stream->next_uframe = start; stream->next_uframe = start;
/* NOTE: assumes URB_ISO_ASAP, to limit complexity/bugs */ /* NOTE: assumes URB_ISO_ASAP, to limit complexity/bugs */
...@@ -1483,7 +1483,7 @@ iso_stream_schedule ( ...@@ -1483,7 +1483,7 @@ iso_stream_schedule (
/* schedule it here if there's enough bandwidth */ /* schedule it here if there's enough bandwidth */
if (enough_space) { if (enough_space) {
stream->next_uframe = start % mod; stream->next_uframe = start & (mod - 1);
goto ready; goto ready;
} }
} }
...@@ -1599,7 +1599,7 @@ itd_link_urb ( ...@@ -1599,7 +1599,7 @@ itd_link_urb (
struct ehci_iso_sched *iso_sched = urb->hcpriv; struct ehci_iso_sched *iso_sched = urb->hcpriv;
struct ehci_itd *itd; struct ehci_itd *itd;
next_uframe = stream->next_uframe % mod; next_uframe = stream->next_uframe & (mod - 1);
if (unlikely (list_empty(&stream->td_list))) { if (unlikely (list_empty(&stream->td_list))) {
ehci_to_hcd(ehci)->self.bandwidth_allocated ehci_to_hcd(ehci)->self.bandwidth_allocated
...@@ -1637,13 +1637,13 @@ itd_link_urb ( ...@@ -1637,13 +1637,13 @@ itd_link_urb (
next_uframe += stream->interval; next_uframe += stream->interval;
stream->depth += stream->interval; stream->depth += stream->interval;
next_uframe %= mod; next_uframe &= mod - 1;
packet++; packet++;
/* link completed itds into the schedule */ /* link completed itds into the schedule */
if (((next_uframe >> 3) != frame) if (((next_uframe >> 3) != frame)
|| packet == urb->number_of_packets) { || packet == urb->number_of_packets) {
itd_link (ehci, frame % ehci->periodic_size, itd); itd_link(ehci, frame & (ehci->periodic_size - 1), itd);
itd = NULL; itd = NULL;
} }
} }
...@@ -2020,7 +2020,7 @@ sitd_link_urb ( ...@@ -2020,7 +2020,7 @@ sitd_link_urb (
"sched devp %s ep%d%s-iso [%d] %dms/%04x\n", "sched devp %s ep%d%s-iso [%d] %dms/%04x\n",
urb->dev->devpath, stream->bEndpointAddress & 0x0f, urb->dev->devpath, stream->bEndpointAddress & 0x0f,
(stream->bEndpointAddress & USB_DIR_IN) ? "in" : "out", (stream->bEndpointAddress & USB_DIR_IN) ? "in" : "out",
(next_uframe >> 3) % ehci->periodic_size, (next_uframe >> 3) & (ehci->periodic_size - 1),
stream->interval, hc32_to_cpu(ehci, stream->splits)); stream->interval, hc32_to_cpu(ehci, stream->splits));
stream->start = jiffies; stream->start = jiffies;
} }
...@@ -2043,13 +2043,13 @@ sitd_link_urb ( ...@@ -2043,13 +2043,13 @@ sitd_link_urb (
sitd->urb = urb; sitd->urb = urb;
sitd_patch(ehci, stream, sitd, sched, packet); sitd_patch(ehci, stream, sitd, sched, packet);
sitd_link (ehci, (next_uframe >> 3) % ehci->periodic_size, sitd_link(ehci, (next_uframe >> 3) & (ehci->periodic_size - 1),
sitd); sitd);
next_uframe += stream->interval << 3; next_uframe += stream->interval << 3;
stream->depth += stream->interval << 3; stream->depth += stream->interval << 3;
} }
stream->next_uframe = next_uframe % mod; stream->next_uframe = next_uframe & (mod - 1);
/* don't need that schedule data any more */ /* don't need that schedule data any more */
iso_sched_free (stream, sched); iso_sched_free (stream, sched);
...@@ -2258,7 +2258,7 @@ scan_periodic (struct ehci_hcd *ehci) ...@@ -2258,7 +2258,7 @@ scan_periodic (struct ehci_hcd *ehci)
now_uframe = ehci->next_uframe; now_uframe = ehci->next_uframe;
if (HC_IS_RUNNING(ehci_to_hcd(ehci)->state)) { if (HC_IS_RUNNING(ehci_to_hcd(ehci)->state)) {
clock = ehci_readl(ehci, &ehci->regs->frame_index); clock = ehci_readl(ehci, &ehci->regs->frame_index);
clock_frame = (clock >> 3) % ehci->periodic_size; clock_frame = (clock >> 3) & (ehci->periodic_size - 1);
} else { } else {
clock = now_uframe + mod - 1; clock = now_uframe + mod - 1;
clock_frame = -1; clock_frame = -1;
...@@ -2267,7 +2267,7 @@ scan_periodic (struct ehci_hcd *ehci) ...@@ -2267,7 +2267,7 @@ scan_periodic (struct ehci_hcd *ehci)
free_cached_lists(ehci); free_cached_lists(ehci);
ehci->clock_frame = clock_frame; ehci->clock_frame = clock_frame;
} }
clock %= mod; clock &= mod - 1;
clock_frame = clock >> 3; clock_frame = clock >> 3;
for (;;) { for (;;) {
...@@ -2356,7 +2356,7 @@ scan_periodic (struct ehci_hcd *ehci) ...@@ -2356,7 +2356,7 @@ scan_periodic (struct ehci_hcd *ehci)
* frame is current. * frame is current.
*/ */
if (((frame == clock_frame) || if (((frame == clock_frame) ||
(((frame + 1) % ehci->periodic_size) (((frame + 1) & (ehci->periodic_size - 1))
== clock_frame)) == clock_frame))
&& live && live
&& (q.sitd->hw_results & && (q.sitd->hw_results &
...@@ -2423,7 +2423,8 @@ scan_periodic (struct ehci_hcd *ehci) ...@@ -2423,7 +2423,8 @@ scan_periodic (struct ehci_hcd *ehci)
|| ehci->periodic_sched == 0) || ehci->periodic_sched == 0)
break; break;
ehci->next_uframe = now_uframe; ehci->next_uframe = now_uframe;
now = ehci_readl(ehci, &ehci->regs->frame_index) % mod; now = ehci_readl(ehci, &ehci->regs->frame_index) &
(mod - 1);
if (now_uframe == now) if (now_uframe == now)
break; break;
...@@ -2436,7 +2437,7 @@ scan_periodic (struct ehci_hcd *ehci) ...@@ -2436,7 +2437,7 @@ scan_periodic (struct ehci_hcd *ehci)
} }
} else { } else {
now_uframe++; now_uframe++;
now_uframe %= mod; now_uframe &= mod - 1;
} }
} }
} }
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment