diff options
| author | 2020-03-13 12:48:01 +0700 | |
|---|---|---|
| committer | 2020-03-13 12:48:01 +0700 | |
| commit | 465ba30d08fd294a6ccc05f9257894241a5240fc (patch) | |
| tree | f6946bd8f03d30c4739de63aeff02f2f3f4d8606 /src | |
| parent | Merge pull request #3483 from namkazt/patch-1 (diff) | |
| download | yuzu-465ba30d08fd294a6ccc05f9257894241a5240fc.tar.gz yuzu-465ba30d08fd294a6ccc05f9257894241a5240fc.tar.xz yuzu-465ba30d08fd294a6ccc05f9257894241a5240fc.zip | |
shader_decode: Reimplement BFE instructions
Diffstat (limited to 'src')
| -rw-r--r-- | src/video_core/shader/decode/bfe.cpp | 52 |
1 files changed, 27 insertions, 25 deletions
diff --git a/src/video_core/shader/decode/bfe.cpp b/src/video_core/shader/decode/bfe.cpp index e02bcd097..c3ef88373 100644 --- a/src/video_core/shader/decode/bfe.cpp +++ b/src/video_core/shader/decode/bfe.cpp | |||
| @@ -17,32 +17,34 @@ u32 ShaderIR::DecodeBfe(NodeBlock& bb, u32 pc) { | |||
| 17 | const Instruction instr = {program_code[pc]}; | 17 | const Instruction instr = {program_code[pc]}; |
| 18 | const auto opcode = OpCode::Decode(instr); | 18 | const auto opcode = OpCode::Decode(instr); |
| 19 | 19 | ||
| 20 | UNIMPLEMENTED_IF(instr.bfe.negate_b); | ||
| 21 | |||
| 22 | Node op_a = GetRegister(instr.gpr8); | 20 | Node op_a = GetRegister(instr.gpr8); |
| 23 | op_a = GetOperandAbsNegInteger(op_a, false, instr.bfe.negate_a, false); | 21 | Node op_b = [&] { |
| 24 | 22 | switch (opcode->get().GetId()) { | |
| 25 | switch (opcode->get().GetId()) { | 23 | case OpCode::Id::BFE_R: |
| 26 | case OpCode::Id::BFE_IMM: { | 24 | return GetRegister(instr.gpr20); |
| 27 | UNIMPLEMENTED_IF_MSG(instr.generates_cc, | 25 | case OpCode::Id::BFE_C: |
| 28 | "Condition codes generation in BFE is not implemented"); | 26 | return GetConstBuffer(instr.cbuf34.index, instr.cbuf34.GetOffset()); |
| 29 | 27 | case OpCode::Id::BFE_IMM: | |
| 30 | const Node inner_shift_imm = Immediate(static_cast<u32>(instr.bfe.GetLeftShiftValue())); | 28 | return Immediate(instr.alu.GetSignedImm20_20()); |
| 31 | const Node outer_shift_imm = | 29 | default: |
| 32 | Immediate(static_cast<u32>(instr.bfe.GetLeftShiftValue() + instr.bfe.shift_position)); | 30 | UNREACHABLE(); |
| 33 | 31 | return Immediate(0); | |
| 34 | const Node inner_shift = | 32 | } |
| 35 | Operation(OperationCode::ILogicalShiftLeft, NO_PRECISE, op_a, inner_shift_imm); | 33 | }(); |
| 36 | const Node outer_shift = | 34 | |
| 37 | Operation(OperationCode::ILogicalShiftRight, NO_PRECISE, inner_shift, outer_shift_imm); | 35 | UNIMPLEMENTED_IF_MSG(instr.bfe.rd_cc, "Condition codes in BFE is not implemented"); |
| 38 | 36 | UNIMPLEMENTED_IF_MSG(instr.bfe.brev, "BREV in BFE is not implemented"); | |
| 39 | SetInternalFlagsFromInteger(bb, outer_shift, instr.generates_cc); | 37 | |
| 40 | SetRegister(bb, instr.gpr0, outer_shift); | 38 | const bool is_signed = instr.bfe.is_signed; |
| 41 | break; | 39 | |
| 42 | } | 40 | const auto start_position = SignedOperation(OperationCode::IBitfieldExtract, is_signed, op_b, |
| 43 | default: | 41 | Immediate(0), Immediate(8)); |
| 44 | UNIMPLEMENTED_MSG("Unhandled BFE instruction: {}", opcode->get().GetName()); | 42 | const auto bits = SignedOperation(OperationCode::IBitfieldExtract, is_signed, op_b, |
| 45 | } | 43 | Immediate(8), Immediate(8)); |
| 44 | |||
| 45 | auto result = | ||
| 46 | SignedOperation(OperationCode::IBitfieldExtract, is_signed, op_a, start_position, bits); | ||
| 47 | SetRegister(bb, instr.gpr0, result); | ||
| 46 | 48 | ||
| 47 | return pc; | 49 | return pc; |
| 48 | } | 50 | } |