summaryrefslogtreecommitdiff
path: root/mknes.h
diff options
context:
space:
mode:
Diffstat (limited to 'mknes.h')
-rw-r--r--mknes.h227
1 files changed, 158 insertions, 69 deletions
diff --git a/mknes.h b/mknes.h
index d3e3840..c41d7af 100644
--- a/mknes.h
+++ b/mknes.h
@@ -19,55 +19,69 @@
#define MIRROR_FOURSCREEN 2
struct ppu_state {
- uint16_t bg_shift_pattern_low;
- uint16_t bg_shift_pattern_high;
- uint16_t bg_shift_attrib_low;
- uint16_t bg_shift_attrib_high;
-
- uint16_t scanline;
- uint16_t dot;
- uint16_t vram_addr;
- uint16_t temp_addr;
- uint8_t fine_x;
- uint8_t bg_next_tile_id;
- uint8_t bg_next_tile_attrib;
- uint8_t bg_next_tile_lsb;
- uint8_t bg_next_tile_msb;
- uint8_t oam_addr;
- uint8_t oam_data;
- uint8_t even_frame;
-
- uint8_t reg_ctrl;
- uint8_t reg_mask;
- uint8_t reg_status;
-
- uint8_t write_latch;
- uint8_t vram_read_buffer;
- uint8_t open_bus;
-
- uint8_t sprite_count;
- uint8_t palette[32];
-
- uint8_t frame_ready;
- // NOTE(peter): CACHELINE 2 start here!
-
- uint8_t sprite_indexes[8];
- uint8_t sprite_positions[8];
- uint8_t sprite_priorities[8];
- uint8_t sprite_shift_lo[8];
- uint8_t sprite_shift_hi[8];
- uint8_t secondary_oam[32];
- uint8_t oam[256];
-
- uint8_t input[2]; // Controller 1 & 2
- uint8_t input_latch[2]; // Latched inputs after strobe
- uint8_t input_bit[2]; // Current bit position being shifted out
- uint8_t input_strobe; // Control bit (0 or 1)
-} __attribute__((packed, aligned(64)));
+ uint16_t bg_shift_pattern_low; // 0
+ uint16_t bg_shift_pattern_high; // 2
+ uint16_t bg_shift_attrib_low; // 4
+ uint16_t bg_shift_attrib_high; // 6
+
+ uint16_t scanline; // 8
+ uint16_t dot; // 10
+ uint16_t vram_addr; // 12
+ uint16_t temp_addr; // 14
+ uint8_t fine_x; // 16
+ uint8_t bg_next_tile_id; // 17
+ uint8_t bg_next_tile_attrib; // 18
+ uint8_t bg_next_tile_lsb; // 19
+ uint8_t bg_next_tile_msb; // 20
+ uint8_t oam_addr; // 21
+ uint8_t oam_data; // 22
+ uint8_t even_frame; // 23
+
+ uint8_t reg_ctrl; // 24
+ uint8_t reg_mask; // 25
+ uint8_t reg_status; // 26
+
+ uint8_t write_latch; // 27
+ uint8_t vram_read_buffer; // 28
+ uint8_t open_bus; // 29
+
+ uint8_t sprite_count; // 30
+ uint8_t overflow_scheduled_dot; // 31
+ uint8_t palette[32]; // 32
+
+ // NOTE(peter): CACHELINE 2
+ uint8_t secondary_oam[32] __attribute__((aligned(64)));
+ uint8_t temp_secondary_oam[32];
+
+ // NOTE(peter): CACHELINE 3
+ struct sprite_data {
+ uint8_t shift_lo;
+ uint8_t shift_hi;
+ uint8_t position;
+ uint8_t priority;
+ uint8_t palette;
+ } __attribute__((packed, aligned(64))) sprites[8];
+
+ uint8_t input[2]; // 40 - Controller 1 & 2
+ uint8_t input_latch[2]; // 42 - Latched inputs after strobe
+ uint8_t input_bit[2]; // 44 - Current bit position being shifted out
+ uint8_t input_strobe; // 46 - Control bit (0 or 1)
+ uint8_t frame_ready; // 47
+ uint8_t sprite_zero_in_range; // 48 - Boolean: is sprite 0 in range (will always be slot 0 if true)
+ uint8_t sprite_count_next; // 49 - Sprite count for next scanline
+ // 15 bytes left.
+
+ // NOTE(peter): CACHELINE 4
+ uint8_t oam[256] __attribute__((aligned(64)));
+} __attribute__((packed));
struct apu_state {
uint32_t frame_cycle;
+ uint16_t dmc_current_addr;
+ uint16_t dmc_bytes_remaining;
+ uint16_t dmc_sample_timer;
+
uint8_t mode;
uint8_t irq_inhibit;
uint8_t irq_pending;
@@ -79,11 +93,7 @@ struct apu_state {
uint8_t dmc_freq_index;
uint8_t dmc_sample_addr;
uint8_t dmc_sample_len;
-
- uint16_t dmc_current_addr;
- uint16_t dmc_bytes_remaining;
- uint16_t dmc_sample_timer;
-} __attribute__((packed, aligned(64)));
+} __attribute__((packed));
struct cpu_state {
size_t cycles;
@@ -96,15 +106,14 @@ struct cpu_state {
uint8_t n; // Negative Flag
uint8_t v; // Overflow Flag
// uint8_t b; // Break Flag (Set by BRK instruction) -- does not exist outside the stack
- uint8_t d; // Decimal Flag
+ uint8_t d; // Decimal Flag (exists but ignored on NES)
uint8_t i; // Interrupt Disable Flag
uint8_t z; // Zero Flag
uint8_t c; // Carry Flag
// --
uint8_t irq_pending;
uint8_t nmi_pending;
-} __attribute__((packed, aligned(64)));
-
+};
struct ines_state {
uint8_t mapper;
@@ -112,24 +121,24 @@ struct ines_state {
uint8_t mirroring; // 0 = H, 1 = V, 2 = 4-screen
uint32_t prg_size;
uint32_t chr_size;
-} __attribute__((packed, aligned(64)));
+};
struct nes_state {
- struct ppu_state ppu;
- struct mapper_functions mapper_function;
- union mapper_data mapper_data;
- struct cpu_state cpu;
- struct ines_state ines;
- struct apu_state apu;
-
- uint8_t ram[RAM_SIZE] __attribute__((aligned(4096)));
- uint8_t ciram[CIRAM_SIZE] __attribute__((aligned(4096)));
- uint8_t prg_rom[PRG_ROM_SIZE] __attribute__((aligned(4096)));
- uint8_t chr_rom[CHR_ROM_SIZE] __attribute__((aligned(4096)));
- uint8_t chr_ram[CHR_RAM_SIZE] __attribute__((aligned(4096)));
- uint8_t pixels[PIXELS_SIZE] __attribute__((aligned(4096)));
- uint8_t sram[SRAM_SIZE] __attribute__((aligned(4096)));
-} __attribute__((packed, aligned(4096)));
+ struct ppu_state ppu __attribute__((aligned(4096)));
+ struct mapper_functions mapper_function __attribute__((aligned(64)));
+ union mapper_data mapper_data __attribute__((aligned(64)));
+ struct cpu_state cpu __attribute__((aligned(64)));
+ struct ines_state ines __attribute__((aligned(64)));
+ struct apu_state apu __attribute__((aligned(64)));
+
+ uint8_t ram[RAM_SIZE] __attribute__((aligned(4096)));
+ uint8_t ciram[CIRAM_SIZE] __attribute__((aligned(4096)));
+ uint8_t prg_rom[PRG_ROM_SIZE] __attribute__((aligned(4096)));
+ uint8_t chr_rom[CHR_ROM_SIZE] __attribute__((aligned(4096)));
+ uint8_t chr_ram[CHR_RAM_SIZE] __attribute__((aligned(4096)));
+ uint8_t pixels[PIXELS_SIZE] __attribute__((aligned(4096)));
+ uint8_t sram[SRAM_SIZE] __attribute__((aligned(4096)));
+};
__attribute__((aligned(4096))) static uint32_t nes_palette[65] = {
0x585858ff, 0x00237cff, 0x0d1099ff, 0x300092ff, 0x4f006cff, 0x600035ff, 0x5c0500ff, 0x461800ff,
@@ -142,3 +151,83 @@ __attribute__((aligned(4096))) static uint32_t nes_palette[65] = {
0xdee086ff, 0xc6ec87ff, 0xb2f29dff, 0xa7f0c3ff, 0xa8e7f0ff, 0xacacacff, 0x000000ff, 0x000000ff,
0xffffffff // one extra for debug-coloring...
};
+
+struct remake_state {
+ struct { int32_t x, y, w, h; } viewport;
+ int32_t mouse_dx;
+ int32_t mouse_dy;
+
+ float contrast;
+ float saturation;
+ float brightness;
+ float tone_data[4];
+
+ // OpenGL Objects
+ GLuint shader_program;
+ GLuint persistence_program;
+ // GLuint upscale_program;
+ GLuint upscale_warp_program;
+ GLuint bloom_extract_program;
+ GLuint bloom_blur_program;
+ GLuint bloom_warp_program;
+ GLuint bloom_composite_program;
+
+ GLuint texture;
+ GLuint persistence_texture;
+ GLuint persistence_output_texture;
+ GLuint crt_output_texture;
+ GLuint bloom_texture;
+ GLuint bloom_temp_texture;
+ GLuint bloom_warped_texture;
+ GLuint upscaled_source_texture;
+
+ GLuint persistence_fbo;
+ GLuint upscaled_source_fbo;
+ GLuint crt_fbo;
+ GLuint bloom_fbo;
+ GLuint bloom_temp_fbo;
+ GLuint bloom_warp_fbo;
+
+ GLuint vao;
+ GLuint vbo;
+ GLuint ebo;
+
+ // CRT Shader Uniforms
+ GLuint uniform_resolution;
+ GLuint uniform_src_image_size;
+ GLuint uniform_brightness;
+ GLuint uniform_tone;
+ GLuint uniform_crt_emulation;
+ GLuint uniform_apply_mask;
+ GLuint uniform_sampler_location;
+
+ // Bloom Shader Uniforms
+ GLuint bloom_uniform_threshold;
+ GLuint bloom_uniform_sampler;
+ GLuint blur_uniform_horizontal;
+ GLuint blur_uniform_sampler;
+ GLuint composite_uniform_bloom_strength;
+ GLuint composite_uniform_crt_sampler;
+ GLuint composite_uniform_bloom_sampler;
+
+ // Bloom settings
+ float bloom_threshold;
+ float bloom_strength;
+ uint32_t bloom_width;
+ uint32_t bloom_height;
+
+ // Phosphor persistence
+ float persistence_decay;
+
+ // Rendering & Dynamic Resolution
+ uint32_t render_width; // The actual remake resolution (e.g., 360)
+ uint32_t render_height; // The actual remake resolution (e.g., 270)
+ uint32_t frame_number;
+ uint8_t running;
+ uint8_t toggle_crt_emulation;
+ uint8_t toggle_bloom;
+ uint8_t fullscreen;
+ uint8_t viewport_changed; // Flag to signal render thread to recreate FBOs
+};
+
+// static struct remake_state state;