summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorKenneth Graunke <[email protected]>2019-02-06 16:45:25 -0800
committerDylan Baker <[email protected]>2019-02-26 10:40:21 -0800
commita4ea63e884873216bea767c7a6d8ef9313ce780a (patch)
treeafc13b97b7dab475ff206c787387b683eef063e8 /src
parentbdc946c23a3085840f737eddfe8e87dbb27f5a0a (diff)
spirv: Eliminate dead input/output variables after translation.
spirv_to_nir can generate input/output variables which are illegal for the current shader stage, which would cause nir_validate_shader to balk. After my recent commit to start decorating arrays as compact, dEQP-VK.spirv_assembly.instruction.graphics.module.same_module started hitting validation errors due to outputs in a TCS (not intended for the TCS at all) not being per-vertex arrays. Thanks to Jason Ekstrand for suggesting this approach. Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=109573 Fixes: ef99f4c8d17 compiler: Mark clip/cull distance arrays as compact before lowering. Reviewed-by: Juan A. Suarez <[email protected]> (cherry picked from commit 6775665e5eec7db3f291508a8b7ba2a792f62ec0)
Diffstat (limited to 'src')
-rw-r--r--src/compiler/spirv/spirv_to_nir.c25
1 files changed, 20 insertions, 5 deletions
diff --git a/src/compiler/spirv/spirv_to_nir.c b/src/compiler/spirv/spirv_to_nir.c
index 670bd1bcb89..42731f7eb62 100644
--- a/src/compiler/spirv/spirv_to_nir.c
+++ b/src/compiler/spirv/spirv_to_nir.c
@@ -4481,20 +4481,35 @@ spirv_to_nir(const uint32_t *words, size_t word_count,
}
} while (progress);
+ vtn_assert(b->entry_point->value_type == vtn_value_type_function);
+ nir_function *entry_point = b->entry_point->func->impl->function;
+ vtn_assert(entry_point);
+
+ entry_point->is_entrypoint = true;
+
+ /* When multiple shader stages exist in the same SPIR-V module, we
+ * generate input and output variables for every stage, in the same
+ * NIR program. These dead variables can be invalid NIR. For example,
+ * TCS outputs must be per-vertex arrays (or decorated 'patch'), while
+ * VS output variables wouldn't be.
+ *
+ * To ensure we have valid NIR, we eliminate any dead inputs and outputs
+ * right away. In order to do so, we must lower any constant initializers
+ * on outputs so nir_remove_dead_variables sees that they're written to.
+ */
+ nir_lower_constant_initializers(b->shader, nir_var_shader_out);
+ nir_remove_dead_variables(b->shader,
+ nir_var_shader_in | nir_var_shader_out);
+
/* We sometimes generate bogus derefs that, while never used, give the
* validator a bit of heartburn. Run dead code to get rid of them.
*/
nir_opt_dce(b->shader);
- vtn_assert(b->entry_point->value_type == vtn_value_type_function);
- nir_function *entry_point = b->entry_point->func->impl->function;
- vtn_assert(entry_point);
-
/* Unparent the shader from the vtn_builder before we delete the builder */
ralloc_steal(NULL, b->shader);
ralloc_free(b);
- entry_point->is_entrypoint = true;
return entry_point;
}