Skip to content

nir/opt_if: Simplify if's with general conditions

Alyssa Rosenzweig requested to merge alyssa/mesa:nir/opt-if-general into main

What does this MR do and why?

nir/opt_if: Simplify if's with general conditions

Dolphin ubershaders have a pattern:

if (x && y) { } else { discard; }

The current code to simplify if's will bail on this pattern, since the condition is not a comparison. However, if that check is dropped and we allow NIR to invert this, we get:

if (!(x && y)) { discard; } else { }

which is now in a form for nir_opt_conditional_discard to turn into it

discard_if(!(x && y))

which may be substantially cheaper than the original code.

In general, I see no reason to restrict to conditionals. Assuming the backend is clever enough to delete empty else blocks (I think most are), then this patch is a strict win as long as inot instructions are cheaper than empty else blocks. This matches my intuition for typical GPUs, where simple ALU instructions are cheaper than control flow. Furthermore, it may be possible in practice for backends to fold the inot into a richer set of instructions. For example, most GPUs have a NAND instructions which would fold in the inot in the above code.

So just drop the check, simplify the pass, get the win.

Signed-off-by: Alyssa Rosenzweig alyssa@rosenzweig.io


@hakzsam you introduced this condition, let me know if there's a gotcha

Merge request reports