nir/algebraic: Add optimizations for "a == a && a CMP b"
authorJason Ekstrand <jason.ekstrand@intel.com>
Tue, 20 Dec 2016 05:29:51 +0000 (21:29 -0800)
committerJason Ekstrand <jason.ekstrand@intel.com>
Fri, 23 Dec 2016 00:27:19 +0000 (16:27 -0800)
This sequence shows up The Talos Principal, at least under Vulkan,
and prevents loop analysis from properly computing trip counts in a
few loops.

Reviewed-by: Ian Romanick <ian.d.romanick@intel.com>
src/compiler/nir/nir_opt_algebraic.py

index 698ac6736588e24cd2ceb67d91b2744aae5db9c7..ff10d701f5e5ab662ab0fcb384af654638dc13cb 100644 (file)
@@ -464,6 +464,14 @@ def bitfield_reverse(u):
 
 optimizations += [(bitfield_reverse('x@32'), ('bitfield_reverse', 'x'))]
 
+# For any float comparison operation, "cmp", if you have "a == a && a cmp b"
+# then the "a == a" is redundant because it's equivalent to "a is not NaN"
+# and, if a is a NaN then the second comparison will fail anyway.
+for op in ['flt', 'fge', 'feq']:
+   optimizations += [
+      (('iand', ('feq', a, a), (op, a, b)), (op, a, b)),
+      (('iand', ('feq', a, a), (op, b, a)), (op, b, a)),
+   ]
 
 # Add optimizations to handle the case where the result of a ternary is
 # compared to a constant.  This way we can take things like