aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorZhang Rui <rui.zhang@intel.com>2014-07-07 08:07:38 -0400
committerRafael J. Wysocki <rafael.j.wysocki@intel.com>2014-07-07 08:07:38 -0400
commitf1b1dc845cb1418b2b0de35491b0da87498ea6a8 (patch)
tree526bd85e432bd8b9dcbe8d132f0d3e2dbb854c5b
parentcd3de83f147601356395b57a8673e9c5ff1e59d1 (diff)
ACPI / PNP: do ACPI binding directly
PNPACPI uses acpi_bus_type to do ACPI binding for the PNPACPI devices. This is overkill because PNPACPI code already knows which ACPI device object to bind during PNPACPI device enumeration. This patch removes acpi_pnp_bus and does the binding by invoking acpi_bind_one() directly after device enumerated. This also fixes a bug in the previous code that some PNPACPI devices failed to be bound because 1. the ACPI device _HID is not pnpid, e.g. "MSFT0001", but its _CID is, e.g. "PNP0303", thus ACPI _CID is used as the pnp device device id. 2. device is bound only if the pnp device id matches the ACPI device _HID. Tested-by: Prigent Christophe <christophe.prigent@intel.com> Signed-off-by: Zhang Rui <rui.zhang@intel.com> Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
-rw-r--r--drivers/acpi/internal.h2
-rw-r--r--drivers/pnp/pnpacpi/core.c41
-rw-r--r--include/acpi/acpi_bus.h2
3 files changed, 5 insertions, 40 deletions
diff --git a/drivers/acpi/internal.h b/drivers/acpi/internal.h
index 7de5b603f272..151f3e76d47a 100644
--- a/drivers/acpi/internal.h
+++ b/drivers/acpi/internal.h
@@ -84,8 +84,6 @@ void acpi_init_device_object(struct acpi_device *device, acpi_handle handle,
84 int type, unsigned long long sta); 84 int type, unsigned long long sta);
85void acpi_device_add_finalize(struct acpi_device *device); 85void acpi_device_add_finalize(struct acpi_device *device);
86void acpi_free_pnp_ids(struct acpi_device_pnp *pnp); 86void acpi_free_pnp_ids(struct acpi_device_pnp *pnp);
87int acpi_bind_one(struct device *dev, struct acpi_device *adev);
88int acpi_unbind_one(struct device *dev);
89bool acpi_device_is_present(struct acpi_device *adev); 87bool acpi_device_is_present(struct acpi_device *adev);
90bool acpi_device_is_battery(struct acpi_device *adev); 88bool acpi_device_is_battery(struct acpi_device *adev);
91 89
diff --git a/drivers/pnp/pnpacpi/core.c b/drivers/pnp/pnpacpi/core.c
index b81448b2c75d..3bebedaee8e1 100644
--- a/drivers/pnp/pnpacpi/core.c
+++ b/drivers/pnp/pnpacpi/core.c
@@ -295,9 +295,11 @@ static int __init pnpacpi_add_device(struct acpi_device *device)
295 return error; 295 return error;
296 } 296 }
297 297
298 error = acpi_bind_one(&dev->dev, device);
299
298 num++; 300 num++;
299 301
300 return 0; 302 return error;
301} 303}
302 304
303static acpi_status __init pnpacpi_add_device_handler(acpi_handle handle, 305static acpi_status __init pnpacpi_add_device_handler(acpi_handle handle,
@@ -313,41 +315,6 @@ static acpi_status __init pnpacpi_add_device_handler(acpi_handle handle,
313 return AE_OK; 315 return AE_OK;
314} 316}
315 317
316static int __init acpi_pnp_match(struct device *dev, void *_pnp)
317{
318 struct acpi_device *acpi = to_acpi_device(dev);
319 struct pnp_dev *pnp = _pnp;
320
321 /* true means it matched */
322 return !acpi->physical_node_count
323 && compare_pnp_id(pnp->id, acpi_device_hid(acpi));
324}
325
326static struct acpi_device * __init acpi_pnp_find_companion(struct device *dev)
327{
328 dev = bus_find_device(&acpi_bus_type, NULL, to_pnp_dev(dev),
329 acpi_pnp_match);
330 if (!dev)
331 return NULL;
332
333 put_device(dev);
334 return to_acpi_device(dev);
335}
336
337/* complete initialization of a PNPACPI device includes having
338 * pnpdev->dev.archdata.acpi_handle point to its ACPI sibling.
339 */
340static bool acpi_pnp_bus_match(struct device *dev)
341{
342 return dev->bus == &pnp_bus_type;
343}
344
345static struct acpi_bus_type __initdata acpi_pnp_bus = {
346 .name = "PNP",
347 .match = acpi_pnp_bus_match,
348 .find_companion = acpi_pnp_find_companion,
349};
350
351int pnpacpi_disabled __initdata; 318int pnpacpi_disabled __initdata;
352static int __init pnpacpi_init(void) 319static int __init pnpacpi_init(void)
353{ 320{
@@ -357,10 +324,8 @@ static int __init pnpacpi_init(void)
357 } 324 }
358 printk(KERN_INFO "pnp: PnP ACPI init\n"); 325 printk(KERN_INFO "pnp: PnP ACPI init\n");
359 pnp_register_protocol(&pnpacpi_protocol); 326 pnp_register_protocol(&pnpacpi_protocol);
360 register_acpi_bus_type(&acpi_pnp_bus);
361 acpi_get_devices(NULL, pnpacpi_add_device_handler, NULL, NULL); 327 acpi_get_devices(NULL, pnpacpi_add_device_handler, NULL, NULL);
362 printk(KERN_INFO "pnp: PnP ACPI: found %d devices\n", num); 328 printk(KERN_INFO "pnp: PnP ACPI: found %d devices\n", num);
363 unregister_acpi_bus_type(&acpi_pnp_bus);
364 pnp_platform_devices = 1; 329 pnp_platform_devices = 1;
365 return 0; 330 return 0;
366} 331}
diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h
index b5714580801a..4bcbb941bc09 100644
--- a/include/acpi/acpi_bus.h
+++ b/include/acpi/acpi_bus.h
@@ -487,6 +487,8 @@ struct acpi_bus_type {
487}; 487};
488int register_acpi_bus_type(struct acpi_bus_type *); 488int register_acpi_bus_type(struct acpi_bus_type *);
489int unregister_acpi_bus_type(struct acpi_bus_type *); 489int unregister_acpi_bus_type(struct acpi_bus_type *);
490int acpi_bind_one(struct device *dev, struct acpi_device *adev);
491int acpi_unbind_one(struct device *dev);
490 492
491struct acpi_pci_root { 493struct acpi_pci_root {
492 struct acpi_device * device; 494 struct acpi_device * device;