GBA Memory: Minor prefetch fixes
Jeffrey Pfau jeffrey@endrift.com
Sat, 27 Jun 2015 14:05:37 -0700
2 files changed,
6 insertions(+),
4 deletions(-)
M
src/gba/gba.c
→
src/gba/gba.c
@@ -452,8 +452,8 @@ void GBATimerUpdateRegister(struct GBA* gba, int timer) {
struct GBATimer* currentTimer = &gba->timers[timer]; if (currentTimer->enable && !currentTimer->countUp) { int32_t prefetchSkew = 0; - if ((gba->memory.lastPrefetchedPc - gba->cpu->gprs[ARM_PC]) < gba->memory.lastPrefetchedLoads * WORD_SIZE_THUMB) { - prefetchSkew = (gba->memory.lastPrefetchedPc - gba->cpu->gprs[ARM_PC]) / gba->cpu->memory.activeSeqCycles16; + if (gba->memory.lastPrefetchedPc - gba->memory.lastPrefetchedLoads * WORD_SIZE_THUMB >= (uint32_t) gba->cpu->gprs[ARM_PC]) { + prefetchSkew = (gba->memory.lastPrefetchedPc - gba->cpu->gprs[ARM_PC]) * (gba->cpu->memory.activeSeqCycles16 + 1) / WORD_SIZE_THUMB; } // Reading this takes two cycles (1N+1I), so let's remove them preemptively gba->memory.io[(REG_TM0CNT_LO + (timer << 2)) >> 1] = currentTimer->oldReload + ((gba->cpu->cycles - currentTimer->lastEvent - 2 + prefetchSkew) >> currentTimer->prescaleBits);
M
src/gba/memory.c
→
src/gba/memory.c
@@ -235,6 +235,8 @@ }
} gba->lastJump = address; + memory->lastPrefetchedPc = 0; + memory->lastPrefetchedLoads = 0; if (newRegion == memory->activeRegion && (newRegion < REGION_CART0 || (address & (SIZE_CART0 - 1)) < memory->romSize)) { return; }@@ -1541,10 +1543,10 @@ int32_t loads = 1;
int32_t previousLoads = 0; // Don't prefetch too much if we're overlapping with a previous prefetch - if ((memory->lastPrefetchedPc - cpu->gprs[ARM_PC]) < memory->lastPrefetchedLoads * WORD_SIZE_THUMB) { + if (UNLIKELY((memory->lastPrefetchedPc - cpu->gprs[ARM_PC]) < memory->lastPrefetchedLoads * WORD_SIZE_THUMB)) { previousLoads = (memory->lastPrefetchedPc - cpu->gprs[ARM_PC]) >> 1; } - while (stall < wait && loads + previousLoads < 8) { + while (stall < wait && LIKELY(loads + previousLoads < 8)) { stall += s; ++loads; }