Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 27 Dec 2015 17:51:10 +0000 (UTC)
From:      Marius Strobl <marius@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-10@freebsd.org
Subject:   svn commit: r292785 - stable/10/sys/sparc64/ebus
Message-ID:  <201512271751.tBRHpA2Q036231@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: marius
Date: Sun Dec 27 17:51:10 2015
New Revision: 292785
URL: https://svnweb.freebsd.org/changeset/base/292785

Log:
  MFC: r287767
  
  - Sanity check that the parent ranges given in the "ranges" property
    of PCI-EBus-bridges actually match the BARs as specified in and
    required by [1, p. 113 f.]. Doing so earlier would have simplified
    diagnosing a bug in QEMU/OpenBIOS getting the mapping of child
    addresses wrong, which still needs to be fixed there.
    In theory, we could try to change the BARs accordingly if we hit
    this problem. However, at least with real machines changing the
    decoding likely won't work, especially if the PCI-EBus-bridge is
    beneath an APB one. So implementing such functionality generally
    is rather pointless.
  - Actually change the allocation type of EBus resources if they
    change from SYS_RES_MEMORY to SYS_RES_IOPORT when mapping them
    to PCI ranges in ebus_alloc_resource() and passing them up to
    bus_activate_resource(9). This may happen with the QEMU/OpenBIOS
    PCI-EBus-bridge but not real ones. Still, this is only cleans up
    the code and the result of resource allocation and activation is
    unchanged.
  - Change the remainder of printf(9) to device_printf(9) calls and
    canonicalize their wording.
  
  Peripheral Component Interconnect Input Output Controller,
  Part No.: 802-7837-01, Sun Microelectronics, March 1997 [1]

Modified:
  stable/10/sys/sparc64/ebus/ebus.c
Directory Properties:
  stable/10/   (props changed)

Modified: stable/10/sys/sparc64/ebus/ebus.c
==============================================================================
--- stable/10/sys/sparc64/ebus/ebus.c	Sun Dec 27 17:34:29 2015	(r292784)
+++ stable/10/sys/sparc64/ebus/ebus.c	Sun Dec 27 17:51:10 2015	(r292785)
@@ -69,7 +69,6 @@ __FBSDID("$FreeBSD$");
 #include <sys/kernel.h>
 #include <sys/malloc.h>
 #include <sys/module.h>
-
 #include <sys/rman.h>
 
 #include <dev/ofw/ofw_bus.h>
@@ -294,7 +293,7 @@ ebus_nexus_attach(device_t dev)
 	sc->sc_nrange = OF_getprop_alloc(node, "ranges",
 	    sizeof(struct ebus_nexus_ranges), &sc->sc_range);
 	if (sc->sc_nrange == -1) {
-		printf("%s: could not get ranges property\n", __func__);
+		device_printf(dev, "could not get ranges property\n");
 		return (ENXIO);
 	}
 	return (ebus_attach(dev, sc, node));
@@ -306,6 +305,7 @@ ebus_pci_attach(device_t dev)
 	struct ebus_softc *sc;
 	struct ebus_rinfo *eri;
 	struct resource *res;
+	struct isa_ranges *range;
 	phandle_t node;
 	int i, rnum, rid;
 
@@ -322,7 +322,7 @@ ebus_pci_attach(device_t dev)
 	sc->sc_nrange = OF_getprop_alloc(node, "ranges",
 	    sizeof(struct isa_ranges), &sc->sc_range);
 	if (sc->sc_nrange == -1) {
-		printf("%s: could not get ranges property\n", __func__);
+		device_printf(dev, "could not get ranges property\n");
 		return (ENXIO);
 	}
 
@@ -332,21 +332,34 @@ ebus_pci_attach(device_t dev)
 	/* For every range, there must be a matching resource. */
 	for (rnum = 0; rnum < sc->sc_nrange; rnum++) {
 		eri = &sc->sc_rinfo[rnum];
-		eri->eri_rtype = ofw_isa_range_restype(
-		    &((struct isa_ranges *)sc->sc_range)[rnum]);
+		range = &((struct isa_ranges *)sc->sc_range)[rnum];
+		eri->eri_rtype = ofw_isa_range_restype(range);
 		rid = PCIR_BAR(rnum);
 		res = bus_alloc_resource_any(dev, eri->eri_rtype, &rid,
 		    RF_ACTIVE);
 		if (res == NULL) {
-			printf("%s: failed to allocate range resource!\n",
-			    __func__);
+			device_printf(dev,
+			    "could not allocate range resource %d\n", rnum);
+			goto fail;
+		}
+		if (rman_get_start(res) != ISA_RANGE_PHYS(range)) {
+			device_printf(dev,
+			    "mismatch in start of range %d (0x%lx/0x%lx)\n",
+			    rnum, rman_get_start(res), ISA_RANGE_PHYS(range));
+			goto fail;
+		}
+		if (rman_get_size(res) != range->size) {
+			device_printf(dev,
+			    "mismatch in size of range %d (0x%lx/0x%x)\n",
+			    rnum, rman_get_size(res), range->size);
 			goto fail;
 		}
 		eri->eri_res = res;
 		eri->eri_rman.rm_type = RMAN_ARRAY;
 		eri->eri_rman.rm_descr = "EBus range";
 		if (rman_init_from_resource(&eri->eri_rman, res) != 0) {
-			printf("%s: failed to initialize rman!", __func__);
+			device_printf(dev,
+			    "could not initialize rman for range %d", rnum);
 			goto fail;
 		}
 	}
@@ -452,7 +465,7 @@ ebus_alloc_resource(device_t bus, device
 			 * Map EBus ranges to PCI ranges.  This may include
 			 * changing the allocation type.
 			 */
-			(void)ofw_isa_range_map(sc->sc_range, sc->sc_nrange,
+			type = ofw_isa_range_map(sc->sc_range, sc->sc_nrange,
 			    &start, &end, &ridx);
 			eri = &sc->sc_rinfo[ridx];
 			res = rman_reserve_resource(&eri->eri_rman, start,
@@ -507,7 +520,7 @@ ebus_activate_resource(device_t bus, dev
 	int i, rv;
 
 	sc = device_get_softc(bus);
-	if ((sc->sc_flags & EBUS_PCI) != 0 && type == SYS_RES_MEMORY) {
+	if ((sc->sc_flags & EBUS_PCI) != 0 && type != SYS_RES_IRQ) {
 		for (i = 0; i < sc->sc_nrange; i++) {
 			eri = &sc->sc_rinfo[i];
 			if (rman_is_region_manager(res, &eri->eri_rman) != 0) {
@@ -550,7 +563,7 @@ ebus_release_resource(device_t bus, devi
 	passthrough = (device_get_parent(child) != bus);
 	rl = BUS_GET_RESOURCE_LIST(bus, child);
 	sc = device_get_softc(bus);
-	if ((sc->sc_flags & EBUS_PCI) != 0 && type == SYS_RES_MEMORY) {
+	if ((sc->sc_flags & EBUS_PCI) != 0 && type != SYS_RES_IRQ) {
 		if ((rman_get_flags(res) & RF_ACTIVE) != 0 ){
 			rv = bus_deactivate_resource(child, type, rid, res);
 			if (rv != 0)



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201512271751.tBRHpA2Q036231>