From 423f2f50697b25a0267b69e8b86c5e359bb0d32d Mon Sep 17 00:00:00 2001 From: tildearrow Date: Sat, 29 Jul 2023 16:04:39 -0500 Subject: [PATCH] OPN/A/B: implement 30xx on ExtCh issue #1113 --- src/engine/platform/genesisext.cpp | 15 ------------ src/engine/platform/ym2203ext.cpp | 39 +++++++++++++++++++++++++++++- src/engine/platform/ym2608ext.cpp | 39 +++++++++++++++++++++++++++++- src/engine/platform/ym2610bext.cpp | 39 +++++++++++++++++++++++++++++- src/engine/platform/ym2610ext.cpp | 39 +++++++++++++++++++++++++++++- 5 files changed, 152 insertions(+), 19 deletions(-) diff --git a/src/engine/platform/genesisext.cpp b/src/engine/platform/genesisext.cpp index 1a90adf92..7e9278daa 100644 --- a/src/engine/platform/genesisext.cpp +++ b/src/engine/platform/genesisext.cpp @@ -477,13 +477,6 @@ void DivPlatformGenesisExt::tick(bool sysTick) { if (chan[csmChan].active) { // CSM writeMask^=0xf0; } - /*printf( - "Mask: %c %c %c %c\n", - (writeMask&0x10)?'1':'-', - (writeMask&0x20)?'2':'-', - (writeMask&0x40)?'3':'-', - (writeMask&0x80)?'4':'-' - );*/ immWrite(0x28,writeMask); } } @@ -638,13 +631,6 @@ void DivPlatformGenesisExt::tick(bool sysTick) { if (chan[csmChan].active) { // CSM writeMask^=0xf0; } - /*printf( - "Mask: %c %c %c %c\n", - (writeMask&0x10)?'1':'-', - (writeMask&0x20)?'2':'-', - (writeMask&0x40)?'3':'-', - (writeMask&0x80)?'4':'-' - );*/ writeMask^=hardResetMask; immWrite(0x28,writeMask); writeMask^=hardResetMask; @@ -657,7 +643,6 @@ void DivPlatformGenesisExt::tick(bool sysTick) { for (int i=0; i<4; i++) { if (opChan[i].keyOn && opChan[i].hardReset) { // restore SL/RR - logV("eco: %d",extChanOffs); unsigned short baseAddr=chanOffs[extChanOffs]|opOffs[i]; DivInstrumentFM::Operator& op=chan[extChanOffs].state.op[i]; immWrite(baseAddr+ADDR_SL_RR,(op.rr&15)|(op.sl<<4)); diff --git a/src/engine/platform/ym2203ext.cpp b/src/engine/platform/ym2203ext.cpp index 6398ba7f1..8842b3cc8 100644 --- a/src/engine/platform/ym2203ext.cpp +++ b/src/engine/platform/ym2203ext.cpp @@ -355,6 +355,9 @@ int DivPlatformYM2203Ext::dispatch(DivCommand c) { } break; } + case DIV_CMD_FM_HARD_RESET: + opChan[ch].hardReset=c.value; + break; case DIV_CMD_GET_VOLMAX: return 127; break; @@ -385,6 +388,9 @@ static int opChanOffsH[4]={ }; void DivPlatformYM2203Ext::tick(bool sysTick) { + int hardResetElapsed=0; + bool mustHardReset=false; + if (extMode) { bool writeSomething=false; unsigned char writeMask=2; @@ -395,6 +401,12 @@ void DivPlatformYM2203Ext::tick(bool sysTick) { writeMask&=~(1<<(4+i)); opChan[i].keyOff=false; } + if (opChan[i].hardReset && opChan[i].keyOn) { + mustHardReset=true; + unsigned short baseAddr=chanOffs[extChanOffs]|opOffs[i]; + immWrite(baseAddr+ADDR_SL_RR,0x0f); + hardResetElapsed++; + } } if (writeSomething) { immWrite(0x28,writeMask); @@ -491,6 +503,7 @@ void DivPlatformYM2203Ext::tick(bool sysTick) { bool writeNoteOn=false; unsigned char writeMask=2; + unsigned char hardResetMask=0; if (extMode) for (int i=0; i<4; i++) { if (opChan[i].freqChanged) { if (parent->song.linearPitch==2) { @@ -517,12 +530,36 @@ void DivPlatformYM2203Ext::tick(bool sysTick) { writeNoteOn=true; if (opChan[i].mask) { writeMask|=1<<(4+i); + if (opChan[i].hardReset) { + hardResetMask|=1<<(4+i); + } + } + if (!opChan[i].hardReset) { + opChan[i].keyOn=false; } - opChan[i].keyOn=false; } } if (writeNoteOn) { + writeMask^=hardResetMask; immWrite(0x28,writeMask); + writeMask^=hardResetMask; + + // hard reset handling + if (mustHardReset) { + for (unsigned int i=hardResetElapsed; isong.linearPitch==2) { @@ -539,12 +552,36 @@ void DivPlatformYM2608Ext::tick(bool sysTick) { writeNoteOn=true; if (opChan[i].mask) { writeMask|=1<<(4+i); + if (opChan[i].hardReset) { + hardResetMask|=1<<(4+i); + } + } + if (!opChan[i].hardReset) { + opChan[i].keyOn=false; } - opChan[i].keyOn=false; } } if (writeNoteOn) { + writeMask^=hardResetMask; immWrite(0x28,writeMask); + writeMask^=hardResetMask; + + // hard reset handling + if (mustHardReset) { + for (unsigned int i=hardResetElapsed; isong.linearPitch==2) { @@ -535,12 +548,36 @@ void DivPlatformYM2610BExt::tick(bool sysTick) { writeNoteOn=true; if (opChan[i].mask) { writeMask|=1<<(4+i); + if (opChan[i].hardReset) { + hardResetMask|=1<<(4+i); + } + } + if (!opChan[i].hardReset) { + opChan[i].keyOn=false; } - opChan[i].keyOn=false; } } if (writeNoteOn) { + writeMask^=hardResetMask; immWrite(0x28,writeMask); + writeMask^=hardResetMask; + + // hard reset handling + if (mustHardReset) { + for (unsigned int i=hardResetElapsed; isong.linearPitch==2) { @@ -535,12 +548,36 @@ void DivPlatformYM2610Ext::tick(bool sysTick) { writeNoteOn=true; if (opChan[i].mask) { writeMask|=1<<(4+i); + if (opChan[i].hardReset) { + hardResetMask|=1<<(4+i); + } + } + if (!opChan[i].hardReset) { + opChan[i].keyOn=false; } - opChan[i].keyOn=false; } } if (writeNoteOn) { + writeMask^=hardResetMask; immWrite(0x28,writeMask); + writeMask^=hardResetMask; + + // hard reset handling + if (mustHardReset) { + for (unsigned int i=hardResetElapsed; i