BSNESv115+: apply patch to fix $4203 mul/div behavior

see https://github.com/bsnes-emu/bsnes/issues/256 or https://forums.nesdev.org/viewtopic.php?t=24087 for context
This commit is contained in:
Morilli 2022-12-11 17:18:01 +01:00
parent 74b37ab947
commit 837592ca11
4 changed files with 20 additions and 6 deletions

Binary file not shown.

View File

@ -165,7 +165,9 @@ private:
struct ALU {
uint mpyctr = 0;
uint mpylast = 0;
uint divctr = 0;
uint divlast = 0;
uint shift = 0;
} alu;

View File

@ -159,8 +159,10 @@ auto CPU::writeCPU(uint addr, uint8 data) -> void {
io.rddiv = io.wrmpyb << 8 | io.wrmpya;
if(!configuration.hacks.cpu.fastMath) {
alu.mpyctr = 8; //perform multiplication over the next eight cycles
alu.shift = io.wrmpyb;
if (!alu.mpylast) {
alu.mpyctr = 8; //perform multiplication over the next eight cycles
alu.shift = io.wrmpyb;
}
} else {
io.rdmpy = io.wrmpya * io.wrmpyb;
}
@ -178,12 +180,14 @@ auto CPU::writeCPU(uint addr, uint8 data) -> void {
io.rdmpy = io.wrdiva;
if(alu.mpyctr || alu.divctr) return;
io.wrdivb = data;
if(!configuration.hacks.cpu.fastMath) {
alu.divctr = 16; //perform division over the next sixteen cycles
alu.shift = io.wrdivb << 16;
if (!alu.divlast) {
io.wrdivb = data;
alu.divctr = 16; //perform division over the next sixteen cycles
alu.shift = io.wrdivb << 16;
}
} else {
io.wrdivb = data;
if(io.wrdivb) {
io.rddiv = io.wrdiva / io.wrdivb;
io.rdmpy = io.wrdiva % io.wrdivb;

View File

@ -143,13 +143,19 @@ auto CPU::scanline() -> void {
auto CPU::aluEdge() -> void {
if(alu.mpyctr) {
alu.mpyctr--;
if (!alu.mpyctr)
alu.mpylast = 1;
if(io.rddiv & 1) io.rdmpy += alu.shift;
io.rddiv >>= 1;
alu.shift <<= 1;
}
else
alu.mpylast = 0;
if(alu.divctr) {
alu.divctr--;
if (!alu.divctr)
alu.divlast = 1;
io.rddiv <<= 1;
alu.shift >>= 1;
if(io.rdmpy >= alu.shift) {
@ -157,6 +163,8 @@ auto CPU::aluEdge() -> void {
io.rddiv |= 1;
}
}
else
alu.divlast = 0;
}
auto CPU::dmaEdge() -> void {