diff options
| author | Yuri Kunde Schlesner <yuriks@yuriks.net> | 2015-07-23 16:25:59 -0300 |
|---|---|---|
| committer | Yuri Kunde Schlesner <yuriks@yuriks.net> | 2015-08-16 01:52:51 -0300 |
| commit | 9ae5a09655a568b55279f9b3cb6704144d9c442f (patch) | |
| tree | 2001047afb3ba55683a4d795ff62c2c799d927bd /src/core/hle/service/gsp_gpu.cpp | |
| parent | 2e5696dba4056a40239e68f3646ec328be531ad7 (diff) | |
GPU: Implement TextureCopy-mode display transfers
Fixes glitchy garbage in Fire Emblem 3D scenes.
Diffstat (limited to 'src/core/hle/service/gsp_gpu.cpp')
| -rw-r--r-- | src/core/hle/service/gsp_gpu.cpp | 25 |
1 files changed, 15 insertions, 10 deletions
diff --git a/src/core/hle/service/gsp_gpu.cpp b/src/core/hle/service/gsp_gpu.cpp index e93c1b436..3c41e656c 100644 --- a/src/core/hle/service/gsp_gpu.cpp +++ b/src/core/hle/service/gsp_gpu.cpp @@ -418,7 +418,7 @@ static void ExecuteCommand(const Command& command, u32 thread_id) { case CommandId::SET_DISPLAY_TRANSFER: { - auto& params = command.image_copy; + auto& params = command.display_transfer; WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.input_address)), Memory::VirtualToPhysicalAddress(params.in_buffer_address) >> 3); WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.output_address)), @@ -433,17 +433,22 @@ static void ExecuteCommand(const Command& command, u32 thread_id) { // TODO: Check if texture copies are implemented correctly.. case CommandId::SET_TEXTURE_COPY: { - auto& params = command.image_copy; - WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.input_address)), + auto& params = command.texture_copy; + WriteGPURegister((u32)GPU_REG_INDEX(display_transfer_config.input_address), Memory::VirtualToPhysicalAddress(params.in_buffer_address) >> 3); - WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.output_address)), + WriteGPURegister((u32)GPU_REG_INDEX(display_transfer_config.output_address), Memory::VirtualToPhysicalAddress(params.out_buffer_address) >> 3); - WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.input_size)), params.in_buffer_size); - WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.output_size)), params.out_buffer_size); - WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.flags)), params.flags); - - // TODO: Should this register be set to 1 or should instead its value be OR-ed with 1? - WriteGPURegister(static_cast<u32>(GPU_REG_INDEX(display_transfer_config.trigger)), 1); + WriteGPURegister((u32)GPU_REG_INDEX(display_transfer_config.texture_copy.size), + params.size); + WriteGPURegister((u32)GPU_REG_INDEX(display_transfer_config.texture_copy.input_size), + params.in_width_gap); + WriteGPURegister((u32)GPU_REG_INDEX(display_transfer_config.texture_copy.output_size), + params.out_width_gap); + WriteGPURegister((u32)GPU_REG_INDEX(display_transfer_config.flags), + params.flags); + + // NOTE: Actual GSP ORs 1 with current register instead of overwriting. Doesn't seem to matter. + WriteGPURegister((u32)GPU_REG_INDEX(display_transfer_config.trigger), 1); break; } |
