drm/radeon/kms: fix r6xx+ scanout on BE systems
R6xx+ have per-block swappers. BE content in the framebuffer will now be swapped properly during scanout. Untested, however, the same code is reported working in the UMS ddx. Signed-off-by: Alex Deucher <alexdeucher@gmail.com> Signed-off-by: Dave Airlie <airlied@gmail.com>
This commit is contained in:
parent
d75ee3be44
commit
fa6bee46a6
2 changed files with 22 additions and 1 deletions
|
@ -994,6 +994,7 @@ static int evergreen_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
struct radeon_bo *rbo;
|
||||
uint64_t fb_location;
|
||||
uint32_t fb_format, fb_pitch_pixels, tiling_flags;
|
||||
u32 fb_swap = EVERGREEN_GRPH_ENDIAN_SWAP(EVERGREEN_GRPH_ENDIAN_NONE);
|
||||
int r;
|
||||
|
||||
/* no fb bound */
|
||||
|
@ -1045,11 +1046,17 @@ static int evergreen_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
case 16:
|
||||
fb_format = (EVERGREEN_GRPH_DEPTH(EVERGREEN_GRPH_DEPTH_16BPP) |
|
||||
EVERGREEN_GRPH_FORMAT(EVERGREEN_GRPH_FORMAT_ARGB565));
|
||||
#ifdef __BIG_ENDIAN
|
||||
fb_swap = EVERGREEN_GRPH_ENDIAN_SWAP(EVERGREEN_GRPH_ENDIAN_8IN16);
|
||||
#endif
|
||||
break;
|
||||
case 24:
|
||||
case 32:
|
||||
fb_format = (EVERGREEN_GRPH_DEPTH(EVERGREEN_GRPH_DEPTH_32BPP) |
|
||||
EVERGREEN_GRPH_FORMAT(EVERGREEN_GRPH_FORMAT_ARGB8888));
|
||||
#ifdef __BIG_ENDIAN
|
||||
fb_swap = EVERGREEN_GRPH_ENDIAN_SWAP(EVERGREEN_GRPH_ENDIAN_8IN32);
|
||||
#endif
|
||||
break;
|
||||
default:
|
||||
DRM_ERROR("Unsupported screen depth %d\n",
|
||||
|
@ -1094,6 +1101,7 @@ static int evergreen_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
WREG32(EVERGREEN_GRPH_SECONDARY_SURFACE_ADDRESS + radeon_crtc->crtc_offset,
|
||||
(u32) fb_location & EVERGREEN_GRPH_SURFACE_ADDRESS_MASK);
|
||||
WREG32(EVERGREEN_GRPH_CONTROL + radeon_crtc->crtc_offset, fb_format);
|
||||
WREG32(EVERGREEN_GRPH_SWAP_CONTROL + radeon_crtc->crtc_offset, fb_swap);
|
||||
|
||||
WREG32(EVERGREEN_GRPH_SURFACE_OFFSET_X + radeon_crtc->crtc_offset, 0);
|
||||
WREG32(EVERGREEN_GRPH_SURFACE_OFFSET_Y + radeon_crtc->crtc_offset, 0);
|
||||
|
@ -1150,6 +1158,7 @@ static int avivo_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
struct drm_framebuffer *target_fb;
|
||||
uint64_t fb_location;
|
||||
uint32_t fb_format, fb_pitch_pixels, tiling_flags;
|
||||
u32 fb_swap = R600_D1GRPH_SWAP_ENDIAN_NONE;
|
||||
int r;
|
||||
|
||||
/* no fb bound */
|
||||
|
@ -1203,12 +1212,18 @@ static int avivo_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
fb_format =
|
||||
AVIVO_D1GRPH_CONTROL_DEPTH_16BPP |
|
||||
AVIVO_D1GRPH_CONTROL_16BPP_RGB565;
|
||||
#ifdef __BIG_ENDIAN
|
||||
fb_swap = R600_D1GRPH_SWAP_ENDIAN_16BIT;
|
||||
#endif
|
||||
break;
|
||||
case 24:
|
||||
case 32:
|
||||
fb_format =
|
||||
AVIVO_D1GRPH_CONTROL_DEPTH_32BPP |
|
||||
AVIVO_D1GRPH_CONTROL_32BPP_ARGB8888;
|
||||
#ifdef __BIG_ENDIAN
|
||||
fb_swap = R600_D1GRPH_SWAP_ENDIAN_32BIT;
|
||||
#endif
|
||||
break;
|
||||
default:
|
||||
DRM_ERROR("Unsupported screen depth %d\n",
|
||||
|
@ -1248,6 +1263,8 @@ static int avivo_crtc_do_set_base(struct drm_crtc *crtc,
|
|||
WREG32(AVIVO_D1GRPH_SECONDARY_SURFACE_ADDRESS +
|
||||
radeon_crtc->crtc_offset, (u32) fb_location);
|
||||
WREG32(AVIVO_D1GRPH_CONTROL + radeon_crtc->crtc_offset, fb_format);
|
||||
if (rdev->family >= CHIP_R600)
|
||||
WREG32(R600_D1GRPH_SWAP_CONTROL + radeon_crtc->crtc_offset, fb_swap);
|
||||
|
||||
WREG32(AVIVO_D1GRPH_SURFACE_OFFSET_X + radeon_crtc->crtc_offset, 0);
|
||||
WREG32(AVIVO_D1GRPH_SURFACE_OFFSET_Y + radeon_crtc->crtc_offset, 0);
|
||||
|
|
|
@ -81,7 +81,11 @@
|
|||
#define R600_MEDIUM_VID_LOWER_GPIO_CNTL 0x720
|
||||
#define R600_LOW_VID_LOWER_GPIO_CNTL 0x724
|
||||
|
||||
|
||||
#define R600_D1GRPH_SWAP_CONTROL 0x610C
|
||||
# define R600_D1GRPH_SWAP_ENDIAN_NONE (0 << 0)
|
||||
# define R600_D1GRPH_SWAP_ENDIAN_16BIT (1 << 0)
|
||||
# define R600_D1GRPH_SWAP_ENDIAN_32BIT (2 << 0)
|
||||
# define R600_D1GRPH_SWAP_ENDIAN_64BIT (3 << 0)
|
||||
|
||||
#define R600_HDP_NONSURFACE_BASE 0x2c04
|
||||
|
||||
|
|
Loading…
Reference in a new issue