[Mesa-dev] [PATCH] nir: switch fmul to increase chance of optimising it away
Timothy Arceri
timothy.arceri at collabora.com
Thu Jan 12 04:20:55 UTC 2017
If one of the inputs to the multiplcation in ffma is the result of
an fmul there is a chance that we can reuse the result of that
fmul in other ffma calls if we do the multiplication in the right
order.
For example it is a fairly common pattern for shaders to do something
similar to this:
const float a = 0.5;
in vec4 b;
in float c;
...
b.x = b.x * c;
b.y = b.y * c;
...
b.x = b.x * a + a;
b.y = b.y * a + a;
So by simply detecting that constant a is part of the multiplication
in ffma and switching it with previous fmul that updates b we end up
with:
...
c = a * c;
...
b.x = b.x * c + a;
b.y = b.y * c + a;
shader-db results BDW:
total instructions in shared programs: 13056473 -> 13038614 (-0.14%)
instructions in affected programs: 2433641 -> 2415782 (-0.73%)
helped: 10114
HURT: 330
total cycles in shared programs: 256515402 -> 256331740 (-0.07%)
cycles in affected programs: 137476650 -> 137292988 (-0.13%)
helped: 10802
HURT: 3871
total spills in shared programs: 14923 -> 14675 (-1.66%)
spills in affected programs: 7976 -> 7728 (-3.11%)
helped: 280
HURT: 27
total fills in shared programs: 20141 -> 19691 (-2.23%)
fills in affected programs: 11408 -> 10958 (-3.94%)
helped: 282
HURT: 27
LOST: 6
GAINED: 1
---
src/compiler/nir/nir_opt_algebraic.py | 2 ++
src/compiler/nir/nir_search_helpers.h | 11 +++++++++++
2 files changed, 13 insertions(+)
diff --git a/src/compiler/nir/nir_opt_algebraic.py b/src/compiler/nir/nir_opt_algebraic.py
index b5974a7..3cddda3 100644
--- a/src/compiler/nir/nir_opt_algebraic.py
+++ b/src/compiler/nir/nir_opt_algebraic.py
@@ -331,6 +331,8 @@ optimizations = [
(('~fadd', '#a', ('fadd', b, '#c')), ('fadd', ('fadd', a, c), b)),
(('iadd', '#a', ('iadd', b, '#c')), ('iadd', ('iadd', a, c), b)),
+ (('fadd', ('fmul(is_used_once)', ('fmul(is_used_once)', 'a(is_not_const)', 'b(is_not_const)'), '#c'), d), ('fadd', ('fmul', ('fmul', a, '#c'), b), d)),
+
# Misc. lowering
(('fmod at 32', a, b), ('fsub', a, ('fmul', b, ('ffloor', ('fdiv', a, b)))), 'options->lower_fmod32'),
(('fmod at 64', a, b), ('fsub', a, ('fmul', b, ('ffloor', ('fdiv', a, b)))), 'options->lower_fmod64'),
diff --git a/src/compiler/nir/nir_search_helpers.h b/src/compiler/nir/nir_search_helpers.h
index ddaff52..f89e417 100644
--- a/src/compiler/nir/nir_search_helpers.h
+++ b/src/compiler/nir/nir_search_helpers.h
@@ -115,6 +115,17 @@ is_zero_to_one(nir_alu_instr *instr, unsigned src, unsigned num_components,
}
static inline bool
+is_not_const(nir_alu_instr *instr, unsigned src, unsigned num_components)
+{
+ nir_const_value *val = nir_src_as_const_value(instr->src[src].src);
+
+ if (val)
+ return false;
+
+ return true;
+}
+
+static inline bool
is_used_more_than_once(nir_alu_instr *instr)
{
bool zero_if_use = list_empty(&instr->dest.dest.ssa.if_uses);
--
2.9.3
More information about the mesa-dev
mailing list