From 4857ed73e80619d6046af223a61242e99e81235a Mon Sep 17 00:00:00 2001 From: Determinant Date: Tue, 14 Nov 2017 20:38:45 -0500 Subject: ppu optimization --- src/main.rs | 51 ++++++++++++---------------- src/mapper.rs | 71 +++++++++++++++++++------------------- src/memory.rs | 64 ++++++++++++++++++++--------------- src/ppu.rs | 107 ++++++++++++++++++++++++++-------------------------------- 4 files changed, 143 insertions(+), 150 deletions(-) diff --git a/src/main.rs b/src/main.rs index eb327ac..19364c7 100644 --- a/src/main.rs +++ b/src/main.rs @@ -19,11 +19,11 @@ use sdl2::rect::Rect; use sdl2::event::Event; use sdl2::keyboard::Keycode; -struct Window { +struct DummyWindow { buff: RefCell<[[u8; 256]; 240]> } -impl ppu::Screen for Window { +impl ppu::Screen for DummyWindow { fn put(&self, x: u8, y: u8, color: u8) { self.buff.borrow_mut()[y as usize][x as usize] = color; } @@ -75,20 +75,20 @@ impl SDLWindow { } } -const PIXEL_SIZE: u32 = 4; -const COLORS: [u32; 64] = [ - 0x666666, 0x002A88, 0x1412A7, 0x3B00A4, 0x5C007E, 0x6E0040, 0x6C0600, 0x561D00, - 0x333500, 0x0B4800, 0x005200, 0x004F08, 0x00404D, 0x000000, 0x000000, 0x000000, - 0xADADAD, 0x155FD9, 0x4240FF, 0x7527FE, 0xA01ACC, 0xB71E7B, 0xB53120, 0x994E00, - 0x6B6D00, 0x388700, 0x0C9300, 0x008F32, 0x007C8D, 0x000000, 0x000000, 0x000000, - 0xFFFEFF, 0x64B0FF, 0x9290FF, 0xC676FF, 0xF36AFF, 0xFE6ECC, 0xFE8170, 0xEA9E22, - 0xBCBE00, 0x88D800, 0x5CE430, 0x45E082, 0x48CDDE, 0x4F4F4F, 0x000000, 0x000000, - 0xFFFEFF, 0xC0DFFF, 0xD3D2FF, 0xE8C8FF, 0xFBC2FF, 0xFEC4EA, 0xFECCC5, 0xF7D8A5, - 0xE4E594, 0xCFEF96, 0xBDF4AB, 0xB3F3CC, 0xB5EBF2, 0xB8B8B8, 0x000000, 0x000000, +const PIXEL_SIZE: u32 = 2; +const RGB_COLORS: [u32; 64] = [ + 0x666666, 0x002a88, 0x1412a7, 0x3b00a4, 0x5c007e, 0x6e0040, 0x6c0600, 0x561d00, + 0x333500, 0x0b4800, 0x005200, 0x004f08, 0x00404d, 0x000000, 0x000000, 0x000000, + 0xadadad, 0x155fd9, 0x4240ff, 0x7527fe, 0xa01acc, 0xb71e7b, 0xb53120, 0x994e00, + 0x6b6d00, 0x388700, 0x0c9300, 0x008f32, 0x007c8d, 0x000000, 0x000000, 0x000000, + 0xfffeff, 0x64b0ff, 0x9290ff, 0xc676ff, 0xf36aff, 0xfe6ecc, 0xfe8170, 0xea9e22, + 0xbcbe00, 0x88d800, 0x5ce430, 0x45e082, 0x48cdde, 0x4f4f4f, 0x000000, 0x000000, + 0xfffeff, 0xc0dfff, 0xd3d2ff, 0xe8c8ff, 0xfbc2ff, 0xfec4ea, 0xfeccc5, 0xf7d8a5, + 0xe4e594, 0xcfef96, 0xbdf4ab, 0xb3f3cc, 0xb5ebf2, 0xb8b8b8, 0x000000, 0x000000, ]; fn get_rgb(color: u8) -> Color { - let c = COLORS[color as usize]; + let c = RGB_COLORS[color as usize]; Color::RGB((c >> 16) as u8, ((c >> 8) & 0xff) as u8, (c & 0xff) as u8) } @@ -162,19 +162,23 @@ fn main() { } let sram = vec![0; 0x4000]; println!("read prg {}", file.read(&mut prg_rom[..]).unwrap()); + /* for (i, v) in prg_rom.iter().enumerate() { print!("{:02x} ", v); if i & 15 == 15 { println!(" {:04x}", i); } } + */ println!("read chr {}", file.read(&mut chr_rom[..]).unwrap()); + /* for (i, v) in chr_rom.iter().enumerate() { print!("{:02x} ", v); if i & 15 == 15 { println!(""); } } + */ let cart = cartridge::Cartridge::new(chr_rom, prg_rom, sram, mirror); //let win = Window {buff: RefCell::new([[0; 256]; 240])}; let win = SDLWindow::new(); @@ -185,33 +189,22 @@ fn main() { let mut cpu = mos6502::CPU::new(&mem); mem.init(&mut cpu, &mut ppu); let mut cnt = 0; - let mut cnt2 = 0; - let mut flag = false; loop { - if win.poll() {break} + if cnt == 1000 { + if win.poll() {break} + cnt = 0; + } cpu.step(); //println!("cpu at 0x{:04x}", cpu.get_pc()); while cpu.cycle > 0 { for _ in 0..3 { - cnt2 += 1; if ppu.tick() { println!("triggering nmi"); cpu.trigger_nmi(); } - if ppu.get_flag_vblank() { - if !flag { - println!("{} cpu {} ppu per frame", cnt, cnt2); - cnt2 = 0; - cnt = 0; - flag = true; - //pmem.dump(); - } - } else { - flag = false; - } } cpu.cycle -= 1; - cnt += 1; } + cnt += 1; } } diff --git a/src/mapper.rs b/src/mapper.rs index c54acb4..210b59f 100644 --- a/src/mapper.rs +++ b/src/mapper.rs @@ -1,61 +1,64 @@ #![allow(dead_code)] use memory::VMem; use cartridge::{Cartridge, BankType}; -use core::cell::RefCell; +use core::cell::UnsafeCell; pub struct Mapper2<'a> { cart: &'a Cartridge, - prg_bank1: RefCell<&'a [u8]>, - prg_bank2: RefCell<&'a [u8]>, - chr_bank: RefCell<&'a mut [u8]>, - sram: RefCell<&'a mut [u8]>, + prg_bank1: UnsafeCell<&'a [u8]>, + prg_bank2: UnsafeCell<&'a [u8]>, + chr_bank: UnsafeCell<&'a mut [u8]>, + sram: UnsafeCell<&'a mut [u8]>, prg_nbank: usize } impl<'a> VMem for Mapper2<'a> { fn read(&self, addr: u16) -> u8 { let addr = addr as usize; - if addr < 0x2000 { /* 0x2000 size bank */ - self.chr_bank.borrow()[addr] - } else if addr >= 0xc000 { /* 0x4000 size bank */ - self.prg_bank2.borrow()[addr - 0xc000] - } else if addr >= 0x8000 { /* 0x4000 size bank */ - self.prg_bank1.borrow()[addr - 0x8000] - } else if addr >= 0x6000 { - self.sram.borrow()[addr - 0x6000] - } else { - panic!("unmapped address: 0x{:04x}", addr) + unsafe { + if addr < 0x2000 { /* 0x2000 size bank */ + (*self.chr_bank.get())[addr] + } else if addr >= 0xc000 { /* 0x4000 size bank */ + (*self.prg_bank2.get())[addr - 0xc000] + } else if addr >= 0x8000 { /* 0x4000 size bank */ + (*self.prg_bank1.get())[addr - 0x8000] + } else if addr >= 0x6000 { + (*self.sram.get())[addr - 0x6000] + } else { + panic!("unmapped address: 0x{:04x}", addr) + } } } fn write(&self, addr: u16, data: u8) { let addr = addr as usize; - if addr < 0x2000 { - self.chr_bank.borrow_mut()[addr] = data; - } else if addr >= 0x8000 { - (*self.prg_bank1.borrow_mut()) = unsafe { - &*self.cart.get_bank(((data as usize) % self.prg_nbank) << 14, - 0x4000, - BankType::PrgRom)}; - } else if addr >= 0x6000 { - self.sram.borrow_mut()[addr - 0x6000] = data; - } else { - panic!("invalid write to address: 0x{:04x}", addr); + unsafe { + if addr < 0x2000 { + (*self.chr_bank.get())[addr] = data; + } else if addr >= 0x8000 { + (*self.prg_bank1.get()) = + &*self.cart.get_bank(((data as usize) % self.prg_nbank) << 14, + 0x4000, + BankType::PrgRom); + } else if addr >= 0x6000 { + (*self.sram.get())[addr - 0x6000] = data; + } else { + panic!("invalid write to address: 0x{:04x}", addr); + } } } } impl<'a> Mapper2<'a> { - pub fn new(cart: *const Cartridge) -> Self { + pub fn new(cart: &'a Cartridge) -> Self { unsafe { - let cart = &*cart; let nbank = cart.get_size(BankType::PrgRom) >> 14; - Mapper2{cart: &cart, - prg_bank1: RefCell::new(&*cart.get_bank(0, 0x4000, BankType::PrgRom)), - prg_bank2: RefCell::new(&*cart.get_bank((nbank - 1) << 14, 0x4000, BankType::PrgRom)), - chr_bank: RefCell::new(&mut *cart.get_bank(0, 0x2000, BankType::ChrRom)), - sram: RefCell::new(&mut *cart.get_bank(0, 0x2000, BankType::Sram)), - prg_nbank: nbank} + Mapper2{cart, + prg_bank1: UnsafeCell::new(&*cart.get_bank(0, 0x4000, BankType::PrgRom)), + prg_bank2: UnsafeCell::new(&*cart.get_bank((nbank - 1) << 14, 0x4000, BankType::PrgRom)), + chr_bank: UnsafeCell::new(&mut *cart.get_bank(0, 0x2000, BankType::ChrRom)), + sram: UnsafeCell::new(&mut *cart.get_bank(0, 0x2000, BankType::Sram)), + prg_nbank: nbank} } } } diff --git a/src/memory.rs b/src/memory.rs index a3e9d70..7d14b61 100644 --- a/src/memory.rs +++ b/src/memory.rs @@ -2,7 +2,7 @@ use ppu::PPU; use mos6502::CPU; use cartridge::{MirrorType, Cartridge}; -use core::cell::{RefCell, Cell}; +use core::cell::{UnsafeCell, Cell}; use core::ptr::null_mut; pub trait VMem { @@ -11,7 +11,7 @@ pub trait VMem { } pub struct CPUMemory<'a> { - sram: RefCell<[u8; 2048]>, + sram: UnsafeCell<[u8; 2048]>, ppu: Cell<*mut PPU<'a>>, cpu: Cell<*mut CPU<'a>>, mapper: &'a VMem @@ -19,7 +19,7 @@ pub struct CPUMemory<'a> { impl<'a> CPUMemory<'a> { pub fn new(mapper: &'a VMem) -> Self { - CPUMemory{sram: RefCell::new([0; 2048]), + CPUMemory{sram: UnsafeCell::new([0; 2048]), cpu: Cell::new(null_mut()), ppu: Cell::new(null_mut()), mapper} @@ -37,7 +37,7 @@ impl<'a> VMem for CPUMemory<'a> { fn read(&self, addr: u16) -> u8 { match addr { _ => if addr < 0x2000 { - self.sram.borrow()[(addr & 0x07ff) as usize] + unsafe{(*self.sram.get())[(addr & 0x07ff) as usize]} } else if addr < 0x4000 { let ppu = unsafe {&mut *self.ppu.get()}; match addr & 0x7 { @@ -47,7 +47,6 @@ impl<'a> VMem for CPUMemory<'a> { _ => 0 } } else if addr < 0x6000 { - println!("feeding dummy data for 0x{:04x}", addr); 0 } else { self.mapper.read(addr) @@ -58,7 +57,7 @@ impl<'a> VMem for CPUMemory<'a> { let ppu = unsafe {&mut *self.ppu.get()}; let cpu = unsafe {&mut *self.cpu.get()}; if addr < 0x2000 { - self.sram.borrow_mut()[(addr & 0x07ff) as usize] = data; + unsafe{(*self.sram.get())[(addr & 0x07ff) as usize] = data;} } else if addr < 0x4000 { match addr & 0x7 { 0x0 => ppu.write_ctl(data), @@ -83,9 +82,8 @@ impl<'a> VMem for CPUMemory<'a> { } pub struct PPUMemory<'a> { - pattern_table: RefCell<[u8; 0x2000]>, - nametable: RefCell<[u8; 0x800]>, - palette: RefCell<[u8; 0x20]>, + nametable: UnsafeCell<[u8; 0x800]>, + palette: UnsafeCell<[u8; 0x20]>, cart: &'a Cartridge, mapper: &'a VMem, } @@ -94,21 +92,22 @@ impl<'a> PPUMemory<'a> { pub fn new(mapper: &'a VMem, cart: &'a Cartridge) -> Self { PPUMemory{ - pattern_table: RefCell::new([0; 0x2000]), - nametable: RefCell::new([0; 0x800]), - palette: RefCell::new([0; 0x20]), + nametable: UnsafeCell::new([0; 0x800]), + palette: UnsafeCell::new([0; 0x20]), cart, mapper} } pub fn dump(&self) { - for (i, v) in self.palette.borrow().iter().enumerate() { - print!("{:02x} ", *v); - if (i & 0x7) == 0x7 {println!("@{:02x}", i)} - } - for (i, v) in self.nametable.borrow().iter().enumerate() { - print!("{:02x} ", *v); - if (i & 0x1f) == 0x1f {println!("@{:02x}", i)} + unsafe { + for (i, v) in (*self.palette.get()).iter().enumerate() { + print!("{:02x} ", *v); + if (i & 0x7) == 0x7 {println!("@{:02x}", i)} + } + for (i, v) in (*self.nametable.get()).iter().enumerate() { + print!("{:02x} ", *v); + if (i & 0x1f) == 0x1f {println!("@{:02x}", i)} + } } } } @@ -121,6 +120,7 @@ const MIRROR_IDX: [[u8; 4]; 5] = [ [0, 1, 2, 3], ]; +#[inline(always)] fn get_mirror_addr(kind: MirrorType, mut addr: u16) -> u16 { addr = (addr - 0x2000) & 0x0fff; let table = addr >> 10; @@ -128,7 +128,8 @@ fn get_mirror_addr(kind: MirrorType, mut addr: u16) -> u16 { 0x2000 + ((MIRROR_IDX[kind as usize][table as usize] as u16) << 10) + offset } -fn mirror_palette(addr: u16) -> u16 { +#[inline(always)] +fn get_mirror_palette(addr: u16) -> u16 { if addr >= 0x10 && addr & 3 == 0 { addr - 0x10 } else { addr } @@ -141,11 +142,15 @@ impl<'a> VMem for PPUMemory<'a> { self.mapper.read(addr) } else if addr < 0x3f00 { let kind = self.cart.mirror_type; - self.nametable.borrow() + unsafe { + (*self.nametable.get()) [(get_mirror_addr(kind, addr) & 0x07ff) as usize] + } } else if addr < 0x4000 { - self.palette.borrow() - [mirror_palette(addr & 0x1f) as usize] + unsafe { + (*self.palette.get()) + [get_mirror_palette(addr & 0x1f) as usize] + } } else { panic!("invalid ppu read access at 0x{:04x}", addr) } @@ -153,16 +158,19 @@ impl<'a> VMem for PPUMemory<'a> { fn write(&self, mut addr: u16, data: u8) { addr &= 0x3fff; - println!("writing 0x{:02x} to 0x{:04x}", data, addr); if addr < 0x2000 { self.mapper.write(addr, data) } else if addr < 0x3f00 { let kind = self.cart.mirror_type; - self.nametable.borrow_mut() - [(get_mirror_addr(kind, addr) & 0x07ff) as usize] = data + unsafe { + (*self.nametable.get()) + [(get_mirror_addr(kind, addr) & 0x07ff) as usize] = data; + } } else if addr < 0x4000 { - self.palette.borrow_mut() - [mirror_palette(addr & 0x1f) as usize] = data + unsafe { + (*self.palette.get()) + [get_mirror_palette(addr & 0x1f) as usize] = data; + } } else { panic!("invalid ppu write access at 0x{:04x}", addr) } diff --git a/src/ppu.rs b/src/ppu.rs index 7f8a39d..8daf009 100644 --- a/src/ppu.rs +++ b/src/ppu.rs @@ -34,8 +34,7 @@ pub struct PPU<'a> { cycle: u16, /* cycle in the current scanline */ /* rendering regs & latches */ /* background registers */ - bg_bitmap: [u16; 2], - bg_palette: [u16; 2], + bg_pixel: u64, /* background latches */ bg_nt: u8, bg_attr: u8, @@ -44,7 +43,7 @@ pub struct PPU<'a> { /* sprites */ oam: [Sprite; 64], oam2: [usize; 8], - sp_bitmap: [[u8; 2]; 8], + sp_pixel: [u32; 8], sp_idx: [usize; 8], sp_cnt: [u8; 8], rendering: bool, @@ -56,17 +55,20 @@ pub struct PPU<'a> { } impl<'a> PPU<'a> { + #[inline] pub fn write_ctl(&mut self, data: u8) { self.reg = data; self.ppuctl = data; self.t = (self.t & 0x73ff) | ((data as u16 & 3) << 10); } + #[inline] pub fn write_mask(&mut self, data: u8) { self.reg = data; self.ppumask = data; } + #[inline] pub fn read_status(&mut self) -> u8 { let res = (self.ppustatus & !0x1fu8) | (self.reg & 0x1f); self.ppustatus &= !PPU::FLAG_VBLANK; @@ -77,11 +79,13 @@ impl<'a> PPU<'a> { res } + #[inline] pub fn write_oamaddr(&mut self, data: u8) { self.reg = data; self.oamaddr = data; } + #[inline] pub fn write_oamdata(&mut self, data: u8) { self.reg = data; if self.rendering { return } @@ -92,6 +96,7 @@ impl<'a> PPU<'a> { } } + #[inline] pub fn read_oamdata(&self) -> u8 { unsafe { let oam_raw = transmute::<&[Sprite; 64], &[u8; 256]>(&self.oam); @@ -99,6 +104,7 @@ impl<'a> PPU<'a> { } } + #[inline] pub fn write_scroll(&mut self, data: u8) { self.reg = data; let data = data as u16; @@ -116,6 +122,7 @@ impl<'a> PPU<'a> { } } + #[inline] pub fn write_addr(&mut self, data: u8) { self.reg = data; let data = data as u16; @@ -132,6 +139,7 @@ impl<'a> PPU<'a> { } } + #[inline] pub fn read_data(&mut self) -> u8 { let data = self.mem.read(self.v); let res = if self.v & 0x3fff < 0x3f00 { @@ -149,6 +157,7 @@ impl<'a> PPU<'a> { res } + #[inline] pub fn write_data(&mut self, data: u8) { self.reg = data; self.mem.write(self.v, data); @@ -158,6 +167,7 @@ impl<'a> PPU<'a> { }); } + #[inline] pub fn write_oamdma(&mut self, data: u8, cpu: &mut CPU) { self.reg = data; let mut addr = (data as u16) << 8; @@ -182,6 +192,7 @@ impl<'a> PPU<'a> { #[inline(always)] fn get_show_bg(&self) -> bool { (self.ppumask >> 3) & 1 == 1} #[inline(always)] fn get_show_sp(&self) -> bool { (self.ppumask >> 4) & 1 == 1} #[inline(always)] pub fn get_flag_vblank(&self) -> bool { (self.ppustatus >> 7) & 1 == 1 } + const FLAG_OVERFLOW: u8 = 1 << 5; const FLAG_SPRITE_ZERO: u8 = 1 << 6; const FLAG_VBLANK: u8 = 1 << 7; @@ -224,19 +235,16 @@ impl<'a> PPU<'a> { fn load_bgtile(&mut self) { /* load the tile bitmap to high 8 bits of bitmap, * assume the high 8 bits are zeros */ - //if (!(self.bg_bitmap[0] >> 8 == 0 && - // self.bg_bitmap[1] >> 8 == 0 && - // self.bg_palette[0] >> 8 == 0 && - // self.bg_palette[1] >> 8 == 0)) { - // println!("at cycle {} {}", self.scanline, self.cycle) } - assert!(self.bg_bitmap[0] >> 8 == 0 && - self.bg_bitmap[1] >> 8 == 0 && - self.bg_palette[0] >> 8 == 0 && - self.bg_palette[1] >> 8 == 0); - self.bg_bitmap[0] |= (PPU::reverse_byte(self.bg_bit_low) as u16) << 8; - self.bg_bitmap[1] |= (PPU::reverse_byte(self.bg_bit_high) as u16) << 8; - self.bg_palette[0] |= (self.bg_attr & 1) as u16 * 0xff00; - self.bg_palette[1] |= ((self.bg_attr >> 1) & 1) as u16 * 0xff00; + assert!(self.bg_pixel >> 32 == 0); + let mut t: u64 = 0; + let mut bl = self.bg_bit_low; + let mut bh = self.bg_bit_high; + for _ in 0..8 { + t = (t << 4) | ((self.bg_attr << 2) | (bl & 1) | ((bh & 1) << 1)) as u64; + bl >>= 1; + bh >>= 1; + } + self.bg_pixel |= t << 32; } #[inline(always)] @@ -245,11 +253,7 @@ impl<'a> PPU<'a> { if self.sp_idx[i] > 0xff { break } let c0 = *c; match c0 { - 0 => { - let t = &mut self.sp_bitmap[i]; - t[0] = t[0].wrapping_shr(1); - t[1] = t[1].wrapping_shr(1); - }, + 0 => self.sp_pixel[i] >>= 4, _ => *c = c0 - 1 } } @@ -257,12 +261,7 @@ impl<'a> PPU<'a> { #[inline(always)] fn shift_bgtile(&mut self) { - let t1 = &mut self.bg_bitmap; - let t2 = &mut self.bg_palette; - t1[0] = t1[0].wrapping_shr(1); - t1[1] = t1[1].wrapping_shr(1); - t2[0] = t2[0].wrapping_shr(1); - t2[1] = t2[1].wrapping_shr(1); + self.bg_pixel >>= 4; } #[inline(always)] @@ -381,44 +380,39 @@ impl<'a> PPU<'a> { self.sp_cnt[i] = s.x; let mut low = self.mem.read(ptable | ((tidx as u16) << 4) | 0x0 | y as u16); let mut high = self.mem.read(ptable | ((tidx as u16) << 4) | 0x8 | y as u16); - if (s.attr & 0x40) != 0x40 { + if (s.attr & 0x40) == 0x40 { low = PPU::reverse_byte(low); high = PPU::reverse_byte(high); } - self.sp_bitmap[i][0] = low; - self.sp_bitmap[i][1] = high; + let attr = s.attr & 3; + let mut t = 0u32; + for _ in 0..8 { + t = (t << 4) | ((attr << 2) | ((high & 1) << 1) | (low & 1)) as u32; + high >>= 1; + low >>= 1; + } + self.sp_pixel[i] = t; } } - #[inline(always)] - fn get_bg_pidx(&self) -> u8 { - if self.get_show_bg() { - (((self.bg_bitmap[1] >> self.x) & 1) << 1) as u8 | - ((self.bg_bitmap[0] >> self.x) & 1) as u8 - } else { 0 } - } - - #[inline(always)] - fn get_sp_pidx(&self, i: usize) -> u8 { - if self.get_show_sp() { - ((self.sp_bitmap[i][1] & 1) << 1) | (self.sp_bitmap[i][0] & 1) - } else { 0 } - } - fn render_pixel(&mut self) { let x = self.cycle - 1; + let bg = ((self.bg_pixel >> (self.x << 2)) & 0xf) as u16; let bg_pidx = - if x >= 8 || self.get_show_leftmost_bg() {self.get_bg_pidx()} - else {0}; + if x >= 8 || self.get_show_leftmost_bg() { + if self.get_show_bg() {bg & 3} else {0} + } else {0}; let mut sp_pidx = 0x0; - let mut sp_id = 0; let mut pri = 0x1; + let mut sp = 0; + let show_sp = self.get_show_sp(); if x >= 8 || self.get_show_leftmost_sp() { for i in 0..8 { if self.sp_idx[i] > 0xff { break } - let s = &self.oam[self.sp_idx[i]]; if self.sp_cnt[i] != 0 { continue; } /* not active */ - match self.get_sp_pidx(i) { + let s = &self.oam[self.sp_idx[i]]; + sp = if show_sp {(self.sp_pixel[i] & 0xf) as u16} else { 0 }; + match sp & 3 { 0x0 => (), pidx => { if bg_pidx != 0 && self.sp_idx[i] == 0 && @@ -426,7 +420,6 @@ impl<'a> PPU<'a> { self.ppustatus |= PPU::FLAG_SPRITE_ZERO; /* set sprite zero hit */ } sp_pidx = pidx; - sp_id = i; pri = (s.attr >> 5) & 1; break; } @@ -438,14 +431,11 @@ impl<'a> PPU<'a> { self.scr.put((self.cycle - 1) as u8, self.scanline as u8, self.mem.read(if (pri == 0 || bg_pidx == 0) && sp_pidx != 0 { - 0x3f10 | ((self.oam[self.sp_idx[sp_id]].attr & 3) << 2) as u16 | - sp_pidx as u16 + 0x3f10 | sp } else { 0x3f00 | match bg_pidx { 0 => 0, - _ => ((((self.bg_palette[1] >> self.x) & 1) << 3) | - (((self.bg_palette[0] >> self.x) & 1) << 2)) as u16 | - bg_pidx as u16 + _ => bg } })); } @@ -467,14 +457,13 @@ impl<'a> PPU<'a> { oamaddr, reg: 0, x: 0, v: 0, t: 0, w, cycle, - bg_bitmap: [0; 2], - bg_palette: [0; 2], + bg_pixel: 0, bg_nt: 0, bg_attr: 0, bg_bit_low: 0, bg_bit_high: 0, oam: [Sprite{y: 0, tile: 0, attr: 0, x: 0}; 64], oam2: [0x100; 8], sp_idx: [0x100; 8], - sp_bitmap: [[0; 2]; 8], + sp_pixel: [0; 8], sp_cnt: [0; 8], rendering: false, buffered_read, -- cgit v1.2.3-70-g09d2