Module Name:    src
Committed By:   thorpej
Date:           Wed May 12 23:22:33 UTC 2021

Modified Files:
        src/sys/arch/arm/acpi: acpi_platform.c
        src/sys/arch/evbarm/conf: files.fdt
        src/sys/arch/macppc/conf: files.macppc
        src/sys/arch/ofppc/conf: files.ofppc
        src/sys/arch/sparc64/conf: files.sparc64
        src/sys/arch/sparc64/sparc64: autoconf.c
        src/sys/arch/x86/acpi: acpi_machdep.c
        src/sys/dev/acpi: acpi.c acpi_pci.c acpivar.h
        src/sys/dev/ofw: files.ofw
        src/sys/dev/pci: pci.c pcivar.h
Added Files:
        src/sys/dev/ofw: ofw_pci_subr.c

Log Message:
- Define a device call for PCI bus instances to fetch a direct child's
  device handle given the device's device/function #s (extracted from
  a pcitag_t).  Use it to associate the handle with the child device
  at config_found() time.
- Implement this device call for ACPI and OpenFirmware.
- Enable the OpenFirmware variant for evbarm FDT, macppc, ofppc, sparc64.
- Obsolete acpi_device_register(); it is no longer needed.
- Obsolete setting the OpenFirmware handle in PCI devices in the
  sparc64 device_register(); it is no longer needed.


