From patchwork Tue Apr 14 19:46:18 2009 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jesse Barnes X-Patchwork-Id: 18209 X-Patchwork-Delegate: bjorn.helgaas@hp.com 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 n3EJqNZ3000708 for ; Tue, 14 Apr 2009 19:53:04 GMT Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752993AbZDNTxD (ORCPT ); Tue, 14 Apr 2009 15:53:03 -0400 Received: (majordomo@vger.kernel.org) by vger.kernel.org id S1753973AbZDNTxB (ORCPT ); Tue, 14 Apr 2009 15:53:01 -0400 Received: from outbound-mail-124.bluehost.com ([67.222.38.24]:46700 "HELO outbound-mail-124.bluehost.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with SMTP id S1752993AbZDNTxA (ORCPT ); Tue, 14 Apr 2009 15:53:00 -0400 X-Greylist: delayed 397 seconds by postgrey-1.27 at vger.kernel.org; Tue, 14 Apr 2009 15:53:00 EDT Received: (qmail 23306 invoked by uid 0); 14 Apr 2009 19:46:14 -0000 Received: from unknown (HELO box514.bluehost.com) (74.220.219.114) by outboundproxy4.bluehost.com with SMTP; 14 Apr 2009 19:46:14 -0000 DomainKey-Signature: a=rsa-sha1; q=dns; c=nofws; s=default; d=virtuousgeek.org; h=Received:Date:From:To:Subject:Message-ID:X-Mailer:Mime-Version:Content-Type:Content-Transfer-Encoding:X-Identified-User; b=ppxSr5epjysRLdW0XOd8h5/Ymi9pgqq0N/y1RlK/yiiCuUX48Ch3+Cf1phlt2QPCYQZuzUn3o4qIQXm2t75e0O49xIOfUSN33A0MvK1GF2/O/Fi4PUT1DdfuCKCj/1Kz; Received: from [75.111.28.251] (helo=hobbes) by box514.bluehost.com with esmtpsa (TLSv1:AES128-SHA:128) (Exim 4.69) (envelope-from ) id 1LtoaK-0000Es-DH; Tue, 14 Apr 2009 13:46:20 -0600 Date: Tue, 14 Apr 2009 12:46:18 -0700 From: Jesse Barnes To: Bjorn Helgaas , lenb@kernel.org, linux-acpi@vger.kernel.org, intel-gfx@lists.freedesktop.org Subject: [PATCH] pnp: add PNP resource range checking function Message-ID: <20090414124618.0dd9f536@hobbes> X-Mailer: Claws Mail 3.6.1 (GTK+ 2.16.1; x86_64-pc-linux-gnu) Mime-Version: 1.0 X-Identified-User: {10642:box514.bluehost.com:virtuous:virtuousgeek.org} {sentby:smtp auth 75.111.28.251 authed with jbarnes@virtuousgeek.org} Sender: linux-acpi-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-acpi@vger.kernel.org This patch adds a new export from the ACPI PNP core, is_acpi_pnp_reserved, which is intended for use by drivers to check whether a given range is already reserved (and therefore likely safe to use) or not (indicating that new resource space should probably be allocated). If it looks reasonable, there's code in arch/x86/pci that could probably be moved over to this as well. Signed-off-by: Jesse Barnes --- 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/pnp/pnpacpi/core.c b/drivers/pnp/pnpacpi/core.c index 2834846..810feff 100644 --- a/drivers/pnp/pnpacpi/core.c +++ b/drivers/pnp/pnpacpi/core.c @@ -27,6 +27,94 @@ #include "../base.h" #include "pnpacpi.h" +/* + * Check the given resource against our test range + */ +static acpi_status check_pnp_resource(struct acpi_resource *res, + void *data) +{ + struct resource *test_res = data; + struct acpi_resource_address64 address; + acpi_status status; + + if (res->type == ACPI_RESOURCE_TYPE_FIXED_MEMORY32) { + struct acpi_resource_fixed_memory32 *fixmem32 = + &res->data.fixed_memory32; + if (!fixmem32) + return AE_OK; + + if ((test_res->start >= fixmem32->address) && + (test_res->end < (fixmem32->address + + fixmem32->address_length))) { + test_res->flags = 1; + return AE_CTRL_TERMINATE; + } + } + if ((res->type != ACPI_RESOURCE_TYPE_ADDRESS32) && + (res->type != ACPI_RESOURCE_TYPE_ADDRESS64)) + return AE_OK; + + status = acpi_resource_to_address64(res, &address); + if (ACPI_FAILURE(status) || + (address.address_length <= 0) || + (address.resource_type != ACPI_MEMORY_RANGE)) + return AE_OK; + + if ((test_res->start >= address.minimum) && + (test_res->end < (address.minimum + address.address_length))) { + test_res->flags = 1; + return AE_CTRL_TERMINATE; + } + return AE_OK; +} + +/* + * Walk the current resource settings and check status + */ +static acpi_status find_pnp_resource(acpi_handle handle, u32 lvl, + void *context, void **rv) +{ + struct resource *res = context; + + acpi_walk_resources(handle, METHOD_NAME__CRS, + check_pnp_resource, context); + + if (res->flags) + return AE_CTRL_TERMINATE; + + return AE_OK; +} + +/** + * is_acpi_pnp_reserved - check whether a given range is reserved + * @start: start of range + * @end: end of range + * + * Check the given range (specified by @start and @end) against the current + * PNP resource settings. + * + * RETURNS: + * Zero if the range is not currently reserved. + * Nonzero if the range is reserved. + */ +int is_acpi_pnp_reserved(u64 start, u64 end) +{ + struct resource res; + + res.start = start; + res.end = end; + res.flags = 0; + + acpi_get_devices("PNP0C01", find_pnp_resource, &res, NULL); + + if (!res.flags) + acpi_get_devices("PNP0C02", find_pnp_resource, &res, + NULL); + + return res.flags; +} +EXPORT_SYMBOL(is_acpi_pnp_reserved); + static int num = 0; /* We need only to blacklist devices that have already an acpi driver that diff --git a/include/linux/pnp.h b/include/linux/pnp.h index ca3c887..2bc9cfc 100644 --- a/include/linux/pnp.h +++ b/include/linux/pnp.h @@ -446,6 +446,7 @@ int pnp_start_dev(struct pnp_dev *dev); int pnp_stop_dev(struct pnp_dev *dev); int pnp_activate_dev(struct pnp_dev *dev); int pnp_disable_dev(struct pnp_dev *dev); +int is_acpi_pnp_reserved(u64 start, u64 end); /* protocol helpers */ int pnp_is_active(struct pnp_dev *dev); @@ -476,6 +477,7 @@ static inline int pnp_start_dev(struct pnp_dev *dev) { return -ENODEV; } static inline int pnp_stop_dev(struct pnp_dev *dev) { return -ENODEV; } static inline int pnp_activate_dev(struct pnp_dev *dev) { return -ENODEV; } static inline int pnp_disable_dev(struct pnp_dev *dev) { return -ENODEV; } +static inline int is_acpi_pnp_reserved(u64 start, u64 end) { return FALSE; } /* protocol helpers */ static inline int pnp_is_active(struct pnp_dev *dev) { return 0; }