[Mesa-dev] [PATCH 18/18] panfrost/midgard: Decode texture offset register swizzle

Alyssa Rosenzweig alyssa.rosenzweig at collabora.com
Mon Jun 10 22:01:46 UTC 2019


Signed-off-by: Alyssa Rosenzweig <alyssa.rosenzweig at collabora.com>
---
 .../drivers/panfrost/midgard/disassemble.c    | 21 ++++++++++++++-----
 .../drivers/panfrost/midgard/midgard.h        | 13 ++++++------
 2 files changed, 23 insertions(+), 11 deletions(-)

diff --git a/src/gallium/drivers/panfrost/midgard/disassemble.c b/src/gallium/drivers/panfrost/midgard/disassemble.c
index 743a3d4fe90..4eb490ff681 100644
--- a/src/gallium/drivers/panfrost/midgard/disassemble.c
+++ b/src/gallium/drivers/panfrost/midgard/disassemble.c
@@ -36,6 +36,7 @@
 #include "disassemble.h"
 #include "helpers.h"
 #include "util/half_float.h"
+#include "util/u_math.h"
 
 #define DEFINE_CASE(define, str) case define: { printf(str); break; }
 
@@ -1139,12 +1140,22 @@ print_texture_word(uint32_t *word, unsigned tabs)
                 printf(" + ");
                 print_texture_reg_triple(texture->offset_x);
 
-                /* I've never seen them different than this */
-                if (texture->offset_y != 2)
-                        printf(" /* y = %d */", texture->offset_y);
+                /* The less questions you ask, the better. */
 
-                if (texture->offset_z != 1)
-                        printf(" /* z = %d */", texture->offset_z);
+                unsigned swizzle_lo, swizzle_hi;
+                unsigned orig_y = texture->offset_y;
+                unsigned orig_z = texture->offset_z;
+
+                memcpy(&swizzle_lo, &orig_y, sizeof(unsigned));
+                memcpy(&swizzle_hi, &orig_z, sizeof(unsigned));
+
+                /* Duplicate hi swizzle over */
+                assert(swizzle_hi < 4);
+                swizzle_hi = (swizzle_hi << 2) | swizzle_hi;
+
+                unsigned swiz = (swizzle_lo << 4) | swizzle_hi;
+                unsigned reversed = util_bitreverse(swiz) >> 24;
+                print_swizzle_vec4(reversed, false, false);
 
                 printf(", ");
         } else if (texture->offset_x || texture->offset_y || texture->offset_z) {
diff --git a/src/gallium/drivers/panfrost/midgard/midgard.h b/src/gallium/drivers/panfrost/midgard/midgard.h
index fa3e38e0879..532734820e9 100644
--- a/src/gallium/drivers/panfrost/midgard/midgard.h
+++ b/src/gallium/drivers/panfrost/midgard/midgard.h
@@ -558,14 +558,15 @@ __attribute__((__packed__))
 
         unsigned unknownA  : 4;
 
-        /* Each offset field is either an immediate (range 0-7) or, in the case of X, a
-         * register full / select / upper triplet to select the offset vector
-         * register in register mode. In register mode, Y=2 and Z=1 for some
-         * reason. The range in register mode is [-8, 7].
+        /* In immediate mode, each offset field is an immediate range [0, 7].
          *
-         * In immediate mode, for texel fethces the range is the full [-8, 7],
+         * In register mode, offset_x becomes a register full / select / upper
+         * triplet and a vec3 swizzle is splattered across offset_y/offset_z in
+         * a genuinely bizarre way.
+         *
+         * For texel fetches in immediate mode, the range is the full [-8, 7],
          * but for normal texturing the top bit must be zero and a register
-         * used instead. It's not clear where this limitated is from. */
+         * used instead. It's not clear where this limitation is from. */
 
         signed offset_x : 4;
         signed offset_y : 4;
-- 
2.20.1



More information about the mesa-dev mailing list