[Mesa-dev] [PATCH] nir: Copy-propagate vecN operations that are actually moves

Jason Ekstrand jason at jlekstrand.net
Thu Feb 19 22:03:15 PST 2015


We were already do this for ALU operations but we haven't for non-ALU
operations.  This changes that.

total NIR instructions in shared programs: 2039883 -> 2022338 (-0.86%)
NIR instructions in affected programs:     1768850 -> 1751305 (-0.99%)
helped:                                    14244
HURT:                                      124

total FS instructions in shared programs: 4083960 -> 4084036 (0.00%)
FS instructions in affected programs:     7302 -> 7378 (1.04%)
helped:                                   12
HURT:                                     51

Signed-off-by: Jason Ekstrand <jason.ekstrand at intel.com>
---
 src/glsl/nir/nir_opt_copy_propagate.c | 45 ++++++++++++++++++++++-------------
 1 file changed, 29 insertions(+), 16 deletions(-)

diff --git a/src/glsl/nir/nir_opt_copy_propagate.c b/src/glsl/nir/nir_opt_copy_propagate.c
index dd0ec01..ee78e5a 100644
--- a/src/glsl/nir/nir_opt_copy_propagate.c
+++ b/src/glsl/nir/nir_opt_copy_propagate.c
@@ -53,22 +53,6 @@ static bool is_move(nir_alu_instr *instr)
 
 }
 
-static bool
-is_swizzleless_move(nir_alu_instr *instr)
-{
-   if (!is_move(instr))
-      return false;
-
-   for (unsigned i = 0; i < 4; i++) {
-      if (!((instr->dest.write_mask >> i) & 1))
-         break;
-      if (instr->src[0].swizzle[i] != i)
-         return false;
-   }
-
-   return true;
-}
-
 static bool is_vec(nir_alu_instr *instr)
 {
    for (unsigned i = 0; i < nir_op_infos[instr->op].num_inputs; i++)
@@ -80,6 +64,35 @@ static bool is_vec(nir_alu_instr *instr)
           instr->op == nir_op_vec4;
 }
 
+static bool
+is_swizzleless_move(nir_alu_instr *instr)
+{
+   if (is_move(instr)) {
+      for (unsigned i = 0; i < 4; i++) {
+         if (!((instr->dest.write_mask >> i) & 1))
+            break;
+         if (instr->src[0].swizzle[i] != i)
+            return false;
+      }
+      return true;
+   } else if (is_vec(instr)) {
+      nir_ssa_def *def = NULL;
+      for (unsigned i = 0; i < nir_op_infos[instr->op].num_inputs; i++) {
+         if (instr->src[i].swizzle[0] != i)
+            return false;
+
+         if (def == NULL) {
+            def = instr->src[i].src.ssa;
+         } else if (instr->src[i].src.ssa != def) {
+            return false;
+         }
+      }
+      return true;
+   } else {
+      return false;
+   }
+}
+
 typedef struct {
    nir_ssa_def *def;
    bool found;
-- 
2.3.0



More information about the mesa-dev mailing list