From ca5c0e8a3e2716f9e91e8a4b193f99595448c699 Mon Sep 17 00:00:00 2001 From: Jake Turner Date: Mon, 9 Dec 2024 15:10:55 +0000 Subject: [PATCH] DXIL ControlFlow optimisations Lazy evaluate the connections map --- .../driver/shaders/dxil/dxil_controlflow.cpp | 30 ++++++++++++++++++- .../driver/shaders/dxil/dxil_controlflow.h | 11 +++++-- 2 files changed, 38 insertions(+), 3 deletions(-) diff --git a/renderdoc/driver/shaders/dxil/dxil_controlflow.cpp b/renderdoc/driver/shaders/dxil/dxil_controlflow.cpp index b0dd23b31..7a40382c9 100644 --- a/renderdoc/driver/shaders/dxil/dxil_controlflow.cpp +++ b/renderdoc/driver/shaders/dxil/dxil_controlflow.cpp @@ -300,7 +300,23 @@ void ControlFlow::Construct(const rdcarray> &links) { m_Connections[from].resize(maxBlockIndex); for(uint32_t to = 0; to < maxBlockIndex; ++to) - m_Connections[from][to] = IsBlockConnected(from, to); + m_Connections[from][to] = ConnectionState::Unknown; + } + + for(uint32_t p = 0; p < m_Paths.size(); ++p) + { + const BlockPath &path = m_Paths[p]; + for(size_t i = 0; i < path.size() - 1; ++i) + { + uint32_t from = path[i]; + for(size_t j = i + 1; j < path.size(); ++j) + { + uint32_t to = path[j]; + if(to == PATH_END) + break; + m_Connections[from][to] = ConnectionState::Connected; + } + } } // A loop block is defined by any block which appears in any path starting from the block @@ -446,6 +462,18 @@ uint32_t ControlFlow::GetNextUniformBlock(uint32_t from) const } return bestBlock; } + +bool ControlFlow::IsForwardConnection(uint32_t from, uint32_t to) const +{ + if(m_Connections[from][to] == ConnectionState::Unknown) + { + if(IsBlockConnected(from, to)) + m_Connections[from][to] = ConnectionState::Connected; + else + m_Connections[from][to] = ConnectionState::NotConnected; + } + return m_Connections[from][to] == ConnectionState::Connected; +} }; // namespace DXIL #if ENABLED(ENABLE_UNIT_TESTS) diff --git a/renderdoc/driver/shaders/dxil/dxil_controlflow.h b/renderdoc/driver/shaders/dxil/dxil_controlflow.h index cae68bba2..5aae6fcad 100644 --- a/renderdoc/driver/shaders/dxil/dxil_controlflow.h +++ b/renderdoc/driver/shaders/dxil/dxil_controlflow.h @@ -39,11 +39,18 @@ public: rdcarray GetUniformBlocks() const { return m_UniformBlocks; } rdcarray GetLoopBlocks() const { return m_LoopBlocks; } uint32_t GetNextUniformBlock(uint32_t from) const; - bool IsForwardConnection(uint32_t from, uint32_t to) const { return m_Connections[from][to]; } + bool IsForwardConnection(uint32_t from, uint32_t to) const; private: typedef rdcarray BlockPath; + enum class ConnectionState : uint8_t + { + Unknown, + NotConnected, + Connected, + }; + bool TraceBlockFlow(const uint32_t from, BlockPath &path); bool BlockInAllPaths(uint32_t block, uint32_t pathIdx, int32_t startIdx) const; int32_t BlockInAnyPath(uint32_t block, uint32_t pathIdx, int32_t startIdx, int32_t steps) const; @@ -61,6 +68,6 @@ private: rdcarray m_UniformBlocks; rdcarray m_LoopBlocks; - rdcarray> m_Connections; + mutable rdcarray> m_Connections; }; }; // namespace DXIL