Mesa (master): pan/mdg: Legalize inverts with constants

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Thu Jun 4 13:28:48 UTC 2020


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

Author: Alyssa Rosenzweig <alyssa.rosenzweig at collabora.com>
Date:   Tue Jun  2 12:15:18 2020 -0400

pan/mdg: Legalize inverts with constants

We need to force src_invert to be in the right place even if we flip
when lowering an embedded->inline constant.

Signed-off-by: Alyssa Rosenzweig <alyssa.rosenzweig at collabora.com>
Fixes: 449e5ded934 ("pan/mdg: Treat inot as a modifier")
Reported-by: Icecream95 <ixn at keemail.me>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/5299>

---

 src/panfrost/midgard/midgard_compile.c | 40 ++++++++++++++++++++++++++++------
 src/panfrost/midgard/mir.c             |  4 ++++
 2 files changed, 37 insertions(+), 7 deletions(-)

diff --git a/src/panfrost/midgard/midgard_compile.c b/src/panfrost/midgard/midgard_compile.c
index e9e6c15c678..98f948a9b88 100644
--- a/src/panfrost/midgard/midgard_compile.c
+++ b/src/panfrost/midgard/midgard_compile.c
@@ -1147,13 +1147,6 @@ emit_alu(compiler_context *ctx, nir_alu_instr *instr)
                 ins.is_pack = true;
         }
 
-        /* Arrange for creation of iandnot/iornot */
-        if (ins.src_invert[0] && !ins.src_invert[1]) {
-                mir_flip(&ins);
-                ins.src_invert[0] = false;
-                ins.src_invert[1] = true;
-        }
-
         if ((opcode_props & UNITS_ALL) == UNIT_VLUT) {
                 /* To avoid duplicating the lookup tables (probably), true LUT
                  * instructions can only operate as if they were scalars. Lower
@@ -2307,6 +2300,38 @@ midgard_cull_dead_branch(compiler_context *ctx, midgard_block *block)
         }
 }
 
+/* We want to force the invert on AND/OR to the second slot to legalize into
+ * iandnot/iornot. The relevant patterns are for AND (and OR respectively)
+ *
+ *   ~a & #b = ~a & ~(#~b)
+ *   ~a & b = b & ~a
+ */
+
+static void
+midgard_legalize_invert(compiler_context *ctx, midgard_block *block)
+{
+        mir_foreach_instr_in_block(block, ins) {
+                if (ins->type != TAG_ALU_4) continue;
+
+                if (ins->alu.op != midgard_alu_op_iand &&
+                    ins->alu.op != midgard_alu_op_ior) continue;
+
+                if (ins->src_invert[1] || !ins->src_invert[0]) continue;
+
+                if (ins->has_inline_constant) {
+                        /* ~(#~a) = ~(~#a) = a, so valid, and forces both
+                         * inverts on */
+                        ins->inline_constant = ~ins->inline_constant;
+                        ins->src_invert[1] = true;
+                } else {
+                        /* Flip to the right invert order. Note
+                         * has_inline_constant false by assumption on the
+                         * branch, so flipping makes sense. */
+                        mir_flip(ins);
+                }
+        }
+}
+
 static unsigned
 emit_fragment_epilogue(compiler_context *ctx, unsigned rt)
 {
@@ -2665,6 +2690,7 @@ midgard_compile_shader_nir(nir_shader *nir, panfrost_program *program, bool is_b
         mir_foreach_block(ctx, _block) {
                 midgard_block *block = (midgard_block *) _block;
                 midgard_lower_derivatives(ctx, block);
+                midgard_legalize_invert(ctx, block);
                 midgard_cull_dead_branch(ctx, block);
         }
 
diff --git a/src/panfrost/midgard/mir.c b/src/panfrost/midgard/mir.c
index 0bb87c8fe00..771d600e945 100644
--- a/src/panfrost/midgard/mir.c
+++ b/src/panfrost/midgard/mir.c
@@ -445,6 +445,10 @@ mir_flip(midgard_instruction *ins)
         ins->src_neg[0] = ins->src_neg[1];
         ins->src_neg[1] = temp;
 
+        temp = ins->src_invert[0];
+        ins->src_invert[0] = ins->src_invert[1];
+        ins->src_invert[1] = temp;
+
         unsigned temp_swizzle[16];
         memcpy(temp_swizzle, ins->swizzle[0], sizeof(ins->swizzle[0]));
         memcpy(ins->swizzle[0], ins->swizzle[1], sizeof(ins->swizzle[0]));



More information about the mesa-commit mailing list