aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/pci/pci-driver.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/pci/pci-driver.c')
-rw-r--r--drivers/pci/pci-driver.c47
1 files changed, 45 insertions, 2 deletions
diff --git a/drivers/pci/pci-driver.c b/drivers/pci/pci-driver.c
index 474e9cd0e9e4..b1c0c707d96c 100644
--- a/drivers/pci/pci-driver.c
+++ b/drivers/pci/pci-driver.c
@@ -17,6 +17,16 @@
17 * Registration of PCI drivers and handling of hot-pluggable devices. 17 * Registration of PCI drivers and handling of hot-pluggable devices.
18 */ 18 */
19 19
20/* multithreaded probe logic */
21static int pci_multithread_probe =
22#ifdef CONFIG_PCI_MULTITHREAD_PROBE
23 1;
24#else
25 0;
26#endif
27__module_param_call("", pci_multithread_probe, param_set_bool, param_get_bool, &pci_multithread_probe, 0644);
28
29
20/* 30/*
21 * Dynamic device IDs are disabled for !CONFIG_HOTPLUG 31 * Dynamic device IDs are disabled for !CONFIG_HOTPLUG
22 */ 32 */
@@ -46,6 +56,7 @@ store_new_id(struct device_driver *driver, const char *buf, size_t count)
46 subdevice=PCI_ANY_ID, class=0, class_mask=0; 56 subdevice=PCI_ANY_ID, class=0, class_mask=0;
47 unsigned long driver_data=0; 57 unsigned long driver_data=0;
48 int fields=0; 58 int fields=0;
59 int retval = 0;
49 60
50 fields = sscanf(buf, "%x %x %x %x %x %x %lux", 61 fields = sscanf(buf, "%x %x %x %x %x %x %lux",
51 &vendor, &device, &subvendor, &subdevice, 62 &vendor, &device, &subvendor, &subdevice,
@@ -72,10 +83,12 @@ store_new_id(struct device_driver *driver, const char *buf, size_t count)
72 spin_unlock(&pdrv->dynids.lock); 83 spin_unlock(&pdrv->dynids.lock);
73 84
74 if (get_driver(&pdrv->driver)) { 85 if (get_driver(&pdrv->driver)) {
75 driver_attach(&pdrv->driver); 86 retval = driver_attach(&pdrv->driver);
76 put_driver(&pdrv->driver); 87 put_driver(&pdrv->driver);
77 } 88 }
78 89
90 if (retval)
91 return retval;
79 return count; 92 return count;
80} 93}
81static DRIVER_ATTR(new_id, S_IWUSR, NULL, store_new_id); 94static DRIVER_ATTR(new_id, S_IWUSR, NULL, store_new_id);
@@ -279,6 +292,18 @@ static int pci_device_suspend(struct device * dev, pm_message_t state)
279 return i; 292 return i;
280} 293}
281 294
295static int pci_device_suspend_late(struct device * dev, pm_message_t state)
296{
297 struct pci_dev * pci_dev = to_pci_dev(dev);
298 struct pci_driver * drv = pci_dev->driver;
299 int i = 0;
300
301 if (drv && drv->suspend_late) {
302 i = drv->suspend_late(pci_dev, state);
303 suspend_report_result(drv->suspend_late, i);
304 }
305 return i;
306}
282 307
283/* 308/*
284 * Default resume method for devices that have no driver provided resume, 309 * Default resume method for devices that have no driver provided resume,
@@ -313,6 +338,17 @@ static int pci_device_resume(struct device * dev)
313 return error; 338 return error;
314} 339}
315 340
341static int pci_device_resume_early(struct device * dev)
342{
343 int error = 0;
344 struct pci_dev * pci_dev = to_pci_dev(dev);
345 struct pci_driver * drv = pci_dev->driver;
346
347 if (drv && drv->resume_early)
348 error = drv->resume_early(pci_dev);
349 return error;
350}
351
316static void pci_device_shutdown(struct device *dev) 352static void pci_device_shutdown(struct device *dev)
317{ 353{
318 struct pci_dev *pci_dev = to_pci_dev(dev); 354 struct pci_dev *pci_dev = to_pci_dev(dev);
@@ -386,6 +422,11 @@ int __pci_register_driver(struct pci_driver *drv, struct module *owner)
386 drv->driver.owner = owner; 422 drv->driver.owner = owner;
387 drv->driver.kobj.ktype = &pci_driver_kobj_type; 423 drv->driver.kobj.ktype = &pci_driver_kobj_type;
388 424
425 if (pci_multithread_probe)
426 drv->driver.multithread_probe = pci_multithread_probe;
427 else
428 drv->driver.multithread_probe = drv->multithread_probe;
429
389 spin_lock_init(&drv->dynids.lock); 430 spin_lock_init(&drv->dynids.lock);
390 INIT_LIST_HEAD(&drv->dynids.list); 431 INIT_LIST_HEAD(&drv->dynids.list);
391 432
@@ -509,8 +550,10 @@ struct bus_type pci_bus_type = {
509 .probe = pci_device_probe, 550 .probe = pci_device_probe,
510 .remove = pci_device_remove, 551 .remove = pci_device_remove,
511 .suspend = pci_device_suspend, 552 .suspend = pci_device_suspend,
512 .shutdown = pci_device_shutdown, 553 .suspend_late = pci_device_suspend_late,
554 .resume_early = pci_device_resume_early,
513 .resume = pci_device_resume, 555 .resume = pci_device_resume,
556 .shutdown = pci_device_shutdown,
514 .dev_attrs = pci_dev_attrs, 557 .dev_attrs = pci_dev_attrs,
515}; 558};
516 559