diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/main.rs | 5 | ||||
-rw-r--r-- | src/memory.rs | 14 | ||||
-rw-r--r-- | src/ppu.rs | 48 |
3 files changed, 28 insertions, 39 deletions
diff --git a/src/main.rs b/src/main.rs index 9220694..57af3e4 100644 --- a/src/main.rs +++ b/src/main.rs @@ -89,6 +89,7 @@ impl SDLWindow { } } + #[inline(always)] fn poll(&self) -> bool { for event in self.events.borrow_mut().poll_iter() { match event { @@ -239,9 +240,9 @@ fn main() { if duration_per_frame > e { let diff = duration_per_frame - e; sleep(diff); - println!("{} faster", diff.subsec_nanos() as f64 / 1e6); + //println!("{} faster", diff.subsec_nanos() as f64 / 1e6); } else { - println!("{} slower", (e - duration_per_frame).subsec_nanos() as f64 / 1e6); + //println!("{} slower", (e - duration_per_frame).subsec_nanos() as f64 / 1e6); } timer = Instant::now(); cnt -= CYC_PER_FRAME; diff --git a/src/memory.rs b/src/memory.rs index 6d83cbc..d2c9e52 100644 --- a/src/memory.rs +++ b/src/memory.rs @@ -1,5 +1,5 @@ #![allow(dead_code)] -use ppu::{PPU, PMem}; +use ppu::PPU; use mos6502::CPU; use cartridge::{MirrorType, Cartridge}; use core::cell::{UnsafeCell, Cell}; @@ -133,31 +133,31 @@ fn get_mirror_palette(addr: u16) -> u16 { } else { addr } } -impl<'a> PMem for PPUMemory<'a> { +impl<'a> PPUMemory<'a> { #[inline(always)] - fn read_nametable(&self, addr: u16) -> u8 { + pub fn read_nametable(&self, addr: u16) -> u8 { let kind = self.cart.mirror_type; unsafe {(*self.nametable.get())[(get_mirror_addr(kind, addr) & 0x7ff) as usize]} } #[inline(always)] - fn read_palette(&self, addr: u16) -> u8 { unsafe { + pub fn read_palette(&self, addr: u16) -> u8 { unsafe { (*self.palette.get())[get_mirror_palette(addr) as usize] }} #[inline(always)] - fn write_nametable(&self, addr: u16, data: u8) { + pub fn write_nametable(&self, addr: u16, data: u8) { let kind = self.cart.mirror_type; unsafe {(*self.nametable.get())[(get_mirror_addr(kind, addr) & 0x7ff) as usize] = data} } #[inline(always)] - fn write_palette(&self, addr: u16, data: u8) { unsafe { + pub fn write_palette(&self, addr: u16, data: u8) { unsafe { (*self.palette.get())[get_mirror_palette(addr) as usize] = data; }} #[inline(always)] - fn read_mapper(&self, addr: u16) -> u8 { + pub fn read_mapper(&self, addr: u16) -> u8 { self.mapper.read(addr) } @@ -1,5 +1,5 @@ #![allow(dead_code)] -use memory::VMem; +use memory::{VMem, PPUMemory}; use mos6502::CPU; use core::intrinsics::transmute; @@ -9,15 +9,6 @@ pub trait Screen { fn render(&self); } -pub trait PMem: VMem { - fn read_nametable(&self, addr: u16) -> u8; - fn read_palette(&self, addr: u16) -> u8; - fn write_nametable(&self, addr: u16, data: u8); - fn write_palette(&self, addr: u16, data: u8); - fn read_mapper(&self, addr: u16) -> u8; - fn write_mapper(&self, addr: u16, data: u8); -} - #[repr(C, packed)] #[derive(Copy, Clone)] struct Sprite { @@ -60,7 +51,7 @@ pub struct PPU<'a> { buffered_read: u8, early_read: bool, /* IO */ - mem: &'a PMem, + mem: &'a PPUMemory<'a>, scr: &'a Screen, } @@ -313,12 +304,12 @@ impl<'a> PPU<'a> { #[inline(always)] fn clear_sprite(&mut self) { - if self.scanline == 261 { return } + assert!(self.scanline != 261); self.oam2 = [0x100; 8]; } fn eval_sprite(&mut self) { - if self.scanline == 261 { return } + assert!(self.scanline != 261); /* we use scanline here because s.y is the (actual y) - 1 */ let mut nidx = 0; let mut n = 0; @@ -450,7 +441,7 @@ impl<'a> PPU<'a> { })); } - pub fn new(mem: &'a PMem, scr: &'a Screen) -> Self { + pub fn new(mem: &'a PPUMemory<'a>, scr: &'a Screen) -> Self { let ppuctl = 0x00; let ppumask = 0x00; let ppustatus = 0xa0; @@ -499,20 +490,16 @@ impl<'a> PPU<'a> { return false; } let visible_line = self.scanline < 240; - let pre_render = self.scanline == 261; - self.rendering = pre_render || visible_line; - if pre_render && cycle == 1 { - /* clear vblank, sprite zero hit & overflow */ - self.ppustatus &= !(PPU::FLAG_VBLANK | - PPU::FLAG_SPRITE_ZERO | PPU::FLAG_OVERFLOW); - - } else if self.rendering && (self.get_show_bg() || self.get_show_sp()) { - if pre_render && 279 < cycle && cycle < 305 { + let pre_line = self.scanline == 261; + self.rendering = pre_line || visible_line; + if self.rendering && (self.get_show_bg() || self.get_show_sp()) { + if pre_line && 279 < cycle && cycle < 305 { self.reset_y(); } else { let visible_cycle = 0 < cycle && cycle < 257; /* 1..256 */ - let fetch_cycle = visible_cycle || (320 < cycle && cycle < 337); - if fetch_cycle { /* 1..256 and 321..336 */ + let prefetch_cycle = 320 < cycle && cycle < 337; + let fetch_cycle = visible_cycle || prefetch_cycle; + if (visible_line && fetch_cycle) || (pre_line && prefetch_cycle) { match cycle & 0x7 { 1 => { self.load_bgtile(); @@ -530,15 +517,11 @@ impl<'a> PPU<'a> { 256 => self.wrapping_inc_y(), _ => () } - if visible_line && visible_cycle { + if visible_cycle { self.render_pixel(); self.shift_sprites(); } self.shift_bgtile(); - } else if cycle > 336 { /* 337..340 */ - if cycle & 1 == 1 { - self.fetch_nametable_byte(); - } } else if cycle == 257 { /* we don't emulate fetch to per cycle precision because all data are fetched * from the secondary OAM which is not subject to any change during this @@ -546,6 +529,11 @@ impl<'a> PPU<'a> { self.reset_cx(); self.fetch_sprite(); } + if pre_line && cycle == 1 { + /* clear vblank, sprite zero hit & overflow */ + self.ppustatus &= !(PPU::FLAG_VBLANK | + PPU::FLAG_SPRITE_ZERO | PPU::FLAG_OVERFLOW); + } } } else if self.scanline == 241 && cycle == 1 { if !self.early_read { |