Update to v072r11 release.

A number of changes in this release were contributed by Cydrak in the
WIP thread, who described his changes from r09/r10 thusly:

- Call cpu.synchronize_coprocessor() on external R/W to avoid missing data
- Sign-extend K, L before multiplying
- Load IDB before ALU. Supports the MOV A, d; XOR A, A idiom which is
  all over the place
- Use 16-bit types in flag checks (notably Z)
- Flags mostly unified; hopefully at least OV0 and SGN work
- Carry-in comes from the *other* accumulator's flags, this is used for
  long arithmetic
- CMP is ~q (see the many CMP A; INC A where values get negated)
- SHR1 is arithmetic shift and retains the sign bit (Mario Kart sprites
  and physics are broken without it)
- SHL1 has carry-in per the datasheet, it doesn't seem to be used though
- XCHG probably byteswaps, but it's not used either
- Reversed DR external R/W order again, big-endian seems to break it

byuu described the remaining changes:

You do not need the XML files anymore, bsnes will automatically choose
the new uPD module, and look for dsp1b.bin.
If you make your own XML file, you can force the old HLE mode, or use
a differently-named PROM.
If and when we get the DSP-2,3,4 modules, bsnes v072.11 and above should
already be able to run them, assuming no more emulation core bugs.
This commit is contained in:
Tim Allen 2010-12-23 01:07:36 +11:00
parent 05526571e7
commit 9762a092d2
10 changed files with 188 additions and 293 deletions

View File

