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

[PATCH] UHCI: remove main list of URBs

As part of reorienting uhci-hcd away from URBs and toward endpoint
queues, this patch (as625) eliminates the driver's main list of URBs.
The list wsa used mainly in checking for URB completions; now the driver
goes through the list of active endpoints and checks the members of the
queues.

As a side effect, I had to remove the code that looks for FSBR timeouts.
For now, FSBR will remain on so long as any URBs on a full-speed control
or bulk queue request it, even if the queue isn't advancing.  A later
patch can add more intelligent handling.  This isn't a huge drawback;
it's pretty rare for an URB to get stuck for more than a fraction of a
second.  (And it will help the people trying to use those insane HP USB
devices.)
Signed-off-by: default avatarAlan Stern <stern@rowland.harvard.edu>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@suse.de>
parent af0bb599
......@@ -114,7 +114,6 @@ static int uhci_show_urbp(struct urb_priv *urbp, char *buf, int len, int space)
}
out += sprintf(out, "%s", (urbp->fsbr ? " FSBR" : ""));
out += sprintf(out, "%s", (urbp->fsbr_timeout ? " FSBR_TO" : ""));
if (urbp->urb->status != -EINPROGRESS)
out += sprintf(out, " Status=%d", urbp->urb->status);
......
......@@ -491,8 +491,6 @@ static int uhci_start(struct usb_hcd *hcd)
spin_lock_init(&uhci->lock);
INIT_LIST_HEAD(&uhci->td_remove_list);
INIT_LIST_HEAD(&uhci->urb_list);
INIT_LIST_HEAD(&uhci->complete_list);
INIT_LIST_HEAD(&uhci->idle_qh_list);
init_waitqueue_head(&uhci->waitqh);
......
......@@ -132,6 +132,10 @@ struct uhci_qh {
unsigned int unlink_frame; /* When the QH was unlinked */
int state; /* QH_STATE_xxx; see above */
unsigned int initial_toggle:1; /* Endpoint's current toggle value */
unsigned int needs_fixup:1; /* Must fix the TD toggle values */
unsigned int is_stopped:1; /* Queue was stopped by an error */
} __attribute__((aligned(16)));
/*
......@@ -384,6 +388,7 @@ struct uhci_hcd {
struct uhci_td *term_td; /* Terminating TD, see UHCI bug */
struct uhci_qh *skelqh[UHCI_NUM_SKELQH]; /* Skeleton QHs */
struct uhci_qh *next_qh; /* Next QH to scan */
spinlock_t lock;
......@@ -413,16 +418,10 @@ struct uhci_hcd {
unsigned long resuming_ports;
unsigned long ports_timeout; /* Time to stop signalling */
/* Main list of URBs currently controlled by this HC */
struct list_head urb_list;
/* List of TDs that are done, but waiting to be freed (race) */
struct list_head td_remove_list;
unsigned int td_remove_age; /* Age in frames */
/* List of URBs awaiting completion callback */
struct list_head complete_list;
struct list_head idle_qh_list; /* Where the idle QHs live */
int rh_numports; /* Number of root-hub ports */
......@@ -448,7 +447,6 @@ static inline struct usb_hcd *uhci_to_hcd(struct uhci_hcd *uhci)
* Private per-URB data
*/
struct urb_priv {
struct list_head urb_list;
struct list_head node; /* Node in the QH's urbp list */
struct urb *urb;
......@@ -456,10 +454,7 @@ struct urb_priv {
struct uhci_qh *qh; /* QH for this URB */
struct list_head td_list;
unsigned long fsbrtime; /* In jiffies */
unsigned fsbr : 1; /* URB turned on FSBR */
unsigned fsbr_timeout : 1; /* URB timed out on FSBR */
unsigned short_transfer : 1; /* URB got a short transfer, no
* need to rescan */
};
......
This diff is collapsed.
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