ChangeSet 1.1757.66.19, 2004/07/14 14:52:00-07:00, david-b@pacbell.net [PATCH] USB: misc ohci tweaks Various minor OHCI tweaks; - Fix osdl bugid=2503 by: * Change needlessly-scarey message (WARN_ON dumps stack) * Tries cleaning up, as if it's just IRQ lossage. - Force IRQs off when shutting down a controller that was already stopped ... just in case. - Allow suspending OHCI during driver initialization, to support more aggressive power management. - Fix some misleading/wrong debug messages. Signed-off-by: David Brownell Signed-off-by: Greg Kroah-Hartman drivers/usb/host/ohci-hcd.c | 8 +++++++- drivers/usb/host/ohci-hub.c | 4 ++-- drivers/usb/host/ohci-mem.c | 1 + drivers/usb/host/ohci-q.c | 2 +- 4 files changed, 11 insertions(+), 4 deletions(-) diff -Nru a/drivers/usb/host/ohci-hcd.c b/drivers/usb/host/ohci-hcd.c --- a/drivers/usb/host/ohci-hcd.c 2004-07-14 16:44:42 -07:00 +++ b/drivers/usb/host/ohci-hcd.c 2004-07-14 16:44:42 -07:00 @@ -340,6 +340,7 @@ goto done; if (!HCD_IS_RUNNING (ohci->hcd.state)) { +sanitize: ed->state = ED_IDLE; finish_unlinks (ohci, 0, NULL); } @@ -347,7 +348,10 @@ switch (ed->state) { case ED_UNLINK: /* wait for hw to finish? */ /* major IRQ delivery trouble loses INTR_SF too... */ - WARN_ON (limit-- == 0); + if (limit-- == 0) { + ohci_warn (ohci, "IRQ INTR_SF lossage\n"); + goto sanitize; + } spin_unlock_irqrestore (&ohci->lock, flags); set_current_state (TASK_UNINTERRUPTIBLE); schedule_timeout (1); @@ -671,6 +675,8 @@ flush_scheduled_work(); if (HCD_IS_RUNNING(ohci->hcd.state)) hc_reset (ohci); + else + writel (OHCI_INTR_MIE, &ohci->regs->intrdisable); remove_debug_files (ohci); ohci_mem_cleanup (ohci); diff -Nru a/drivers/usb/host/ohci-hub.c b/drivers/usb/host/ohci-hub.c --- a/drivers/usb/host/ohci-hub.c 2004-07-14 16:44:42 -07:00 +++ b/drivers/usb/host/ohci-hub.c 2004-07-14 16:44:42 -07:00 @@ -190,7 +190,7 @@ break; case OHCI_USB_RESUME: /* HCFS changes sometime after INTR_RD */ - ohci_info (ohci, "remote wakeup\n"); + ohci_info (ohci, "wakeup\n"); break; case OHCI_USB_OPER: ohci_dbg (ohci, "odd resume\n"); @@ -515,7 +515,7 @@ #ifndef OHCI_VERBOSE_DEBUG if (*(u16*)(buf+2)) /* only if wPortChange is interesting */ #endif - dbg_port (ohci, "GetStatus", wIndex + 1, temp); + dbg_port (ohci, "GetStatus", wIndex, temp); break; case SetHubFeature: switch (wValue) { diff -Nru a/drivers/usb/host/ohci-mem.c b/drivers/usb/host/ohci-mem.c --- a/drivers/usb/host/ohci-mem.c 2004-07-14 16:44:42 -07:00 +++ b/drivers/usb/host/ohci-mem.c 2004-07-14 16:44:42 -07:00 @@ -31,6 +31,7 @@ if (ohci != 0) { memset (ohci, 0, sizeof (struct ohci_hcd)); ohci->hcd.product_desc = "OHCI Host Controller"; + ohci->next_statechange = jiffies; spin_lock_init (&ohci->lock); INIT_LIST_HEAD (&ohci->pending); INIT_WORK (&ohci->rh_resume, ohci_rh_resume, &ohci->hcd); diff -Nru a/drivers/usb/host/ohci-q.c b/drivers/usb/host/ohci-q.c --- a/drivers/usb/host/ohci-q.c 2004-07-14 16:44:42 -07:00 +++ b/drivers/usb/host/ohci-q.c 2004-07-14 16:44:42 -07:00 @@ -924,7 +924,7 @@ /* only take off EDs that the HC isn't using, accounting for * frame counter wraps and EDs with partially retired TDs */ - if (likely (HCD_IS_RUNNING(ohci->hcd.state))) { + if (likely (regs && HCD_IS_RUNNING(ohci->hcd.state))) { if (tick_before (tick, ed->tick)) { skip_ed: last = &ed->ed_next;