From b9c068896914b4132a24839c9ef7f9fcd6282d88 Mon Sep 17 00:00:00 2001 From: Marcin Ko?cielnicki Date: Wed, 5 Feb 2014 09:01:25 +0100 Subject: Fix IO access functions on linux+sysfs. The offsets on the resourceX files are relative to BAR base - don't add the base address ourselves. Reviewed-by: Adam Jackson --- src/freebsd_pci.c | 2 ++ src/linux_sysfs.c | 62 +++++++++++++++++++++++++++++++++++-------------- src/netbsd_pci.c | 2 ++ src/openbsd_pci.c | 3 +++ src/pciaccess_private.h | 1 + src/solx_devfs.c | 1 + src/x86_pci.c | 1 + 7 files changed, 54 insertions(+), 18 deletions(-) diff --git a/src/freebsd_pci.c b/src/freebsd_pci.c index 14ec3bc..7f5f56b 100644 --- a/src/freebsd_pci.c +++ b/src/freebsd_pci.c @@ -579,6 +579,7 @@ pci_device_freebsd_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; #elif defined(PCI_MAGIC_IO_RANGE) ret->memory = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_SHARED, @@ -588,6 +589,7 @@ pci_device_freebsd_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; #else return NULL; diff --git a/src/linux_sysfs.c b/src/linux_sysfs.c index 97fcf36..8fca65e 100644 --- a/src/linux_sysfs.c +++ b/src/linux_sysfs.c @@ -759,6 +759,7 @@ pci_device_linux_sysfs_open_device_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 0; return ret; } @@ -796,6 +797,7 @@ pci_device_linux_sysfs_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; } @@ -813,10 +815,14 @@ pci_device_linux_sysfs_read32(struct pci_io_handle *handle, uint32_t port) { uint32_t ret; - if (handle->fd > -1) - pread(handle->fd, &ret, 4, port + handle->base); - else + if (handle->fd > -1) { + if (handle->is_legacy) + pread(handle->fd, &ret, 4, port + handle->base); + else + pread(handle->fd, &ret, 4, port); + } else { ret = inl(port + handle->base); + } return ret; } @@ -826,10 +832,14 @@ pci_device_linux_sysfs_read16(struct pci_io_handle *handle, uint32_t port) { uint16_t ret; - if (handle->fd > -1) - pread(handle->fd, &ret, 2, port + handle->base); - else + if (handle->fd > -1) { + if (handle->is_legacy) + pread(handle->fd, &ret, 2, port + handle->base); + else + pread(handle->fd, &ret, 2, port); + } else { ret = inw(port + handle->base); + } return ret; } @@ -839,10 +849,14 @@ pci_device_linux_sysfs_read8(struct pci_io_handle *handle, uint32_t port) { uint8_t ret; - if (handle->fd > -1) - pread(handle->fd, &ret, 1, port + handle->base); - else + if (handle->fd > -1) { + if (handle->is_legacy) + pread(handle->fd, &ret, 1, port + handle->base); + else + pread(handle->fd, &ret, 1, port); + } else { ret = inb(port + handle->base); + } return ret; } @@ -851,30 +865,42 @@ static void pci_device_linux_sysfs_write32(struct pci_io_handle *handle, uint32_t port, uint32_t data) { - if (handle->fd > -1) - pwrite(handle->fd, &data, 4, port + handle->base); - else + if (handle->fd > -1) { + if (handle->is_legacy) + pwrite(handle->fd, &data, 4, port + handle->base); + else + pwrite(handle->fd, &data, 4, port); + } else { outl(data, port + handle->base); + } } static void pci_device_linux_sysfs_write16(struct pci_io_handle *handle, uint32_t port, uint16_t data) { - if (handle->fd > -1) - pwrite(handle->fd, &data, 2, port + handle->base); - else + if (handle->fd > -1) { + if (handle->is_legacy) + pwrite(handle->fd, &data, 2, port + handle->base); + else + pwrite(handle->fd, &data, 2, port); + } else { outw(data, port + handle->base); + } } static void pci_device_linux_sysfs_write8(struct pci_io_handle *handle, uint32_t port, uint8_t data) { - if (handle->fd > -1) - pwrite(handle->fd, &data, 1, port + handle->base); - else + if (handle->fd > -1) { + if (handle->is_legacy) + pwrite(handle->fd, &data, 1, port + handle->base); + else + pwrite(handle->fd, &data, 1, port); + } else { outb(data, port + handle->base); + } } static int diff --git a/src/netbsd_pci.c b/src/netbsd_pci.c index b3f7f2d..e6dae4c 100644 --- a/src/netbsd_pci.c +++ b/src/netbsd_pci.c @@ -733,6 +733,7 @@ pci_device_netbsd_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; #elif defined(__amd64__) struct x86_64_iopl_args ia; @@ -743,6 +744,7 @@ pci_device_netbsd_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; #else return NULL; diff --git a/src/openbsd_pci.c b/src/openbsd_pci.c index 73c68f4..fe034f3 100644 --- a/src/openbsd_pci.c +++ b/src/openbsd_pci.c @@ -412,6 +412,7 @@ pci_device_openbsd_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; #elif defined(__amd64__) struct amd64_iopl_args ia; @@ -422,6 +423,7 @@ pci_device_openbsd_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; #elif defined(PCI_MAGIC_IO_RANGE) ret->memory = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_SHARED, @@ -431,6 +433,7 @@ pci_device_openbsd_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; #else return NULL; diff --git a/src/pciaccess_private.h b/src/pciaccess_private.h index 339ec0f..9f4e8f9 100644 --- a/src/pciaccess_private.h +++ b/src/pciaccess_private.h @@ -109,6 +109,7 @@ struct pci_io_handle { pciaddr_t size; void *memory; int fd; + int is_legacy; }; struct pci_device_private { diff --git a/src/solx_devfs.c b/src/solx_devfs.c index 41f5c19..8e7ea9b 100644 --- a/src/solx_devfs.c +++ b/src/solx_devfs.c @@ -911,6 +911,7 @@ pci_device_solx_devfs_open_legacy_io(struct pci_io_handle *ret, if (sysi86(SI86V86, V86SC_IOPL, PS_IOPL) == 0) { ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; } #endif diff --git a/src/x86_pci.c b/src/x86_pci.c index 1075367..49c1cab 100644 --- a/src/x86_pci.c +++ b/src/x86_pci.c @@ -729,6 +729,7 @@ pci_device_x86_open_legacy_io(struct pci_io_handle *ret, ret->base = base; ret->size = size; + ret->is_legacy = 1; return ret; } -- cgit v1.2.1