From 55b30f98bcbd0ba8b539fa04f46d34896a1c7d2e Mon Sep 17 00:00:00 2001 From: oga Date: Thu, 10 Jul 2008 00:10:22 +0000 Subject: [PATCH] the DRM_{READ,WRITE}$NUMBER() macros currently use bus_space_{read,write}(). A bug in the code this was based on means that this is also used for scatter gather maps, which are bus_dma memory, not pci memory. This obviously fails. Pull them out into a function and Special case scatter gather to use the mapped virtual address to write instead. Makes writeback test pass on pci and pci express radeon cards. Tested by, among others ckuethe@ and sthen@. --- sys/dev/pci/drm/drmP.h | 24 +++++------ sys/dev/pci/drm/drm_memory.c | 83 ++++++++++++++++++++++++++++++++++++ 2 files changed, 95 insertions(+), 12 deletions(-) diff --git a/sys/dev/pci/drm/drmP.h b/sys/dev/pci/drm/drmP.h index 3b448aff895..24f8c6b19b9 100644 --- a/sys/dev/pci/drm/drmP.h +++ b/sys/dev/pci/drm/drmP.h @@ -229,18 +229,12 @@ typedef u_int8_t u8; "lock; addl $0,0(%%rsp)" : : : "memory"); #endif -#define DRM_READ8(map, offset) \ - bus_space_read_1( (map)->bst, (map)->bsh, (offset)) -#define DRM_READ16(map, offset) \ - bus_space_read_2( (map)->bst, (map)->bsh, (offset)) -#define DRM_READ32(map, offset) \ - bus_space_read_4( (map)->bst, (map)->bsh, (offset)) -#define DRM_WRITE8(map, offset, val) \ - bus_space_write_1((map)->bst, (map)->bsh, (offset), (val)) -#define DRM_WRITE16(map, offset, val) \ - bus_space_write_2((map)->bst, (map)->bsh, (offset), (val)) -#define DRM_WRITE32(map, offset, val) \ - bus_space_write_4((map)->bst, (map)->bsh, (offset), (val)) +#define DRM_READ8(map, offset) drm_read8(map, offset) +#define DRM_READ16(map, offset) drm_read16(map, offset) +#define DRM_READ32(map, offset) drm_read32(map, offset) +#define DRM_WRITE8(map, offset, val) drm_write8(map, offset, val) +#define DRM_WRITE16(map, offset, val) drm_write16(map, offset, val) +#define DRM_WRITE32(map, offset, val) drm_write32(map, offset, val) #define DRM_VERIFYAREA_READ( uaddr, size ) \ (!uvm_map_checkprot(&(curproc->p_vmspace->vm_map), \ @@ -757,6 +751,12 @@ int drm_ctxbitmap_init(struct drm_device *); void drm_ctxbitmap_cleanup(struct drm_device *); void drm_ctxbitmap_free(struct drm_device *, int); int drm_ctxbitmap_next(struct drm_device *); +u_int8_t drm_read8(drm_local_map_t *, unsigned long); +u_int16_t drm_read16(drm_local_map_t *, unsigned long); +u_int32_t drm_read32(drm_local_map_t *, unsigned long); +void drm_write8(drm_local_map_t *, unsigned long, u_int8_t); +void drm_write16(drm_local_map_t *, unsigned long, u_int16_t); +void drm_write32(drm_local_map_t *, unsigned long, u_int32_t); /* Locking IOCTL support (drm_lock.c) */ int drm_lock_take(__volatile__ unsigned int *, unsigned int); diff --git a/sys/dev/pci/drm/drm_memory.c b/sys/dev/pci/drm/drm_memory.c index c727da1202b..44714ca310b 100644 --- a/sys/dev/pci/drm/drm_memory.c +++ b/sys/dev/pci/drm/drm_memory.c @@ -174,3 +174,86 @@ drm_mtrr_del(int __unused handle, unsigned long offset, size_t size, int flags) return 0; #endif } + +u_int8_t +drm_read8(drm_local_map_t *map, unsigned long offset) +{ + u_int8_t *ptr; + + switch (map->type) { + case _DRM_SCATTER_GATHER: + ptr = map->handle + offset; + return (*ptr); + + default: + return (bus_space_read_1(map->bst, map->bsh, offset)); + } +} + +u_int16_t +drm_read16(drm_local_map_t *map, unsigned long offset) +{ + u_int16_t *ptr; + switch (map->type) { + case _DRM_SCATTER_GATHER: + ptr = map->handle + offset; + return (*ptr); + default: + return (bus_space_read_2(map->bst, map->bsh, offset)); + } +} + +u_int32_t +drm_read32(drm_local_map_t *map, unsigned long offset) +{ + u_int32_t *ptr; + switch (map->type) { + case _DRM_SCATTER_GATHER: + ptr = map->handle + offset; + return (*ptr); + default: + return (bus_space_read_4(map->bst, map->bsh, offset)); + } +} + +void +drm_write8(drm_local_map_t *map, unsigned long offset, u_int8_t val) +{ + u_int8_t *ptr; + switch (map->type) { + case _DRM_SCATTER_GATHER: + ptr = map->handle + offset; + *ptr = val; + break; + default: + bus_space_write_1(map->bst, map->bsh, offset, val); + } +} + +void +drm_write16(drm_local_map_t *map, unsigned long offset, u_int16_t val) +{ + u_int16_t *ptr; + switch (map->type) { + case _DRM_SCATTER_GATHER: + ptr = map->handle + offset; + *ptr = val; + break; + default: + bus_space_write_2(map->bst, map->bsh, offset, val); + } +} + +void +drm_write32(drm_local_map_t *map, unsigned long offset, u_int32_t val) +{ + u_int32_t *ptr; + switch (map->type) { + case _DRM_SCATTER_GATHER: + ptr = map->handle + offset; + *ptr = val; + break; + default: + bus_space_write_4(map->bst, map->bsh, offset, val); + } +} -- 2.20.1