summaryrefslogtreecommitdiffstats
path: root/drivers/acpi
diff options
context:
space:
mode:
authorLukas Wunner <lukas@wunner.de>2015-11-25 21:19:55 +0100
committerRafael J. Wysocki <rafael.j.wysocki@intel.com>2015-12-09 01:31:41 +0100
commit2d12b6b381ba059d5f92798f5ea739672a2f5fcf (patch)
tree43b44ae5508885d7170fc074d394f9e4aad7ca0b /drivers/acpi
parentca9dc8d42b30e2d766b471fe5ecf0c71fd309c8f (diff)
downloadlinux-2d12b6b381ba059d5f92798f5ea739672a2f5fcf.tar.bz2
ACPI / utils: Add acpi_dev_present()
There's an idiom in use by 7 Linux drivers to detect the presence of a particular ACPI HID by walking the namespace with acpi_get_devices(). The callback passed to acpi_get_devices() is mostly identical across the drivers, leading to lots of duplicate code. Add acpi_dev_present(), the ACPI equivalent to pci_dev_present(), allowing us to deduplicate all that boilerplate in the drivers. Signed-off-by: Lukas Wunner <lukas@wunner.de> Reviewed-by: Hanjun Guo <hanjun.guo@linaro.org> Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Diffstat (limited to 'drivers/acpi')
-rw-r--r--drivers/acpi/internal.h8
-rw-r--r--drivers/acpi/scan.c8
-rw-r--r--drivers/acpi/utils.c31
3 files changed, 40 insertions, 7 deletions
diff --git a/drivers/acpi/internal.h b/drivers/acpi/internal.h
index 11d87bf67e73..60bda0d2cf9a 100644
--- a/drivers/acpi/internal.h
+++ b/drivers/acpi/internal.h
@@ -86,6 +86,14 @@ bool acpi_scan_is_offline(struct acpi_device *adev, bool uevent);
#define ACPI_STA_DEFAULT (ACPI_STA_DEVICE_PRESENT | ACPI_STA_DEVICE_ENABLED | \
ACPI_STA_DEVICE_UI | ACPI_STA_DEVICE_FUNCTIONING)
+extern struct list_head acpi_bus_id_list;
+
+struct acpi_device_bus_id{
+ char bus_id[15];
+ unsigned int instance_no;
+ struct list_head node;
+};
+
int acpi_device_add(struct acpi_device *device,
void (*release)(struct device *));
void acpi_init_device_object(struct acpi_device *device, acpi_handle handle,
diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c
index be1fc12a17ee..407a3760e8de 100644
--- a/drivers/acpi/scan.c
+++ b/drivers/acpi/scan.c
@@ -39,7 +39,7 @@ static const char *dummy_hid = "device";
static LIST_HEAD(acpi_dep_list);
static DEFINE_MUTEX(acpi_dep_list_lock);
-static LIST_HEAD(acpi_bus_id_list);
+LIST_HEAD(acpi_bus_id_list);
static DEFINE_MUTEX(acpi_scan_lock);
static LIST_HEAD(acpi_scan_handlers_list);
DEFINE_MUTEX(acpi_device_lock);
@@ -52,12 +52,6 @@ struct acpi_dep_data {
acpi_handle slave;
};
-struct acpi_device_bus_id{
- char bus_id[15];
- unsigned int instance_no;
- struct list_head node;
-};
-
void acpi_scan_lock_acquire(void)
{
mutex_lock(&acpi_scan_lock);
diff --git a/drivers/acpi/utils.c b/drivers/acpi/utils.c
index 475c9079bf85..f2f9873bb5c3 100644
--- a/drivers/acpi/utils.c
+++ b/drivers/acpi/utils.c
@@ -29,6 +29,7 @@
#include <linux/dynamic_debug.h>
#include "internal.h"
+#include "sleep.h"
#define _COMPONENT ACPI_BUS_COMPONENT
ACPI_MODULE_NAME("utils");
@@ -709,6 +710,36 @@ bool acpi_check_dsm(acpi_handle handle, const u8 *uuid, int rev, u64 funcs)
}
EXPORT_SYMBOL(acpi_check_dsm);
+/**
+ * acpi_dev_present - Detect presence of a given ACPI device in the system.
+ * @hid: Hardware ID of the device.
+ *
+ * Return %true if the device was present at the moment of invocation.
+ * Note that if the device is pluggable, it may since have disappeared.
+ *
+ * For this function to work, acpi_bus_scan() must have been executed
+ * which happens in the subsys_initcall() subsection. Hence, do not
+ * call from a subsys_initcall() or earlier (use acpi_get_devices()
+ * instead). Calling from module_init() is fine (which is synonymous
+ * with device_initcall()).
+ */
+bool acpi_dev_present(const char *hid)
+{
+ struct acpi_device_bus_id *acpi_device_bus_id;
+ bool found = false;
+
+ mutex_lock(&acpi_device_lock);
+ list_for_each_entry(acpi_device_bus_id, &acpi_bus_id_list, node)
+ if (!strcmp(acpi_device_bus_id->bus_id, hid)) {
+ found = true;
+ break;
+ }
+ mutex_unlock(&acpi_device_lock);
+
+ return found;
+}
+EXPORT_SYMBOL(acpi_dev_present);
+
/*
* acpi_backlight= handling, this is done here rather then in video_detect.c
* because __setup cannot be used in modules.