[PATCH pciaccess] Use PCIOCREADMASK on OpenBSD.

Mark Kettenis kettenis at openbsd.org
Mon Sep 29 14:14:51 PDT 2014


If the machdep.allowaperture sysctl(8) variable is set to 0, writing to PCI
config space is not allowed.  So instead of writing 0xffffffff to the BARs
in order to determine their size, use the PCIOCREADMASK ioctl(2) which
returns the mask of changeable bits that was saved by the kernel when the
devices was initially probed.

Reviewed-by: Matthieu Herrb <matthieu at herbb.eu>
Signed-off-by: Mark Kettenis <kettenis at openbsd.org>
---

Given that Matthieu already reviewed this diff, I'll push it in a couple of
days unless somebody speaks up.

 src/openbsd_pci.c | 31 +++++++++++++++++++++++++------
 1 file changed, 25 insertions(+), 6 deletions(-)

diff --git a/src/openbsd_pci.c b/src/openbsd_pci.c
index fe034f3..4d1b5cd 100644
--- a/src/openbsd_pci.c
+++ b/src/openbsd_pci.c
@@ -81,6 +81,29 @@ pci_write(int domain, int bus, int dev, int func, uint32_t reg, uint32_t val)
 	return ioctl(pcifd[domain], PCIOCWRITE, &io);
 }
 
+static int
+pci_readmask(int domain, int bus, int dev, int func, uint32_t reg,
+    uint32_t *val)
+{
+	struct pci_io io;
+	int err;
+
+	bzero(&io, sizeof(io));
+	io.pi_sel.pc_bus = bus;
+	io.pi_sel.pc_dev = dev;
+	io.pi_sel.pc_func = func;
+	io.pi_reg = reg;
+	io.pi_width = 4;
+
+	err = ioctl(pcifd[domain], PCIOCREADMASK, &io);
+	if (err)
+		return (err);
+
+	*val = io.pi_data;
+
+	return 0;
+}
+
 /**
  * Read a VGA ROM
  *
@@ -328,11 +351,9 @@ pci_device_openbsd_probe(struct pci_device *device)
 			return err;
 
 		/* Probe the size of the region. */
-		err = pci_write(domain, bus, dev, func, bar, ~0);
+		err = pci_readmask(domain, bus, dev, func, bar, &size);
 		if (err)
 			return err;
-		pci_read(domain, bus, dev, func, bar, &size);
-		pci_write(domain, bus, dev, func, bar, reg);
 
 		if (PCI_MAPREG_TYPE(reg) == PCI_MAPREG_TYPE_IO) {
 			region->is_IO = 1;
@@ -360,11 +381,9 @@ pci_device_openbsd_probe(struct pci_device *device)
 					return err;
 				reg64 |= (uint64_t)reg << 32;
 
-				err = pci_write(domain, bus, dev, func, bar, ~0);
+				err = pci_readmask(domain, bus, dev, func, bar, &size);
 				if (err)
 					return err;
-				pci_read(domain, bus, dev, func, bar, &size);
-				pci_write(domain, bus, dev, func, bar, reg64 >> 32);
 				size64 |= (uint64_t)size << 32;
 
 				region->base_addr = PCI_MAPREG_MEM64_ADDR(reg64);
-- 
2.1.0



More information about the xorg-devel mailing list