VGM export: fix NES DPCM
This commit is contained in:
parent
1cabe743d6
commit
defbeae704
|
@ -583,7 +583,7 @@ class DivEngine {
|
||||||
void processRow(int i, bool afterDelay);
|
void processRow(int i, bool afterDelay);
|
||||||
void nextOrder();
|
void nextOrder();
|
||||||
void nextRow();
|
void nextRow();
|
||||||
void performVGMWrite(SafeWriter* w, DivSystem sys, DivRegWrite& write, int streamOff, double* loopTimer, double* loopFreq, int* loopSample, bool* sampleDir, bool isSecond, int* pendingFreq, int* playingSample, int* setPos, unsigned int* sampleOff8, unsigned int* sampleLen8, size_t bankOffset, bool directStream, bool* sampleStoppable);
|
void performVGMWrite(SafeWriter* w, DivSystem sys, DivRegWrite& write, int streamOff, double* loopTimer, double* loopFreq, int* loopSample, bool* sampleDir, bool isSecond, int* pendingFreq, int* playingSample, int* setPos, unsigned int* sampleOff8, unsigned int* sampleLen8, size_t bankOffset, bool directStream, bool* sampleStoppable, bool dpcm07, DivDispatch** writeNES);
|
||||||
// returns true if end of song.
|
// returns true if end of song.
|
||||||
bool nextTick(bool noAccum=false, bool inhibitLowLat=false);
|
bool nextTick(bool noAccum=false, bool inhibitLowLat=false);
|
||||||
bool perSystemEffect(int ch, unsigned char effect, unsigned char effectVal);
|
bool perSystemEffect(int ch, unsigned char effect, unsigned char effectVal);
|
||||||
|
|
|
@ -24,7 +24,7 @@
|
||||||
|
|
||||||
// this function is so long
|
// this function is so long
|
||||||
// may as well make it something else
|
// may as well make it something else
|
||||||
void DivEngine::performVGMWrite(SafeWriter* w, DivSystem sys, DivRegWrite& write, int streamOff, double* loopTimer, double* loopFreq, int* loopSample, bool* sampleDir, bool isSecond, int* pendingFreq, int* playingSample, int* setPos, unsigned int* sampleOff8, unsigned int* sampleLen8, size_t bankOffset, bool directStream, bool* sampleStoppable) {
|
void DivEngine::performVGMWrite(SafeWriter* w, DivSystem sys, DivRegWrite& write, int streamOff, double* loopTimer, double* loopFreq, int* loopSample, bool* sampleDir, bool isSecond, int* pendingFreq, int* playingSample, int* setPos, unsigned int* sampleOff8, unsigned int* sampleLen8, size_t bankOffset, bool directStream, bool* sampleStoppable, bool dpcm07, DivDispatch** writeNES) {
|
||||||
unsigned char baseAddr1=isSecond?0xa0:0x50;
|
unsigned char baseAddr1=isSecond?0xa0:0x50;
|
||||||
unsigned char baseAddr2=isSecond?0x80:0;
|
unsigned char baseAddr2=isSecond?0x80:0;
|
||||||
unsigned short baseAddr2S=isSecond?0x8000:0;
|
unsigned short baseAddr2S=isSecond?0x8000:0;
|
||||||
|
@ -712,6 +712,7 @@ void DivEngine::performVGMWrite(SafeWriter* w, DivSystem sys, DivRegWrite& write
|
||||||
if (write.addr==0xffff0004) { // switch sample bank
|
if (write.addr==0xffff0004) { // switch sample bank
|
||||||
switch (sys) {
|
switch (sys) {
|
||||||
case DIV_SYSTEM_NES: {
|
case DIV_SYSTEM_NES: {
|
||||||
|
if (dpcm07) {
|
||||||
unsigned int bankAddr=bankOffset+(write.val<<14);
|
unsigned int bankAddr=bankOffset+(write.val<<14);
|
||||||
w->writeC(0x68);
|
w->writeC(0x68);
|
||||||
w->writeC(0x66);
|
w->writeC(0x66);
|
||||||
|
@ -725,6 +726,23 @@ void DivEngine::performVGMWrite(SafeWriter* w, DivSystem sys, DivRegWrite& write
|
||||||
w->writeC(0x00);
|
w->writeC(0x00);
|
||||||
w->writeC(0x40);
|
w->writeC(0x40);
|
||||||
w->writeC(0x00);
|
w->writeC(0x00);
|
||||||
|
} else {
|
||||||
|
// write the whole damn bank.
|
||||||
|
// this code looks like a mess because it is a hack.
|
||||||
|
// don't blame me if your VGM ends up being over a gigabyte!
|
||||||
|
size_t howMuchWillBeWritten=writeNES[isSecond?1:0]->getSampleMemUsage();
|
||||||
|
// refuse to switch if we're going out of bounds
|
||||||
|
if ((write.val<<14)>=howMuchWillBeWritten) break;
|
||||||
|
howMuchWillBeWritten-=(write.val<<14);
|
||||||
|
if (howMuchWillBeWritten>16384) howMuchWillBeWritten=16384;
|
||||||
|
w->writeC(0x67);
|
||||||
|
w->writeC(0x66);
|
||||||
|
w->writeC(0xc2);
|
||||||
|
w->writeI(howMuchWillBeWritten+2);
|
||||||
|
// data
|
||||||
|
w->writeS(0xc000);
|
||||||
|
w->write(&(((unsigned char*)writeNES[isSecond?1:0]->getSampleMem())[write.val<<14]),howMuchWillBeWritten);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
|
@ -2387,6 +2405,7 @@ SafeWriter* DivEngine::saveVGM(bool* sysToExport, bool loop, int version, bool p
|
||||||
w->write(writeK053260[i]->getSampleMem(),writeK053260[i]->getSampleMemUsage());
|
w->write(writeK053260[i]->getSampleMem(),writeK053260[i]->getSampleMemUsage());
|
||||||
}
|
}
|
||||||
if (writeNES[i]!=NULL && writeNES[i]->getSampleMemUsage()>0) {
|
if (writeNES[i]!=NULL && writeNES[i]->getSampleMemUsage()>0) {
|
||||||
|
if (dpcm07) {
|
||||||
size_t howMuchWillBeWritten=writeNES[i]->getSampleMemUsage();
|
size_t howMuchWillBeWritten=writeNES[i]->getSampleMemUsage();
|
||||||
w->writeC(0x67);
|
w->writeC(0x67);
|
||||||
w->writeC(0x66);
|
w->writeC(0x66);
|
||||||
|
@ -2409,6 +2428,18 @@ SafeWriter* DivEngine::saveVGM(bool* sysToExport, bool loop, int version, bool p
|
||||||
w->writeC(0x00);
|
w->writeC(0x00);
|
||||||
w->writeC(0x40);
|
w->writeC(0x40);
|
||||||
w->writeC(0x00);
|
w->writeC(0x00);
|
||||||
|
} else {
|
||||||
|
// write the first bank
|
||||||
|
size_t howMuchWillBeWritten=writeNES[i]->getSampleMemUsage();
|
||||||
|
if (howMuchWillBeWritten>16384) howMuchWillBeWritten=16384;
|
||||||
|
w->writeC(0x67);
|
||||||
|
w->writeC(0x66);
|
||||||
|
w->writeC(0xc2);
|
||||||
|
w->writeI(howMuchWillBeWritten+2);
|
||||||
|
// data
|
||||||
|
w->writeS(0xc000);
|
||||||
|
w->write(writeNES[i]->getSampleMem(),howMuchWillBeWritten);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2799,7 +2830,7 @@ SafeWriter* DivEngine::saveVGM(bool* sysToExport, bool loop, int version, bool p
|
||||||
lastOne=i.second.time;
|
lastOne=i.second.time;
|
||||||
}
|
}
|
||||||
// write write
|
// write write
|
||||||
performVGMWrite(w,song.system[i.first],i.second.write,streamIDs[i.first],loopTimer,loopFreq,loopSample,sampleDir,isSecond[i.first],pendingFreq,playingSample,setPos,sampleOff8,sampleLen8,bankOffset[i.first],directStream,sampleStoppable);
|
performVGMWrite(w,song.system[i.first],i.second.write,streamIDs[i.first],loopTimer,loopFreq,loopSample,sampleDir,isSecond[i.first],pendingFreq,playingSample,setPos,sampleOff8,sampleLen8,bankOffset[i.first],directStream,sampleStoppable,dpcm07,writeNES);
|
||||||
writeCount++;
|
writeCount++;
|
||||||
}
|
}
|
||||||
sortedWrites.clear();
|
sortedWrites.clear();
|
||||||
|
|
Loading…
Reference in a new issue