From ce2661df6649f5f16f62529ce0be18d9bcb9fbd2 Mon Sep 17 00:00:00 2001 From: tildearrow Date: Thu, 6 Jul 2023 18:29:29 -0500 Subject: [PATCH 01/13] audio issue debugging --- src/audio/sdlAudio.cpp | 10 ++++++++-- src/engine/engine.h | 4 ++++ src/engine/playback.cpp | 4 ++++ src/gui/debugWindow.cpp | 28 ++++++++++++++++++++++++++++ 4 files changed, 44 insertions(+), 2 deletions(-) diff --git a/src/audio/sdlAudio.cpp b/src/audio/sdlAudio.cpp index 6d0ceff0..5d07921e 100644 --- a/src/audio/sdlAudio.cpp +++ b/src/audio/sdlAudio.cpp @@ -127,14 +127,20 @@ bool TAAudioSDL::init(TAAudioDesc& request, TAAudioDesc& response) { ac.callback=taSDLProcess; ac.userdata=this; - ai=SDL_OpenAudioDevice(request.deviceName.empty()?NULL:request.deviceName.c_str(),0,&ac,&ar,SDL_AUDIO_ALLOW_FREQUENCY_CHANGE); + ai=SDL_OpenAudioDevice(request.deviceName.empty()?NULL:request.deviceName.c_str(),0,&ac,&ar,0); if (ai==0) { logE("could not open audio device: %s",SDL_GetError()); return false; } + const char* backendName=SDL_GetCurrentAudioDriver(); + desc.deviceName=request.deviceName; - desc.name=""; + if (backendName==NULL) { + desc.name=""; + } else { + desc.name=backendName; + } desc.rate=ar.freq; desc.inChans=0; desc.outChans=ar.channels; diff --git a/src/engine/engine.h b/src/engine/engine.h index aceee308..e4b3e56a 100644 --- a/src/engine/engine.h +++ b/src/engine/engine.h @@ -570,6 +570,7 @@ class DivEngine { float oscSize; int oscReadPos, oscWritePos; int tickMult; + int lastNBIns, lastNBOuts, lastNBSize; std::atomic processTime; void runExportThread(); @@ -1252,6 +1253,9 @@ class DivEngine { oscReadPos(0), oscWritePos(0), tickMult(1), + lastNBIns(0), + lastNBOuts(0), + lastNBSize(0), processTime(0), yrw801ROM(NULL), tg100ROM(NULL), diff --git a/src/engine/playback.cpp b/src/engine/playback.cpp index 798de87b..7825e188 100644 --- a/src/engine/playback.cpp +++ b/src/engine/playback.cpp @@ -1694,6 +1694,10 @@ void DivEngine::runMidiTime(int totalCycles) { } void DivEngine::nextBuf(float** in, float** out, int inChans, int outChans, unsigned int size) { + lastNBIns=inChans; + lastNBOuts=outChans; + lastNBSize=size; + if (!size) { logW("nextBuf called with size 0!"); return; diff --git a/src/gui/debugWindow.cpp b/src/gui/debugWindow.cpp index b9dc6c42..bfeb9067 100644 --- a/src/gui/debugWindow.cpp +++ b/src/gui/debugWindow.cpp @@ -388,6 +388,34 @@ void FurnaceGUI::drawDebug() { ImGui::Text("System Managed Scale: %d",sysManagedScale); ImGui::TreePop(); } + if (ImGui::TreeNode("Audio Debug")) { + TAAudioDesc& audioWant=e->getAudioDescWant(); + TAAudioDesc& audioGot=e->getAudioDescGot(); + + ImGui::Text("want:"); + ImGui::Text("- name: %s",audioWant.name.c_str()); + ImGui::Text("- device name: %s",audioWant.deviceName.c_str()); + ImGui::Text("- rate: %f",audioWant.rate); + ImGui::Text("- buffer size: %d",audioWant.bufsize); + ImGui::Text("- fragments: %d",audioWant.fragments); + ImGui::Text("- inputs: %d",audioWant.inChans); + ImGui::Text("- outputs: %d",audioWant.outChans); + ImGui::Text("- format: %d",audioWant.outFormat); + + ImGui::Text("got:"); + ImGui::Text("- name: %s",audioGot.name.c_str()); + ImGui::Text("- device name: %s",audioGot.deviceName.c_str()); + ImGui::Text("- rate: %f",audioGot.rate); + ImGui::Text("- buffer size: %d",audioGot.bufsize); + ImGui::Text("- fragments: %d",audioGot.fragments); + ImGui::Text("- inputs: %d",audioGot.inChans); + ImGui::Text("- outputs: %d",audioGot.outChans); + ImGui::Text("- format: %d",audioGot.outFormat); + + ImGui::Text("last call to nextBuf(): in %d, out %d, size %d",e->lastNBIns,e->lastNBOuts,e->lastNBSize); + + ImGui::TreePop(); + } if (ImGui::TreeNode("Visualizer Debug")) { if (ImGui::BeginTable("visX",3,ImGuiTableFlags_Borders)) { ImGui::TableNextRow(ImGuiTableRowFlags_Headers); From 5c97f9981a9b184c952d88df764525d1e771beef Mon Sep 17 00:00:00 2001 From: tildearrow Date: Thu, 6 Jul 2023 21:14:25 -0500 Subject: [PATCH 02/13] add option to change SDL audio driver --- src/engine/engine.cpp | 11 ++++++++++- src/gui/gui.cpp | 13 +++++++++++++ src/gui/gui.h | 5 ++++- src/gui/settings.cpp | 27 +++++++++++++++++++++++++++ 4 files changed, 54 insertions(+), 2 deletions(-) diff --git a/src/engine/engine.cpp b/src/engine/engine.cpp index 1aa8188e..c7b5ac9e 100644 --- a/src/engine/engine.cpp +++ b/src/engine/engine.cpp @@ -4586,6 +4586,15 @@ bool DivEngine::initAudioBackend() { } } +#ifdef HAVE_SDL2 + if (audioEngine==DIV_AUDIO_SDL) { + String audioDriver=getConfString("sdlAudioDriver",""); + if (!audioDriver.empty()) { + SDL_SetHint("SDL_HINT_AUDIODRIVER",audioDriver.c_str()); + } + } +#endif + lowQuality=getConfInt("audioQuality",0); forceMono=getConfInt("forceMono",0); clampSamples=getConfInt("clampSamples",0); @@ -4594,7 +4603,7 @@ bool DivEngine::initAudioBackend() { midiOutClock=getConfInt("midiOutClock",0); midiOutTime=getConfInt("midiOutTime",0); midiOutTimeRate=getConfInt("midiOutTimeRate",0); - midiOutProgramChange = getConfInt("midiOutProgramChange",0); + midiOutProgramChange=getConfInt("midiOutProgramChange",0); midiOutMode=getConfInt("midiOutMode",DIV_MIDI_MODE_NOTE); if (metroVol<0.0f) metroVol=0.0f; if (metroVol>2.0f) metroVol=2.0f; diff --git a/src/gui/gui.cpp b/src/gui/gui.cpp index a1a5cb84..3e7ed027 100644 --- a/src/gui/gui.cpp +++ b/src/gui/gui.cpp @@ -6329,6 +6329,19 @@ bool FurnaceGUI::init() { } #endif + int numDriversA=SDL_GetNumAudioDrivers(); + if (numDriversA<0) { + logW("could not list audio drivers! %s",SDL_GetError()); + } else { + for (int i=0; i recentFile; std::vector makeInsTypeList; std::vector availRenderDrivers; + std::vector availAudioDrivers; bool quit, warnQuit, willCommit, edit, modified, displayError, displayExporting, vgmExportLoop, zsmExportLoop, vgmExportPatternHints; bool vgmExportDirectStream, displayInsTypeList; @@ -1534,6 +1535,7 @@ class FurnaceGUI { String macroRelLabel; String emptyLabel; String emptyLabel2; + String sdlAudioDriver; DivConfig initialSys; Settings(): @@ -1686,7 +1688,8 @@ class FurnaceGUI { noteRelLabel("==="), macroRelLabel("REL"), emptyLabel("..."), - emptyLabel2("..") {} + emptyLabel2(".."), + sdlAudioDriver("") {} } settings; struct Tutorial { diff --git a/src/gui/settings.cpp b/src/gui/settings.cpp index ab06d74f..6c70a891 100644 --- a/src/gui/settings.cpp +++ b/src/gui/settings.cpp @@ -807,6 +807,25 @@ void FurnaceGUI::drawSettings() { } #endif + if (settings.audioEngine==DIV_AUDIO_SDL) { + ImGui::Text("Driver"); + ImGui::SameLine(); + if (ImGui::BeginCombo("##SDLADriver",settings.sdlAudioDriver.empty()?"Automatic":settings.sdlAudioDriver.c_str())) { + if (ImGui::Selectable("Automatic",settings.sdlAudioDriver.empty())) { + settings.sdlAudioDriver=""; + } + for (String& i: availAudioDrivers) { + if (ImGui::Selectable(i.c_str(),i==settings.sdlAudioDriver)) { + settings.sdlAudioDriver=i; + } + } + ImGui::EndCombo(); + } + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip("you may need to restart Furnace for this setting to take effect."); + } + } + ImGui::Text("Device"); ImGui::SameLine(); String audioDevName=settings.audioDevice.empty()?"":settings.audioDevice; @@ -1324,6 +1343,9 @@ void FurnaceGUI::drawSettings() { #endif ImGui::EndCombo(); } + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip("you may need to restart Furnace for this setting to take effect."); + } if (curRenderBackend=="SDL") { if (ImGui::BeginCombo("Render driver",settings.renderDriver.empty()?"Automatic":settings.renderDriver.c_str())) { if (ImGui::Selectable("Automatic",settings.renderDriver.empty())) { @@ -1336,6 +1358,9 @@ void FurnaceGUI::drawSettings() { } ImGui::EndCombo(); } + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip("you may need to restart Furnace for this setting to take effect."); + } } bool dpiScaleAuto=(settings.dpiScale<0.5f); @@ -2638,6 +2663,7 @@ void FurnaceGUI::syncSettings() { settings.midiOutDevice=e->getConfString("midiOutDevice",""); settings.c163Name=e->getConfString("c163Name",DIV_C163_DEFAULT_NAME); settings.renderDriver=e->getConfString("renderDriver",""); + settings.sdlAudioDriver=e->getConfString("sdlAudioDriver",""); settings.audioQuality=e->getConfInt("audioQuality",0); settings.audioBufSize=e->getConfInt("audioBufSize",1024); settings.audioRate=e->getConfInt("audioRate",44100); @@ -2986,6 +3012,7 @@ void FurnaceGUI::commitSettings() { e->setConf("midiOutDevice",settings.midiOutDevice); e->setConf("c163Name",settings.c163Name); e->setConf("renderDriver",settings.renderDriver); + e->setConf("sdlAudioDriver",settings.sdlAudioDriver); e->setConf("audioQuality",settings.audioQuality); e->setConf("audioBufSize",settings.audioBufSize); e->setConf("audioRate",settings.audioRate); From f841025ce6cfc0b4030f57a0c7110dea296a5832 Mon Sep 17 00:00:00 2001 From: tildearrow Date: Fri, 7 Jul 2023 02:21:13 -0500 Subject: [PATCH 03/13] Game Boy: fix wave corruption this time for real thanks jvsTSX --- src/engine/platform/gb.cpp | 2 +- src/gui/about.cpp | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/src/engine/platform/gb.cpp b/src/engine/platform/gb.cpp index 683f9721..c5c66092 100644 --- a/src/engine/platform/gb.cpp +++ b/src/engine/platform/gb.cpp @@ -322,7 +322,7 @@ void DivPlatformGB::tick(bool sysTick) { rWrite(16+i*5+4,((chan[i].keyOn||chan[i].keyOff)?0x80:0x00)|((chan[i].soundLen<64)<<6)); } else { rWrite(16+i*5+3,(2048-chan[i].freq)&0xff); - rWrite(16+i*5+4,(((2048-chan[i].freq)>>8)&7)|((chan[i].keyOn||chan[i].keyOff)?0x80:0x00)|((chan[i].soundLen<63)<<6)); + rWrite(16+i*5+4,(((2048-chan[i].freq)>>8)&7)|((chan[i].keyOn||(chan[i].keyOff && i!=2))?0x80:0x00)|((chan[i].soundLen<63)<<6)); } if (enoughAlready) { // more compat garbage rWrite(16+i*5+1,((chan[i].duty&3)<<6)|(63-(chan[i].soundLen&63))); diff --git a/src/gui/about.cpp b/src/gui/about.cpp index 2aef20b9..7afd015c 100644 --- a/src/gui/about.cpp +++ b/src/gui/about.cpp @@ -134,6 +134,7 @@ const char* aboutLine[]={ "fd", "GENATARi", "host12prog", + "jvsTSX", "Lumigado", "Lunathir", "plane", From aececf352f671b44cf5e723045a4b7f55490bdeb Mon Sep 17 00:00:00 2001 From: tildearrow Date: Fri, 7 Jul 2023 02:25:32 -0500 Subject: [PATCH 04/13] Game Boy: fix 10xx turning wave channel on when it's off --- src/engine/platform/gb.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/engine/platform/gb.cpp b/src/engine/platform/gb.cpp index c5c66092..9b565cdc 100644 --- a/src/engine/platform/gb.cpp +++ b/src/engine/platform/gb.cpp @@ -466,7 +466,9 @@ int DivPlatformGB::dispatch(DivCommand c) { if (c.chan!=2) break; chan[c.chan].wave=c.value; ws.changeWave1(chan[c.chan].wave); - chan[c.chan].keyOn=true; + if (chan[c.chan].active) { + chan[c.chan].keyOn=true; + } break; case DIV_CMD_NOTE_PORTA: { int destFreq=NOTE_PERIODIC(c.value2); From 97fec35b00b98a3a7d2c8bb2160d9ea6cac3a2bc Mon Sep 17 00:00:00 2001 From: tildearrow Date: Fri, 7 Jul 2023 03:15:09 -0500 Subject: [PATCH 05/13] GUI: fix hidden channels breaking visualizer --- src/gui/pattern.cpp | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/gui/pattern.cpp b/src/gui/pattern.cpp index a34a856d..6e2fc1ed 100644 --- a/src/gui/pattern.cpp +++ b/src/gui/pattern.cpp @@ -133,17 +133,20 @@ inline void FurnaceGUI::patternRow(int i, bool isPlaying, float lineHeight, int } ImGui::PopStyleColor(); // for each column + int mustSetXOf=0; for (int j=0; j