diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/video_core/shader/decode/other.cpp | 19 |
1 files changed, 19 insertions, 0 deletions
diff --git a/src/video_core/shader/decode/other.cpp b/src/video_core/shader/decode/other.cpp index 3f058324c..4c2d24202 100644 --- a/src/video_core/shader/decode/other.cpp +++ b/src/video_core/shader/decode/other.cpp | |||
| @@ -57,6 +57,25 @@ u32 ShaderIR::DecodeOther(BasicBlock& bb, u32 pc) { | |||
| 57 | bb.push_back(Operation(OperationCode::Bra, Immediate(target))); | 57 | bb.push_back(Operation(OperationCode::Bra, Immediate(target))); |
| 58 | break; | 58 | break; |
| 59 | } | 59 | } |
| 60 | case OpCode::Id::SSY: { | ||
| 61 | UNIMPLEMENTED_IF_MSG(instr.bra.constant_buffer != 0, | ||
| 62 | "Constant buffer flow is not supported"); | ||
| 63 | |||
| 64 | // The SSY opcode tells the GPU where to re-converge divergent execution paths, it sets the | ||
| 65 | // target of the jump that the SYNC instruction will make. The SSY opcode has a similar | ||
| 66 | // structure to the BRA opcode. | ||
| 67 | bb.push_back(Operation(OperationCode::Ssy, Immediate(pc + instr.bra.GetBranchTarget()))); | ||
| 68 | break; | ||
| 69 | } | ||
| 70 | case OpCode::Id::SYNC: { | ||
| 71 | const Tegra::Shader::ConditionCode cc = instr.flow_condition_code; | ||
| 72 | UNIMPLEMENTED_IF_MSG(cc != Tegra::Shader::ConditionCode::T, "SYNC condition code used: {}", | ||
| 73 | static_cast<u32>(cc)); | ||
| 74 | |||
| 75 | // The SYNC opcode jumps to the address previously set by the SSY opcode | ||
| 76 | bb.push_back(Operation(OperationCode::Sync)); | ||
| 77 | break; | ||
| 78 | } | ||
| 60 | case OpCode::Id::IPA: { | 79 | case OpCode::Id::IPA: { |
| 61 | const auto& attribute = instr.attribute.fmt28; | 80 | const auto& attribute = instr.attribute.fmt28; |
| 62 | const Tegra::Shader::IpaMode input_mode{instr.ipa.interp_mode.Value(), | 81 | const Tegra::Shader::IpaMode input_mode{instr.ipa.interp_mode.Value(), |