diff --git a/src/app/CMakeLists.txt b/src/app/CMakeLists.txt index 03e7baa5..8a81fddb 100644 --- a/src/app/CMakeLists.txt +++ b/src/app/CMakeLists.txt @@ -6,6 +6,7 @@ add_executable( app/emu/audio/spc700.cc app/emu/audio/dsp.cc app/emu/video/ppu.cc + app/emu/memory/dma.cc app/emu/cpu.cc app/emu/snes.cc ${YAZE_APP_CORE_SRC} diff --git a/src/app/emu/memory/dma.cc b/src/app/emu/memory/dma.cc new file mode 100644 index 00000000..1f334f46 --- /dev/null +++ b/src/app/emu/memory/dma.cc @@ -0,0 +1,75 @@ +#include "app/emu/memory/dma.h" + +#include + +namespace yaze { +namespace app { +namespace emu { + +void DMA::StartDMATransfer(uint8_t channelMask) { + for (int i = 0; i < 8; ++i) { + if ((channelMask & (1 << i)) != 0) { + Channel& ch = channels[i]; + + // Validate channel parameters (e.g., DMAPn, BBADn, A1Tn, DASn) + // ... + + // Determine the transfer direction based on the DMAPn register + bool fromMemory = (ch.DMAPn & 0x80) != 0; + + // Determine the transfer size based on the DMAPn register + bool transferTwoBytes = (ch.DMAPn & 0x40) != 0; + + // Perform the DMA transfer based on the channel parameters + std::cout << "Starting DMA transfer for channel " << i << std::endl; + + for (uint16_t j = 0; j < ch.DASn; ++j) { + // Read a byte or two bytes from memory based on the transfer size + // ... + + // Write the data to the B-bus address (BBADn) if transferring from + // memory + // ... + + // Update the A1Tn register based on the transfer direction + if (fromMemory) { + ch.A1Tn += transferTwoBytes ? 2 : 1; + } else { + ch.A1Tn -= transferTwoBytes ? 2 : 1; + } + } + + // Update the channel registers after the transfer (e.g., A1Tn, DASn) + // ... + } + } + MDMAEN = channelMask; // Set the MDMAEN register to the channel mask +} + +void DMA::EnableHDMATransfers(uint8_t channelMask) { + for (int i = 0; i < 8; ++i) { + if ((channelMask & (1 << i)) != 0) { + Channel& ch = channels[i]; + + // Validate channel parameters (e.g., DMAPn, BBADn, A1Tn, A2An, NLTRn) + // ... + + // Perform the HDMA setup based on the channel parameters + std::cout << "Enabling HDMA transfer for channel " << i << std::endl; + + // Read the HDMA table from memory starting at A1Tn + // ... + + // Update the A2An register based on the HDMA table + // ... + + // Update the NLTRn register based on the HDMA table + // ... + } + } + HDMAEN = channelMask; // Set the HDMAEN register to the channel mask +} + +} // namespace emu +} // namespace app +} // namespace yaze \ No newline at end of file diff --git a/src/app/emu/snes.cc b/src/app/emu/snes.cc index 313f48f9..d6f1fbaa 100644 --- a/src/app/emu/snes.cc +++ b/src/app/emu/snes.cc @@ -58,70 +58,6 @@ void audio_callback(void* userdata, uint8_t* stream, int len) { } // namespace -void DMA::StartDMATransfer(uint8_t channelMask) { - for (int i = 0; i < 8; ++i) { - if ((channelMask & (1 << i)) != 0) { - Channel& ch = channels[i]; - - // Validate channel parameters (e.g., DMAPn, BBADn, A1Tn, DASn) - // ... - - // Determine the transfer direction based on the DMAPn register - bool fromMemory = (ch.DMAPn & 0x80) != 0; - - // Determine the transfer size based on the DMAPn register - bool transferTwoBytes = (ch.DMAPn & 0x40) != 0; - - // Perform the DMA transfer based on the channel parameters - std::cout << "Starting DMA transfer for channel " << i << std::endl; - - for (uint16_t j = 0; j < ch.DASn; ++j) { - // Read a byte or two bytes from memory based on the transfer size - // ... - - // Write the data to the B-bus address (BBADn) if transferring from - // memory - // ... - - // Update the A1Tn register based on the transfer direction - if (fromMemory) { - ch.A1Tn += transferTwoBytes ? 2 : 1; - } else { - ch.A1Tn -= transferTwoBytes ? 2 : 1; - } - } - - // Update the channel registers after the transfer (e.g., A1Tn, DASn) - // ... - } - } - MDMAEN = channelMask; // Set the MDMAEN register to the channel mask -} - -void DMA::EnableHDMATransfers(uint8_t channelMask) { - for (int i = 0; i < 8; ++i) { - if ((channelMask & (1 << i)) != 0) { - Channel& ch = channels[i]; - - // Validate channel parameters (e.g., DMAPn, BBADn, A1Tn, A2An, NLTRn) - // ... - - // Perform the HDMA setup based on the channel parameters - std::cout << "Enabling HDMA transfer for channel " << i << std::endl; - - // Read the HDMA table from memory starting at A1Tn - // ... - - // Update the A2An register based on the HDMA table - // ... - - // Update the NLTRn register based on the HDMA table - // ... - } - } - HDMAEN = channelMask; // Set the HDMAEN register to the channel mask -} - ROMInfo SNES::ReadRomHeader(uint32_t offset) { ROMInfo romInfo; @@ -289,9 +225,7 @@ void SNES::Run() { running_ = true; const double targetFPS = 60.0; // 60 frames per second - - const double frameTime = 1.0 / targetFPS; - + const double frame_time = 1.0 / targetFPS; double frame_accumulated_time = 0.0; auto last_time = std::chrono::high_resolution_clock::now(); @@ -316,9 +250,9 @@ void SNES::Run() { apu.UpdateClock(delta_time); apu.Update(); - if (frame_accumulated_time >= frameTime) { + if (frame_accumulated_time >= frame_time) { // renderer.Render(); - frame_accumulated_time -= frameTime; + frame_accumulated_time -= frame_time; } HandleInput(); @@ -376,7 +310,6 @@ void SNES::NmiIsr() { void SNES::VBlankRoutine() { // Execute code that needs to run during VBlank, such as transferring data to // the PPU - // ... } void SNES::BootAPUWithIPL() {