The patch titled revert gregkh-usb-usb-ehci-hcd-split-scan_periodic-to-reuse-code-for-spanned-completions has been added to the -mm tree. Its filename is revert-gregkh-usb-usb-ehci-hcd-split-scan_periodic-to-reuse-code-for-spanned-completions.patch See http://www.zip.com.au/~akpm/linux/patches/stuff/added-to-mm.txt to find out what to do about this ------------------------------------------------------ Subject: revert gregkh-usb-usb-ehci-hcd-split-scan_periodic-to-reuse-code-for-spanned-completions From: Andrew Morton <akpm@xxxxxxxx> Signed-off-by: Andrew Morton <akpm@xxxxxxxx> --- drivers/usb/host/ehci-sched.c | 246 +++++++++++--------------------- 1 file changed, 90 insertions(+), 156 deletions(-) diff -puN drivers/usb/host/ehci-sched.c~revert-gregkh-usb-usb-ehci-hcd-split-scan_periodic-to-reuse-code-for-spanned-completions drivers/usb/host/ehci-sched.c --- a/drivers/usb/host/ehci-sched.c~revert-gregkh-usb-usb-ehci-hcd-split-scan_periodic-to-reuse-code-for-spanned-completions +++ a/drivers/usb/host/ehci-sched.c @@ -3337,158 +3337,6 @@ static void unlink_dummy(struct ehci_hcd } } -static int scan_frame(struct ehci_hcd *ehci, struct pt_regs *regs, - int frame, int uframes, int rescan){ - - unsigned modified = 0; - union ehci_shadow q, *q_p; - __le32 type, *hw_p; - - frame = frame & (ehci->periodic_size-1); - - q_p = &ehci->pshadow [frame]; - hw_p = &ehci->periodic [frame]; - - q.ptr = q_p->ptr; - type = Q_NEXT_TYPE (*hw_p); - - while (q.ptr != NULL) { - unsigned uf; - union ehci_shadow temp; - int live; - - live = HC_IS_RUNNING (ehci_to_hcd(ehci)->state); - switch (type) { - case Q_TYPE_QH: - /* handle any completions */ - temp.qh = qh_get (q.qh); - q_p = &q.qh->qh_next; - hw_p = &q.qh->hw_next; - type = Q_NEXT_TYPE (*hw_p); - - q = *q_p; - - /* process completions for this frame only if - * we're certain all completions for a - * preceeding spanning frame have first been - * processed; that is true iff clock was past - * uframe 1 when we started */ - if(uframes>2){ - modified = - qh_completions (ehci, temp.qh, regs); - if (unlikely (list_empty (&temp.qh->qtd_list))) - periodic_qh_deschedule (ehci, temp.qh); - } - - qh_put (temp.qh); - break; - case Q_TYPE_FSTN: - - /* for save-place FSTNs, inspect all QH - * entries in the previous frame for - * completions, but not if we're already in - * recovery mode. */ - - if (q.fstn->hw_prev != EHCI_LIST_END && !rescan) { - modified = scan_frame (ehci,regs,frame-1,8,1); - rescan = 1; - } - - q_p = &q.fstn->fstn_next; - hw_p = &q.fstn->hw_next; - type = Q_NEXT_TYPE (*hw_p); - q = *q_p; - - break; - - case Q_TYPE_ITD: - /* skip itds for later in the frame */ - rmb (); - for (uf = live ? uframes : 8; uf < 8; uf++) { - if (0 == (q.itd->hw_transaction [uf] - & ITD_ACTIVE)) - continue; - q_p = &q.itd->itd_next; - hw_p = &q.itd->hw_next; - type = Q_NEXT_TYPE (*hw_p); - q = *q_p; - break; - } - if (uf != 8) - break; - - /* this one's ready ... HC won't cache the - * pointer for much longer, if at all. - */ - *q_p = q.itd->itd_next; - *hw_p = q.itd->hw_next; - type = Q_NEXT_TYPE (*hw_p); - wmb(); - modified = itd_complete (ehci, q.itd, regs); - q = *q_p; - break; - - case Q_TYPE_SITD: - - /* is this a spanning dummy? */ - if (q.sitd->hw_backpointer != EHCI_LIST_END){ - q_p = &q.sitd->sitd_next; - hw_p = &q.sitd->hw_next; - type = Q_NEXT_TYPE (*hw_p); - q = *q_p; - - if(rescan) break; - - /* note that the original sITD's - completion will unlink the dummy */ - modified = scan_frame(ehci,regs, - frame-1,8,1); - rescan = 1; - - }else{ - /* process completions for this frame only if - * we're certain all completions for a - * preceeding spanning frame have first been - * processed; that is true iff clock was past - * uframe 1 when we started */ - if ( ((q.sitd->hw_results & SITD_ACTIVE) || - uframes < 3) - && live) { - q_p = &q.sitd->sitd_next; - hw_p = &q.sitd->hw_next; - type = Q_NEXT_TYPE (*hw_p); - q = *q_p; - break; - } - - /* unlink the sITD */ - *q_p = q.sitd->sitd_next; - *hw_p = q.sitd->hw_next; - type = Q_NEXT_TYPE (*hw_p); - wmb(); - - /* unlink the dummy (if any) */ - if(BUDGET_WRAP_P(q.sitd->budget)) - unlink_dummy(ehci,q.sitd,regs,frame+1); - - modified = sitd_complete (ehci, q.sitd, regs); - - q = *q_p; - } - break; - default: - dbg ("corrupt type %d frame %d shadow %p", - type, frame, q.ptr); - // BUG (); - q.ptr = NULL; - } - - /* assume completion callbacks modify the queue */ - if (unlikely (modified)) return 1; - } - return 0; -} - /* scan_periodic - completion worker; called out of interrupt (or * poll) handler to finish processing of transactions that have been * completed by the host controller. Also now has the responsibility @@ -3502,6 +3350,7 @@ static void scan_periodic (struct ehci_hcd *ehci) { unsigned frame, clock, now_uframe, mod; + unsigned modified; mod = ehci->periodic_size << 3; @@ -3518,8 +3367,9 @@ scan_periodic (struct ehci_hcd *ehci) clock &= (mod-1); for (;;) { + union ehci_shadow q, *q_p; + __le32 type, *hw_p; unsigned uframes; - int repeat = 1; /* don't scan past the live uframe */ frame = now_uframe >> 3; @@ -3531,9 +3381,94 @@ scan_periodic (struct ehci_hcd *ehci) uframes = 8; } +restart: /* scan each element in frame's queue for completions */ - while (repeat) - repeat = scan_frame(ehci, regs, frame, uframes, 0); + q_p = &ehci->pshadow [frame]; + hw_p = &ehci->periodic [frame]; + q.ptr = q_p->ptr; + type = Q_NEXT_TYPE (*hw_p); + modified = 0; + + while (q.ptr != NULL) { + unsigned uf; + union ehci_shadow temp; + int live; + + live = HC_IS_RUNNING (ehci_to_hcd(ehci)->state); + switch (type) { + case Q_TYPE_QH: + /* handle any completions */ + temp.qh = qh_get (q.qh); + type = Q_NEXT_TYPE (q.qh->hw_next); + q = q.qh->qh_next; + modified = qh_completions (ehci, temp.qh); + if (unlikely (list_empty (&temp.qh->qtd_list))) + periodic_qh_deschedule (ehci, temp.qh); + qh_put (temp.qh); + break; + case Q_TYPE_FSTN: + /* for "save place" FSTNs, look at QH entries + * in the previous frame for completions. + */ + if (q.fstn->hw_prev != EHCI_LIST_END) { + dbg ("ignoring completions from FSTNs"); + } + type = Q_NEXT_TYPE (q.fstn->hw_next); + q = q.fstn->fstn_next; + break; + case Q_TYPE_ITD: + /* skip itds for later in the frame */ + rmb (); + for (uf = live ? uframes : 8; uf < 8; uf++) { + if (0 == (q.itd->hw_transaction [uf] + & ITD_ACTIVE)) + continue; + q_p = &q.itd->itd_next; + hw_p = &q.itd->hw_next; + type = Q_NEXT_TYPE (q.itd->hw_next); + q = *q_p; + break; + } + if (uf != 8) + break; + + /* this one's ready ... HC won't cache the + * pointer for much longer, if at all. + */ + *q_p = q.itd->itd_next; + *hw_p = q.itd->hw_next; + type = Q_NEXT_TYPE (q.itd->hw_next); + wmb(); + modified = itd_complete (ehci, q.itd); + q = *q_p; + break; + case Q_TYPE_SITD: + if ((q.sitd->hw_results & SITD_ACTIVE) + && live) { + q_p = &q.sitd->sitd_next; + hw_p = &q.sitd->hw_next; + type = Q_NEXT_TYPE (q.sitd->hw_next); + q = *q_p; + break; + } + *q_p = q.sitd->sitd_next; + *hw_p = q.sitd->hw_next; + type = Q_NEXT_TYPE (q.sitd->hw_next); + wmb(); + modified = sitd_complete (ehci, q.sitd); + q = *q_p; + break; + default: + dbg ("corrupt type %d frame %d shadow %p", + type, frame, q.ptr); + // BUG (); + q.ptr = NULL; + } + + /* assume completion callbacks modify the queue */ + if (unlikely (modified)) + goto restart; + } /* stop when we catch up to the HC */ @@ -3550,7 +3485,6 @@ scan_periodic (struct ehci_hcd *ehci) if (!HC_IS_RUNNING (ehci_to_hcd(ehci)->state)) break; - ehci->next_uframe = now_uframe; now = readl (&ehci->regs->frame_index) & (mod-1); if (now_uframe == now) _ Patches currently in -mm which might be from akpm@xxxxxxxx are i386-irqs-build-fix.patch kauditd_thread-warning-fix.patch revert-pci-quirk-for-ibm-dock-ii-cardbus-controllers.patch fix-warn_on--warn_on_once-regression.patch irq_reqs-export-__irq_regs.patch ext4_blk_type_from_sector_t_to_ulonglong-fix.patch ext4-uninline-ext4_get_group_no_and_offset.patch ext4-64-bit-divide-fix.patch ext4-rename-logic_sb_block.patch ext4-whitespace-cleanups.patch git-acpi.patch acpi-preserve-correct-battery-state-through-suspend-resume-cycles-tidy.patch acpi-asus-s3-resume-fix.patch sony_apci-resume.patch git-cifs-fixup.patch cifs-kconfig-dont-select-connector.patch w1-kconfig-fix.patch git-geode-fixup.patch git-input-fixup.patch libata-return-sense-data-in-hdio_drive_cmd-ioctl-tidy.patch git-netdev-all.patch forcedeth-power-management-support-tidy.patch drivers-net-ns83820c-add-paramter-to-disable-auto.patch git-pcmcia-fixup.patch git-serial-fixup.patch pci-optionally-sort-device-lists-breadth-first-tweaks.patch pci-optionally-sort-device-lists-breadth-first-force-on.patch git-scsi-target-fixup.patch git-scsi-target-vs-git-block.patch revert-gregkh-usb-usb-ehci-hcd-split-scan_periodic-to-reuse-code-for-spanned-completions.patch xpad-dance-pad-support-tidy.patch git-watchdog.patch x86_64-dump_trace-atomicity-fix.patch spinlock-debug-all-cpu-backtrace.patch spinlock-debug-all-cpu-backtrace-fix.patch spinlock-debug-all-cpu-backtrace-fix-2.patch spinlock-debug-all-cpu-backtrace-fix-3.patch xfs-rename-uio_read.patch get-rid-of-zone_table.patch slab-reduce-numa-text-size-tidy.patch swap-token-new-scheme-to-preempt-token-tidy.patch radix-tree-rcu-lockless-readside.patch acx1xx-wireless-driver.patch swsusp-add-resume_offset-command-line-parameter-rev-2.patch deprecate-smbfs-in-favour-of-cifs.patch edac-new-opteron-athlon64-memory-controller-driver.patch add-address_space_operationsbatch_write.patch add-config_headers_check-option-to-automatically-run-make-headers_check-nobble.patch kbuild-dont-put-temp-files-in-the-source-tree.patch grow_buffers-infinite-loop-fix.patch invalidate_inode_pages2_range-debug.patch generic-implementatation-of-bug.patch generic-implementatation-of-bug-fix.patch generic-bug-for-i386.patch generic-bug-for-x86-64.patch fs-cache-make-kafs-use-fs-cache-fix.patch fs-cache-make-kafs-use-fs-cache-vs-streamline-generic_file_-interfaces-and-filemap.patch nfs-use-local-caching-12-fix.patch swap_prefetch-vs-zoned-counters.patch readahead-sysctl-parameters.patch make-copy_from_user_inatomic-not-zero-the-tail-on-i386-vs-reiser4.patch make-kmem_cache_destroy-return-void-reiser4.patch reiser4-hardirq-include-fix.patch reiser4-run-truncate_inode_pages-in-reiser4_delete_inode.patch reiser4-get_sb_dev-fix.patch reiser4-vs-zoned-allocator.patch reiser4-rename-generic_sounding_globalspatch-fix.patch hpt3xx-rework-rate-filtering-tidy.patch kevent-core-files-fix.patch kevent-core-files-s390-hack.patch kevent-socket-notifications-fix-2.patch kevent-socket-notifications-fix-4.patch nr_blockdev_pages-in_interrupt-warning.patch device-suspend-debug.patch slab-leaks3-default-y.patch x86-kmap_atomic-debugging.patch restore-rogue-readahead-printk.patch put_bh-debug.patch acpi_format_exception-debug.patch jmicron-warning-fix.patch squash-ipc-warnings.patch squash-transmeta-warnings.patch squash-udf-warnings.patch - To unsubscribe from this list: send the line "unsubscribe mm-commits" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html