From 9c3c206e711030b17428a2ef506cc498ef7eedcc Mon Sep 17 00:00:00 2001 From: Caio Marcelo de Oliveira Filho Date: Tue, 29 Oct 2019 12:09:38 -0700 Subject: [PATCH] spirv: Don't fail if multiple ordering semantics bits are set Vulkan requires that only one bit for the ordering is set, but old versions of GLSLang just set all the bits. This was fixed as part of https://github.com/KhronosGroup/glslang/commit/c51287d744fb6e7e9ccc09f6f8451e6c64b1dad6 but we can still find older versions (or shaders compiled with it) around. So instead of failing, emit a warning and fallback to the effective result of any combination of multiple bits: AcquireRelease. Closes: https://gitlab.freedesktop.org/mesa/mesa/issues/2018 Reviewed-by: Jason Ekstrand --- src/compiler/spirv/spirv_to_nir.c | 39 ++++++++++++++++++++++++------- 1 file changed, 30 insertions(+), 9 deletions(-) diff --git a/src/compiler/spirv/spirv_to_nir.c b/src/compiler/spirv/spirv_to_nir.c index e436f28de60..4c1da666261 100644 --- a/src/compiler/spirv/spirv_to_nir.c +++ b/src/compiler/spirv/spirv_to_nir.c @@ -1954,12 +1954,22 @@ vtn_split_barrier_semantics(struct vtn_builder *b, *before = SpvMemorySemanticsMaskNone; *after = SpvMemorySemanticsMaskNone; - const SpvMemorySemanticsMask order_semantics = + SpvMemorySemanticsMask order_semantics = semantics & (SpvMemorySemanticsAcquireMask | SpvMemorySemanticsReleaseMask | SpvMemorySemanticsAcquireReleaseMask | SpvMemorySemanticsSequentiallyConsistentMask); + if (util_bitcount(order_semantics) > 1) { + /* Old GLSLang versions incorrectly set all the ordering bits. This was + * fixed in c51287d744fb6e7e9ccc09f6f8451e6c64b1dad6 of glslang repo, + * and it is in GLSLang since revision "SPIRV99.1321" (from Jul-2016). + */ + vtn_warn("Multiple memory ordering semantics specified, " + "assuming AcquireRelease."); + order_semantics = SpvMemorySemanticsAcquireReleaseMask; + } + const SpvMemorySemanticsMask av_vis_semantics = semantics & (SpvMemorySemanticsMakeAvailableMask | SpvMemorySemanticsMakeVisibleMask); @@ -1979,9 +1989,6 @@ vtn_split_barrier_semantics(struct vtn_builder *b, if (other_semantics) vtn_warn("Ignoring unhandled memory semantics: %u\n", other_semantics); - vtn_fail_if(util_bitcount(order_semantics) > 1, - "Multiple memory ordering bits specified"); - /* SequentiallyConsistent is treated as AcquireRelease. */ /* The RELEASE barrier happens BEFORE the operation, and it is usually @@ -2016,10 +2023,24 @@ vtn_emit_scoped_memory_barrier(struct vtn_builder *b, SpvScope scope, SpvMemorySemanticsMask semantics) { nir_memory_semantics nir_semantics = 0; - switch (semantics & (SpvMemorySemanticsAcquireMask | - SpvMemorySemanticsReleaseMask | - SpvMemorySemanticsAcquireReleaseMask | - SpvMemorySemanticsSequentiallyConsistentMask)) { + + SpvMemorySemanticsMask order_semantics = + semantics & (SpvMemorySemanticsAcquireMask | + SpvMemorySemanticsReleaseMask | + SpvMemorySemanticsAcquireReleaseMask | + SpvMemorySemanticsSequentiallyConsistentMask); + + if (util_bitcount(order_semantics) > 1) { + /* Old GLSLang versions incorrectly set all the ordering bits. This was + * fixed in c51287d744fb6e7e9ccc09f6f8451e6c64b1dad6 of glslang repo, + * and it is in GLSLang since revision "SPIRV99.1321" (from Jul-2016). + */ + vtn_warn("Multiple memory ordering semantics bits specified, " + "assuming AcquireRelease."); + order_semantics = SpvMemorySemanticsAcquireReleaseMask; + } + + switch (order_semantics) { case 0: /* Not an ordering barrier. */ break; @@ -2039,7 +2060,7 @@ vtn_emit_scoped_memory_barrier(struct vtn_builder *b, SpvScope scope, break; default: - vtn_fail("Multiple memory ordering bits specified"); + unreachable("Invalid memory order semantics"); } if (semantics & SpvMemorySemanticsMakeAvailableMask) { -- 2.30.2