Mesa (master): freedreno/a6xx: refactor fd6_tex_swiz()

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Thu Mar 7 20:36:01 UTC 2019


Module: Mesa
Branch: master
Commit: f5d80ff2db36736636aede2040c716d7fb437286
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=f5d80ff2db36736636aede2040c716d7fb437286

Author: Rob Clark <robdclark at gmail.com>
Date:   Wed Mar  6 10:04:21 2019 -0500

freedreno/a6xx: refactor fd6_tex_swiz()

We need a version of fd6_tex_swiz() that just returns the composed
swizzle without building part of the TEX_CONST_0 state.  So just
refactor the existing function to build more of the TEX_CONST_0 state,
and leave fd6_tex_swiz() simply composing swizzles.

The small IBO state change (to use LINEAR for smaller sizes/levels) is
to match the state in fd6_tex_const_0().  It seems like maybe tiled
actually works at the smaller sizes but not if minification is in play,
so best just to make images match what we do for textures.

Signed-off-by: Rob Clark <robdclark at gmail.com>
Reviewed-by: Kristian H. Kristensen <hoegsberg at chromium.org>

---

 src/gallium/drivers/freedreno/a6xx/fd6_format.c  | 44 +++++++++++++++++++-----
 src/gallium/drivers/freedreno/a6xx/fd6_format.h  | 11 ++++--
 src/gallium/drivers/freedreno/a6xx/fd6_image.c   | 19 ++++++----
 src/gallium/drivers/freedreno/a6xx/fd6_texture.c | 21 +++--------
 4 files changed, 61 insertions(+), 34 deletions(-)

diff --git a/src/gallium/drivers/freedreno/a6xx/fd6_format.c b/src/gallium/drivers/freedreno/a6xx/fd6_format.c
index 2016d31501e..5ba641d50a5 100644
--- a/src/gallium/drivers/freedreno/a6xx/fd6_format.c
+++ b/src/gallium/drivers/freedreno/a6xx/fd6_format.c
@@ -434,16 +434,13 @@ fd6_pipe2swiz(unsigned swiz)
 	}
 }
 
-uint32_t
-fd6_tex_swiz(struct pipe_resource *prsc, enum pipe_format format,
+void
+fd6_tex_swiz(enum pipe_format format, unsigned char *swiz,
 			 unsigned swizzle_r, unsigned swizzle_g,
 			 unsigned swizzle_b, unsigned swizzle_a)
 {
 	const struct util_format_description *desc =
 			util_format_description(format);
-
-	uint32_t swap = fd6_pipe2swap(format);
-	unsigned char swiz[4];
 	const unsigned char uswiz[4] = {
 		swizzle_r, swizzle_g, swizzle_b, swizzle_a
 	};
@@ -456,25 +453,54 @@ fd6_tex_swiz(struct pipe_resource *prsc, enum pipe_format format,
 			PIPE_SWIZZLE_X, PIPE_SWIZZLE_X, PIPE_SWIZZLE_X, PIPE_SWIZZLE_X
 		};
 		util_format_compose_swizzles(stencil_swiz, uswiz, swiz);
-	} else if (swap != WZYX) {
+	} else if (fd6_pipe2swap(format) != WZYX) {
 		/* Formats with a non-pass-through swap are permutations of RGBA
 		 * formats. We program the permutation using the swap and don't
 		 * need to compose the format swizzle with the user swizzle.
 		 */
-		memcpy(swiz, uswiz, sizeof(swiz));
+		memcpy(swiz, uswiz, sizeof(uswiz));
 	} else {
 		/* Otherwise, it's an unswapped RGBA format or a format like L8 where
 		 * we need the XXX1 swizzle from the gallium format description.
 		 */
 		util_format_compose_swizzles(desc->swizzle, uswiz, swiz);
 	}
+}
+
+/* Compute the TEX_CONST_0 value for texture state, including SWIZ/SWAP/etc: */
+uint32_t
+fd6_tex_const_0(struct pipe_resource *prsc,
+			 unsigned level, enum pipe_format format,
+			 unsigned swizzle_r, unsigned swizzle_g,
+			 unsigned swizzle_b, unsigned swizzle_a)
+{
+	struct fd_resource *rsc = fd_resource(prsc);
+	uint32_t swap, texconst0 = 0;
+	unsigned char swiz[4];
+
+	if (util_format_is_srgb(format)) {
+		texconst0 |= A6XX_TEX_CONST_0_SRGB;
+	}
 
-	swap = fd_resource(prsc)->tile_mode ? WZYX : fd6_pipe2swap(format);
+	if (rsc->tile_mode && !fd_resource_level_linear(prsc, level)) {
+		texconst0 |= A6XX_TEX_CONST_0_TILE_MODE(rsc->tile_mode);
+		swap = WZYX;
+	} else {
+		swap = fd6_pipe2swap(format);
+	}
 
-	return
+	fd6_tex_swiz(format, swiz,
+			swizzle_r, swizzle_g,
+			swizzle_b, swizzle_a);
+
+	texconst0 |=
+		A6XX_TEX_CONST_0_FMT(fd6_pipe2tex(format)) |
+		A6XX_TEX_CONST_0_SAMPLES(fd_msaa_samples(prsc->nr_samples)) |
 		A6XX_TEX_CONST_0_SWAP(swap) |
 		A6XX_TEX_CONST_0_SWIZ_X(fd6_pipe2swiz(swiz[0])) |
 		A6XX_TEX_CONST_0_SWIZ_Y(fd6_pipe2swiz(swiz[1])) |
 		A6XX_TEX_CONST_0_SWIZ_Z(fd6_pipe2swiz(swiz[2])) |
 		A6XX_TEX_CONST_0_SWIZ_W(fd6_pipe2swiz(swiz[3]));
+
+	return texconst0;
 }
