pci: Remove xf86MapDomainMemory

This is slightly draconian, but that API is just awful.  In all but
one case in the callers it's used to get a map of some legacy VGA
memory, and it would be cleaner for the caller to just call
pci_device_map_legacy.

The sole exception is in the vesa driver, which uses it to avoid having
to look up which device the BAR belongs to.  That's similarly trivial to
fix.

Having done that, Linux's PCI layer is now very small indeed.

Reviewed-by: Jeremy Huddleston <jeremyhu@apple.com>
Tested-by: Jeremy Huddleston <jeremyhu@apple.com>
Signed-off-by: Adam Jackson <ajax@redhat.com>
This commit is contained in:
Adam Jackson 2011-05-10 17:34:23 -04:00 committed by Jeremy Huddleston
parent 6f5041d0b8
commit 7757b80924
7 changed files with 5 additions and 283 deletions

View File

@ -793,7 +793,7 @@ LIBXEXT="xext >= 1.0.99.4"
LIBXFONT="xfont >= 1.4.2"
LIBXI="xi >= 1.2.99.1"
LIBXTST="xtst >= 1.0.99.2"
LIBPCIACCESS="pciaccess >= 0.8.0"
LIBPCIACCESS="pciaccess >= 0.12.901"
LIBUDEV="libudev >= 143"
LIBSELINUX="libselinux >= 2.0.86"
LIBDBUS="dbus-1 >= 1.0"
@ -1521,7 +1521,6 @@ if test "x$XORG" = xauto; then
fi
AC_MSG_RESULT([$XORG])
xorg_bus_linuxpci=no
xorg_bus_bsdpci=no
xorg_bus_sparc=no
@ -1592,7 +1591,6 @@ if test "x$XORG" = xyes; then
XORG_CFLAGS="$XORG_CFLAGS -DXF86PM"
fi
XORG_OS_SUBDIR="linux"
xorg_bus_linuxpci="yes"
linux_acpi="no"
case $host_cpu in
alpha*)
@ -1775,7 +1773,6 @@ if test "x$XORG" = xyes; then
AC_SUBST([abi_extension])
fi
AM_CONDITIONAL([XORG], [test "x$XORG" = xyes])
AM_CONDITIONAL([XORG_BUS_LINUXPCI], [test "x$xorg_bus_linuxpci" = xyes])
AM_CONDITIONAL([XORG_BUS_BSDPCI], [test "x$xorg_bus_bsdpci" = xyes])
AM_CONDITIONAL([XORG_BUS_SPARC], [test "x$xorg_bus_sparc" = xyes])
AM_CONDITIONAL([LINUX_ALPHA], [test "x$linux_alpha" = xyes])

View File

@ -238,9 +238,7 @@ MapVRam(xf86Int10InfoPtr pInt)
int pagesize = getpagesize();
int size = ((VRAM_SIZE + pagesize - 1) / pagesize) * pagesize;
INTPriv(pInt)->vRam = xf86MapDomainMemory(pInt->scrnIndex, VIDMEM_MMIO,
pInt->dev, V_RAM, size);
pci_device_map_legacy(pInt->dev, V_RAM, size, PCI_DEV_MAP_FLAG_WRITABLE, &(INTPriv(pInt)->vRam));
pInt->io = pci_legacy_open_io(pInt->dev, 0, 64 * 1024);
}
@ -251,8 +249,7 @@ UnmapVRam(xf86Int10InfoPtr pInt)
int pagesize = getpagesize();
int size = ((VRAM_SIZE + pagesize - 1)/pagesize) * pagesize;
xf86UnMapVidMem(screen, INTPriv(pInt)->vRam, size);
pci_device_unmap_legacy(pInt->dev, INTPriv(pInt)->vRam, size);
pci_device_close_io(pInt->dev, pInt->io);
pInt->io = NULL;
}

View File

@ -3,10 +3,6 @@ sdk_HEADERS = xf86Pci.h
PCI_SOURCES = Pci.c Pci.h
if XORG_BUS_LINUXPCI
PCI_SOURCES += linuxPci.c
endif
if XORG_BUS_BSDPCI
PCI_SOURCES += bsd_pci.c
endif

View File

