1 /* 2 * (C) Copyright David Brownell 2000-2002 3 * 4 * This program is free software; you can redistribute it and/or modify it 5 * under the terms of the GNU General Public License as published by the 6 * Free Software Foundation; either version 2 of the License, or (at your 7 * option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, but 10 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 11 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, write to the Free Software Foundation, 16 * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 17 */ 18 19 #include <linux/kernel.h> 20 #include <linux/module.h> 21 #include <linux/pci.h> 22 #include <linux/pm_runtime.h> 23 #include <linux/usb.h> 24 #include <linux/usb/hcd.h> 25 26 #include <asm/io.h> 27 #include <asm/irq.h> 28 29 #ifdef CONFIG_PPC_PMAC 30 #include <asm/machdep.h> 31 #include <asm/pmac_feature.h> 32 #include <asm/pci-bridge.h> 33 #include <asm/prom.h> 34 #endif 35 36 #include "usb.h" 37 38 39 /* PCI-based HCs are common, but plenty of non-PCI HCs are used too */ 40 41 #ifdef CONFIG_PM_SLEEP 42 43 /* Coordinate handoffs between EHCI and companion controllers 44 * during system resume 45 */ 46 47 static DEFINE_MUTEX(companions_mutex); 48 49 #define CL_UHCI PCI_CLASS_SERIAL_USB_UHCI 50 #define CL_OHCI PCI_CLASS_SERIAL_USB_OHCI 51 #define CL_EHCI PCI_CLASS_SERIAL_USB_EHCI 52 53 enum companion_action { 54 SET_HS_COMPANION, CLEAR_HS_COMPANION, WAIT_FOR_COMPANIONS 55 }; 56 57 static void companion_common(struct pci_dev *pdev, struct usb_hcd *hcd, 58 enum companion_action action) 59 { 60 struct pci_dev *companion; 61 struct usb_hcd *companion_hcd; 62 unsigned int slot = PCI_SLOT(pdev->devfn); 63 64 /* Iterate through other PCI functions in the same slot. 65 * If pdev is OHCI or UHCI then we are looking for EHCI, and 66 * vice versa. 67 */ 68 companion = NULL; 69 for (;;) { 70 companion = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, companion); 71 if (!companion) 72 break; 73 if (companion->bus != pdev->bus || 74 PCI_SLOT(companion->devfn) != slot) 75 continue; 76 77 companion_hcd = pci_get_drvdata(companion); 78 if (!companion_hcd) 79 continue; 80 81 /* For SET_HS_COMPANION, store a pointer to the EHCI bus in 82 * the OHCI/UHCI companion bus structure. 83 * For CLEAR_HS_COMPANION, clear the pointer to the EHCI bus 84 * in the OHCI/UHCI companion bus structure. 85 * For WAIT_FOR_COMPANIONS, wait until the OHCI/UHCI 86 * companion controllers have fully resumed. 87 */ 88 89 if ((pdev->class == CL_OHCI || pdev->class == CL_UHCI) && 90 companion->class == CL_EHCI) { 91 /* action must be SET_HS_COMPANION */ 92 dev_dbg(&companion->dev, "HS companion for %s\n", 93 dev_name(&pdev->dev)); 94 hcd->self.hs_companion = &companion_hcd->self; 95 96 } else if (pdev->class == CL_EHCI && 97 (companion->class == CL_OHCI || 98 companion->class == CL_UHCI)) { 99 switch (action) { 100 case SET_HS_COMPANION: 101 dev_dbg(&pdev->dev, "HS companion for %s\n", 102 dev_name(&companion->dev)); 103 companion_hcd->self.hs_companion = &hcd->self; 104 break; 105 case CLEAR_HS_COMPANION: 106 companion_hcd->self.hs_companion = NULL; 107 break; 108 case WAIT_FOR_COMPANIONS: 109 device_pm_wait_for_dev(&pdev->dev, 110 &companion->dev); 111 break; 112 } 113 } 114 } 115 } 116 117 static void set_hs_companion(struct pci_dev *pdev, struct usb_hcd *hcd) 118 { 119 mutex_lock(&companions_mutex); 120 dev_set_drvdata(&pdev->dev, hcd); 121 companion_common(pdev, hcd, SET_HS_COMPANION); 122 mutex_unlock(&companions_mutex); 123 } 124 125 static void clear_hs_companion(struct pci_dev *pdev, struct usb_hcd *hcd) 126 { 127 mutex_lock(&companions_mutex); 128 dev_set_drvdata(&pdev->dev, NULL); 129 130 /* If pdev is OHCI or UHCI, just clear its hs_companion pointer */ 131 if (pdev->class == CL_OHCI || pdev->class == CL_UHCI) 132 hcd->self.hs_companion = NULL; 133 134 /* Otherwise search for companion buses and clear their pointers */ 135 else 136 companion_common(pdev, hcd, CLEAR_HS_COMPANION); 137 mutex_unlock(&companions_mutex); 138 } 139 140 static void wait_for_companions(struct pci_dev *pdev, struct usb_hcd *hcd) 141 { 142 /* Only EHCI controllers need to wait. 143 * No locking is needed because a controller cannot be resumed 144 * while one of its companions is getting unbound. 145 */ 146 if (pdev->class == CL_EHCI) 147 companion_common(pdev, hcd, WAIT_FOR_COMPANIONS); 148 } 149 150 #else /* !CONFIG_PM_SLEEP */ 151 152 static inline void set_hs_companion(struct pci_dev *d, struct usb_hcd *h) {} 153 static inline void clear_hs_companion(struct pci_dev *d, struct usb_hcd *h) {} 154 static inline void wait_for_companions(struct pci_dev *d, struct usb_hcd *h) {} 155 156 #endif /* !CONFIG_PM_SLEEP */ 157 158 /*-------------------------------------------------------------------------*/ 159 160 /* configure so an HC device and id are always provided */ 161 /* always called with process context; sleeping is OK */ 162 163 /** 164 * usb_hcd_pci_probe - initialize PCI-based HCDs 165 * @dev: USB Host Controller being probed 166 * @id: pci hotplug id connecting controller to HCD framework 167 * Context: !in_interrupt() 168 * 169 * Allocates basic PCI resources for this USB host controller, and 170 * then invokes the start() method for the HCD associated with it 171 * through the hotplug entry's driver_data. 172 * 173 * Store this function in the HCD's struct pci_driver as probe(). 174 */ 175 int usb_hcd_pci_probe(struct pci_dev *dev, const struct pci_device_id *id) 176 { 177 struct hc_driver *driver; 178 struct usb_hcd *hcd; 179 int retval; 180 181 if (usb_disabled()) 182 return -ENODEV; 183 184 if (!id) 185 return -EINVAL; 186 driver = (struct hc_driver *)id->driver_data; 187 if (!driver) 188 return -EINVAL; 189 190 if (pci_enable_device(dev) < 0) 191 return -ENODEV; 192 dev->current_state = PCI_D0; 193 194 if (!dev->irq) { 195 dev_err(&dev->dev, 196 "Found HC with no IRQ. Check BIOS/PCI %s setup!\n", 197 pci_name(dev)); 198 retval = -ENODEV; 199 goto err1; 200 } 201 202 hcd = usb_create_hcd(driver, &dev->dev, pci_name(dev)); 203 if (!hcd) { 204 retval = -ENOMEM; 205 goto err1; 206 } 207 208 if (driver->flags & HCD_MEMORY) { 209 /* EHCI, OHCI */ 210 hcd->rsrc_start = pci_resource_start(dev, 0); 211 hcd->rsrc_len = pci_resource_len(dev, 0); 212 if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, 213 driver->description)) { 214 dev_dbg(&dev->dev, "controller already in use\n"); 215 retval = -EBUSY; 216 goto err2; 217 } 218 hcd->regs = ioremap_nocache(hcd->rsrc_start, hcd->rsrc_len); 219 if (hcd->regs == NULL) { 220 dev_dbg(&dev->dev, "error mapping memory\n"); 221 retval = -EFAULT; 222 goto err3; 223 } 224 225 } else { 226 /* UHCI */ 227 int region; 228 229 for (region = 0; region < PCI_ROM_RESOURCE; region++) { 230 if (!(pci_resource_flags(dev, region) & 231 IORESOURCE_IO)) 232 continue; 233 234 hcd->rsrc_start = pci_resource_start(dev, region); 235 hcd->rsrc_len = pci_resource_len(dev, region); 236 if (request_region(hcd->rsrc_start, hcd->rsrc_len, 237 driver->description)) 238 break; 239 } 240 if (region == PCI_ROM_RESOURCE) { 241 dev_dbg(&dev->dev, "no i/o regions available\n"); 242 retval = -EBUSY; 243 goto err2; 244 } 245 } 246 247 pci_set_master(dev); 248 249 retval = usb_add_hcd(hcd, dev->irq, IRQF_DISABLED | IRQF_SHARED); 250 if (retval != 0) 251 goto err4; 252 set_hs_companion(dev, hcd); 253 return retval; 254 255 err4: 256 if (driver->flags & HCD_MEMORY) { 257 iounmap(hcd->regs); 258 err3: 259 release_mem_region(hcd->rsrc_start, hcd->rsrc_len); 260 } else 261 release_region(hcd->rsrc_start, hcd->rsrc_len); 262 err2: 263 clear_hs_companion(dev, hcd); 264 usb_put_hcd(hcd); 265 err1: 266 pci_disable_device(dev); 267 dev_err(&dev->dev, "init %s fail, %d\n", pci_name(dev), retval); 268 return retval; 269 } 270 EXPORT_SYMBOL_GPL(usb_hcd_pci_probe); 271 272 273 /* may be called without controller electrically present */ 274 /* may be called with controller, bus, and devices active */ 275 276 /** 277 * usb_hcd_pci_remove - shutdown processing for PCI-based HCDs 278 * @dev: USB Host Controller being removed 279 * Context: !in_interrupt() 280 * 281 * Reverses the effect of usb_hcd_pci_probe(), first invoking 282 * the HCD's stop() method. It is always called from a thread 283 * context, normally "rmmod", "apmd", or something similar. 284 * 285 * Store this function in the HCD's struct pci_driver as remove(). 286 */ 287 void usb_hcd_pci_remove(struct pci_dev *dev) 288 { 289 struct usb_hcd *hcd; 290 291 hcd = pci_get_drvdata(dev); 292 if (!hcd) 293 return; 294 295 usb_remove_hcd(hcd); 296 if (hcd->driver->flags & HCD_MEMORY) { 297 iounmap(hcd->regs); 298 release_mem_region(hcd->rsrc_start, hcd->rsrc_len); 299 } else { 300 release_region(hcd->rsrc_start, hcd->rsrc_len); 301 } 302 clear_hs_companion(dev, hcd); 303 usb_put_hcd(hcd); 304 pci_disable_device(dev); 305 } 306 EXPORT_SYMBOL_GPL(usb_hcd_pci_remove); 307 308 /** 309 * usb_hcd_pci_shutdown - shutdown host controller 310 * @dev: USB Host Controller being shutdown 311 */ 312 void usb_hcd_pci_shutdown(struct pci_dev *dev) 313 { 314 struct usb_hcd *hcd; 315 316 hcd = pci_get_drvdata(dev); 317 if (!hcd) 318 return; 319 320 if (hcd->driver->shutdown) 321 hcd->driver->shutdown(hcd); 322 } 323 EXPORT_SYMBOL_GPL(usb_hcd_pci_shutdown); 324 325 #ifdef CONFIG_PM_SLEEP 326 327 static int check_root_hub_suspended(struct device *dev) 328 { 329 struct pci_dev *pci_dev = to_pci_dev(dev); 330 struct usb_hcd *hcd = pci_get_drvdata(pci_dev); 331 332 if (!(hcd->state == HC_STATE_SUSPENDED || 333 hcd->state == HC_STATE_HALT)) { 334 dev_warn(dev, "Root hub is not suspended\n"); 335 return -EBUSY; 336 } 337 return 0; 338 } 339 340 static int hcd_pci_suspend(struct device *dev) 341 { 342 struct pci_dev *pci_dev = to_pci_dev(dev); 343 struct usb_hcd *hcd = pci_get_drvdata(pci_dev); 344 int retval; 345 346 /* Root hub suspend should have stopped all downstream traffic, 347 * and all bus master traffic. And done so for both the interface 348 * and the stub usb_device (which we check here). But maybe it 349 * didn't; writing sysfs power/state files ignores such rules... 350 */ 351 retval = check_root_hub_suspended(dev); 352 if (retval) 353 return retval; 354 355 /* We might already be suspended (runtime PM -- not yet written) */ 356 if (pci_dev->current_state != PCI_D0) 357 return retval; 358 359 if (hcd->driver->pci_suspend) { 360 retval = hcd->driver->pci_suspend(hcd); 361 suspend_report_result(hcd->driver->pci_suspend, retval); 362 if (retval) 363 return retval; 364 } 365 366 synchronize_irq(pci_dev->irq); 367 368 /* Downstream ports from this root hub should already be quiesced, so 369 * there will be no DMA activity. Now we can shut down the upstream 370 * link (except maybe for PME# resume signaling). We'll enter a 371 * low power state during suspend_noirq, if the hardware allows. 372 */ 373 pci_disable_device(pci_dev); 374 return retval; 375 } 376 377 static int hcd_pci_suspend_noirq(struct device *dev) 378 { 379 struct pci_dev *pci_dev = to_pci_dev(dev); 380 struct usb_hcd *hcd = pci_get_drvdata(pci_dev); 381 int retval; 382 383 retval = check_root_hub_suspended(dev); 384 if (retval) 385 return retval; 386 387 pci_save_state(pci_dev); 388 389 /* If the root hub is HALTed rather than SUSPENDed, 390 * disallow remote wakeup. 391 */ 392 if (hcd->state == HC_STATE_HALT) 393 device_set_wakeup_enable(dev, 0); 394 dev_dbg(dev, "wakeup: %d\n", device_may_wakeup(dev)); 395 396 /* Possibly enable remote wakeup, 397 * choose the appropriate low-power state, and go to that state. 398 */ 399 retval = pci_prepare_to_sleep(pci_dev); 400 if (retval == -EIO) { /* Low-power not supported */ 401 dev_dbg(dev, "--> PCI D0 legacy\n"); 402 retval = 0; 403 } else if (retval == 0) { 404 dev_dbg(dev, "--> PCI %s\n", 405 pci_power_name(pci_dev->current_state)); 406 } else { 407 suspend_report_result(pci_prepare_to_sleep, retval); 408 return retval; 409 } 410 411 #ifdef CONFIG_PPC_PMAC 412 /* Disable ASIC clocks for USB */ 413 if (machine_is(powermac)) { 414 struct device_node *of_node; 415 416 of_node = pci_device_to_OF_node(pci_dev); 417 if (of_node) 418 pmac_call_feature(PMAC_FTR_USB_ENABLE, of_node, 0, 0); 419 } 420 #endif 421 return retval; 422 } 423 424 static int hcd_pci_resume_noirq(struct device *dev) 425 { 426 struct pci_dev *pci_dev = to_pci_dev(dev); 427 428 #ifdef CONFIG_PPC_PMAC 429 /* Reenable ASIC clocks for USB */ 430 if (machine_is(powermac)) { 431 struct device_node *of_node; 432 433 of_node = pci_device_to_OF_node(pci_dev); 434 if (of_node) 435 pmac_call_feature(PMAC_FTR_USB_ENABLE, 436 of_node, 0, 1); 437 } 438 #endif 439 440 /* Go back to D0 and disable remote wakeup */ 441 pci_back_from_sleep(pci_dev); 442 return 0; 443 } 444 445 static int resume_common(struct device *dev, bool hibernated) 446 { 447 struct pci_dev *pci_dev = to_pci_dev(dev); 448 struct usb_hcd *hcd = pci_get_drvdata(pci_dev); 449 int retval; 450 451 if (hcd->state != HC_STATE_SUSPENDED) { 452 dev_dbg(dev, "can't resume, not suspended!\n"); 453 return 0; 454 } 455 456 retval = pci_enable_device(pci_dev); 457 if (retval < 0) { 458 dev_err(dev, "can't re-enable after resume, %d!\n", retval); 459 return retval; 460 } 461 462 pci_set_master(pci_dev); 463 464 clear_bit(HCD_FLAG_SAW_IRQ, &hcd->flags); 465 466 if (hcd->driver->pci_resume) { 467 /* This call should be made only during system resume, 468 * not during runtime resume. 469 */ 470 wait_for_companions(pci_dev, hcd); 471 472 retval = hcd->driver->pci_resume(hcd, hibernated); 473 if (retval) { 474 dev_err(dev, "PCI post-resume error %d!\n", retval); 475 usb_hc_died(hcd); 476 } 477 } 478 return retval; 479 } 480 481 static int hcd_pci_resume(struct device *dev) 482 { 483 return resume_common(dev, false); 484 } 485 486 static int hcd_pci_restore(struct device *dev) 487 { 488 return resume_common(dev, true); 489 } 490 491 const struct dev_pm_ops usb_hcd_pci_pm_ops = { 492 .suspend = hcd_pci_suspend, 493 .suspend_noirq = hcd_pci_suspend_noirq, 494 .resume_noirq = hcd_pci_resume_noirq, 495 .resume = hcd_pci_resume, 496 .freeze = check_root_hub_suspended, 497 .freeze_noirq = check_root_hub_suspended, 498 .thaw_noirq = NULL, 499 .thaw = NULL, 500 .poweroff = hcd_pci_suspend, 501 .poweroff_noirq = hcd_pci_suspend_noirq, 502 .restore_noirq = hcd_pci_resume_noirq, 503 .restore = hcd_pci_restore, 504 }; 505 EXPORT_SYMBOL_GPL(usb_hcd_pci_pm_ops); 506 507 #endif /* CONFIG_PM_SLEEP */ 508