#include "memorymap.hpp" #include "sh7091/serial.hpp" #include "systembus.hpp" #include "systembus_bits.hpp" #include "aica/aica.hpp" #include "example/arm/xm.bin.h" extern void * _binary_start __asm("_binary_example_arm_channel_bin_start"); extern void * _binary_size __asm("_binary_example_arm_channel_bin_size"); void wait() { uint32_t ffst = system.FFST; while ( ffst::holly_cpu_if_block_internal_write_buffer(ffst) | ffst::holly_g2_if_block_internal_write_buffer(ffst) | ffst::aica_internal_write_buffer(ffst)) { ffst = system.FFST; }; } constexpr uint32_t dma_address_mask = 0x1fffffe0; void g2_aica_dma(uint32_t g2_address, uint32_t system_address, int length) { // is DMAOR needed? sh7091.DMAC.DMAOR = dmaor::ddt::on_demand_data_transfer_mode /* on-demand data transfer mode */ | dmaor::pr::ch2_ch0_ch1_ch3 /* priority mode; CH2 > CH0 > CH1 > CH3 */ | dmaor::dme::operation_enabled_on_all_channels; /* DMAC master enable */ system.G2APRO = 0x4659007f; // disable protection system.ADSTAG = dma_address_mask & g2_address; // G2 address system.ADSTAR = dma_address_mask & system_address; // system memory address system.ADLEN = length / 32; // 32-byte units system.ADDIR = 0; // from root bus to G2 device system.ADTSEL = 0; // CPU controlled trigger system.ADEN = 1; // enable G2-DMA system.ADST = 1; // start G2-DMA } void g2_aica_dma_wait_complete() { // wait for maple DMA completion while ((system.ISTNRM & istnrm::end_of_dma_aica_dma) == 0); system.ISTNRM = istnrm::end_of_dma_aica_dma; } void main() { serial::init(0); const int start = reinterpret_cast(&_binary_start); const int size = reinterpret_cast(&_binary_size); /* const uint32_t * binary = reinterpret_cast(&_binary_example_arm_xm_bin_start); const uint32_t binary_size = reinterpret_cast(&_binary_example_arm_xm_bin_size); wait(); aica_sound.common.vreg_armrst = aica::vreg_armrst::ARMRST(1); wait(); aica_sound.common.dmea0_mrwinh = aica::dmea0_mrwinh::MRWINH(0b0111); for (uint32_t i = 0; i < binary_size / 4; i++) { // copy while (aica_wave_memory[i] != binary[i]) { wait(); aica_wave_memory[i] = binary[i]; } } wait(); aica_sound.common.dmea0_mrwinh = aica::dmea0_mrwinh::MRWINH(0b0001); wait(); aica_sound.common.vreg_armrst = aica::vreg_armrst::ARMRST(0); wait(); aica_sound.common.afsel_mslc_mobuf = aica::afsel_mslc_mobuf::MSLC(0); serial::string("mrwinh: "); wait(); serial::integer(aica_sound.common.MRWINH()); int last_dram = -1; while (1) { wait(); int read = aica_wave_memory[0]; if (read != last_dram) { serial::integer(read); } last_dram = read; }; */ }