From 587aa20dcc55fb6dbe2d8f43d719d23eb9f5c9b7 Mon Sep 17 00:00:00 2001 From: png183 <97423514+png183@users.noreply.github.com> Date: Mon, 10 Jun 2024 00:26:22 -0700 Subject: [PATCH] gba: improve video capture DMA (#1519) Video capture DMAs should run only if the mode was enabled on scanline 162 of the previous frame, and should clear the DMA enable bit once complete. --- ares/gba/ppu/ppu.cpp | 6 +++++- ares/gba/ppu/ppu.hpp | 2 ++ ares/gba/ppu/serialization.cpp | 2 ++ ares/gba/system/serialization.cpp | 2 +- 4 files changed, 10 insertions(+), 2 deletions(-) diff --git a/ares/gba/ppu/ppu.cpp b/ares/gba/ppu/ppu.cpp index 0079e48bf..0939d3673 100644 --- a/ares/gba/ppu/ppu.cpp +++ b/ares/gba/ppu/ppu.cpp @@ -141,7 +141,11 @@ auto PPU::main() -> void { step(226); io.hblank = 0; if(++io.vcounter == 228) io.vcounter = 0; - if(io.vcounter > 1 && io.vcounter < 162) cpu.dmaHDMA(); + if(io.vcounter == 162) { + if(videoCapture) cpu.dma[3].enable = 0; + videoCapture = !videoCapture && cpu.dma[3].timingMode == 3 && cpu.dma[3].enable; + } + if(io.vcounter >= 2 && io.vcounter < 162 && videoCapture) cpu.dmaHDMA(); } auto PPU::frame() -> void { diff --git a/ares/gba/ppu/ppu.hpp b/ares/gba/ppu/ppu.hpp index 3a3843f4c..cf5d61377 100644 --- a/ares/gba/ppu/ppu.hpp +++ b/ares/gba/ppu/ppu.hpp @@ -255,6 +255,8 @@ private: i16 pc; i16 pd; } objectParam[32]; + + n1 videoCapture = 0; }; extern PPU ppu; diff --git a/ares/gba/ppu/serialization.cpp b/ares/gba/ppu/serialization.cpp index 7d0f9e044..8f7b94d88 100644 --- a/ares/gba/ppu/serialization.cpp +++ b/ares/gba/ppu/serialization.cpp @@ -16,6 +16,8 @@ auto PPU::serialize(serializer& s) -> void { s(io.vcompare); s(io.vcounter); + s(videoCapture); + s(Background::IO::mode); s(Background::IO::frame); s(Background::IO::mosaicWidth); diff --git a/ares/gba/system/serialization.cpp b/ares/gba/system/serialization.cpp index ce9dd53ea..e58e702b8 100644 --- a/ares/gba/system/serialization.cpp +++ b/ares/gba/system/serialization.cpp @@ -1,4 +1,4 @@ -static const string SerializerVersion = "v138"; +static const string SerializerVersion = "v138.1"; auto System::serialize(bool synchronize) -> serializer { if(synchronize) scheduler.enter(Scheduler::Mode::Synchronize);