diff options
Diffstat (limited to 'src/SPI.cpp')
-rw-r--r-- | src/SPI.cpp | 105 |
1 files changed, 100 insertions, 5 deletions
diff --git a/src/SPI.cpp b/src/SPI.cpp index 12e9291..7c49555 100644 --- a/src/SPI.cpp +++ b/src/SPI.cpp @@ -1,5 +1,5 @@ /* - Copyright 2016-2017 StapleButter + Copyright 2016-2019 StapleButter This file is part of melonDS. @@ -22,6 +22,7 @@ #include "Config.h" #include "NDS.h" #include "SPI.h" +#include "melon_fopen.h" namespace SPI_Firmware @@ -89,7 +90,7 @@ void Reset() if (Firmware) delete[] Firmware; Firmware = NULL; - FILE* f = Config::GetConfigFile("firmware.bin", "rb"); + FILE* f = melon_fopen_local("firmware.bin", "rb"); if (!f) { printf("firmware.bin not found\n"); @@ -129,7 +130,7 @@ void Reset() // take a backup char* firmbkp = "firmware.bin.bak"; - f = Config::GetConfigFile(firmbkp, "rb"); + f = melon_fopen_local(firmbkp, "rb"); if (f) fclose(f); else { @@ -193,6 +194,22 @@ void Reset() StatusReg = 0x00; } +void DoSavestate(Savestate* file) +{ + file->Section("SPFW"); + + // CHECKME/TODO: trust the firmware to stay the same????? + // embedding the whole firmware in the savestate would be derpo tho?? + + file->Var32(&Hold); + file->Var8(&CurCmd); + file->Var32(&DataPos); + file->Var8(&Data); + + file->Var8(&StatusReg); + file->Var32(&Addr); +} + void SetupDirectBoot() { NDS::ARM9Write32(0x027FF864, 0); @@ -308,7 +325,7 @@ void Write(u8 val, u32 hold) if (!hold && (CurCmd == 0x02 || CurCmd == 0x0A)) { - FILE* f = Config::GetConfigFile("firmware.bin", "r+b"); + FILE* f = melon_fopen_local("firmware.bin", "r+b"); if (f) { u32 cutoff = 0x7FA00 & FirmwareMask; @@ -360,6 +377,19 @@ void Reset() RegMasks[4] = 0x0F; } +void DoSavestate(Savestate* file) +{ + file->Section("SPPW"); + + file->Var32(&Hold); + file->Var32(&DataPos); + file->Var8(&Index); + file->Var8(&Data); + + file->VarArray(Registers, 8); + file->VarArray(RegMasks, 8); // is that needed?? +} + u8 Read() { return Data; @@ -423,6 +453,9 @@ u16 ConvResult; u16 TouchX, TouchY; +s16 MicBuffer[1024]; +int MicBufferLen; + bool Init() { @@ -439,6 +472,19 @@ void Reset() Data = 0; ConvResult = 0; + + MicBufferLen = 0; +} + +void DoSavestate(Savestate* file) +{ + file->Section("SPTS"); + + file->Var32(&DataPos); + file->Var8(&ControlByte); + file->Var8(&Data); + + file->Var16(&ConvResult); } void SetTouchCoords(u16 x, u16 y) @@ -456,6 +502,19 @@ void SetTouchCoords(u16 x, u16 y) TouchY <<= 4; } +void MicInputFrame(s16* data, int samples) +{ + if (!data) + { + MicBufferLen = 0; + return; + } + + if (samples > 1024) samples = 1024; + memcpy(MicBuffer, data, samples*sizeof(s16)); + MicBufferLen = samples; +} + u8 Read() { return Data; @@ -479,7 +538,31 @@ void Write(u8 val, u32 hold) { case 0x10: ConvResult = TouchY; break; case 0x50: ConvResult = TouchX; break; - case 0x60: ConvResult = 0x800; break; // TODO: mic + + case 0x60: + { + if (MicBufferLen == 0) + ConvResult = 0x800; + else + { + // 560190 cycles per frame + u32 cyclepos = (u32)NDS::GetSysClockCycles(2); + u32 samplepos = (cyclepos * MicBufferLen) / 560190; + if (samplepos >= MicBufferLen) samplepos = MicBufferLen-1; + s16 sample = MicBuffer[samplepos]; + + // make it louder + //if (sample > 0x3FFF) sample = 0x7FFF; + //else if (sample < -0x4000) sample = -0x8000; + //else sample <<= 1; + + // make it unsigned 12-bit + sample ^= 0x8000; + ConvResult = sample >> 4; + } + } + break; + default: ConvResult = 0xFFF; break; } @@ -526,6 +609,18 @@ void Reset() SPI_TSC::Reset(); } +void DoSavestate(Savestate* file) +{ + file->Section("SPIG"); + + file->Var16(&Cnt); + file->Var32(&CurDevice); + + SPI_Firmware::DoSavestate(file); + SPI_Powerman::DoSavestate(file); + SPI_TSC::DoSavestate(file); +} + void WriteCnt(u16 val) { |