To generate a diff of this commit:
cvs rdiff -u -r1.25 -r1.26 src/sys/arch/arm/acpi/acpi_platform.c
cvs rdiff -u -r1.7 -r1.8 src/sys/arch/evbarm/conf/files.fdt
cvs rdiff -u -r1.117 -r1.118 src/sys/arch/macppc/conf/files.macppc
cvs rdiff -u -r1.47 -r1.48 src/sys/arch/ofppc/conf/files.ofppc
cvs rdiff -u -r1.165 -r1.166 src/sys/arch/sparc64/conf/files.sparc64
cvs rdiff -u -r1.230 -r1.231 src/sys/arch/sparc64/sparc64/autoconf.c
cvs rdiff -u -r1.31 -r1.32 src/sys/arch/x86/acpi/acpi_machdep.c
cvs rdiff -u -r1.291 -r1.292 src/sys/dev/acpi/acpi.c
cvs rdiff -u -r1.30 -r1.31 src/sys/dev/acpi/acpi_pci.c
cvs rdiff -u -r1.85 -r1.86 src/sys/dev/acpi/acpivar.h
cvs rdiff -u -r1.16 -r1.17 src/sys/dev/ofw/files.ofw
cvs rdiff -u -r0 -r1.1 src/sys/dev/ofw/ofw_pci_subr.c
cvs rdiff -u -r1.159 -r1.160 src/sys/dev/pci/pci.c
cvs rdiff -u -r1.114 -r1.115 src/sys/dev/pci/pcivar.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/arch/arm/acpi/acpi_platform.c
diff -u src/sys/arch/arm/acpi/acpi_platform.c:1.25 src/sys/arch/arm/acpi/acpi_platform.c:1.26
--- src/sys/arch/arm/acpi/acpi_platform.c:1.25	Sat Apr 24 23:36:25 2021
+++ src/sys/arch/arm/acpi/acpi_platform.c	Wed May 12 23:22:32 2021
@@ -1,4 +1,4 @@
-/* $NetBSD: acpi_platform.c,v 1.25 2021/04/24 23:36:25 thorpej Exp $ */
+/* $NetBSD: acpi_platform.c,v 1.26 2021/05/12 23:22:32 thorpej Exp $ */
 
 /*-
  * Copyright (c) 2018 The NetBSD Foundation, Inc.
@@ -35,7 +35,7 @@
 #include "opt_multiprocessor.h"
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: acpi_platform.c,v 1.25 2021/04/24 23:36:25 thorpej Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi_platform.c,v 1.26 2021/05/12 23:22:32 thorpej Exp $");
 
 #include <sys/param.h>
 #include <sys/bus.h>
@@ -287,8 +287,6 @@ acpi_platform_init_attach_args(struct fd
 static void
 acpi_platform_device_register(device_t self, void *aux)
 {
-	acpi_device_register(self, aux);
-
 #if NCOM > 0
 	prop_dictionary_t prop = device_properties(self);
 	ACPI_STATUS rv;

Index: src/sys/arch/evbarm/conf/files.fdt
diff -u src/sys/arch/evbarm/conf/files.fdt:1.7 src/sys/arch/evbarm/conf/files.fdt:1.8
--- src/sys/arch/evbarm/conf/files.fdt:1.7	Sat Dec 12 09:27:31 2020
+++ src/sys/arch/evbarm/conf/files.fdt	Wed May 12 23:22:32 2021
@@ -1,9 +1,10 @@
-#	$NetBSD: files.fdt,v 1.7 2020/12/12 09:27:31 skrll Exp $
+#	$NetBSD: files.fdt,v 1.8 2021/05/12 23:22:32 thorpej Exp $
 #
 # FDT-based kernel configuration info
 #
 
 file	arch/evbarm/fdt/fdt_dma_machdep.c	fdt
 file	arch/evbarm/fdt/fdt_machdep.c		fdt
+file	dev/ofw/ofw_pci_subr.c			fdt & pci
 
 include "arch/arm/fdt/files.fdt"

Index: src/sys/arch/macppc/conf/files.macppc
diff -u src/sys/arch/macppc/conf/files.macppc:1.117 src/sys/arch/macppc/conf/files.macppc:1.118
--- src/sys/arch/macppc/conf/files.macppc:1.117	Sat May  1 15:12:25 2021
+++ src/sys/arch/macppc/conf/files.macppc	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-#	$NetBSD: files.macppc,v 1.117 2021/05/01 15:12:25 thorpej Exp $
+#	$NetBSD: files.macppc,v 1.118 2021/05/12 23:22:33 thorpej Exp $
 #
 # macppc-specific configuration info
 
@@ -93,6 +93,7 @@ include "dev/isa/files.isa"
 include "dev/pci/files.pci"
 include "dev/pci/files.agp"
 file arch/macppc/pci/pci_machdep.c		pci
+file dev/ofw/ofw_pci_subr.c			pci
 file arch/macppc/pci/agp_machdep.c		agp
 file arch/powerpc/pci/pciconf_indirect.c	pci
 file arch/powerpc/pci/pci_machdep_common.c	pci

Index: src/sys/arch/ofppc/conf/files.ofppc
diff -u src/sys/arch/ofppc/conf/files.ofppc:1.47 src/sys/arch/ofppc/conf/files.ofppc:1.48
--- src/sys/arch/ofppc/conf/files.ofppc:1.47	Mon Dec 18 15:53:39 2017
+++ src/sys/arch/ofppc/conf/files.ofppc	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-#	$NetBSD: files.ofppc,v 1.47 2017/12/18 15:53:39 skrll Exp $
+#	$NetBSD: files.ofppc,v 1.48 2021/05/12 23:22:33 thorpej Exp $
 #
 # NetBSD/ofppc configuration info
 #
@@ -77,6 +77,7 @@ file	arch/powerpc/pci/pciconf_ofmethod.c
 file	arch/powerpc/pci/pci_machdep_common.c	pci
 file	arch/powerpc/pci/pci_machdep_ofw.c	pci
 file    arch/powerpc/pci/pci_module.c		pci & modular
+file	dev/ofw/ofw_pci_subr.c			pci
 
 device ofwpci: pcibus
 attach ofwpci at mainbus

Index: src/sys/arch/sparc64/conf/files.sparc64
diff -u src/sys/arch/sparc64/conf/files.sparc64:1.165 src/sys/arch/sparc64/conf/files.sparc64:1.166
--- src/sys/arch/sparc64/conf/files.sparc64:1.165	Sun Apr 25 13:22:49 2021
+++ src/sys/arch/sparc64/conf/files.sparc64	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-#	$NetBSD: files.sparc64,v 1.165 2021/04/25 13:22:49 thorpej Exp $
+#	$NetBSD: files.sparc64,v 1.166 2021/05/12 23:22:33 thorpej Exp $
 
 # @(#)files.sparc64	8.1 (Berkeley) 7/19/93
 # sparc64-specific configuration info
@@ -44,6 +44,7 @@ file	arch/sparc64/dev/schizo.c		schizo
 file	arch/sparc64/dev/pyro.c			pyro
 file	arch/sparc64/dev/vpci.c			vpci
 file	arch/sparc64/dev/pci_machdep.c		psycho | schizo | pyro | vpci
+file	dev/ofw/ofw_pci_subr.c			pci
 
 device jbusi2c: i2cexec, i2c_bitbang, i2cbus
 attach jbusi2c at mainbus

Index: src/sys/arch/sparc64/sparc64/autoconf.c
diff -u src/sys/arch/sparc64/sparc64/autoconf.c:1.230 src/sys/arch/sparc64/sparc64/autoconf.c:1.231
--- src/sys/arch/sparc64/sparc64/autoconf.c:1.230	Tue May 11 03:43:30 2021
+++ src/sys/arch/sparc64/sparc64/autoconf.c	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: autoconf.c,v 1.230 2021/05/11 03:43:30 thorpej Exp $ */
+/*	$NetBSD: autoconf.c,v 1.231 2021/05/12 23:22:33 thorpej Exp $ */
 
 /*
  * Copyright (c) 1996
@@ -48,7 +48,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: autoconf.c,v 1.230 2021/05/11 03:43:30 thorpej Exp $");
+__KERNEL_RCSID(0, "$NetBSD: autoconf.c,v 1.231 2021/05/12 23:22:33 thorpej Exp $");
 
 #include "opt_ddb.h"
 #include "opt_kgdb.h"
@@ -1025,18 +1025,6 @@ device_register(device_t dev, void *aux)
 		 * Ignore mainbus0 itself, it certainly is not a boot
 		 * device.
 		 */
