Separate analysis info from SPIR-V execution modes Fixes: b/177839655 Change-Id: I1186ee62fe34ea0a06904c4907c710853b2f8dd2 Reviewed-on: https://swiftshader-review.googlesource.com/c/SwiftShader/+/56270 Kokoro-Result: kokoro <noreply+kokoro@google.com> Tested-by: Nicolas Capens <nicolascapens@google.com> Reviewed-by: Alexis Hétu <sugoi@google.com>
diff --git a/src/Device/PixelProcessor.cpp b/src/Device/PixelProcessor.cpp index de940fa..a3e96b9 100644 --- a/src/Device/PixelProcessor.cpp +++ b/src/Device/PixelProcessor.cpp
@@ -142,7 +142,7 @@ state.occlusionEnabled = occlusionEnabled; - bool fragmentContainsKill = (fragmentShader && fragmentShader->getModes().ContainsKill); + bool fragmentContainsKill = (fragmentShader && fragmentShader->getAnalysis().ContainsKill); for(int i = 0; i < RENDERTARGETS; i++) { state.colorWriteMask |= pipelineState.colorWriteActive(i, attachments) << (4 * i); @@ -177,7 +177,7 @@ if(state.enableMultiSampling && fragmentShader) { - state.centroid = fragmentShader->getModes().NeedsCentroid; + state.centroid = fragmentShader->getAnalysis().NeedsCentroid; } state.frontFace = pipelineState.getFrontFace();
diff --git a/src/Pipeline/ComputeProgram.cpp b/src/Pipeline/ComputeProgram.cpp index 1016663..43926f4 100644 --- a/src/Pipeline/ComputeProgram.cpp +++ b/src/Pipeline/ComputeProgram.cpp
@@ -214,10 +214,10 @@ uint32_t baseGroupX, uint32_t baseGroupY, uint32_t baseGroupZ, uint32_t groupCountX, uint32_t groupCountY, uint32_t groupCountZ) { - auto &modes = shader->getModes(); + auto &executionModes = shader->getExecutionModes(); auto invocationsPerSubgroup = SIMD::Width; - auto invocationsPerWorkgroup = modes.WorkgroupSizeX * modes.WorkgroupSizeY * modes.WorkgroupSizeZ; + auto invocationsPerWorkgroup = executionModes.WorkgroupSizeX * executionModes.WorkgroupSizeY * executionModes.WorkgroupSizeZ; auto subgroupsPerWorkgroup = (invocationsPerWorkgroup + invocationsPerSubgroup - 1) / invocationsPerSubgroup; Data data; @@ -227,9 +227,9 @@ data.numWorkgroups[Y] = groupCountY; data.numWorkgroups[Z] = groupCountZ; data.numWorkgroups[3] = 0; - data.workgroupSize[X] = modes.WorkgroupSizeX; - data.workgroupSize[Y] = modes.WorkgroupSizeY; - data.workgroupSize[Z] = modes.WorkgroupSizeZ; + data.workgroupSize[X] = executionModes.WorkgroupSizeX; + data.workgroupSize[Y] = executionModes.WorkgroupSizeY; + data.workgroupSize[Z] = executionModes.WorkgroupSizeZ; data.workgroupSize[3] = 0; data.invocationsPerSubgroup = invocationsPerSubgroup; data.invocationsPerWorkgroup = invocationsPerWorkgroup; @@ -266,7 +266,7 @@ using Coroutine = std::unique_ptr<rr::Stream<SpirvShader::YieldResult>>; std::queue<Coroutine> coroutines; - if(modes.ContainsControlBarriers) + if(shader->getAnalysis().ContainsControlBarriers) { // Make a function call per subgroup so each subgroup // can yield, bringing all subgroups to the barrier
diff --git a/src/Pipeline/PixelProgram.cpp b/src/Pipeline/PixelProgram.cpp index 705ccf5..3c6d136 100644 --- a/src/Pipeline/PixelProgram.cpp +++ b/src/Pipeline/PixelProgram.cpp
@@ -220,7 +220,7 @@ clampColor(c); - if(spirvShader->getModes().ContainsKill) + if(spirvShader->getAnalysis().ContainsKill) { for(unsigned int q : samples) {
diff --git a/src/Pipeline/PixelRoutine.cpp b/src/Pipeline/PixelRoutine.cpp index 069544d..019477b 100644 --- a/src/Pipeline/PixelRoutine.cpp +++ b/src/Pipeline/PixelRoutine.cpp
@@ -33,7 +33,7 @@ , routine(pipelineLayout) , descriptorSets(descriptorSets) , shaderContainsInterpolation(spirvShader && spirvShader->getUsedCapabilities().InterpolationFunction) - , shaderContainsSampleQualifier(spirvShader && spirvShader->getModes().ContainsSampleQualifier) + , shaderContainsSampleQualifier(spirvShader && spirvShader->getAnalysis().ContainsSampleQualifier) , perSampleShading((state.sampleShadingEnabled && (state.minSampleShading * state.multiSampleCount > 1.0f)) || shaderContainsSampleQualifier || shaderContainsInterpolation) // TODO(b/194714095) , invocationCount(perSampleShading ? state.multiSampleCount : 1) @@ -81,7 +81,7 @@ void PixelRoutine::quad(Pointer<Byte> cBuffer[RENDERTARGETS], Pointer<Byte> &zBuffer, Pointer<Byte> &sBuffer, Int cMask[4], Int &x, Int &y) { - const bool earlyFragmentTests = !spirvShader || spirvShader->getModes().EarlyFragmentTests; + const bool earlyFragmentTests = !spirvShader || spirvShader->getExecutionModes().EarlyFragmentTests; Int zMask[4]; // Depth mask Int sMask[4]; // Stencil mask @@ -295,7 +295,7 @@ Bool alphaPass = alphaTest(cMask, samples); - if((spirvShader && spirvShader->getModes().ContainsKill) || state.alphaToCoverage) + if((spirvShader && spirvShader->getAnalysis().ContainsKill) || state.alphaToCoverage) { for(unsigned int q : samples) {
diff --git a/src/Pipeline/SpirvShader.cpp b/src/Pipeline/SpirvShader.cpp index 3d330b8..37ccbb3 100644 --- a/src/Pipeline/SpirvShader.cpp +++ b/src/Pipeline/SpirvShader.cpp
@@ -118,7 +118,7 @@ descriptorDecorations[targetId].InputAttachmentIndex = value; break; case spv::DecorationSample: - modes.ContainsSampleQualifier = true; + analysis.ContainsSampleQualifier = true; break; default: // Only handling descriptor decorations here. @@ -127,7 +127,7 @@ if(decoration == spv::DecorationCentroid) { - modes.NeedsCentroid = true; + analysis.NeedsCentroid = true; } } break; @@ -147,7 +147,7 @@ if(decoration == spv::DecorationCentroid) { - modes.NeedsCentroid = true; + analysis.NeedsCentroid = true; } } break; @@ -234,7 +234,7 @@ if(opcode == spv::OpKill) { - modes.ContainsKill = true; + analysis.ContainsKill = true; } } break; @@ -376,9 +376,9 @@ // The object decorated with WorkgroupSize must be declared // as a three-component vector of 32-bit integers. ASSERT(getType(object).componentCount == 3); - modes.WorkgroupSizeX = object.constantValue[0]; - modes.WorkgroupSizeY = object.constantValue[1]; - modes.WorkgroupSizeZ = object.constantValue[2]; + executionModes.WorkgroupSizeX = object.constantValue[0]; + executionModes.WorkgroupSizeY = object.constantValue[1]; + executionModes.WorkgroupSizeZ = object.constantValue[2]; } } break; @@ -739,7 +739,7 @@ break; case spv::OpControlBarrier: - modes.ContainsControlBarriers = true; + analysis.ContainsControlBarriers = true; break; case spv::OpExtension: @@ -943,27 +943,27 @@ switch(mode) { case spv::ExecutionModeEarlyFragmentTests: - modes.EarlyFragmentTests = true; + executionModes.EarlyFragmentTests = true; break; case spv::ExecutionModeDepthReplacing: - modes.DepthReplacing = true; + executionModes.DepthReplacing = true; break; case spv::ExecutionModeDepthGreater: // TODO(b/177915067): Can be used to optimize depth test, currently unused. - modes.DepthGreater = true; + executionModes.DepthGreater = true; break; case spv::ExecutionModeDepthLess: // TODO(b/177915067): Can be used to optimize depth test, currently unused. - modes.DepthLess = true; + executionModes.DepthLess = true; break; case spv::ExecutionModeDepthUnchanged: // TODO(b/177915067): Can be used to optimize depth test, currently unused. - modes.DepthUnchanged = true; + executionModes.DepthUnchanged = true; break; case spv::ExecutionModeLocalSize: - modes.WorkgroupSizeX = insn.word(3); - modes.WorkgroupSizeY = insn.word(4); - modes.WorkgroupSizeZ = insn.word(5); + executionModes.WorkgroupSizeX = insn.word(3); + executionModes.WorkgroupSizeY = insn.word(4); + executionModes.WorkgroupSizeZ = insn.word(5); break; case spv::ExecutionModeOriginUpperLeft: // This is always the case for a Vulkan shader. Do nothing.
diff --git a/src/Pipeline/SpirvShader.hpp b/src/Pipeline/SpirvShader.hpp index d08925f..62b885b 100644 --- a/src/Pipeline/SpirvShader.hpp +++ b/src/Pipeline/SpirvShader.hpp
@@ -573,7 +573,7 @@ ~SpirvShader(); - struct Modes + struct ExecutionModes { bool EarlyFragmentTests : 1; bool DepthReplacing : 1; @@ -581,22 +581,28 @@ bool DepthLess : 1; bool DepthUnchanged : 1; - // TODO(b/177839655): These are not SPIR-V execution modes. - // Move to an Analysis structure. - bool ContainsKill : 1; - bool ContainsControlBarriers : 1; - bool NeedsCentroid : 1; - bool ContainsSampleQualifier : 1; - // Compute workgroup dimensions int WorkgroupSizeX = 1; int WorkgroupSizeY = 1; int WorkgroupSizeZ = 1; }; - Modes const &getModes() const + const ExecutionModes &getExecutionModes() const { - return modes; + return executionModes; + } + + struct Analysis + { + bool ContainsKill : 1; + bool ContainsControlBarriers : 1; + bool NeedsCentroid : 1; + bool ContainsSampleQualifier : 1; + }; + + const Analysis &getAnalysis() const + { + return analysis; } struct Capabilities @@ -630,7 +636,7 @@ bool StencilExportEXT : 1; }; - Capabilities const &getUsedCapabilities() const + const Capabilities &getUsedCapabilities() const { return capabilities; } @@ -830,7 +836,8 @@ private: const uint32_t codeSerialID; - Modes modes = {}; + ExecutionModes executionModes = {}; + Analysis analysis = {}; Capabilities capabilities = {}; HandleMap<Type> types; HandleMap<Object> defs;