@ -48,13 +48,6 @@
#include "pciaccess.h"
pointer
xf86MapDomainMemory(int ScreenNum, int Flags, struct pci_device *dev,
ADDRESS Base, unsigned long Size)
{
return xf86MapVidMem(ScreenNum, Flags, Base, Size);
}
void
osPciInit(void)
{

View File

@ -1,256 +0,0 @@
/*
* Copyright 1998 by Concurrent Computer Corporation
*
* Permission to use, copy, modify, distribute, and sell this software
* and its documentation for any purpose is hereby granted without fee,
* provided that the above copyright notice appear in all copies and that
* both that copyright notice and this permission notice appear in
* supporting documentation, and that the name of Concurrent Computer
* Corporation not be used in advertising or publicity pertaining to
* distribution of the software without specific, written prior
* permission. Concurrent Computer Corporation makes no representations
* about the suitability of this software for any purpose. It is
* provided "as is" without express or implied warranty.
*
* CONCURRENT COMPUTER CORPORATION DISCLAIMS ALL WARRANTIES WITH REGARD
* TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS, IN NO EVENT SHALL CONCURRENT COMPUTER CORPORATION BE
* LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY
* DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
* WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
* ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
* SOFTWARE.
*
* Copyright 1998 by Metro Link Incorporated
*
* Permission to use, copy, modify, distribute, and sell this software
* and its documentation for any purpose is hereby granted without fee,
* provided that the above copyright notice appear in all copies and that
* both that copyright notice and this permission notice appear in
* supporting documentation, and that the name of Metro Link
* Incorporated not be used in advertising or publicity pertaining to
* distribution of the software without specific, written prior
* permission. Metro Link Incorporated makes no representations
* about the suitability of this software for any purpose. It is
* provided "as is" without express or implied warranty.
*
* METRO LINK INCORPORATED DISCLAIMS ALL WARRANTIES WITH REGARD
* TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS, IN NO EVENT SHALL METRO LINK INCORPORATED BE
* LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY
* DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
* WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
* ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
* SOFTWARE.
*/
#ifdef HAVE_XORG_CONFIG_H
#include <xorg-config.h>
#endif
#include <stdio.h>
#include "xf86_OSlib.h"
#include "Pci.h"
/**
* \bug
* The generation of the procfs file name for the domain != 0 case may not be
* correct.
*/
static int
linuxPciOpenFile(struct pci_device *dev, Bool write)
{
static struct pci_device *last_dev = NULL;
static int fd = -1,is_write = 0;
char file[64];
if (dev == NULL) {
return -1;
}
if (fd == -1 || (write && (!is_write)) || (last_dev != dev)) {
if (fd != -1) {
close(fd);
fd = -1;
}
sprintf(file,"/sys/bus/pci/devices/%04u:%02x:%02x.%01x/config",
dev->domain, dev->bus, dev->dev, dev->func);
if (write) {
fd = open(file,O_RDWR);
if (fd != -1) is_write = TRUE;
} else {
switch (is_write) {
case TRUE:
fd = open(file,O_RDWR);
if (fd > -1)
break;
default:
fd = open(file,O_RDONLY);
is_write = FALSE;
}
}
last_dev = dev;
}
return fd;
}
/*
* Compiling the following simply requires the presence of <linux/pci.c>.
* Actually running this is another matter altogether...
*
* This scheme requires that the kernel allow mmap()'ing of a host bridge's I/O
* and memory spaces through its /proc/bus/pci/BUS/DFN entry. Which one is
* determined by a prior ioctl().
*
* For the sparc64 port, this means 2.4.12 or later. For ppc, this
* functionality is almost, but not quite there yet. Alpha and other kernel
* ports to multi-domain architectures still need to implement this.
*
* TO DO: Address the deleterious reaction some host bridges have to master
* aborts. This is already done for secondary PCI buses, but not yet
* for accesses to primary buses (except for the SPARC port, where
* master aborts are avoided during PCI scans).
*/
#include <linux/pci.h>
#ifndef PCIIOC_BASE /* Ioctls for /proc/bus/pci/X/Y nodes. */
#define PCIIOC_BASE ('P' << 24 | 'C' << 16 | 'I' << 8)
/* Get controller for PCI device. */
#define PCIIOC_CONTROLLER (PCIIOC_BASE | 0x00)
/* Set mmap state to I/O space. */
#define PCIIOC_MMAP_IS_IO (PCIIOC_BASE | 0x01)
/* Set mmap state to MEM space. */
#define PCIIOC_MMAP_IS_MEM (PCIIOC_BASE | 0x02)
/* Enable/disable write-combining. */
#define PCIIOC_WRITE_COMBINE (PCIIOC_BASE | 0x03)
#endif
static pointer
linuxMapPci(int ScreenNum, int Flags, struct pci_device *dev,
ADDRESS Base, unsigned long Size, int mmap_ioctl)
{
/* Align to page boundary */
const ADDRESS realBase = Base & ~(getpagesize() - 1);
const ADDRESS Offset = Base - realBase;
do {
unsigned char *result;
int fd, mmapflags, prot;
xf86InitVidMem();
/* If dev is NULL, linuxPciOpenFile will return -1, and this routine
* will fail gracefully.
*/
prot = ((Flags & VIDMEM_READONLY) == 0);
if (((fd = linuxPciOpenFile(dev, prot)) < 0) ||
(ioctl(fd, mmap_ioctl, 0) < 0))
break;
/* Note: IA-64 doesn't compile this and doesn't need to */
#ifdef __ia64__
# ifndef MAP_WRITECOMBINED
# define MAP_WRITECOMBINED 0x00010000
# endif
# ifndef MAP_NONCACHED
# define MAP_NONCACHED 0x00020000
# endif
if (Flags & VIDMEM_FRAMEBUFFER)
mmapflags = MAP_SHARED | MAP_WRITECOMBINED;
else
mmapflags = MAP_SHARED | MAP_NONCACHED;
#else /* !__ia64__ */
mmapflags = (Flags & VIDMEM_FRAMEBUFFER) / VIDMEM_FRAMEBUFFER;
if (ioctl(fd, PCIIOC_WRITE_COMBINE, mmapflags) < 0)
break;
mmapflags = MAP_SHARED;
#endif /* ?__ia64__ */
if (Flags & VIDMEM_READONLY)
prot = PROT_READ;
else
prot = PROT_READ | PROT_WRITE;
result = mmap(NULL, Size + Offset, prot, mmapflags, fd, realBase);
if (!result || ((pointer)result == MAP_FAILED))
return NULL;
xf86MakeNewMapping(ScreenNum, Flags, realBase, Size + Offset, result);
return result + Offset;
} while (0);
if (mmap_ioctl == PCIIOC_MMAP_IS_MEM)
return xf86MapVidMem(ScreenNum, Flags, Base, Size);
return NULL;
}
static int
linuxOpenLegacy(struct pci_device *dev, char *name)
{
static const char PREFIX[] = "/sys/class/pci_bus/%04x:%02x/%s";
char path[sizeof(PREFIX) + 10];
int fd = -1;
while (dev != NULL) {
snprintf(path, sizeof(path) - 1, PREFIX, dev->domain, dev->bus, name);
fd = open(path, O_RDWR);
if (fd >= 0) {
return fd;
}
dev = pci_device_get_parent_bridge(dev);
}
return fd;
}
/*
* xf86MapDomainMemory - memory map PCI domain memory
*
* This routine maps the memory region in the domain specified by Tag and
* returns a pointer to it. The pointer is saved for future use if it's in
* the legacy ISA memory space (memory in a domain between 0 and 1MB).
*/
pointer
xf86MapDomainMemory(int ScreenNum, int Flags, struct pci_device *dev,
ADDRESS Base, unsigned long Size)
{
int fd = -1;
pointer addr;
/*
* We use /proc/bus/pci on non-legacy addresses or if the Linux sysfs
* legacy_mem interface is unavailable.
*/
if ((Base > 1024*1024) || ((fd = linuxOpenLegacy(dev, "legacy_mem")) < 0))
return linuxMapPci(ScreenNum, Flags, dev, Base, Size,
PCIIOC_MMAP_IS_MEM);
else
addr = mmap(NULL, Size, PROT_READ|PROT_WRITE, MAP_SHARED, fd, Base);
if (fd >= 0)
close(fd);
if (addr == NULL || addr == MAP_FAILED) {
perror("mmap failure");
FatalError("xf86MapDomainMem(): mmap() failure\n");
}
return addr;
}

View File

@ -254,8 +254,6 @@ typedef enum {
extern _X_EXPORT Bool xf86scanpci(void);
/* Domain access functions. Some of these probably shouldn't be public */
extern _X_EXPORT pointer xf86MapDomainMemory(int ScreenNum, int Flags, struct pci_device *dev,
ADDRESS Base, unsigned long Size);
extern _X_EXPORT struct pci_io_handle *xf86MapLegacyIO(struct pci_device *dev);
extern _X_EXPORT void xf86UnmapLegacyIO(struct pci_device *, struct pci_io_handle *);

View File

@ -1741,7 +1741,6 @@ Bool
vgaHWMapMem(ScrnInfoPtr scrp)
{
vgaHWPtr hwp = VGAHWPTR(scrp);
int scr_index = scrp->scrnIndex;
if (hwp->Base)
return TRUE;
@ -1759,8 +1758,7 @@ vgaHWMapMem(ScrnInfoPtr scrp)
* for now.
*/
DebugF("Mapping VGAMem\n");
hwp->Base = xf86MapDomainMemory(scr_index, VIDMEM_MMIO_32BIT, hwp->dev,
hwp->MapPhys, hwp->MapSize);
pci_device_map_legacy(hwp->dev, hwp->MapPhys, hwp->MapSize, PCI_DEV_MAP_FLAG_WRITABLE, &hwp->Base);
return hwp->Base != NULL;
}
@ -1769,13 +1767,12 @@ void
vgaHWUnmapMem(ScrnInfoPtr scrp)
{
vgaHWPtr hwp = VGAHWPTR(scrp);
int scr_index = scrp->scrnIndex;
if (hwp->Base == NULL)
return;
DebugF("Unmapping VGAMem\n");
xf86UnMapVidMem(scr_index, hwp->Base, hwp->MapSize);
pci_device_unmap_legacy(hwp->dev, hwp->Base, hwp->MapSize);
hwp->Base = NULL;
}