-	} else if (device_is_a(busdev, "pci")) {
-		struct pci_attach_args *pa = aux;
-
-		/*
-		 * XXX PCI devices don't currently get their devhandles
-		 * set when the PCI layer attaches them, so we need to
-		 * do it here.  (It's not just us; ACPI has the same
-		 * problem...)
-		 */
-		ofnode = (int)PCITAG_NODE(pa->pa_tag);
-		devhandle = devhandle_from_of(ofnode);
-		device_set_handle(dev, devhandle);
 	} else if (device_is_a(busdev, "iic")) {
 		struct i2c_attach_args *ia = aux;
 

Index: src/sys/arch/x86/acpi/acpi_machdep.c
diff -u src/sys/arch/x86/acpi/acpi_machdep.c:1.31 src/sys/arch/x86/acpi/acpi_machdep.c:1.32
--- src/sys/arch/x86/acpi/acpi_machdep.c:1.31	Thu Feb  4 23:54:48 2021
+++ src/sys/arch/x86/acpi/acpi_machdep.c	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-/* $NetBSD: acpi_machdep.c,v 1.31 2021/02/04 23:54:48 thorpej Exp $ */
+/* $NetBSD: acpi_machdep.c,v 1.32 2021/05/12 23:22:33 thorpej Exp $ */
 
 /*
  * Copyright 2001 Wasabi Systems, Inc.
@@ -40,7 +40,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: acpi_machdep.c,v 1.31 2021/02/04 23:54:48 thorpej Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi_machdep.c,v 1.32 2021/05/12 23:22:33 thorpej Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -603,8 +603,6 @@ device_acpi_register(device_t dev, void 
 	if (parent == NULL)
 		return;
 
-	acpi_device_register(dev, aux);
-
 	device_is_vga = device_is_a(dev, "vga") || device_is_a(dev, "genfb");
 	device_is_pci = device_is_a(parent, "pci");
 	device_is_isa = device_is_a(parent, "isa");

Index: src/sys/dev/acpi/acpi.c
diff -u src/sys/dev/acpi/acpi.c:1.291 src/sys/dev/acpi/acpi.c:1.292
--- src/sys/dev/acpi/acpi.c:1.291	Sat Apr 24 23:36:52 2021
+++ src/sys/dev/acpi/acpi.c	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: acpi.c,v 1.291 2021/04/24 23:36:52 thorpej Exp $	*/
+/*	$NetBSD: acpi.c,v 1.292 2021/05/12 23:22:33 thorpej Exp $	*/
 
 /*-
  * Copyright (c) 2003, 2007 The NetBSD Foundation, Inc.
@@ -100,7 +100,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: acpi.c,v 1.291 2021/04/24 23:36:52 thorpej Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi.c,v 1.292 2021/05/12 23:22:33 thorpej Exp $");
 
 #include "pci.h"
 #include "opt_acpi.h"
@@ -1146,43 +1146,6 @@ acpi_print(void *aux, const char *pnp)
 }
 
 /*
- * acpi_device_register --
- *	Called by the platform device_register() routine when
- *	attaching devices.
- */
-void
-acpi_device_register(device_t dev, void *v)
-{
-	/* All we do here is set the devhandle in the device_t. */
-	device_t parent = device_parent(dev);
-	ACPI_HANDLE hdl = NULL;
-
-	if (device_is_a(parent, "pci")) {
-		const struct pci_attach_args *pa = v;
-		struct acpi_devnode *ad;
-		u_int segment;
-
-#ifdef __HAVE_PCI_GET_SEGMENT
-		segment = pci_get_segment(pa->pa_pc);
-#else
-		segment = 0;
-#endif /* __HAVE_PCI_GET_SEGMENT */
-
-		ad = acpi_pcidev_find(segment,
-		    pa->pa_bus, pa->pa_device, pa->pa_function);
-		if (ad == NULL || (hdl = ad->ad_handle) == NULL) {
-			aprint_debug_dev(dev, "no matching ACPI node\n");
-			return;
-		}
-	} else {
-		return;
-	}
-	KASSERT(hdl != NULL);
-
-	device_set_handle(dev, devhandle_from_acpi(hdl));
-}
-
-/*
  * Notify.
  */
 static void

Index: src/sys/dev/acpi/acpi_pci.c
diff -u src/sys/dev/acpi/acpi_pci.c:1.30 src/sys/dev/acpi/acpi_pci.c:1.31
--- src/sys/dev/acpi/acpi_pci.c:1.30	Thu Jan 14 14:37:17 2021
+++ src/sys/dev/acpi/acpi_pci.c	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-/* $NetBSD: acpi_pci.c,v 1.30 2021/01/14 14:37:17 thorpej Exp $ */
+/* $NetBSD: acpi_pci.c,v 1.31 2021/05/12 23:22:33 thorpej 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.30 2021/01/14 14:37:17 thorpej Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi_pci.c,v 1.31 2021/05/12 23:22:33 thorpej Exp $");
 
 #include <sys/param.h>
 #include <sys/device.h>
@@ -542,3 +542,39 @@ acpi_pci_ignore_boot_config(ACPI_HANDLE 
 
 	return ret;
 }
+
+/*
+ * acpi_pci_bus_get_child_devhandle:
+ *
+ *	Implements the "pci-bus-get-child-devhandle" device call for
+ *	ACPI device handles
+ */
+static int
+acpi_pci_bus_get_child_devhandle(device_t dev, devhandle_t call_handle, void *v)
+{
+	struct pci_bus_get_child_devhandle_args *args = v;
+	struct acpi_devnode *ad;
+	ACPI_HANDLE hdl;
+	int b, d, f;
+	u_int segment;
+
+#ifdef __HAVE_PCI_GET_SEGMENT
+	segment = pci_get_segment(args->pc);
+#else
+	segment = 0;
+#endif /* __HAVE_PCI_GET_SEGMENT */
+
+	pci_decompose_tag(args->pc, args->tag, &b, &d, &f);
+
+	ad = acpi_pcidev_find(segment, b, d, f);
+
+	if (ad != NULL && (hdl = ad->ad_handle) != NULL) {
+		/* Found it! */
+		args->devhandle = devhandle_from_acpi(hdl);
+		return 0;
+	}
+
+	return ENODEV;
+}
+ACPI_DEVICE_CALL_REGISTER("pci-bus-get-child-devhandle",
+			  acpi_pci_bus_get_child_devhandle)

Index: src/sys/dev/acpi/acpivar.h
diff -u src/sys/dev/acpi/acpivar.h:1.85 src/sys/dev/acpi/acpivar.h:1.86
--- src/sys/dev/acpi/acpivar.h:1.85	Thu Feb  4 21:39:00 2021
+++ src/sys/dev/acpi/acpivar.h	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: acpivar.h,v 1.85 2021/02/04 21:39:00 thorpej Exp $	*/
+/*	$NetBSD: acpivar.h,v 1.86 2021/05/12 23:22:33 thorpej Exp $	*/
 
 /*
  * Copyright 2001 Wasabi Systems, Inc.
@@ -319,7 +319,6 @@ const struct device_compatible_entry *
 		    const struct device_compatible_entry *);
 
 bool    	acpi_device_present(ACPI_HANDLE);
-void		acpi_device_register(device_t, void *);
 
 int		acpi_reset(void);
 

Index: src/sys/dev/ofw/files.ofw
diff -u src/sys/dev/ofw/files.ofw:1.16 src/sys/dev/ofw/files.ofw:1.17
--- src/sys/dev/ofw/files.ofw:1.16	Thu Feb  4 20:19:09 2021
+++ src/sys/dev/ofw/files.ofw	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-#	$NetBSD: files.ofw,v 1.16 2021/02/04 20:19:09 thorpej Exp $
+#	$NetBSD: files.ofw,v 1.17 2021/05/12 23:22:33 thorpej Exp $
 #
 # First cut on Openfirmware interface
 #
@@ -17,6 +17,9 @@ file	dev/ofw/ofw_i2c_subr.c		ofbus | ope
 file	dev/ofw/ofw_network_subr.c	of_network_dev
 file	dev/ofw/ofw_spi_subr.c		ofbus | openfirm | ofw_subr
 
+# Let individual ports pull this in, as necessary.
+#file	dev/ofw/ofw_pci_subr.c		ofbus | openfirm | ofw_subr
+
 # Generic disk support
 device	ofdisk: disk
 attach	ofdisk at ofbus

Index: src/sys/dev/pci/pci.c
diff -u src/sys/dev/pci/pci.c:1.159 src/sys/dev/pci/pci.c:1.160
--- src/sys/dev/pci/pci.c:1.159	Sat Apr 24 23:36:57 2021
+++ src/sys/dev/pci/pci.c	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: pci.c,v 1.159 2021/04/24 23:36:57 thorpej Exp $	*/
+/*	$NetBSD: pci.c,v 1.160 2021/05/12 23:22:33 thorpej Exp $	*/
 
 /*
  * Copyright (c) 1995, 1996, 1997, 1998
@@ -36,7 +36,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: pci.c,v 1.159 2021/04/24 23:36:57 thorpej Exp $");
+__KERNEL_RCSID(0, "$NetBSD: pci.c,v 1.160 2021/05/12 23:22:33 thorpej Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_pci.h"
@@ -267,6 +267,27 @@ pciprint(void *aux, const char *pnp)
 	return UNCONF;
 }
 
+static devhandle_t
+pci_bus_get_child_devhandle(struct pci_softc *sc, pcitag_t tag)
+{
+	struct pci_bus_get_child_devhandle_args args = {
+		.pc = sc->sc_pc,
+		.tag = tag,
+	};
+
+	if (device_call(sc->sc_dev, "pci-bus-get-child-devhandle",
+			&args) != 0) {
+		/*
+		 * The call is either not supported or the requested
+		 * device was not found in the platform device tree.
+		 * Return an invalid handle.
+		 */
+		devhandle_invalidate(&args.devhandle);
+	}
+
+	return args.devhandle;
+}
+
 int
 pci_probe_device(struct pci_softc *sc, pcitag_t tag,
     int (*match)(const struct pci_attach_args *),
@@ -415,6 +436,8 @@ pci_probe_device(struct pci_softc *sc, p
 	}
 	pa.pa_intrline = PCI_INTERRUPT_LINE(intr);
 
+	devhandle_t devhandle = pci_bus_get_child_devhandle(sc, pa.pa_tag);
+
 #ifdef __HAVE_PCI_MSI_MSIX
 	if (pci_get_ht_capability(pc, tag, PCI_HT_CAP_MSIMAP, &off, &cap)) {
 		/*
@@ -464,6 +487,7 @@ pci_probe_device(struct pci_softc *sc, p
 		c->c_dev = config_found(sc->sc_dev, &pa, pciprint,
 		    CFARG_SUBMATCH, config_stdsubmatch,
 		    CFARG_LOCATORS, locs,
+		    CFARG_DEVHANDLE, devhandle,
 		    CFARG_EOL);
 
 		ret = (c->c_dev != NULL);

Index: src/sys/dev/pci/pcivar.h
diff -u src/sys/dev/pci/pcivar.h:1.114 src/sys/dev/pci/pcivar.h:1.115
--- src/sys/dev/pci/pcivar.h:1.114	Wed Jan 27 05:00:16 2021
+++ src/sys/dev/pci/pcivar.h	Wed May 12 23:22:33 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: pcivar.h,v 1.114 2021/01/27 05:00:16 thorpej Exp $	*/
+/*	$NetBSD: pcivar.h,v 1.115 2021/05/12 23:22:33 thorpej Exp $	*/
 
 /*
  * Copyright (c) 1996, 1997 Christopher G. Demetriou.  All rights reserved.
@@ -277,6 +277,31 @@ struct pci_softc {
 #define PCI_SC_DEVICESC(d, f) sc_devices[(d) * 8 + (f)]
 };
 
+/*
+ * pci-bus-get-child-devhandle device call
+ *
+ *	Called to get the device handle for a device, represented
+ *	by the pcitag_t with the PCI segment represented by the
+ *	pci_chipset_tag_t.  The PCI bus's device_t is the one
+ *	passed to device_call(), and the device whose handle is
+ *	being requested must be a direct child of that bus,
+ *	otherwise the behavior is undefined.
+ *
+ *	Call returns 0 if successful, or an error code upon failure:
+ *
+ *	ENOTSUP		The device handle implementation for the
+ *			PCI bus does not support this device call.
+ *
+ *	ENODEV		The PCI device represented by the pcitag_t
+ *			was not found in a bus-scoped search of the
+ *			platform device tree.
+ */
+struct pci_bus_get_child_devhandle_args {
+	pci_chipset_tag_t pc;		/* IN */
+	pcitag_t tag;			/* IN */
+	devhandle_t devhandle;		/* OUT */
+};
+
 extern struct cfdriver pci_cd;
 
 extern bool pci_mapreg_map_enable_decode;

Added files:

Index: src/sys/dev/ofw/ofw_pci_subr.c
diff -u /dev/null src/sys/dev/ofw/ofw_pci_subr.c:1.1
--- /dev/null	Wed May 12 23:22:34 2021
+++ src/sys/dev/ofw/ofw_pci_subr.c	Wed May 12 23:22:33 2021
@@ -0,0 +1,86 @@
+/*	$NetBSD: ofw_pci_subr.c,v 1.1 2021/05/12 23:22:33 thorpej Exp $	*/
+
+/*-
+ * Copyright (c) 2021 The NetBSD Foundation, Inc.
+ * All rights reserved.
+ *
+ * This code is derived from software contributed to The NetBSD Foundation
+ * by Jason R. Thorpe.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+ * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+__KERNEL_RCSID(0, "$NetBSD: ofw_pci_subr.c,v 1.1 2021/05/12 23:22:33 thorpej Exp $");
+
+#include <sys/types.h>
+#include <sys/device.h>
+#include <sys/endian.h>
+#include <sys/errno.h>
+
+#include <dev/pci/pcivar.h>
+
+#include <dev/ofw/openfirm.h>
+#include <dev/ofw/ofw_pci.h>
+
+static int
+ofw_pci_bus_get_child_devhandle(device_t dev, devhandle_t call_handle, void *v)
+{
+	struct pci_bus_get_child_devhandle_args *args = v;
+	int phandle = devhandle_to_of(call_handle);
+	struct ofw_pci_register opr;
+	int d, f, len;
+	uint32_t phys_hi;
+
+	/*
+	 * No need to compare the bus number; we are searching
+	 * only direct children of the specified node.  Skipping
+	 * the bus number comparison allows us to dodge a slight
+	 * difference between the OpenFirmware and FDT PCI bindings
+	 * as it relates to PCI-PCI bridges.
+	 */
+
+	pci_decompose_tag(args->pc, args->tag, NULL, &d, &f);
+
+	for (phandle = OF_child(phandle); phandle != 0;
+	     phandle = OF_peer(phandle)) {
+		len = OF_getprop(phandle, "reg", &opr, sizeof(opr));
+		if (len < sizeof(opr)) {
+			continue;
+		}
+
+		phys_hi = be32toh(opr.phys_hi);
+
+		if (d != OFW_PCI_PHYS_HI_DEVICE(phys_hi) ||
+		    f != OFW_PCI_PHYS_HI_FUNCTION(phys_hi)) {
+			continue;
+		}
+
+		/* Found it! */
+		args->devhandle = devhandle_from_of(phandle);
+		return 0;
+	}
+
+	return ENODEV;
+}
+OF_DEVICE_CALL_REGISTER("pci-bus-get-child-devhandle",
+			ofw_pci_bus_get_child_devhandle)

Reply via email to