On Monday 09 May 2005 2:22 pm, Alan Stern wrote:
> > > The code still isn't quite right because the root hub doesn't
> > > automatically resume. I haven't tried to track down the reason, but maybe
> > > replacing the schedule_work() call with usb_hcd_resume_root_hub() would
> > > help. (That replacement should be made in any case.)
I was just looking at that in conjunction with a different issue,
and I noticed a glitch: it's conditionalized for USB_SUSPEND
(which implies PM) not just PM, but autosuspend kicks in with PM.
This patch does that conversion, and it also has the other tweak.
Worked for me ... you?
- Dave
This updates OHCI to use the new usbcore resume_root_hub() mechanism,
and fixes that mechanism so it's available with CONFIG_PM. It also
continues getting rid of some #ifdefs of the form (PM || USB_SUSPEND);
they're superfluous: USB_SUSPEND is a strict superset of PM.
Signed-off-by: David Brownell <[EMAIL PROTECTED]>
--- g26.orig/drivers/usb/core/hcd.c 2005-05-09 18:17:30.000000000 -0700
+++ g26/drivers/usb/core/hcd.c 2005-05-09 18:18:56.000000000 -0700
@@ -1420,7 +1420,7 @@
/*-------------------------------------------------------------------------*/
-#ifdef CONFIG_USB_SUSPEND
+#ifdef CONFIG_PM
static int hcd_hub_suspend (struct usb_bus *bus)
{
@@ -1460,13 +1460,9 @@
usb_resume_root_hub (hcd->self.root_hub);
spin_unlock_irqrestore (&hcd_root_hub_lock, flags);
}
+EXPORT_SYMBOL_GPL(usb_hcd_resume_root_hub);
-#else
-void usb_hcd_resume_root_hub (struct usb_hcd *hcd)
-{
-}
#endif
-EXPORT_SYMBOL_GPL(usb_hcd_resume_root_hub);
/*-------------------------------------------------------------------------*/
@@ -1519,7 +1515,7 @@
.buffer_alloc = hcd_buffer_alloc,
.buffer_free = hcd_buffer_free,
.disable = hcd_endpoint_disable,
-#ifdef CONFIG_USB_SUSPEND
+#ifdef CONFIG_PM
.hub_suspend = hcd_hub_suspend,
.hub_resume = hcd_hub_resume,
#endif
--- g26.orig/drivers/usb/host/ohci-hub.c 2005-05-09 18:17:30.000000000 -0700
+++ g26/drivers/usb/host/ohci-hub.c 2005-05-09 18:18:56.000000000 -0700
@@ -36,7 +36,7 @@
/*-------------------------------------------------------------------------*/
-#if defined(CONFIG_USB_SUSPEND) || defined(CONFIG_PM)
+#ifdef CONFIG_PM
#define OHCI_SCHED_ENABLES \
(OHCI_CTRL_CLE|OHCI_CTRL_BLE|OHCI_CTRL_PLE|OHCI_CTRL_IE)
@@ -277,24 +277,7 @@
return 0;
}
-static void ohci_rh_resume (void *_hcd)
-{
- struct usb_hcd *hcd = _hcd;
-
- usb_lock_device (hcd->self.root_hub);
- (void) ohci_hub_resume (hcd);
- usb_unlock_device (hcd->self.root_hub);
-}
-
-#else
-
-static void ohci_rh_resume (void *_hcd)
-{
- struct ohci_hcd *ohci = hcd_to_ohci (_hcd);
- ohci_dbg(ohci, "rh_resume ??\n");
-}
-
-#endif /* CONFIG_USB_SUSPEND || CONFIG_PM */
+#endif /* CONFIG_PM */
/*-------------------------------------------------------------------------*/
@@ -553,7 +536,7 @@
temp = RH_PS_POCI;
if ((ohci->hc_control & OHCI_CTRL_HCFS)
!= OHCI_USB_OPER)
- schedule_work (&ohci->rh_resume);
+ usb_hcd_resume_root_hub(hcd);
break;
case USB_PORT_FEAT_C_SUSPEND:
temp = RH_PS_PSSC;
--- g26.orig/drivers/usb/host/ohci-mem.c 2005-05-09 18:18:25.000000000 -0700
+++ g26/drivers/usb/host/ohci-mem.c 2005-05-09 18:18:56.000000000 -0700
@@ -28,7 +28,6 @@
ohci->next_statechange = jiffies;
spin_lock_init (&ohci->lock);
INIT_LIST_HEAD (&ohci->pending);
- INIT_WORK (&ohci->rh_resume, ohci_rh_resume, ohci_to_hcd(ohci));
ohci->reboot_notifier.notifier_call = ohci_reboot;
}
--- g26.orig/drivers/usb/host/ohci.h 2005-05-09 18:18:25.000000000 -0700
+++ g26/drivers/usb/host/ohci.h 2005-05-09 18:18:56.000000000 -0700
@@ -389,7 +389,6 @@
unsigned long next_statechange; /* suspend/resume */
u32 fminterval; /* saved register */
- struct work_struct rh_resume;
struct notifier_block reboot_notifier;
unsigned long flags; /* for HC bugs */
--- g26.orig/drivers/usb/host/ohci-hcd.c 2005-05-09 18:18:25.000000000 -0700
+++ g26/drivers/usb/host/ohci-hcd.c 2005-05-09 18:18:56.000000000 -0700
@@ -747,7 +747,10 @@
if (ints & OHCI_INTR_RD) {
ohci_vdbg (ohci, "resume detect\n");
if (hcd->state != HC_STATE_QUIESCING)
- schedule_work(&ohci->rh_resume);
+ usb_hcd_resume_root_hub(hcd);
+ /* in case root is autosuspended */
+ ohci_writel (ohci, OHCI_INTR_RD, ®s->intrstatus);
+ ints &= ~OHCI_INTR_RD;
}
if (ints & OHCI_INTR_WDH) {
--- g26.orig/drivers/usb/core/hub.c 2005-05-09 18:17:30.000000000 -0700
+++ g26/drivers/usb/core/hub.c 2005-05-09 18:24:35.000000000 -0700
@@ -1971,14 +1971,6 @@
return 0;
}
-void usb_resume_root_hub(struct usb_device *hdev)
-{
- struct usb_hub *hub = hdev_to_hub(hdev);
-
- hub->resume_root_hub = 1;
- kick_khubd(hub);
-}
-
#else /* !CONFIG_USB_SUSPEND */
int usb_suspend_device(struct usb_device *udev, pm_message_t state)
@@ -2000,6 +1992,17 @@
EXPORT_SYMBOL(usb_suspend_device);
EXPORT_SYMBOL(usb_resume_device);
+#ifdef CONFIG_PM
+
+void usb_resume_root_hub(struct usb_device *hdev)
+{
+ struct usb_hub *hub = hdev_to_hub(hdev);
+
+ hub->resume_root_hub = 1;
+ kick_khubd(hub);
+}
+
+#endif /* CONFIG_PM */
/* USB 2.0 spec, 7.1.7.3 / fig 7-29: