Module Name:    src
Committed By:   gsutre
Date:           Fri Sep 24 07:49:00 UTC 2010

Modified Files:
        src/sys/dev/acpi: acpi_pci.c acpi_verbose.c acpivar.h

Log Message:
Do not discard ACPI PCI addresses with function number 0xFFFF: the
ACPI specification allows them (ACPI 4.0a, p. 200).

ok jruoho@


To generate a diff of this commit:
cvs rdiff -u -r1.14 -r1.15 src/sys/dev/acpi/acpi_pci.c
cvs rdiff -u -r1.10 -r1.11 src/sys/dev/acpi/acpi_verbose.c
cvs rdiff -u -r1.62 -r1.63 src/sys/dev/acpi/acpivar.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/dev/acpi/acpi_pci.c
diff -u src/sys/dev/acpi/acpi_pci.c:1.14 src/sys/dev/acpi/acpi_pci.c:1.15
--- src/sys/dev/acpi/acpi_pci.c:1.14	Mon Aug  9 09:36:42 2010
+++ src/sys/dev/acpi/acpi_pci.c	Fri Sep 24 07:48:59 2010
@@ -1,4 +1,4 @@
-/* $NetBSD: acpi_pci.c,v 1.14 2010/08/09 09:36:42 gsutre Exp $ */
+/* $NetBSD: acpi_pci.c,v 1.15 2010/09/24 07:48:59 gsutre Exp $ */
 
 /*
  * Copyright (c) 2009, 2010 The NetBSD Foundation, Inc.
@@ -29,7 +29,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: acpi_pci.c,v 1.14 2010/08/09 09:36:42 gsutre Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi_pci.c,v 1.15 2010/09/24 07:48:59 gsutre Exp $");
 
 #include <sys/param.h>
 #include <sys/device.h>
@@ -113,9 +113,10 @@
 	if (ACPI_FAILURE(rv))
 		return rv;
 
-	if (bus < 0 || bus > 0xFFFF)
+	if (bus == -1)
 		return AE_NOT_EXIST;
 
+	/* Here it holds that 0 <= bus <= 0xFFFF. */
 	*busp = (uint16_t)bus;
 
 	return rv;
@@ -142,7 +143,10 @@
 	if (*bus != -1)
 		return AE_ALREADY_EXISTS;
 
-	*bus = addr64.Minimum;
+	if (addr64.Minimum > 0xFFFF)
+		return AE_BAD_DATA;
+
+	*bus = (int32_t)addr64.Minimum;
 
 	return AE_OK;
 }
@@ -211,7 +215,7 @@
 		ap->ap_function = ACPI_LOLODWORD(ad->ad_devinfo->Address);
 
 		if (ap->ap_bus > 255 || ap->ap_device > 31 ||
-		    ap->ap_function > 7) {
+		    (ap->ap_function > 7 && ap->ap_function != 0xFFFF)) {
 			aprint_error_dev(ad->ad_root,
 			    "invalid PCI address for %s\n", ad->ad_name);
 			kmem_free(ap, sizeof(*ap));
@@ -246,21 +250,31 @@
 		ap->ap_device = ACPI_HILODWORD(ad->ad_devinfo->Address);
 		ap->ap_function = ACPI_LOLODWORD(ad->ad_devinfo->Address);
 
-		if (ap->ap_device > 31 || ap->ap_function > 7) {
+		if (ap->ap_device > 31 ||
+		    (ap->ap_function > 7 && ap->ap_function != 0xFFFF)) {
 			aprint_error_dev(ad->ad_root,
 			    "invalid PCI address for %s\n", ad->ad_name);
 			kmem_free(ap, sizeof(*ap));
 			goto rec;
 		}
 
-		/*
-		 * Check whether this device is a PCI-to-PCI
-		 * bridge and get its secondary bus number.
-		 */
-		rv = acpi_pcidev_ppb_downbus(ap->ap_segment, ap->ap_bus,
-		    ap->ap_device, ap->ap_function, &ap->ap_downbus);
+		if (ap->ap_function == 0xFFFF) {
+			/*
+			 * Assume that this device is not a PCI-to-PCI bridge.
+			 * XXX: Do we need to be smarter?
+			 */
+			ap->ap_bridge = false;
+		} else {
+			/*
+			 * Check whether this device is a PCI-to-PCI
+			 * bridge and get its secondary bus number.
+			 */
+			rv = acpi_pcidev_ppb_downbus(ap->ap_segment, ap->ap_bus,
+			    ap->ap_device, ap->ap_function, &ap->ap_downbus);
+
+			ap->ap_bridge = (rv != AE_OK) ? false : true;
+		}
 
-		ap->ap_bridge = (rv != AE_OK) ? false : true;
 		ad->ad_pciinfo = ap;
 
 		goto rec;

Index: src/sys/dev/acpi/acpi_verbose.c
diff -u src/sys/dev/acpi/acpi_verbose.c:1.10 src/sys/dev/acpi/acpi_verbose.c:1.11
--- src/sys/dev/acpi/acpi_verbose.c:1.10	Wed Aug 11 10:32:42 2010
+++ src/sys/dev/acpi/acpi_verbose.c	Fri Sep 24 07:48:59 2010
@@ -1,4 +1,4 @@
-/*	$NetBSD: acpi_verbose.c,v 1.10 2010/08/11 10:32:42 gsutre Exp $ */
+/*	$NetBSD: acpi_verbose.c,v 1.11 2010/09/24 07:48:59 gsutre Exp $ */
 
 /*-
  * Copyright (c) 2003, 2007, 2010 The NetBSD Foundation, Inc.
@@ -65,7 +65,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: acpi_verbose.c,v 1.10 2010/08/11 10:32:42 gsutre Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi_verbose.c,v 1.11 2010/09/24 07:48:59 gsutre Exp $");
 
 #include <sys/param.h>
 #include <sys/device.h>
@@ -510,6 +510,9 @@
 	struct pci_softc *pci;
 	deviter_t di;
 
+	if (ap->ap_function == 0xFFFF)
+		return NULL;
+
 	for (dv = deviter_first(&di, DEVITER_F_ROOT_FIRST); dv != NULL;
 	     dv = deviter_next(&di)) {
 		pr = device_parent(dv);

Index: src/sys/dev/acpi/acpivar.h
diff -u src/sys/dev/acpi/acpivar.h:1.62 src/sys/dev/acpi/acpivar.h:1.63
--- src/sys/dev/acpi/acpivar.h:1.62	Mon Sep  6 15:54:27 2010
+++ src/sys/dev/acpi/acpivar.h	Fri Sep 24 07:48:59 2010
@@ -1,4 +1,4 @@
-/*	$NetBSD: acpivar.h,v 1.62 2010/09/06 15:54:27 jmcneill Exp $	*/
+/*	$NetBSD: acpivar.h,v 1.63 2010/09/24 07:48:59 gsutre Exp $	*/
 
 /*
  * Copyright 2001 Wasabi Systems, Inc.
@@ -66,6 +66,17 @@
 
 /*
  * PCI information for ACPI device nodes that correspond to PCI devices.
+ *
+ * Remarks:
+ *
+ *	ap_bus		<= 255
+ *	ap_device	<= 31
+ *	ap_function	<= 7		or	ap_function == 0xFFFF
+ *	ap_downbus	<= 255		if	ap_bridge == true
+ *
+ * The device and function numbers are encoded in the value returned by
+ * _ADR.  A function number of 0xFFFF is used to refer to all the
+ * functions on a PCI device (ACPI 4.0a, p. 200).
  */
 struct acpi_pci_info {
 	uint16_t		 ap_segment;	/* PCI segment group */

Reply via email to