diff options
author | Liam <byteslice@airmail.cc> | 2023-06-10 17:40:58 +0200 |
---|---|---|
committer | Liam <byteslice@airmail.cc> | 2023-06-10 18:30:39 +0200 |
commit | 2bb7ea436dc74f812a8092201dc597ed58ff3c7a (patch) | |
tree | 27b6426a646112e163ae39b733ce60ca6d6aa748 /src/shader_recompiler | |
parent | Merge pull request #10685 from liamwhite/serialization-is-hard (diff) | |
download | yuzu-2bb7ea436dc74f812a8092201dc597ed58ff3c7a.tar yuzu-2bb7ea436dc74f812a8092201dc597ed58ff3c7a.tar.gz yuzu-2bb7ea436dc74f812a8092201dc597ed58ff3c7a.tar.bz2 yuzu-2bb7ea436dc74f812a8092201dc597ed58ff3c7a.tar.lz yuzu-2bb7ea436dc74f812a8092201dc597ed58ff3c7a.tar.xz yuzu-2bb7ea436dc74f812a8092201dc597ed58ff3c7a.tar.zst yuzu-2bb7ea436dc74f812a8092201dc597ed58ff3c7a.zip |
Diffstat (limited to 'src/shader_recompiler')
-rw-r--r-- | src/shader_recompiler/CMakeLists.txt | 1 | ||||
-rw-r--r-- | src/shader_recompiler/frontend/maxwell/translate_program.cpp | 3 | ||||
-rw-r--r-- | src/shader_recompiler/host_translate_info.h | 2 | ||||
-rw-r--r-- | src/shader_recompiler/ir_opt/conditional_barrier_pass.cpp | 44 | ||||
-rw-r--r-- | src/shader_recompiler/ir_opt/passes.h | 1 |
5 files changed, 51 insertions, 0 deletions
diff --git a/src/shader_recompiler/CMakeLists.txt b/src/shader_recompiler/CMakeLists.txt index 525b2363c..2baa64322 100644 --- a/src/shader_recompiler/CMakeLists.txt +++ b/src/shader_recompiler/CMakeLists.txt @@ -216,6 +216,7 @@ add_library(shader_recompiler STATIC frontend/maxwell/translate_program.h host_translate_info.h ir_opt/collect_shader_info_pass.cpp + ir_opt/conditional_barrier_pass.cpp ir_opt/constant_propagation_pass.cpp ir_opt/dead_code_elimination_pass.cpp ir_opt/dual_vertex_pass.cpp diff --git a/src/shader_recompiler/frontend/maxwell/translate_program.cpp b/src/shader_recompiler/frontend/maxwell/translate_program.cpp index 17a6d4888..529382355 100644 --- a/src/shader_recompiler/frontend/maxwell/translate_program.cpp +++ b/src/shader_recompiler/frontend/maxwell/translate_program.cpp @@ -286,6 +286,9 @@ IR::Program TranslateProgram(ObjectPool<IR::Inst>& inst_pool, ObjectPool<IR::Blo if (!host_info.support_int64) { Optimization::LowerInt64ToInt32(program); } + if (!host_info.support_conditional_barrier) { + Optimization::ConditionalBarrierPass(program); + } Optimization::SsaRewritePass(program); Optimization::ConstantPropagationPass(env, program); diff --git a/src/shader_recompiler/host_translate_info.h b/src/shader_recompiler/host_translate_info.h index 2aaa6c5ea..d4e4f4d28 100644 --- a/src/shader_recompiler/host_translate_info.h +++ b/src/shader_recompiler/host_translate_info.h @@ -17,6 +17,8 @@ struct HostTranslateInfo { bool support_viewport_index_layer{}; ///< True when the device supports gl_Layer in VS bool support_geometry_shader_passthrough{}; ///< True when the device supports geometry ///< passthrough shaders + bool support_conditional_barrier{}; ///< True when the device supports barriers in conditional + ///< control flow }; } // namespace Shader diff --git a/src/shader_recompiler/ir_opt/conditional_barrier_pass.cpp b/src/shader_recompiler/ir_opt/conditional_barrier_pass.cpp new file mode 100644 index 000000000..c3ed27f4f --- /dev/null +++ b/src/shader_recompiler/ir_opt/conditional_barrier_pass.cpp @@ -0,0 +1,44 @@ +// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + +#include "shader_recompiler/frontend/ir/program.h" +#include "shader_recompiler/ir_opt/passes.h" + +namespace Shader::Optimization { + +void ConditionalBarrierPass(IR::Program& program) { + s32 conditional_control_flow_count{0}; + s32 conditional_return_count{0}; + for (IR::AbstractSyntaxNode& node : program.syntax_list) { + switch (node.type) { + case IR::AbstractSyntaxNode::Type::If: + case IR::AbstractSyntaxNode::Type::Loop: + conditional_control_flow_count++; + break; + case IR::AbstractSyntaxNode::Type::EndIf: + case IR::AbstractSyntaxNode::Type::Repeat: + conditional_control_flow_count--; + break; + case IR::AbstractSyntaxNode::Type::Unreachable: + case IR::AbstractSyntaxNode::Type::Return: + if (conditional_control_flow_count > 0) { + conditional_return_count++; + } + break; + case IR::AbstractSyntaxNode::Type::Block: + for (IR::Inst& inst : node.data.block->Instructions()) { + if ((conditional_control_flow_count > 0 || conditional_return_count > 0) && + inst.GetOpcode() == IR::Opcode::Barrier) { + LOG_WARNING(Shader, "Barrier within conditional control flow"); + inst.ReplaceOpcode(IR::Opcode::Identity); + } + } + break; + default: + break; + } + } + ASSERT(conditional_control_flow_count == 0); +} + +} // namespace Shader::Optimization diff --git a/src/shader_recompiler/ir_opt/passes.h b/src/shader_recompiler/ir_opt/passes.h index 1f8f2ba95..a677bfc65 100644 --- a/src/shader_recompiler/ir_opt/passes.h +++ b/src/shader_recompiler/ir_opt/passes.h @@ -13,6 +13,7 @@ struct HostTranslateInfo; namespace Shader::Optimization { void CollectShaderInfoPass(Environment& env, IR::Program& program); +void ConditionalBarrierPass(IR::Program& program); void ConstantPropagationPass(Environment& env, IR::Program& program); void DeadCodeEliminationPass(IR::Program& program); void GlobalMemoryToStorageBufferPass(IR::Program& program); |