mirror of https://github.com/mgba-emu/mgba.git
GBA SIO: Fix normal mode SI/SO semantics (fixes #2925)
This commit is contained in:
parent
1acb7dfa9e
commit
a51cb3f921
1
CHANGES
1
CHANGES
|
@ -8,6 +8,7 @@ Emulation fixes:
|
||||||
- GBA Audio: Fix sample timing drifting when changing sample interval
|
- GBA Audio: Fix sample timing drifting when changing sample interval
|
||||||
- GBA Audio: Fix initial channel 3 wave RAM (fixes mgba.io/i/2947)
|
- GBA Audio: Fix initial channel 3 wave RAM (fixes mgba.io/i/2947)
|
||||||
- GBA BIOS: Fix clobbering registers with word-sized CpuSet
|
- GBA BIOS: Fix clobbering registers with word-sized CpuSet
|
||||||
|
- GBA SIO: Fix normal mode SI/SO semantics (fixes mgba.io/i/2925)
|
||||||
Other fixes:
|
Other fixes:
|
||||||
- mGUI: Fix cases where an older save state screenshot would be shown (fixes mgba.io/i/2183)
|
- mGUI: Fix cases where an older save state screenshot would be shown (fixes mgba.io/i/2183)
|
||||||
Misc:
|
Misc:
|
||||||
|
|
|
@ -127,10 +127,10 @@ bool GBASIOLockstepNodeLoad(struct GBASIODriver* driver) {
|
||||||
break;
|
break;
|
||||||
case SIO_NORMAL_8:
|
case SIO_NORMAL_8:
|
||||||
case SIO_NORMAL_32:
|
case SIO_NORMAL_32:
|
||||||
if (ATOMIC_ADD(node->p->attachedNormal, 1) > node->id + 1 && node->id < 3) {
|
if (ATOMIC_ADD(node->p->attachedNormal, 1) > node->id + 1 && node->id > 0) {
|
||||||
node->d.p->siocnt = GBASIONormalSetSi(node->d.p->siocnt, GBASIONormalGetIdleSo(node->p->players[node->id + 1]->d.p->siocnt));
|
node->d.p->siocnt = GBASIONormalSetSi(node->d.p->siocnt, GBASIONormalGetIdleSo(node->p->players[node->id - 1]->d.p->siocnt));
|
||||||
} else {
|
} else {
|
||||||
node->d.p->siocnt = GBASIONormalFillSi(node->d.p->siocnt);
|
node->d.p->siocnt = GBASIONormalClearSi(node->d.p->siocnt);
|
||||||
}
|
}
|
||||||
node->d.writeRegister = GBASIOLockstepNodeNormalWriteRegister;
|
node->d.writeRegister = GBASIOLockstepNodeNormalWriteRegister;
|
||||||
break;
|
break;
|
||||||
|
@ -514,20 +514,20 @@ static uint16_t GBASIOLockstepNodeNormalWriteRegister(struct GBASIODriver* drive
|
||||||
int attached;
|
int attached;
|
||||||
ATOMIC_LOAD(attached, node->p->attachedNormal);
|
ATOMIC_LOAD(attached, node->p->attachedNormal);
|
||||||
value &= 0xFF8B;
|
value &= 0xFF8B;
|
||||||
if (node->id < 3 && attached > node->id + 1) {
|
if (node->id > 0) {
|
||||||
value = GBASIONormalSetSi(value, GBASIONormalGetIdleSo(node->p->players[node->id + 1]->d.p->siocnt));
|
value = GBASIONormalSetSi(value, GBASIONormalGetIdleSo(node->p->players[node->id - 1]->d.p->siocnt));
|
||||||
} else {
|
} else {
|
||||||
value = GBASIONormalFillSi(value);
|
value = GBASIONormalClearSi(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
enum mLockstepPhase transferActive;
|
enum mLockstepPhase transferActive;
|
||||||
ATOMIC_LOAD(transferActive, node->p->d.transferActive);
|
ATOMIC_LOAD(transferActive, node->p->d.transferActive);
|
||||||
if (node->id > 0 && transferActive == TRANSFER_IDLE) {
|
if (node->id < 3 && attached > node->id + 1 && transferActive == TRANSFER_IDLE) {
|
||||||
int try;
|
int try;
|
||||||
for (try = 0; try < 3; ++try) {
|
for (try = 0; try < 3; ++try) {
|
||||||
GBASIONormal parentSiocnt;
|
GBASIONormal nextSiocnct;
|
||||||
ATOMIC_LOAD(parentSiocnt, node->p->players[node->id - 1]->d.p->siocnt);
|
ATOMIC_LOAD(nextSiocnct, node->p->players[node->id + 1]->d.p->siocnt);
|
||||||
if (ATOMIC_CMPXCHG(node->p->players[node->id - 1]->d.p->siocnt, parentSiocnt, GBASIONormalSetSi(parentSiocnt, GBASIONormalGetIdleSo(value)))) {
|
if (ATOMIC_CMPXCHG(node->p->players[node->id + 1]->d.p->siocnt, nextSiocnct, GBASIONormalSetSi(nextSiocnct, GBASIONormalGetIdleSo(value)))) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue