mirror of https://github.com/mgba-emu/mgba.git
GBA DMA: Emulate DMA bus
This commit is contained in:
parent
2ff5809252
commit
8b6a76142a
|
@ -209,9 +209,13 @@ static void GBASetActiveRegion(struct ARMCore* cpu, uint32_t address) {
|
||||||
|
|
||||||
#define LOAD_BAD \
|
#define LOAD_BAD \
|
||||||
GBALog(gba, GBA_LOG_GAME_ERROR, "Bad memory Load32: 0x%08X", address); \
|
GBALog(gba, GBA_LOG_GAME_ERROR, "Bad memory Load32: 0x%08X", address); \
|
||||||
value = cpu->prefetch; \
|
if (cpu->cycles >= cpu->nextEvent) { \
|
||||||
if (cpu->executionMode == MODE_THUMB) { \
|
value = gba->bus; \
|
||||||
value |= value << 16; \
|
} else { \
|
||||||
|
value = cpu->prefetch; \
|
||||||
|
if (cpu->executionMode == MODE_THUMB) { \
|
||||||
|
value |= value << 16; \
|
||||||
|
} \
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t GBALoad32(struct ARMCore* cpu, uint32_t address, int* cycleCounter) {
|
int32_t GBALoad32(struct ARMCore* cpu, uint32_t address, int* cycleCounter) {
|
||||||
|
@ -339,7 +343,11 @@ int16_t GBALoad16(struct ARMCore* cpu, uint32_t address, int* cycleCounter) {
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
GBALog(gba, GBA_LOG_GAME_ERROR, "Bad memory Load16: 0x%08X", address);
|
GBALog(gba, GBA_LOG_GAME_ERROR, "Bad memory Load16: 0x%08X", address);
|
||||||
value = cpu->prefetch;
|
if (cpu->cycles >= cpu->nextEvent) {
|
||||||
|
value = gba->bus;
|
||||||
|
} else {
|
||||||
|
value = cpu->prefetch;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -424,7 +432,11 @@ int8_t GBALoad8(struct ARMCore* cpu, uint32_t address, int* cycleCounter) {
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
GBALog(gba, GBA_LOG_GAME_ERROR, "Bad memory Load8: 0x%08x", address);
|
GBALog(gba, GBA_LOG_GAME_ERROR, "Bad memory Load8: 0x%08x", address);
|
||||||
value = cpu->prefetch & 0xFF;
|
if (cpu->cycles >= cpu->nextEvent) {
|
||||||
|
value = gba->bus;
|
||||||
|
} else {
|
||||||
|
value = cpu->prefetch;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1096,17 +1108,18 @@ void GBAMemoryServiceDMA(struct GBA* gba, int number, struct GBADMA* info) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int32_t word;
|
||||||
if (width == 4) {
|
if (width == 4) {
|
||||||
int32_t word;
|
|
||||||
word = cpu->memory.load32(cpu, source, 0);
|
word = cpu->memory.load32(cpu, source, 0);
|
||||||
|
gba->bus = word;
|
||||||
cpu->memory.store32(cpu, dest, word, 0);
|
cpu->memory.store32(cpu, dest, word, 0);
|
||||||
source += sourceOffset;
|
source += sourceOffset;
|
||||||
dest += destOffset;
|
dest += destOffset;
|
||||||
--wordsRemaining;
|
--wordsRemaining;
|
||||||
} else {
|
} else {
|
||||||
uint16_t word;
|
|
||||||
if (sourceRegion == REGION_CART2_EX && memory->savedata.type == SAVEDATA_EEPROM) {
|
if (sourceRegion == REGION_CART2_EX && memory->savedata.type == SAVEDATA_EEPROM) {
|
||||||
word = GBASavedataReadEEPROM(&memory->savedata);
|
word = GBASavedataReadEEPROM(&memory->savedata);
|
||||||
|
gba->bus = word | (word << 16);
|
||||||
cpu->memory.store16(cpu, dest, word, 0);
|
cpu->memory.store16(cpu, dest, word, 0);
|
||||||
source += sourceOffset;
|
source += sourceOffset;
|
||||||
dest += destOffset;
|
dest += destOffset;
|
||||||
|
@ -1117,12 +1130,14 @@ void GBAMemoryServiceDMA(struct GBA* gba, int number, struct GBADMA* info) {
|
||||||
GBASavedataInitEEPROM(&memory->savedata);
|
GBASavedataInitEEPROM(&memory->savedata);
|
||||||
}
|
}
|
||||||
word = cpu->memory.load16(cpu, source, 0);
|
word = cpu->memory.load16(cpu, source, 0);
|
||||||
|
gba->bus = word | (word << 16);
|
||||||
GBASavedataWriteEEPROM(&memory->savedata, word, wordsRemaining);
|
GBASavedataWriteEEPROM(&memory->savedata, word, wordsRemaining);
|
||||||
source += sourceOffset;
|
source += sourceOffset;
|
||||||
dest += destOffset;
|
dest += destOffset;
|
||||||
--wordsRemaining;
|
--wordsRemaining;
|
||||||
} else {
|
} else {
|
||||||
word = cpu->memory.load16(cpu, source, 0);
|
word = cpu->memory.load16(cpu, source, 0);
|
||||||
|
gba->bus = word | (word << 16);
|
||||||
cpu->memory.store16(cpu, dest, word, 0);
|
cpu->memory.store16(cpu, dest, word, 0);
|
||||||
source += sourceOffset;
|
source += sourceOffset;
|
||||||
dest += destOffset;
|
dest += destOffset;
|
||||||
|
|
|
@ -210,6 +210,11 @@ static void GBAProcessEvents(struct ARMCore* cpu) {
|
||||||
int32_t nextEvent = INT_MAX;
|
int32_t nextEvent = INT_MAX;
|
||||||
int32_t testEvent;
|
int32_t testEvent;
|
||||||
|
|
||||||
|
gba->bus = cpu->prefetch;
|
||||||
|
if (cpu->executionMode == MODE_THUMB) {
|
||||||
|
gba->bus |= cpu->prefetch << 16;
|
||||||
|
}
|
||||||
|
|
||||||
if (gba->springIRQ) {
|
if (gba->springIRQ) {
|
||||||
ARMRaiseIRQ(cpu);
|
ARMRaiseIRQ(cpu);
|
||||||
gba->springIRQ = 0;
|
gba->springIRQ = 0;
|
||||||
|
|
|
@ -94,6 +94,8 @@ struct GBA {
|
||||||
|
|
||||||
struct ARMDebugger* debugger;
|
struct ARMDebugger* debugger;
|
||||||
|
|
||||||
|
uint32_t bus;
|
||||||
|
|
||||||
int timersEnabled;
|
int timersEnabled;
|
||||||
struct GBATimer timers[4];
|
struct GBATimer timers[4];
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue