st/glsl_to_tgsi: fix renumber_registers() in presence of dead code
authorSamuel Pitoiset <samuel.pitoiset@gmail.com>
Thu, 4 May 2017 08:35:29 +0000 (10:35 +0200)
committerSamuel Pitoiset <samuel.pitoiset@gmail.com>
Fri, 5 May 2017 07:48:01 +0000 (09:48 +0200)
commit92ab06e782c31fe0209e5d0181967a2ff6739c9b
tree3b7a6872549b649428989e665a2bc9a0814cf7c2
parent7761cf6d01e97aeb80606e51c11e4885a278ed54
st/glsl_to_tgsi: fix renumber_registers() in presence of dead code

The TGSI DCE pass doesn't eliminate dead assignments like
MOV TEMP[0], TEMP[1] in presence of loops because it assumes
that the visitor doesn't emit dead code. This assumption is
actually wrong and this situation happens.

However, it appears that the merge_registers() pass accidentally
takes care of this for some weird reasons. But since this pass has
been disabled for RadeonSI and Nouveau, the renumber_registers()
pass which is called *after*, can't do its job correctly.

This is because it assumes that no dead code is present. But if
there is still a dead assignment, it might re-use the TEMP
register id incorrectly and emits wrong code.

This patches fixes the issue by recording writes instead of reads,
and this has the advantage to be faster.

This should fix Unigine Heaven on RadeonSI and Nouveau.

shader-db results with RadeonSI:

47109 shaders in 29632 tests
Totals:
SGPRS: 1923308 -> 1923316 (0.00 %)
VGPRS: 1133843 -> 1133847 (0.00 %)
Spilled SGPRs: 2516 -> 2518 (0.08 %)
Spilled VGPRs: 65 -> 65 (0.00 %)
Private memory VGPRs: 1184 -> 1184 (0.00 %)
Scratch size: 1308 -> 1308 (0.00 %) dwords per thread
Code Size: 60095968 -> 60096256 (0.00 %) bytes
LDS: 1077 -> 1077 (0.00 %) blocks
Max Waves: 431889 -> 431889 (0.00 %)
Wait states: 0 -> 0 (0.00 %)

It's still interesting to disable the merge_registers() pass.

Signed-off-by: Samuel Pitoiset <samuel.pitoiset@gmail.com>
Reviewed-by: Nicolai Hähnle <nicolai.haehnle@amd.com>
src/mesa/state_tracker/st_glsl_to_tgsi.cpp