From patchwork Mon Sep 21 19:30:06 2009 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bjorn Helgaas X-Patchwork-Id: 49104 Received: from vger.kernel.org (vger.kernel.org [209.132.176.167]) by demeter.kernel.org (8.14.2/8.14.2) with ESMTP id n8LJTrWZ009260 for ; Mon, 21 Sep 2009 19:30:08 GMT Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753421AbZIUTaE (ORCPT ); Mon, 21 Sep 2009 15:30:04 -0400 Received: (majordomo@vger.kernel.org) by vger.kernel.org id S1753441AbZIUTaD (ORCPT ); Mon, 21 Sep 2009 15:30:03 -0400 Received: from g1t0029.austin.hp.com ([15.216.28.36]:36153 "EHLO g1t0029.austin.hp.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1753421AbZIUTaC (ORCPT ); Mon, 21 Sep 2009 15:30:02 -0400 Received: from g1t0039.austin.hp.com (g1t0039.austin.hp.com [16.236.32.45]) by g1t0029.austin.hp.com (Postfix) with ESMTP id 8ADA438098; Mon, 21 Sep 2009 19:30:06 +0000 (UTC) Received: from ldl (linux.corp.hp.com [15.11.146.101]) by g1t0039.austin.hp.com (Postfix) with ESMTP id 67333340F6; Mon, 21 Sep 2009 19:30:06 +0000 (UTC) Received: from localhost (ldl.fc.hp.com [127.0.0.1]) by ldl (Postfix) with ESMTP id 6CBF4CF000F; Mon, 21 Sep 2009 13:30:06 -0600 (MDT) Received: from ldl ([127.0.0.1]) by localhost (ldl.fc.hp.com [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 4Xdi+fgJMpCe; Mon, 21 Sep 2009 13:30:06 -0600 (MDT) Received: from eh.fc.hp.com (eh.fc.hp.com [15.11.146.105]) by ldl (Postfix) with ESMTP id 56978CF000D; Mon, 21 Sep 2009 13:30:06 -0600 (MDT) Received: from bob.kio (localhost [127.0.0.1]) by eh.fc.hp.com (Postfix) with ESMTP id 3357F2615C; Mon, 21 Sep 2009 13:30:06 -0600 (MDT) Subject: [PATCH v3 16/17] ACPI: factor out device type and status checking To: Len Brown From: Bjorn Helgaas Cc: linux-acpi@vger.kernel.org Date: Mon, 21 Sep 2009 13:30:06 -0600 Message-ID: <20090921193006.21322.96498.stgit@bob.kio> In-Reply-To: <20090921192656.21322.23072.stgit@bob.kio> References: <20090921192656.21322.23072.stgit@bob.kio> User-Agent: StGit/0.14.3.386.gb02d MIME-Version: 1.0 Sender: linux-acpi-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-acpi@vger.kernel.org This patch adds acpi_bus_type_and_status(), which determines the type of the object and whether we want to build an acpi_device for it. If it is acpi_device-worthy, it returns the type and the device's current status. Signed-off-by: Bjorn Helgaas --- drivers/acpi/scan.c | 129 +++++++++++++++++++++------------------------------ 1 files changed, 52 insertions(+), 77 deletions(-) -- To unsubscribe from this list: send the line "unsubscribe linux-acpi" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index ed2b5f9..954bd01 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -1252,6 +1252,7 @@ static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) static int acpi_add_single_object(struct acpi_device **child, acpi_handle handle, int type, + unsigned long long sta, struct acpi_bus_ops *ops) { int result; @@ -1268,61 +1269,21 @@ static int acpi_add_single_object(struct acpi_device **child, device->handle = handle; device->parent = acpi_bus_get_parent(handle); device->bus_ops = *ops; /* workround for not call .start */ + STRUCT_TO_INT(device->status) = sta; acpi_device_get_busid(device); /* * Flags * ----- - * Get prior to calling acpi_bus_get_status() so we know whether - * or not _STA is present. Note that we only look for object - * handles -- cannot evaluate objects until we know the device is - * present and properly initialized. + * Note that we only look for object handles -- cannot evaluate objects + * until we know the device is present and properly initialized. */ result = acpi_bus_get_flags(device); if (result) goto end; /* - * Status - * ------ - * See if the device is present. We always assume that non-Device - * and non-Processor objects (e.g. thermal zones, power resources, - * etc.) are present, functioning, etc. (at least when parent object - * is present). Note that _STA has a different meaning for some - * objects (e.g. power resources) so we need to be careful how we use - * it. - */ - switch (type) { - case ACPI_BUS_TYPE_PROCESSOR: - case ACPI_BUS_TYPE_DEVICE: - result = acpi_bus_get_status(device); - if (ACPI_FAILURE(result)) { - result = -ENODEV; - goto end; - } - /* - * When the device is neither present nor functional, the - * device should not be added to Linux ACPI device tree. - * When the status of the device is not present but functinal, - * it should be added to Linux ACPI tree. For example : bay - * device , dock device. - * In such conditions it is unncessary to check whether it is - * bay device or dock device. - */ - if (!device->status.present && !device->status.functional) { - result = -ENODEV; - goto end; - } - break; - default: - STRUCT_TO_INT(device->status) = - ACPI_STA_DEVICE_PRESENT | ACPI_STA_DEVICE_ENABLED | - ACPI_STA_DEVICE_UI | ACPI_STA_DEVICE_FUNCTIONING; - break; - } - - /* * Initialize Device * ----------------- * TBD: Synch with Core's enumeration/initialization process. @@ -1393,41 +1354,69 @@ end: return result; } -static acpi_status acpi_bus_check_add(acpi_handle handle, u32 lvl, - void *context, void **return_value) +#define ACPI_STA_DEFAULT (ACPI_STA_DEVICE_PRESENT | ACPI_STA_DEVICE_ENABLED | \ + ACPI_STA_DEVICE_UI | ACPI_STA_DEVICE_FUNCTIONING) + +static int acpi_bus_type_and_status(acpi_handle handle, int *type, + unsigned long long *sta) { - acpi_status status = AE_OK; - struct acpi_device *device = NULL; - acpi_object_type type = 0; - struct acpi_bus_ops *ops = context; + acpi_status status; + acpi_object_type acpi_type; - status = acpi_get_type(handle, &type); + status = acpi_get_type(handle, &acpi_type); if (ACPI_FAILURE(status)) - return AE_OK; + return -ENODEV; - /* - * We're only interested in objects that we consider 'devices'. - */ - switch (type) { + switch (acpi_type) { case ACPI_TYPE_ANY: /* for ACPI_ROOT_OBJECT */ case ACPI_TYPE_DEVICE: - type = ACPI_BUS_TYPE_DEVICE; + *type = ACPI_BUS_TYPE_DEVICE; + status = acpi_bus_get_status_handle(handle, sta); + if (ACPI_FAILURE(status)) + return -ENODEV; break; case ACPI_TYPE_PROCESSOR: - type = ACPI_BUS_TYPE_PROCESSOR; + *type = ACPI_BUS_TYPE_PROCESSOR; + status = acpi_bus_get_status_handle(handle, sta); + if (ACPI_FAILURE(status)) + return -ENODEV; break; case ACPI_TYPE_THERMAL: - type = ACPI_BUS_TYPE_THERMAL; + *type = ACPI_BUS_TYPE_THERMAL; + *sta = ACPI_STA_DEFAULT; break; case ACPI_TYPE_POWER: - type = ACPI_BUS_TYPE_POWER; + *type = ACPI_BUS_TYPE_POWER; + *sta = ACPI_STA_DEFAULT; break; default: - return AE_OK; + return -ENODEV; } + return 0; +} + +static acpi_status acpi_bus_check_add(acpi_handle handle, u32 lvl, + void *context, void **return_value) +{ + struct acpi_bus_ops *ops = context; + struct acpi_device *device = NULL; + acpi_status status; + int type; + unsigned long long sta; + int result; + + result = acpi_bus_type_and_status(handle, &type, &sta); + if (result) + return AE_OK; + + if (!(sta & ACPI_STA_DEVICE_PRESENT) && + !(sta & ACPI_STA_DEVICE_FUNCTIONING)) + return AE_CTRL_DEPTH; + if (ops->acpi_op_add) - status = acpi_add_single_object(&device, handle, type, ops); + status = acpi_add_single_object(&device, handle, type, sta, + ops); else status = acpi_bus_get_device(handle, &device); @@ -1440,22 +1429,6 @@ static acpi_status acpi_bus_check_add(acpi_handle handle, u32 lvl, return AE_CTRL_DEPTH; } - /* - * If the device is present, enabled, and functioning then - * parse its scope (depth-first). Note that we need to - * represent absent devices to facilitate PnP notifications - * -- but only the subtree head (not all of its children, - * which will be enumerated when the parent is inserted). - * - * TBD: Need notifications and other detection mechanisms - * in place before we can fully implement this. - * - * When the device is not present but functional, it is also - * necessary to scan the children of this device. - */ - if (!device->status.present && !device->status.functional) - return AE_CTRL_DEPTH; - if (!*return_value) *return_value = device; return AE_OK; @@ -1579,12 +1552,14 @@ static int acpi_bus_scan_fixed(void) if ((acpi_gbl_FADT.flags & ACPI_FADT_POWER_BUTTON) == 0) { result = acpi_add_single_object(&device, NULL, ACPI_BUS_TYPE_POWER_BUTTON, + ACPI_STA_DEFAULT, &ops); } if ((acpi_gbl_FADT.flags & ACPI_FADT_SLEEP_BUTTON) == 0) { result = acpi_add_single_object(&device, NULL, ACPI_BUS_TYPE_SLEEP_BUTTON, + ACPI_STA_DEFAULT, &ops); }