[v3,1/2] nir: Add is_non_scalar_swizzle search helper

Submitted by Alyssa Rosenzweig on May 10, 2019, 5:59 p.m.


Message ID 20190510175915.3786-1-alyssa@rosenzweig.io
State New
Headers show
Series "Series without cover letter" ( rev: 1 ) in Mesa

Not browsing as part of any series.

Commit Message

Alyssa Rosenzweig May 10, 2019, 5:59 p.m.
This allows algebraic optimizations to check if the argument accesses
multiple distinct components of a vector. So a swizzle like "xyz" will
return true, but "yyy" will return false, as will a scalar. This can be
useful for optimizations on vector processors, where a scalar
swizzle can be handled in one clock (replicated a scalar channel) but a
non-scalar swizzle requires multiple scalarized operations. In these
cases, it is useful to optimize differently based on whether the swizzle
is non-scalar.

For my use case, csel on Midgard requires a scalar condition, so this
allows csel to be lowered only with a vector condition.

Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
Cc: Jason Ekstrand <jason@jlekstrand.net>
Cc: Ilia Mirkin <imirkin@alum.mit.edu>
 src/compiler/nir/nir_search_helpers.h | 17 +++++++++++++++++
 1 file changed, 17 insertions(+)

Patch hide | download patch | download mbox

diff --git a/src/compiler/nir/nir_search_helpers.h b/src/compiler/nir/nir_search_helpers.h
index 1624508993d..8e26739a3ce 100644
--- a/src/compiler/nir/nir_search_helpers.h
+++ b/src/compiler/nir/nir_search_helpers.h
@@ -143,6 +143,23 @@  is_not_const(nir_alu_instr *instr, unsigned src, UNUSED unsigned num_components,
    return !nir_src_is_const(instr->src[src].src);
+/* I.e. the vector's swizzle actually accesses multiple channels. True for
+ * xyzw, false for wwww, false for w */
+static inline bool
+is_non_scalar_swizzle(nir_alu_instr *instr, UNUSED unsigned src, 
+             unsigned num_components, const uint8_t *swizzle)
+   unsigned first_component = swizzle[0];
+   for (unsigned i = 1; i < num_components; ++i) {
+      if (swizzle[i] != first_component)
+         return true;
+   }
+   return false;
 static inline bool
 is_used_more_than_once(nir_alu_instr *instr)