Mesa (master): nir/copy_prop_vars: handle indirect vector elements

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Fri Mar 1 07:59:03 UTC 2019


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

Author: Caio Marcelo de Oliveira Filho <caio.oliveira at intel.com>
Date:   Mon Feb 25 20:37:59 2019 -0800

nir/copy_prop_vars: handle indirect vector elements

Differently than the direct case, the indirect array derefs of vector
are handled like regular derefs, with the exception that we ignore any
vector entry that has SSA values when performing a load.  Such SSA
values don't help loading of the indirect unless we emit an if-ladder.

Copy_derefs are supported for indirects.

Also enable two tests that now pass.

v2: Remove unnecessary temporaries.  Be clearer when identifying the
    case where copy_entry doesn't help when we are dealing with an
    indirect array_deref (of a vector).  (Jason)

Reviewed-by: Jason Ekstrand <jason at jlekstrand.net>

---

 src/compiler/nir/nir_opt_copy_prop_vars.c | 45 ++++++++++++++++---------------
 src/compiler/nir/tests/vars_tests.cpp     |  4 +--
 2 files changed, 25 insertions(+), 24 deletions(-)

diff --git a/src/compiler/nir/nir_opt_copy_prop_vars.c b/src/compiler/nir/nir_opt_copy_prop_vars.c
index 7fc84083ea6..19003ccbd86 100644
--- a/src/compiler/nir/nir_opt_copy_prop_vars.c
+++ b/src/compiler/nir/nir_opt_copy_prop_vars.c
@@ -475,11 +475,17 @@ load_from_ssa_entry_value(struct copy_prop_var_state *state,
                           nir_deref_instr *src, struct value *value)
 {
    if (is_array_deref_of_vector(src)) {
-      if (!nir_src_is_const(src->arr.index))
-         return false;
+      if (nir_src_is_const(src->arr.index)) {
+         return load_element_from_ssa_entry_value(state, entry, b, intrin, value,
+                                                  nir_src_as_uint(src->arr.index));
+      }
 
-      return load_element_from_ssa_entry_value(state, entry, b, intrin, value,
-                                               nir_src_as_uint(src->arr.index));
+      /* An SSA copy_entry for the vector won't help indirect load. */
+      if (glsl_type_is_vector(entry->dst->type)) {
+         assert(entry->dst->type == nir_deref_instr_parent(src)->type);
+         /* TODO: If all SSA entries are there, try an if-ladder. */
+         return false;
+      }
    }
 
    *value = entry->src;
@@ -808,16 +814,14 @@ copy_prop_vars_block(struct copy_prop_var_state *state,
 
          nir_deref_instr *src = nir_src_as_deref(intrin->src[0]);
 
+         /* Direct array_derefs of vectors operate on the vectors (the parent
+          * deref).  Indirects will be handled like other derefs.
+          */
          int vec_index = 0;
          nir_deref_instr *vec_src = src;
-         if (is_array_deref_of_vector(src)) {
+         if (is_array_deref_of_vector(src) && nir_src_is_const(src->arr.index)) {
             vec_src = nir_deref_instr_parent(src);
             unsigned vec_comps = glsl_get_vector_elements(vec_src->type);
-
-            /* Indirects are not handled yet.  */
-            if (!nir_src_is_const(src->arr.index))
-               break;
-
             vec_index = nir_src_as_uint(src->arr.index);
 
             /* Loading from an invalid index yields an undef */
@@ -891,18 +895,15 @@ copy_prop_vars_block(struct copy_prop_var_state *state,
          nir_deref_instr *dst = nir_src_as_deref(intrin->src[0]);
          assert(glsl_type_is_vector_or_scalar(dst->type));
 
+         /* Direct array_derefs of vectors operate on the vectors (the parent
+          * deref).  Indirects will be handled like other derefs.
+          */
          int vec_index = 0;
          nir_deref_instr *vec_dst = dst;
-         if (is_array_deref_of_vector(dst)) {
+         if (is_array_deref_of_vector(dst) && nir_src_is_const(dst->arr.index)) {
             vec_dst = nir_deref_instr_parent(dst);
             unsigned vec_comps = glsl_get_vector_elements(vec_dst->type);
 
-            /* Indirects are not handled yet.  Kill everything */
-            if (!nir_src_is_const(dst->arr.index)) {
-               kill_aliases(copies, vec_dst, (1 << vec_comps) - 1);
-               break;
-            }
-
             vec_index = nir_src_as_uint(dst->arr.index);
 
             /* Storing to an invalid index is a no-op. */
@@ -950,11 +951,11 @@ copy_prop_vars_block(struct copy_prop_var_state *state,
          unsigned num_components = glsl_get_vector_elements(dst->type);
          unsigned full_mask = (1 << num_components) - 1;
 
-         if (is_array_deref_of_vector(src) || is_array_deref_of_vector(dst)) {
-            /* Cases not handled yet.  Writing into an element of 'dst'
-             * invalidates any related entries in copies.  Reading from 'src'
-             * doesn't invalidate anything, so no action needed for it.
-             */
+         /* Copy of direct array derefs of vectors are not handled.  Just
+          * invalidate what's written and bail.
+          */
+         if ((is_array_deref_of_vector(src) && nir_src_is_const(src->arr.index)) ||
+             (is_array_deref_of_vector(dst) && nir_src_is_const(dst->arr.index))) {
             kill_aliases(copies, dst, full_mask);
             break;
          }
diff --git a/src/compiler/nir/tests/vars_tests.cpp b/src/compiler/nir/tests/vars_tests.cpp
index 492624a2d0e..893ce297a43 100644
--- a/src/compiler/nir/tests/vars_tests.cpp
+++ b/src/compiler/nir/tests/vars_tests.cpp
@@ -603,7 +603,7 @@ TEST_F(nir_copy_prop_vars_test, store_load_direct_array_deref_on_vector)
    EXPECT_TRUE(nir_src_as_alu_instr(&fourth_store->src[1]));
 }
 
-TEST_F(nir_copy_prop_vars_test, DISABLED_store_load_indirect_array_deref_on_vector)
+TEST_F(nir_copy_prop_vars_test, store_load_indirect_array_deref_on_vector)
 {
    nir_variable *vec = create_ivec2(nir_var_mem_ssbo, "vec");
    nir_variable *idx = create_int(nir_var_mem_ssbo, "idx");
@@ -640,7 +640,7 @@ TEST_F(nir_copy_prop_vars_test, DISABLED_store_load_indirect_array_deref_on_vect
    EXPECT_EQ(first->src[1].ssa, second->src[1].ssa);
 }
 
-TEST_F(nir_copy_prop_vars_test, DISABLED_store_load_direct_and_indirect_array_deref_on_vector)
+TEST_F(nir_copy_prop_vars_test, store_load_direct_and_indirect_array_deref_on_vector)
 {
    nir_variable *vec = create_ivec2(nir_var_mem_ssbo, "vec");
    nir_variable *idx = create_int(nir_var_mem_ssbo, "idx");




More information about the mesa-commit mailing list