[PATCH 2/2] Make alignment functions match the documentation
Simon Farnsworth
simon.farnsworth at onelan.co.uk
Tue Dec 13 07:21:26 PST 2011
Alex Deucher gave me documentation for tiling alignment requirements; this
brings the DDX into line with the documentation for Evergreen and R600.
Signed-off-by: Simon Farnsworth <simon.farnsworth at onelan.co.uk>
---
This doesn't fix my problems with enabling macro tiling, but it does help
somewhat. I also need to fix tile shape in the kernel and alignment in Mesa
to avoid misrendering, at which point I see CP lockups instead.
I'm therefore sending this, the kernel patch, and the Mesa patch out in
order to avoid getting stuck in a world where I have an 80% fix, someone
else has an 80% fix, and if only we talked, we'd have a 100% fix.
src/drmmode_display.c | 61 ++++++++++++++++++++++++++++++++++++++----------
1 files changed, 48 insertions(+), 13 deletions(-)
diff --git a/src/drmmode_display.c b/src/drmmode_display.c
index fcea59e..cb220fb 100644
--- a/src/drmmode_display.c
+++ b/src/drmmode_display.c
@@ -1099,13 +1099,21 @@ int drmmode_get_height_align(ScrnInfoPtr scrn, uint32_t tiling)
RADEONInfoPtr info = RADEONPTR(scrn);
int height_align = 1;
- if (info->ChipFamily >= CHIP_FAMILY_R600) {
+ if (info->ChipFamily >= CHIP_FAMILY_CEDAR) {
+ /* Kernel uses bank height of 8, macro_tile_aspect of 1 */
if (tiling & RADEON_TILING_MACRO)
- height_align = info->num_channels * 8;
+ height_align = info->num_banks * 8 / 1 * 8;
else if (tiling & RADEON_TILING_MICRO)
height_align = 8;
else
+ height_align = 1;
+ } else if (info->ChipFamily >= CHIP_FAMILY_R600) {
+ if (tiling & RADEON_TILING_MACRO)
+ height_align = info->num_channels * 8;
+ else if (tiling & RADEON_TILING_MICRO)
height_align = 8;
+ else
+ height_align = 1;
} else {
if (tiling)
height_align = 16;
@@ -1121,18 +1129,30 @@ int drmmode_get_pitch_align(ScrnInfoPtr scrn, int bpe, uint32_t tiling)
RADEONInfoPtr info = RADEONPTR(scrn);
int pitch_align = 1;
- if (info->ChipFamily >= CHIP_FAMILY_R600) {
+ if (info->ChipFamily >= CHIP_FAMILY_CEDAR) {
+ /* Kernel uses bank_width of 8, macro_tile_aspect of 1 */
+ if (tiling & RADEON_TILING_MACRO)
+ pitch_align = info->num_channels * 8 * 1 * 8;
+ else if (tiling & RADEON_TILING_MICRO)
+ pitch_align = MAX(8, info->group_bytes / (8 * bpe));
+ else {
+ if (info->have_tiling_info)
+ /* linear aligned requirements */
+ pitch_align = MAX(64, info->group_bytes / bpe);
+ else
+ /* default to 512 elements if we don't know the real
+ * group size otherwise the kernel may reject the CS
+ * if the group sizes don't match as the pitch won't
+ * be aligned properly.
+ */
+ pitch_align = 512;
+ }
+ } else if (info->ChipFamily >= CHIP_FAMILY_R600) {
if (tiling & RADEON_TILING_MACRO) {
- /* general surface requirements */
- pitch_align = MAX(info->num_banks,
- (((info->group_bytes / 8) / bpe) * info->num_banks)) * 8;
- /* further restrictions for scanout */
- pitch_align = MAX(info->num_banks * 8, pitch_align);
+ pitch_align = MAX(info->num_banks * 8,
+ ((info->group_bytes / 8) / bpe) * info->num_banks);
} else if (tiling & RADEON_TILING_MICRO) {
- /* general surface requirements */
- pitch_align = MAX(8, (info->group_bytes / (8 * bpe)));
- /* further restrictions for scanout */
- pitch_align = MAX(info->group_bytes / bpe, pitch_align);
+ pitch_align = MAX(8, info->group_bytes / (8 * bpe));
} else {
if (info->have_tiling_info)
/* linear aligned requirements */
@@ -1163,7 +1183,22 @@ int drmmode_get_base_align(ScrnInfoPtr scrn, int bpe, uint32_t tiling)
int height_align = drmmode_get_height_align(scrn, tiling);
int base_align = RADEON_GPU_PAGE_SIZE;
- if (info->ChipFamily >= CHIP_FAMILY_R600) {
+ if (info->ChipFamily >= CHIP_FAMILY_CEDAR) {
+ /* Kernel always uses bank_width and bank_height of 8.
+ Tile split size is between 1024 and 4096 - as it's used in a
+ MIN expression, 4096 is safe */
+ if (tiling & RADEON_TILING_MACRO)
+ base_align = info->num_channels * info->num_banks * 8 * 8 * MIN(4096, 8 * 8 * bpe);
+ else if (info->have_tiling_info)
+ base_align = info->group_bytes;
+ else
+ /* default to 512 if we don't know the real
+ * group size otherwise the kernel may reject the CS
+ * if the group sizes don't match as the base won't
+ * be aligned properly.
+ */
+ base_align = 512;
+ } else if (info->ChipFamily >= CHIP_FAMILY_R600) {
if (tiling & RADEON_TILING_MACRO)
base_align = MAX(info->num_banks * info->num_channels * 8 * 8 * bpe,
pixel_align * bpe * height_align);
--
1.7.6.4
More information about the xorg-driver-ati
mailing list