@ -408,7 +408,7 @@ SNESCartridge::SNESCartridge(const uint8_t *data, unsigned size) {
}
if(has_dsp1) {
xml << " <necdsp program='DSP-1B'>\n";
xml << " <upd77c25 program='dsp1b.bin'>\n";
if(dsp1_mapper == DSP1LoROM1MB) {
xml << " <dr>\n";
xml << " <map address='20-3f:8000-bfff'/>\n";
@ -437,7 +437,7 @@ SNESCartridge::SNESCartridge(const uint8_t *data, unsigned size) {
xml << " <map address='80-9f:7000-7fff'/>\n";
xml << " </sr>\n";
}
xml << " </necdsp>\n";
xml << " </upd77c25>\n";
}
if(has_dsp2) {

View File

@ -232,9 +232,16 @@ void Cartridge::xml_parse_upd77c25(xml_element &root) {
foreach(attr, root.attribute) {
if(attr.name == "program") {
upd77c25.program = attr.content;
} else if(attr.name == "data") {
upd77c25.data = attr.content;
file fp;
if(fp.open(string(dir(basename()), attr.content), file::mode::read)) {
for(unsigned n = 0; n < 2048; n++) {
upd77c25.programROM[n] = fp.readm(3);
fp.read();
}
for(unsigned n = 0; n < 1024; n++) {
upd77c25.dataROM[n] = fp.readm(2);
}
}
}
}

View File

@ -0,0 +1,52 @@
#ifdef UPD77C25_CPP
void UPD77C25::serialize(serializer &s) {
s.array(dataRAM);
s.integer(regs.pc);
for(unsigned n = 0; n < 4; n++) s.integer(regs.stack[n]);
s.integer(regs.rp);
s.integer(regs.dp);
s.integer(regs.k);
s.integer(regs.l);
s.integer(regs.m);
s.integer(regs.n);
s.integer(regs.a);
s.integer(regs.b);
s.integer(regs.flaga.s1);
s.integer(regs.flaga.s0);
s.integer(regs.flaga.c);
s.integer(regs.flaga.z);
s.integer(regs.flaga.ov1);
s.integer(regs.flaga.ov0);
s.integer(regs.flagb.s1);
s.integer(regs.flagb.s0);
s.integer(regs.flagb.c);
s.integer(regs.flagb.z);
s.integer(regs.flagb.ov1);
s.integer(regs.flagb.ov0);
s.integer(regs.tr);
s.integer(regs.trb);
s.integer(regs.sr.rqm);
s.integer(regs.sr.usf1);
s.integer(regs.sr.usf0);
s.integer(regs.sr.drs);
s.integer(regs.sr.dma);
s.integer(regs.sr.drc);
s.integer(regs.sr.soc);
s.integer(regs.sr.sic);
s.integer(regs.sr.ei);
s.integer(regs.sr.p1);
s.integer(regs.sr.p0);
s.integer(regs.dr);
s.integer(regs.siack);
s.integer(regs.soack);
s.integer(regs.idb);
}
#endif

View File

@ -7,6 +7,7 @@
#define UPD77C25_CPP
namespace SNES {
#include "serialization.cpp"
#include "disassembler.cpp"
UPD77C25 upd77c25;
@ -17,7 +18,9 @@ void UPD77C25::Enter() { upd77c25.enter(); }
void UPD77C25::enter() {
while(true) {
//print(disassemble(regs.pc), "\n");
if(scheduler.sync == Scheduler::SynchronizeMode::All) {
scheduler.exit(Scheduler::ExitReason::SynchronizeEvent);
}
uint24 opcode = programROM[regs.pc++];
switch(opcode >> 22) {
@ -27,7 +30,7 @@ void UPD77C25::enter() {
case 3: exec_ld(opcode); break;
}
uint31 result = regs.k * regs.l; //sign + 30-bit result
int32 result = (int32)regs.k * regs.l; //sign + 30-bit result
regs.m = result >> 15; //store sign + top 15-bits
regs.n = result << 1; //store low 15-bits + zero
@ -46,195 +49,6 @@ void UPD77C25::exec_op(uint24 opcode) {
uint4 src = opcode >> 4; //move source
uint4 dst = opcode >> 0; //move destination
unsigned p, q, r;
Flag flag;
switch(pselect) {
case 0: p = dataRAM[regs.dp]; break;
case 1: p = regs.idb; break;
case 2: p = regs.m; break;
case 3: p = regs.n; break;
}
switch(asl) {
case 0: q = regs.a; flag = regs.flaga; break;
case 1: q = regs.b; flag = regs.flagb; break;
}
switch(alu) {
case 0: { //NOP
break;
}
case 1: { //OR
r = q | p;
flag.s0 = r & 0x8000;
flag.c = 0;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 2: { //AND
r = q & p;
flag.s0 = r & 0x8000;
flag.c = 0;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 3: { //XOR
r = q ^ p;
flag.s0 = r & 0x8000;
flag.c = 0;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 4: { //SUB
r = q - p;
bool pov = (((p | q) & 0x8000) == 0x0000) && ((r & 0x8000) == 0x8000);
bool nov = (((p & q) & 0x8000) == 0x8000) && ((r & 0x8000) == 0x0000);
flag.s0 = r & 0x8000;
flag.s1 = pov;
flag.c = r > 0xffff;
flag.z = !r;
flag.ov0 = pov | nov;
flag.ov1 ^= flag.ov0;
break;
}
case 5: { //ADD
r = q + p;
bool pov = (((p | q) & 0x8000) == 0x0000) && ((r & 0x8000) == 0x8000);
bool nov = (((p & q) & 0x8000) == 0x8000) && ((r & 0x8000) == 0x0000);
flag.s0 = r & 0x8000;
flag.s1 = pov;
flag.c = r > 0xffff;
flag.z = !r;
flag.ov0 = pov | nov;
flag.ov1 ^= flag.ov0;
break;
}
case 6: { //SBB
r = q - p - flag.c;
bool pov = (((p | q) & 0x8000) == 0x0000) && ((r & 0x8000) == 0x8000);
bool nov = (((p & q) & 0x8000) == 0x8000) && ((r & 0x8000) == 0x0000);
flag.s0 = r & 0x8000;
flag.s1 = pov;
flag.c = r > 0xffff;
flag.z = !r;
flag.ov0 = pov | nov;
flag.ov1 ^= flag.ov0;
break;
}
case 7: { //ADC
r = q + p + flag.c;
bool pov = (((p | q) & 0x8000) == 0x0000) && ((r & 0x8000) == 0x8000);
bool nov = (((p & q) & 0x8000) == 0x8000) && ((r & 0x8000) == 0x0000);
flag.s0 = r & 0x8000;
flag.s1 = pov;
flag.c = r > 0xffff;
flag.z = !r;
flag.ov0 = pov | nov;
flag.ov1 ^= flag.ov0;
break;
}
case 8: { //DEC
r = q - 1;
bool pov = (((p | q) & 0x8000) == 0x0000) && ((r & 0x8000) == 0x8000);
bool nov = (((p & q) & 0x8000) == 0x8000) && ((r & 0x8000) == 0x0000);
flag.s0 = r & 0x8000;
flag.s1 = pov;
flag.c = r > 0xffff;
flag.z = !r;
flag.ov0 = pov | nov;
flag.ov1 ^= flag.ov0;
break;
}
case 9: { //INC
r = q + 1;
bool pov = (((p | q) & 0x8000) == 0x0000) && ((r & 0x8000) == 0x8000);
bool nov = (((p & q) & 0x8000) == 0x8000) && ((r & 0x8000) == 0x0000);
flag.s0 = r & 0x8000;
flag.s1 = pov;
flag.c = r > 0xffff;
flag.z = !r;
flag.ov0 = pov | nov;
flag.ov1 ^= flag.ov0;
break;
}
case 10: { //CMP (complement)
r = ~q;
flag.s0 = r & 0x8000;
flag.c = 0;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 11: { //SHR1
r = q >> 1;
flag.s0 = r & 0x8000;
flag.c = q & 1;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 12: { //SHL1
r = q << 1;
flag.s0 = r & 0x8000;
flag.c = r & 0x8000;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 13: { //SHL2
r = q << 2;
flag.s0 = r & 0x8000;
flag.c = 0;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 14: { //SHL4
r = q << 4;
flag.s0 = r & 0x8000;
flag.c = 0;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 15: { //XCHG
r = (q << 8) | (q >> 8);
flag.s0 = r & 0x8000;
flag.c = 0;
flag.z = !r;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
}
switch(src) {
case 0: regs.idb = regs.trb; break;
case 1: regs.idb = regs.a; break;
@ -243,7 +57,7 @@ void UPD77C25::exec_op(uint24 opcode) {
case 4: regs.idb = regs.dp; break;
case 5: regs.idb = regs.rp; break;
case 6: regs.idb = dataROM[regs.rp]; break;
case 7: regs.idb = regs.flaga.s1 ? 0x7fff : 0x8000; break;
case 7: regs.idb = 0x8000 - regs.flaga.s1; break;
case 8: regs.idb = regs.dr; regs.sr.rqm = 1; break;
case 9: regs.idb = regs.dr; break;
case 10: regs.idb = regs.sr; break;
@ -252,36 +66,92 @@ void UPD77C25::exec_op(uint24 opcode) {
case 13: regs.idb = regs.k; break;
case 14: regs.idb = regs.l; break;
case 15: regs.idb = dataRAM[regs.dp]; break;
default: print("OP: unhandled src case ", strhex<2>(src), "\n"); break;
}
switch(asl) {
case 0: regs.a = r; regs.flaga = flag; break;
case 1: regs.b = r; regs.flagb = flag; break;
if(alu) {
uint16 p, q, r;
Flag flag;
bool c;
switch(pselect) {
case 0: p = dataRAM[regs.dp]; break;
case 1: p = regs.idb; break;
case 2: p = regs.m; break;
case 3: p = regs.n; break;
}
switch(asl) {
case 0: q = regs.a; flag = regs.flaga; c = regs.flagb.c; break;
case 1: q = regs.b; flag = regs.flagb; c = regs.flaga.c; break;
}
switch(alu) {
case 1: r = q | p; break; //OR
case 2: r = q & p; break; //AND
case 3: r = q ^ p; break; //XOR
case 4: r = q - p; break; //SUB
case 5: r = q + p; break; //ADD
case 6: r = q - p - c; break; //SBB
case 7: r = q + p + c; break; //ADC
case 8: r = q - 1; p = 1; break; //DEC
case 9: r = q + 1; p = 1; break; //INC
case 10: r = ~q; break; //CMP
case 11: r = (q >> 1) | (q & 0x8000); break; //SHR1 (ASR)
case 12: r = (q << 1) | c; break; //SHL1 (ROL)
case 13: r = (q << 2); break; //SHL2
case 14: r = (q << 4); break; //SHL4
case 15: r = (q << 8) | (q >> 8); break; //XCHG
}
flag.s0 = (r & 0x8000);
flag.z = (r == 0);
switch(alu) {
case 1: case 2: case 3: case 10: case 13: case 14: case 15: {
flag.c = 0;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 4: case 5: case 6: case 7: case 8: case 9: {
if(alu & 1) {
//addition
flag.ov0 = (q ^ r) & ~(q ^ p) & 0x8000;
flag.c = (r < q);
} else {
//subtraction
flag.ov0 = (q ^ r) & (q ^ p) & 0x8000;
flag.c = (r > q);
}
if(flag.ov0) {
flag.s1 = flag.ov1 ^ !(r & 0x8000);
flag.ov1 = !flag.ov1;
}
break;
}
case 11: {
flag.c = q & 1;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
case 12: {
flag.c = q >> 15;
flag.ov0 = 0;
flag.ov1 = 0;
break;
}
}
switch(asl) {
case 0: regs.a = r; regs.flaga = flag; break;
case 1: regs.b = r; regs.flagb = flag; break;
}
}
switch(dst) {
case 0: break;
case 1: regs.a = regs.idb; break;
case 2: regs.b = regs.idb; break;
case 3: regs.tr = regs.idb; break;
case 4: regs.dp = regs.idb; break;
case 5: regs.rp = regs.idb; break;
case 6: regs.dr = regs.idb; regs.sr.rqm = 1; break;
case 7: regs.sr = (regs.sr & 0x9000) | (regs.idb & ~0x9000); break;
//case 8: regs.sol = regs.idb; break;
//case 9: regs.som = regs.idb; break;
case 10: regs.k = regs.idb; break;
case 11: regs.k = regs.idb; regs.l = dataROM[regs.rp]; break;
case 12: regs.k = dataRAM[regs.dp | 0x40]; regs.l = regs.idb; break;
case 13: regs.l = regs.idb; break;
case 14: regs.trb = regs.idb; break;
case 15: dataRAM[regs.dp] = regs.idb; break;
default: print("OP: unhandled dst case ", strhex<2>(dst), "\n"); break;
}
exec_ld((regs.idb << 6) + dst);
switch(dpl) {
case 0: break; //DPNOP
case 1: regs.dp = (regs.dp & 0xf0) + ((regs.dp + 1) & 0x0f); break; //DPINC
case 2: regs.dp = (regs.dp & 0xf0) + ((regs.dp - 1) & 0x0f); break; //DPDEC
case 3: regs.dp = (regs.dp & 0xf0); break; //DPCLR
@ -289,10 +159,7 @@ void UPD77C25::exec_op(uint24 opcode) {
regs.dp ^= dphm << 4;
switch(rpdcr) {
case 0: break; //RPNOP
case 1: regs.rp--; break; //RPDEC
}
if(rpdcr) regs.rp--;
}
void UPD77C25::exec_rt(uint24 opcode) {
@ -357,6 +224,8 @@ void UPD77C25::exec_ld(uint24 opcode) {
uint16 id = opcode >> 6; //immediate data
uint4 dst = opcode >> 0; //destination
regs.idb = id;
switch(dst) {
case 0: break;
case 1: regs.a = id; break;
@ -365,16 +234,15 @@ void UPD77C25::exec_ld(uint24 opcode) {
case 4: regs.dp = id; break;
case 5: regs.rp = id; break;
case 6: regs.dr = id; regs.sr.rqm = 1; break;
case 7: regs.sr = (regs.sr & 0x9000) | (id & ~0x9000); break;
case 7: regs.sr = (regs.sr & 0x907c) | (id & ~0x907c); break;
//case 8: regs.sol = id; break;
//case 9: regs.som = id; break;
case 10: regs.k = id; break;
case 11: regs.k = regs.idb; regs.l = dataROM[regs.rp]; break;
case 12: regs.k = dataRAM[regs.dp | 0x40]; regs.l = regs.idb; break;
case 11: regs.k = id; regs.l = dataROM[regs.rp]; break;
case 12: regs.l = id; regs.k = dataRAM[regs.dp | 0x40]; break;
case 13: regs.l = id; break;
case 14: regs.trb = id; break;
case 15: dataRAM[regs.dp] = id; break;
default: print("LD: unhandled dst case ", strhex<2>(dst), "\n"); break;
}
}
@ -394,42 +262,44 @@ void UPD77C25::stack_pull() {
}
uint8 UPD77C25::read(bool mode) {
if(mode == 0) return (unsigned)regs.sr >> 8;
cpu.synchronize_coprocessor();
if(mode == 0) return regs.sr >> 8;
if(regs.sr.drc == 0) {
//16-bit
if(regs.sr.drs == 0) {
regs.sr.drs = 1;
return regs.dr >> 8;
return regs.dr >> 0;
} else {
regs.sr.rqm = 0;
regs.sr.drs = 0;
return regs.dr >> 0;
return regs.dr >> 8;
}
} else {
//8-bit
regs.sr.rqm = 0;
return regs.dr;
return regs.dr >> 0;
}
}
void UPD77C25::write(bool mode, uint8 data) {
cpu.synchronize_coprocessor();
if(mode == 0) return;
if(regs.sr.drc == 0) {
//16-bit
if(regs.sr.drs == 0) {
regs.sr.drs = 1;
regs.dr = (data << 8) | (regs.dr & 0x00ff);
regs.dr = (regs.dr & 0xff00) | (data << 0);
} else {
regs.sr.rqm = 0;
regs.sr.drs = 0;
regs.dr = (regs.dr & 0xff00) | (data << 0);
regs.dr = (data << 8) | (regs.dr & 0x00ff);
}
} else {
//8-bit
regs.sr.rqm = 0;
regs.dr = data;
regs.dr = (regs.dr & 0xff00) | (data << 0);
}
}
@ -440,43 +310,7 @@ void UPD77C25::enable() {
}
void UPD77C25::power() {
for(unsigned i = 0; i < 2048; i++) programROM[i] = 0x000000;
for(unsigned i = 0; i < 1024; i++) dataROM[i] = 0x0000;
for(unsigned i = 0; i < 256; i++) dataRAM[i] = 0x0000;
string filename;
file fp;
filename = string(dir(cartridge.basename()), program);
if(fp.open(filename, file::mode::read)) {
for(unsigned i = 0; i < 2048; i++) {
programROM[i] |= fp.read() << 16;
programROM[i] |= fp.read() << 8;
programROM[i] |= fp.read() << 0;
fp.read(); //skip 24-bit -> 32-bit padding
}
fp.close();
}
filename = string(dir(cartridge.basename()), data);
if(fp.open(filename, file::mode::read)) {
for(unsigned i = 0; i < 1024; i++) {
dataROM[i] |= fp.read() << 8;
dataROM[i] |= fp.read() << 0;
}
fp.close();
}
#if 0
fp.open("/home/byuu/Desktop/disassembly.txt", file::mode::write);
for(unsigned i = 0; i < 2048; i++) {
string output = disassemble(i);
fp.print(output);
fp.print("\n");
}
fp.close();
#endif
reset();
}

View File

@ -7,16 +7,15 @@ public:
void power();
void reset();
string disassemble(uint11 ip);
void serialize(serializer &s);
string program;
string data;
private:
uint24 programROM[2048];
uint16 dataROM[1024];
uint16 dataRAM[256];
string disassemble(uint11 ip);
private:
struct Flag {
bool s1, s0, c, z, ov1, ov0;
@ -52,16 +51,16 @@ private:
uint11 stack[4]; //LIFO
uint10 rp; //ROM pointer
uint8 dp; //data pointer
uint16 k;
uint16 l;
uint16 m;
uint16 n;
uint16 a; //accumulator
uint16 b; //accumulator
int16 k;
int16 l;
int16 m;
int16 n;
int16 a; //accumulator
int16 b; //accumulator
Flag flaga;
Flag flagb;
uint16 tr; //temporary registers
uint16 trb;
uint16 tr; //temporary register
uint16 trb; //temporary register
Status sr; //status register
uint16 dr; //data register
bool siack;
@ -73,8 +72,10 @@ private:
void exec_rt(uint24 opcode);
void exec_jp(uint24 opcode);
void exec_ld(uint24 opcode);
void stack_push();
void stack_pull();
uint8 read(bool mode);
void write(bool mode, uint8 data);

View File

@ -1,12 +1,12 @@
namespace SNES {
namespace Info {
static const char Name[] = "bsnes";
static const char Version[] = "072.10";
static const char Version[] = "072.11";
static const unsigned SerializerVersion = 14;
}
}
#define DEBUGGER
//#define DEBUGGER
#define CHEAT_SYSTEM
#include <libco/libco.h>

View File

@ -60,6 +60,7 @@ void System::serialize_all(serializer &s) {
if(cartridge.mode() == Cartridge::Mode::SuperGameBoy) supergameboy.serialize(s);
if(cartridge.has_superfx()) superfx.serialize(s);
if(cartridge.has_sa1()) sa1.serialize(s);
if(cartridge.has_upd77c25()) upd77c25.serialize(s);
if(cartridge.has_srtc()) srtc.serialize(s);
if(cartridge.has_sdd1()) sdd1.serialize(s);
if(cartridge.has_spc7110()) spc7110.serialize(s);

View File

@ -217,6 +217,7 @@ void System::reset() {
if(cartridge.mode() == Cartridge::Mode::SuperGameBoy) cpu.coprocessors.append(&supergameboy);
if(cartridge.has_superfx()) cpu.coprocessors.append(&superfx);
if(cartridge.has_sa1()) cpu.coprocessors.append(&sa1);
if(cartridge.has_upd77c25()) cpu.coprocessors.append(&upd77c25);
if(cartridge.has_msu1()) cpu.coprocessors.append(&msu1);
if(cartridge.has_serial()) cpu.coprocessors.append(&serial);

View File

@ -4,7 +4,7 @@ Cartridge cartridge;
bool Cartridge::loadNormal(const char *basename) {
unload();
if(loadCartridge(SNES::memory::cartrom, baseXML, basename) == false) return false;
baseName = nall::basename(basename);
SNES::cartridge.basename = baseName = nall::basename(basename);
SNES::cartridge.load(SNES::Cartridge::Mode::Normal, { baseXML });
loadMemory(SNES::memory::cartram, baseName, ".srm");
loadMemory(SNES::memory::cartrtc, baseName, ".rtc");
@ -16,7 +16,7 @@ bool Cartridge::loadBsxSlotted(const char *basename, const char *slotname) {
unload();
if(loadCartridge(SNES::memory::cartrom, baseXML, basename) == false) return false;
loadCartridge(SNES::memory::bsxflash, slotAXML, slotname);
baseName = nall::basename(basename);
SNES::cartridge.basename = baseName = nall::basename(basename);
slotAName = nall::basename(slotname);
SNES::cartridge.load(SNES::Cartridge::Mode::BsxSlotted, { baseXML, slotAXML });
loadMemory(SNES::memory::cartram, baseName, ".srm");
@ -29,7 +29,7 @@ bool Cartridge::loadBsx(const char *basename, const char *slotname) {
unload();
if(loadCartridge(SNES::memory::cartrom, baseXML, basename) == false) return false;
loadCartridge(SNES::memory::bsxflash, slotAXML, slotname);
baseName = nall::basename(basename);
SNES::cartridge.basename = baseName = nall::basename(basename);
slotAName = nall::basename(slotname);
SNES::cartridge.load(SNES::Cartridge::Mode::Bsx, { baseXML, slotAXML });
loadMemory(SNES::memory::bsxram, baseName, ".srm");
@ -43,7 +43,7 @@ bool Cartridge::loadSufamiTurbo(const char *basename, const char *slotAname, con
if(loadCartridge(SNES::memory::cartrom, baseXML, basename) == false) return false;
loadCartridge(SNES::memory::stArom, slotAXML, slotAname);
loadCartridge(SNES::memory::stBrom, slotBXML, slotBname);
baseName = nall::basename(basename);
SNES::cartridge.basename = baseName = nall::basename(basename);
slotAName = nall::basename(slotAname);
slotBName = nall::basename(slotBname);
SNES::cartridge.load(SNES::Cartridge::Mode::SufamiTurbo, { baseXML, slotAXML, slotBXML });
@ -57,7 +57,7 @@ bool Cartridge::loadSuperGameBoy(const char *basename, const char *slotname) {
unload();
if(loadCartridge(SNES::memory::cartrom, baseXML, basename) == false) return false;
loadCartridge(SNES::memory::gbrom, slotAXML, slotname);
baseName = nall::basename(basename);
SNES::cartridge.basename = baseName = nall::basename(basename);
slotAName = nall::basename(slotname);
SNES::cartridge.load(SNES::Cartridge::Mode::SuperGameBoy, { baseXML, slotAXML });
loadMemory(SNES::memory::gbram, slotAName, ".sav");

View File

@ -92,7 +92,6 @@ void Utility::setShader() {
}
void Utility::cartridgeLoaded() {
SNES::cartridge.basename = cartridge.baseName;
SNES::system.power();
cheatEditor.load(cartridge.baseName);
stateManager.load();