summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Fors <peter.fors@mindkiller.com>2025-05-03 01:00:10 +0200
committerPeter Fors <peter.fors@mindkiller.com>2025-05-03 01:00:10 +0200
commit8ed5a368077388c676a4ef27cca9f3a58d91e484 (patch)
tree7e96f35ac933fe97a69c2a8f66f8c22f7a9beb6a
parent5808f00555c48e1cc1cc110af6a5cd73ddf13010 (diff)
cleanup and rewrite of memory_read()
-rw-r--r--.gitignore3
-rwxr-xr-xbuild.sh2
-rw-r--r--mappers/mapper.c4
-rw-r--r--mappers/mapper.h4
-rw-r--r--mappers/mapper_003_0.c27
-rw-r--r--mappers/mapper_003_0.h4
-rw-r--r--memory.c24
-rw-r--r--mknes.c4
-rw-r--r--ppu.c1
-rw-r--r--ppu_registers.c151
10 files changed, 61 insertions, 163 deletions
diff --git a/.gitignore b/.gitignore
index 770f711..33cf98b 100644
--- a/.gitignore
+++ b/.gitignore
@@ -9,3 +9,6 @@ vertex_shader.h
*.fm2
fm2h.py
gmon.out
+*.gcov
+*.gcno
+*.gcda
diff --git a/build.sh b/build.sh
index 02d50d3..de8ecc5 100755
--- a/build.sh
+++ b/build.sh
@@ -3,7 +3,7 @@
# Set the project name here
PROJECT_NAME="mknes" # Change this for each new project
-CC=gcc-14
+CC=gcc
# Base configuration common to all builds
CFLAGS="-std=gnu11 -mtune=generic "
diff --git a/mappers/mapper.c b/mappers/mapper.c
index d63e2a0..099b6d7 100644
--- a/mappers/mapper.c
+++ b/mappers/mapper.c
@@ -24,7 +24,7 @@ static void mapper_default_tick(struct nes_state *state) { }
#include "mapper_000_0.c"
#include "mapper_002_2.c"
-#include "mapper_003_0.c"
+#include "mapper_003_2.c"
#include "mapper_007_2.c"
#include "mapper_011_0.c"
#include "mapper_066_0.c"
@@ -34,7 +34,7 @@ static void mapper_default_tick(struct nes_state *state) { }
static void (*mapper_table[4096])(struct nes_state *state) = {
[MAPPER_ID( 0, 0)] = mapper_000_0_init,
[MAPPER_ID( 2, 2)] = mapper_002_2_init,
- [MAPPER_ID( 3, 0)] = mapper_003_0_init,
+ [MAPPER_ID( 3, 2)] = mapper_003_2_init,
[MAPPER_ID( 7, 2)] = mapper_007_2_init,
[MAPPER_ID(11, 0)] = mapper_011_0_init,
[MAPPER_ID(66, 0)] = mapper_011_0_init,
diff --git a/mappers/mapper.h b/mappers/mapper.h
index 0961370..863201b 100644
--- a/mappers/mapper.h
+++ b/mappers/mapper.h
@@ -1,7 +1,7 @@
#include "mapper_000_0.h"
#include "mapper_002_2.h"
-#include "mapper_003_0.h"
+#include "mapper_003_2.h"
#include "mapper_007_2.h"
#include "mapper_011_0.h"
#include "mapper_066_0.h"
@@ -21,7 +21,7 @@ struct mapper_functions {
union mapper_data {
struct mapper_000_0 m000_0;
struct mapper_002_2 m002_2;
- struct mapper_003_0 m003_0;
+ struct mapper_003_2 m003_2;
struct mapper_007_2 m007_2;
struct mapper_011_0 m011_0;
struct mapper_066_0 m066_0;
diff --git a/mappers/mapper_003_0.c b/mappers/mapper_003_0.c
deleted file mode 100644
index 5ccfb53..0000000
--- a/mappers/mapper_003_0.c
+++ /dev/null
@@ -1,27 +0,0 @@
-
-static uint8_t mapper_003_0_prg_read(struct nes_state *state, uint32_t addr) {
- return state->prg_rom[addr & 0x7fff];
-}
-
-static void mapper_003_0_prg_write(struct nes_state *state, uint32_t addr, uint8_t value) {
- struct mapper_003_0 *mapper = (struct mapper_003_0 *)&state->map;
-
- if(addr >= 0x8000) {
- mapper->chr_ptr = state->chr_rom + (value & 3) * 0x2000;
- }
-}
-
-static uint8_t mapper_003_0_chr_read(struct nes_state *state, uint32_t addr) {
- struct mapper_003_0 *mapper = (struct mapper_003_0 *)&state->map;
- return mapper->chr_ptr[addr];
-}
-
-static void mapper_003_0_init(struct nes_state *state) {
- struct mapper_003_0 *mapper = (struct mapper_003_0 *)&state->map;
-
- mapper->chr_ptr = state->chr_rom;
-
- state->mapper.prg_read = mapper_003_0_prg_read;
- state->mapper.prg_write = mapper_003_0_prg_write;
- state->mapper.chr_read = mapper_003_0_chr_read;
-}
diff --git a/mappers/mapper_003_0.h b/mappers/mapper_003_0.h
deleted file mode 100644
index f03b106..0000000
--- a/mappers/mapper_003_0.h
+++ /dev/null
@@ -1,4 +0,0 @@
-
-struct mapper_003_0 {
- uint8_t *chr_ptr;
-} __attribute__((packed, aligned(64)));
diff --git a/memory.c b/memory.c
index 74b0a0f..6e0c6df 100644
--- a/memory.c
+++ b/memory.c
@@ -7,10 +7,27 @@ static uint8_t memory_read(struct nes_state *restrict state, uint32_t offset) {
ppu_tick(state);
// apu_tick(state);
- if(LIKELY(offset < 0x2000)) {
+ if(LIKELY(offset >= 0x6000)) { // MOST
+ return state->mapper.prg_read(state, offset);
+
+ } else if(LIKELY(offset < 0x2000)) { // SECOND
return state->ram[offset & 0x07ff];
- } else if(offset < 0x4000) {
+ } else if(offset < 0x4000) { // THIRD
+ return ppu_read(state, offset);
+
+ } else if(offset == 0x4016 || offset == 0x4017) {
+ uint32_t index = offset & 1;
+ uint8_t value = (state->ppu.input_latch[index] >> state->ppu.input_bit[index]) & 1;
+ state->ppu.input_bit[index]++;
+ return value | 0x40; // Bit 6 open bus high, bit 7 low
+ }
+
+#if 0
+ if(LIKELY(offset < 0x2000)) { // SECOND
+ return state->ram[offset & 0x07ff];
+
+ } else if(offset < 0x4000) { // THIRD
return ppu_read(state, offset);
} else if(offset == 0x4016 || offset == 0x4017) {
@@ -23,10 +40,11 @@ static uint8_t memory_read(struct nes_state *restrict state, uint32_t offset) {
// static uint32_t apuread = 0;
// // printf("%.5d apu\n", apuread++);
- } else if(LIKELY(offset >= 0x6000)) {
+ } else if(LIKELY(offset >= 0x6000)) { // MOST
return state->mapper.prg_read(state, offset);
}
+#endif
return 0;
}
diff --git a/mknes.c b/mknes.c
index 2aff691..b5f05d3 100644
--- a/mknes.c
+++ b/mknes.c
@@ -206,7 +206,7 @@ int main(int argc, char **argv) {
// ines2_load(nstate, "data/0003/Flipull - An Exciting Cube Game (Japan) (En).zip");
// ines2_load(nstate, "data/0003/Friday the 13th (USA).zip");
// ines2_load(nstate, "data/0003/Ghostbusters (Japan).zip");
- // ines2_load(nstate, "data/0003/Gradius (USA).zip");
+ ines2_load(nstate, "data/0003/Gradius (USA).zip");
// ines2_load(nstate, "data/0007/Battletoads (USA).zip");
// ines2_load(nstate, "data/0007/Beetlejuice (USA).zip");
// ines2_load(nstate, "data/0007/Cabal (USA).zip");
@@ -224,7 +224,7 @@ int main(int argc, char **argv) {
uint32_t hi = nstate->mapper.prg_read(nstate, 0xfffd);
nstate->cpu.pc = (hi << 8) | lo;
-#if 1
+#if 0
for(uint32_t i = 0; i < 0x5000; ++ i) {
while(!nstate->ppu.frame_ready) {
// PROFILE_NAMED("nes emulator");
diff --git a/ppu.c b/ppu.c
index 6b57085..fe54be5 100644
--- a/ppu.c
+++ b/ppu.c
@@ -192,6 +192,7 @@ static void ppu_tick(struct nes_state *state) {
if((ppu->vram_addr & 0x7000) != 0x7000) {
ppu->vram_addr += 0x1000;
} else {
+
ppu->vram_addr &= ~0x7000;
uint32_t y = (ppu->vram_addr & 0x03e0) >> 5;
if(y == 29) {
diff --git a/ppu_registers.c b/ppu_registers.c
index b426f17..f6bd515 100644
--- a/ppu_registers.c
+++ b/ppu_registers.c
@@ -4,22 +4,26 @@ static inline void ppu_write(struct nes_state *state, uint32_t offset, uint8_t v
uint32_t reg = offset & 0x7;
- if(reg == 0) {
- ppu->reg_ctrl = value;
- ppu->temp_addr = (ppu->temp_addr & 0xf3ff) | ((value & 0x03) << 10);
- // ppu->open_bus = value;
+ if(LIKELY(reg == 4)) {
+ ppu->oam[ppu->oam_addr++] = value;
+ ppu->open_bus = value;
+ return;
} else if(reg == 1) {
ppu->reg_mask = value;
- // ppu->open_bus = value;
+ ppu->open_bus = value;
+ return;
+
+ } else if(reg == 0) {
+ ppu->reg_ctrl = value;
+ ppu->temp_addr = (ppu->temp_addr & 0xf3ff) | ((value & 0x03) << 10);
+ ppu->open_bus = value;
+ return;
} else if(reg == 3) {
ppu->oam_addr = value;
- // ppu->open_bus = value;
-
- } else if(reg == 4) {
- ppu->oam[ppu->oam_addr++] = value;
- // ppu->open_bus = value;
+ ppu->open_bus = value;
+ return;
} else if(reg == 5) {
if(ppu->write_latch == 0) {
@@ -30,7 +34,8 @@ static inline void ppu_write(struct nes_state *state, uint32_t offset, uint8_t v
ppu->temp_addr = (ppu->temp_addr & ~0x73e0) | ((value & 0x07) << 12) | ((value & 0xf8) << 2);
ppu->write_latch = 0;
}
- // ppu->open_bus = value;
+ ppu->open_bus = value;
+ return;
} else if(reg == 6) {
if(ppu->write_latch == 0) {
@@ -41,11 +46,12 @@ static inline void ppu_write(struct nes_state *state, uint32_t offset, uint8_t v
ppu->vram_addr = ppu->temp_addr;
ppu->write_latch = 0;
}
- // ppu->open_bus = value;
+ ppu->open_bus = value;
+ return;
} else if(reg == 7) {
uint32_t addr = ppu->vram_addr;
- if(LIKELY(addr < 0x2000)) {
+ if(addr < 0x2000) {
state->mapper.chr_write(state, addr, value);
} else if(LIKELY(addr < 0x3f00)) {
@@ -59,78 +65,9 @@ static inline void ppu_write(struct nes_state *state, uint32_t offset, uint8_t v
ppu->palette[pal_addr] = value;
}
ppu->vram_addr += (ppu->reg_ctrl & 0x04) ? 32 : 1;
- // ppu->open_bus = value;
+ ppu->open_bus = value;
+ return;
}
-
- ppu->open_bus = value;
-
-#if 0
- switch(offset & 7) {
- case 0: { // 2000
- ppu->reg_ctrl = value;
- ppu->temp_addr = (ppu->temp_addr & 0xf3ff) | ((value & 0x03) << 10);
- ppu->open_bus = value;
- } break;
-
- case 1: { // 2001
- ppu->reg_mask = value;
- ppu->open_bus = value;
- } break;
-
- case 3: { // 2003
- ppu->oam_addr = value;
- ppu->open_bus = value;
- } break;
-
- case 4: { // 2004
- ppu->oam[ppu->oam_addr++] = value;
- ppu->open_bus = value;
- } break;
-
- case 5: { // 2005
- if(ppu->write_latch == 0) {
- ppu->fine_x = value & 0x07;
- ppu->temp_addr = (ppu->temp_addr & ~0x001f) | (value >> 3);
- ppu->write_latch = 1;
- } else {
- ppu->temp_addr = (ppu->temp_addr & ~0x73e0) | ((value & 0x07) << 12) | ((value & 0xf8) << 2);
- ppu->write_latch = 0;
- }
- ppu->open_bus = value;
- } break;
-
- case 6: { // 2006
- if(ppu->write_latch == 0) {
- ppu->temp_addr = (ppu->temp_addr & 0x00ff) | ((value & 0x3f) << 8);
- ppu->write_latch = 1;
- } else {
- ppu->temp_addr = (ppu->temp_addr & 0xff00) | value;
- ppu->vram_addr = ppu->temp_addr;
- ppu->write_latch = 0;
- }
- ppu->open_bus = value;
- } break;
-
- case 7: { // 2007
- uint32_t addr = ppu->vram_addr;
- if(LIKELY(addr < 0x2000)) {
- state->mapper.chr_write(state, addr, value);
-
- } else if(LIKELY(addr < 0x3f00)) {
- state->mapper.ciram_write(state, addr, value);
-
- } else if(addr < 0x4000) {
- uint32_t pal_addr = addr & 0x1f;
- if((pal_addr & 3) == 0) {
- pal_addr &= ~0x10;
- }
- ppu->palette[pal_addr] = value;
- }
- ppu->vram_addr += (ppu->reg_ctrl & 0x04) ? 32 : 1;
- ppu->open_bus = value;
- } break;
- }
-#endif
}
__attribute__((always_inline, hot))
@@ -140,13 +77,17 @@ static inline uint8_t ppu_read(struct nes_state *state, uint32_t offset) {
uint32_t reg = offset & 0x7;
- if(reg == 2) {
+ if(LIKELY(reg == 2)) {
result = ppu->reg_status;
ppu->reg_status &= ~0x80;
ppu->write_latch = 0;
+ ppu->open_bus = result;
+ return result;
- } else if(reg == 4) {
+ } else if(LIKELY(reg == 4)) {
result = ppu->oam[ppu->oam_addr];
+ ppu->open_bus = result;
+ return result;
} else if(reg == 7) {
uint32_t addr = ppu->vram_addr;
@@ -168,45 +109,11 @@ static inline uint8_t ppu_read(struct nes_state *state, uint32_t offset) {
}
ppu->vram_addr += (ppu->reg_ctrl & 0x04) ? 32 : 1;
- }
-
-#if 0
- switch(offset & 7) {
- case 2: { // 2002
- result = ppu->reg_status;
- ppu->reg_status &= ~0x80;
- ppu->write_latch = 0;
- } break;
-
- case 4: { // 2004
- result = ppu->oam[ppu->oam_addr];
- } break;
-
- case 7: { // 2007
- uint32_t addr = ppu->vram_addr;
-
- if(LIKELY(addr < 0x2000)) {
- result = ppu->vram_read_buffer;
- ppu->vram_read_buffer = state->mapper.chr_read(state, addr);
-
- } else if(LIKELY(addr < 0x3f00)) {
- result = ppu->vram_read_buffer;
- ppu->vram_read_buffer = state->mapper.ciram_read(state, addr);
-
- } else if(addr < 0x4000) {
- uint32_t pal_addr = addr & 0x1f;
- if((pal_addr & 0x13) == 0x10) {
- pal_addr &= ~0x10;
- }
- result = ppu->palette[pal_addr];
- }
+ ppu->open_bus = result;
+ return result;
- ppu->vram_addr += (ppu->reg_ctrl & 0x04) ? 32 : 1;
- } break;
}
-# endif
- ppu->open_bus = result;
return result;
}