diff --git a/src/gallium/drivers/freedreno/a6xx/fd6_format.h b/src/gallium/drivers/freedreno/a6xx/fd6_format.h
index a1ed03d60f4..2c4f5865527 100644
--- a/src/gallium/drivers/freedreno/a6xx/fd6_format.h
+++ b/src/gallium/drivers/freedreno/a6xx/fd6_format.h
@@ -41,9 +41,14 @@ enum a6xx_tex_fetchsize fd6_pipe2fetchsize(enum pipe_format format);
 enum a6xx_depth_format fd6_pipe2depth(enum pipe_format format);
 enum a6xx_tex_swiz fd6_pipe2swiz(unsigned swiz);
 
-uint32_t fd6_tex_swiz(struct pipe_resource *prsc, enum pipe_format format,
-					  unsigned swizzle_r,
-					  unsigned swizzle_g, unsigned swizzle_b, unsigned swizzle_a);
+void fd6_tex_swiz(enum pipe_format format, unsigned char *swiz,
+			 unsigned swizzle_r, unsigned swizzle_g,
+			 unsigned swizzle_b, unsigned swizzle_a);
+
+uint32_t fd6_tex_const_0(struct pipe_resource *prsc,
+					  unsigned level, enum pipe_format format,
+					  unsigned swizzle_r, unsigned swizzle_g,
+					  unsigned swizzle_b, unsigned swizzle_a);
 
 static inline enum a6xx_2d_ifmt
 fd6_ifmt(enum a6xx_color_fmt fmt)
diff --git a/src/gallium/drivers/freedreno/a6xx/fd6_image.c b/src/gallium/drivers/freedreno/a6xx/fd6_image.c
index 5683612c51c..9c1182777c0 100644
--- a/src/gallium/drivers/freedreno/a6xx/fd6_image.c
+++ b/src/gallium/drivers/freedreno/a6xx/fd6_image.c
@@ -40,6 +40,7 @@ struct fd6_image {
 	enum a6xx_tex_type type;
 	bool srgb;
 	uint32_t cpp;
+	uint32_t level;
 	uint32_t width;
 	uint32_t height;
 	uint32_t depth;
@@ -120,6 +121,7 @@ static void translate_image(struct fd6_image *img, const struct pipe_image_view
 			break;
 		}
 
+		img->level  = lvl;
 		img->width  = u_minify(prsc->width0, lvl);
 		img->height = u_minify(prsc->height0, lvl);
 	}
@@ -161,11 +163,9 @@ static void translate_buf(struct fd6_image *img, const struct pipe_shader_buffer
 
 static void emit_image_tex(struct fd_ringbuffer *ring, struct fd6_image *img)
 {
-	OUT_RING(ring, A6XX_TEX_CONST_0_FMT(img->fmt) |
-		A6XX_TEX_CONST_0_TILE_MODE(fd_resource(img->prsc)->tile_mode) |
-		fd6_tex_swiz(img->prsc, img->pfmt, PIPE_SWIZZLE_X, PIPE_SWIZZLE_Y,
-			PIPE_SWIZZLE_Z, PIPE_SWIZZLE_W) |
-		COND(img->srgb, A6XX_TEX_CONST_0_SRGB));
+	OUT_RING(ring, fd6_tex_const_0(img->prsc, img->level, img->pfmt,
+			PIPE_SWIZZLE_X, PIPE_SWIZZLE_Y,
+			PIPE_SWIZZLE_Z, PIPE_SWIZZLE_W));
 	OUT_RING(ring, A6XX_TEX_CONST_1_WIDTH(img->width) |
 		A6XX_TEX_CONST_1_HEIGHT(img->height));
 	OUT_RING(ring, A6XX_TEX_CONST_2_FETCHSIZE(img->fetchsize) |
@@ -210,8 +210,15 @@ fd6_emit_ssbo_tex(struct fd_ringbuffer *ring, const struct pipe_shader_buffer *p
 
 static void emit_image_ssbo(struct fd_ringbuffer *ring, struct fd6_image *img)
 {
+	struct fd_resource *rsc = fd_resource(img->prsc);
+	enum a6xx_tile_mode tile_mode = TILE6_LINEAR;
+
+	if (rsc->tile_mode && !fd_resource_level_linear(img->prsc, img->level)) {
+		tile_mode = rsc->tile_mode;
+	}
+
 	OUT_RING(ring, A6XX_IBO_0_FMT(img->fmt) |
-		A6XX_IBO_0_TILE_MODE(fd_resource(img->prsc)->tile_mode));
+		A6XX_IBO_0_TILE_MODE(tile_mode));
 	OUT_RING(ring, A6XX_IBO_1_WIDTH(img->width) |
 		A6XX_IBO_1_HEIGHT(img->height));
 	OUT_RING(ring, A6XX_IBO_2_PITCH(img->pitch) |
diff --git a/src/gallium/drivers/freedreno/a6xx/fd6_texture.c b/src/gallium/drivers/freedreno/a6xx/fd6_texture.c
index f2f7276aaa8..f5f747cd14c 100644
--- a/src/gallium/drivers/freedreno/a6xx/fd6_texture.c
+++ b/src/gallium/drivers/freedreno/a6xx/fd6_texture.c
@@ -237,16 +237,6 @@ fd6_sampler_view_create(struct pipe_context *pctx, struct pipe_resource *prsc,
 	so->base.context = pctx;
 	so->seqno = ++fd6_context(fd_context(pctx))->tex_seqno;
 
-	so->texconst0 =
-		A6XX_TEX_CONST_0_FMT(fd6_pipe2tex(format)) |
-		A6XX_TEX_CONST_0_SAMPLES(fd_msaa_samples(prsc->nr_samples)) |
-		fd6_tex_swiz(prsc, cso->format, cso->swizzle_r, cso->swizzle_g,
-				cso->swizzle_b, cso->swizzle_a);
-
-	if (util_format_is_srgb(format)) {
-		so->texconst0 |= A6XX_TEX_CONST_0_SRGB;
-	}
-
 	if (cso->target == PIPE_BUFFER) {
 		unsigned elements = cso->u.buf.size / util_format_get_blocksize(format);
 
@@ -260,17 +250,12 @@ fd6_sampler_view_create(struct pipe_context *pctx, struct pipe_resource *prsc,
 		so->offset = cso->u.buf.offset;
 	} else {
 		unsigned miplevels;
-		enum a6xx_tile_mode tile_mode = TILE6_LINEAR;
 
 		lvl = fd_sampler_first_level(cso);
 		miplevels = fd_sampler_last_level(cso) - lvl;
 		layers = cso->u.tex.last_layer - cso->u.tex.first_layer + 1;
 
-		if (!fd_resource_level_linear(prsc, lvl))
-			tile_mode = fd_resource(prsc)->tile_mode;
-
-		so->texconst0 |= A6XX_TEX_CONST_0_MIPLVLS(miplevels) |
-			A6XX_TEX_CONST_0_TILE_MODE(tile_mode);
+		so->texconst0 |= A6XX_TEX_CONST_0_MIPLVLS(miplevels);
 		so->texconst1 =
 			A6XX_TEX_CONST_1_WIDTH(u_minify(prsc->width0, lvl)) |
 			A6XX_TEX_CONST_1_HEIGHT(u_minify(prsc->height0, lvl));
@@ -284,6 +269,10 @@ fd6_sampler_view_create(struct pipe_context *pctx, struct pipe_resource *prsc,
 		so->ubwc_enabled = rsc->ubwc_size && u_minify(prsc->width0, lvl) >= 16;
 	}
 
+	so->texconst0 |= fd6_tex_const_0(prsc, lvl, cso->format,
+				cso->swizzle_r, cso->swizzle_g,
+				cso->swizzle_b, cso->swizzle_a);
+
 	if (so->ubwc_enabled) {
 		so->texconst9 |= A6XX_TEX_CONST_9_FLAG_BUFFER_PITCH(rsc->ubwc_size);
 		so->texconst10 |= A6XX_TEX_CONST_10_FLAG_BUFFER_ARRAY_PITCH(rsc->ubwc_pitch);




More information about the mesa-commit mailing list