From 875ed46d790e6447394772995ebb06e38c9985c4 Mon Sep 17 00:00:00 2001 From: Tim Allen Date: Mon, 26 Sep 2011 21:38:57 +1000 Subject: [PATCH] Update to v082r23 release. byuu says: Ryphecha fixed the FF1 glitch, added two highpass filters to NES audio output (still working on a lowpass), and fixed VRC6 audio issues. I reduced the complexity of all eight supported mapping modes, and standardized them; and added in an overscan filter (not in archive) for chopping off all the NES edge garbage (8 pixels on the left and right, 16 on the top and bottom.) It's extreme, but anything less shows junk. I may make this part of the menu option, just clip off more on NES mode than SNES mode. --- bsnes/nes/apu/apu.cpp | 28 ++++- bsnes/nes/apu/apu.hpp | 13 ++ bsnes/nes/apu/serialization.cpp | 8 ++ bsnes/nes/cartridge/cartridge.cpp | 12 +- bsnes/nes/cartridge/cartridge.hpp | 12 +- bsnes/nes/mapper/aorom/aorom.cpp | 28 ++--- bsnes/nes/mapper/aorom/aorom.hpp | 11 +- bsnes/nes/mapper/bandai-fcg/bandai-fcg.cpp | 45 +++---- bsnes/nes/mapper/bandai-fcg/bandai-fcg.hpp | 11 +- bsnes/nes/mapper/cnrom/cnrom.cpp | 40 +++---- bsnes/nes/mapper/cnrom/cnrom.hpp | 11 +- bsnes/nes/mapper/mapper.cpp | 13 +- bsnes/nes/mapper/mapper.hpp | 17 +-- bsnes/nes/mapper/mmc1/mmc1.cpp | 70 ++++------- bsnes/nes/mapper/mmc1/mmc1.hpp | 14 +-- bsnes/nes/mapper/mmc3/mmc3.cpp | 27 ++--- bsnes/nes/mapper/mmc3/mmc3.hpp | 11 +- bsnes/nes/mapper/none/none.cpp | 38 +++--- bsnes/nes/mapper/none/none.hpp | 11 +- bsnes/nes/mapper/uorom/uorom.cpp | 35 +++--- bsnes/nes/mapper/uorom/uorom.hpp | 11 +- bsnes/nes/mapper/vrc6/vrc6.cpp | 130 ++++++++------------ bsnes/nes/mapper/vrc6/vrc6.hpp | 18 +-- bsnes/nes/ppu/ppu.cpp | 131 ++------------------- bsnes/nes/ppu/ppu.hpp | 1 - bsnes/ui/interface/interface.cpp | 4 +- bsnes/ui/main.cpp | 2 +- 27 files changed, 287 insertions(+), 465 deletions(-) diff --git a/bsnes/nes/apu/apu.cpp b/bsnes/nes/apu/apu.cpp index 3e55022f..6bd99690 100755 --- a/bsnes/nes/apu/apu.cpp +++ b/bsnes/nes/apu/apu.cpp @@ -47,7 +47,14 @@ void APU::main() { clock_frame_counter_divider(); signed output = rectangle_dac[rectangle_output] + dmc_triangle_noise_dac[dmc_output][triangle_output][noise_output]; - interface->audioSample(output + cartridge_sample); + + output = filter.run_hipass_strong(output); + output += cartridge_sample; + output = filter.run_hipass_weak(output); + //output = filter.run_lopass(output); + output = sclamp<16>(output); + + interface->audioSample(output); tick(); } @@ -67,6 +74,10 @@ void APU::set_sample(int16 sample) { } void APU::power() { + filter.hipass_strong = 0; + filter.hipass_weak = 0; + filter.lopass = 0; + for(unsigned n = 0; n < 2; n++) { rectangle[n].sweep.shift = 0; rectangle[n].sweep.decrement = 0; @@ -302,6 +313,21 @@ void APU::write(uint16 addr, uint8 data) { } } +signed APU::Filter::run_hipass_strong(signed sample) { + hipass_strong += ((((int64)sample << 16) - (hipass_strong >> 16)) * HiPassStrong) >> 16; + return sample - (hipass_strong >> 32); +} + +signed APU::Filter::run_hipass_weak(signed sample) { + hipass_weak += ((((int64)sample << 16) - (hipass_weak >> 16)) * HiPassWeak) >> 16; + return sample - (hipass_weak >> 32); +} + +signed APU::Filter::run_lopass(signed sample) { + lopass += ((((int64)sample << 16) - (lopass >> 16)) * LoPass) >> 16; + return (lopass >> 32); +} + bool APU::Sweep::check_period() { if(rectangle_period > 0x7ff) return false; diff --git a/bsnes/nes/apu/apu.hpp b/bsnes/nes/apu/apu.hpp index 5d56e90f..b9320cef 100755 --- a/bsnes/nes/apu/apu.hpp +++ b/bsnes/nes/apu/apu.hpp @@ -14,6 +14,19 @@ struct APU : Processor { void serialize(serializer&); APU(); + struct Filter { + enum : signed { HiPassStrong = 225574, HiPassWeak = 57593, LoPass = 86322413 }; + + int64 hipass_strong; + int64 hipass_weak; + int64 lopass; + + signed run_hipass_strong(signed sample); + signed run_hipass_weak(signed sample); + signed run_lopass(signed sample); + void serialize(serializer&); + } filter; + struct Envelope { uint4 speed; bool use_speed_as_volume; diff --git a/bsnes/nes/apu/serialization.cpp b/bsnes/nes/apu/serialization.cpp index a59df34f..4ff24314 100755 --- a/bsnes/nes/apu/serialization.cpp +++ b/bsnes/nes/apu/serialization.cpp @@ -1,6 +1,8 @@ void APU::serialize(serializer &s) { Processor::serialize(s); + filter.serialize(s); + rectangle[0].serialize(s); rectangle[1].serialize(s); triangle.serialize(s); @@ -11,6 +13,12 @@ void APU::serialize(serializer &s) { s.integer(cartridge_sample); } +void APU::Filter::serialize(serializer &s) { + s.integer(hipass_strong); + s.integer(hipass_weak); + s.integer(lopass); +} + void APU::Envelope::serialize(serializer &s) { s.integer(speed); s.integer(use_speed_as_volume); diff --git a/bsnes/nes/cartridge/cartridge.cpp b/bsnes/nes/cartridge/cartridge.cpp index dcbd4803..f568c800 100755 --- a/bsnes/nes/cartridge/cartridge.cpp +++ b/bsnes/nes/cartridge/cartridge.cpp @@ -85,27 +85,27 @@ Cartridge::Cartridge() { loaded = false; } -uint8 Cartridge::prg_read(uint16 addr) { +uint8 Cartridge::prg_read(unsigned addr) { return mapper->prg_read(addr); } -void Cartridge::prg_write(uint16 addr, uint8 data) { +void Cartridge::prg_write(unsigned addr, uint8 data) { return mapper->prg_write(addr, data); } -uint8 Cartridge::chr_read(uint16 addr) { +uint8 Cartridge::chr_read(unsigned addr) { return mapper->chr_read(addr); } -void Cartridge::chr_write(uint16 addr, uint8 data) { +void Cartridge::chr_write(unsigned addr, uint8 data) { return mapper->chr_write(addr, data); } -uint8 Cartridge::ciram_read(uint13 addr) { +uint8 Cartridge::ciram_read(unsigned addr) { return mapper->ciram_read(addr); } -void Cartridge::ciram_write(uint13 addr, uint8 data) { +void Cartridge::ciram_write(unsigned addr, uint8 data) { return mapper->ciram_write(addr, data); } diff --git a/bsnes/nes/cartridge/cartridge.hpp b/bsnes/nes/cartridge/cartridge.hpp index 901413b7..3ed45b05 100755 --- a/bsnes/nes/cartridge/cartridge.hpp +++ b/bsnes/nes/cartridge/cartridge.hpp @@ -20,14 +20,14 @@ struct Cartridge : Processor, property { //privileged: Mapper::Mapper *mapper; - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 ciram_read(unsigned addr); + void ciram_write(unsigned addr, uint8 data); uint8 *rom_data; unsigned rom_size; diff --git a/bsnes/nes/mapper/aorom/aorom.cpp b/bsnes/nes/mapper/aorom/aorom.cpp index 639986d9..646572f7 100755 --- a/bsnes/nes/mapper/aorom/aorom.cpp +++ b/bsnes/nes/mapper/aorom/aorom.cpp @@ -1,36 +1,28 @@ AOROM aorom; -uint8 AOROM::prg_read(uint16 addr) { +uint8 AOROM::prg_read(unsigned addr) { if(addr & 0x8000) { - unsigned rom_addr = (prg_bank << 15) | (addr & 0x7fff); - return cartridge.prg_data[mirror(rom_addr, cartridge.prg_size)]; + addr = (prg_bank << 15) | (addr & 0x7fff); + return Mapper::prg_read(addr); } - return cpu.mdr(); } -void AOROM::prg_write(uint16 addr, uint8 data) { +void AOROM::prg_write(unsigned addr, uint8 data) { if(addr & 0x8000) { prg_bank = data & 0x0f; mirror_select = data & 0x10; } } -uint8 AOROM::chr_read(uint16 addr) { - return cartridge.chr_data[mirror(addr, cartridge.chr_size)]; +uint8 AOROM::chr_read(unsigned addr) { + if(addr & 0x2000) return ppu.ciram_read((mirror_select << 10) | (addr & 0x03ff)); + return Mapper::chr_read(addr); } -void AOROM::chr_write(uint16 addr, uint8 data) { - if(cartridge.chr_ram == false) return; - cartridge.chr_data[mirror(addr, cartridge.chr_size)] = data; -} - -uint8 AOROM::ciram_read(uint13 addr) { - return ppu.ciram_read((mirror_select << 10) | (addr & 0x03ff)); -} - -void AOROM::ciram_write(uint13 addr, uint8 data) { - return ppu.ciram_write((mirror_select << 10) | (addr & 0x03ff), data); +void AOROM::chr_write(unsigned addr, uint8 data) { + if(addr & 0x2000) return ppu.ciram_write((mirror_select << 10) | (addr & 0x03ff), data); + return Mapper::chr_write(addr, data); } void AOROM::power() { diff --git a/bsnes/nes/mapper/aorom/aorom.hpp b/bsnes/nes/mapper/aorom/aorom.hpp index e0406ee3..32fd0c60 100755 --- a/bsnes/nes/mapper/aorom/aorom.hpp +++ b/bsnes/nes/mapper/aorom/aorom.hpp @@ -1,12 +1,9 @@ struct AOROM : Mapper { - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); void power(); void reset(); diff --git a/bsnes/nes/mapper/bandai-fcg/bandai-fcg.cpp b/bsnes/nes/mapper/bandai-fcg/bandai-fcg.cpp index e3bbfddc..f00bea12 100755 --- a/bsnes/nes/mapper/bandai-fcg/bandai-fcg.cpp +++ b/bsnes/nes/mapper/bandai-fcg/bandai-fcg.cpp @@ -17,21 +17,21 @@ void BandaiFCG::main() { } } -uint8 BandaiFCG::prg_read(uint16 addr) { - if(addr >= 0x8000 && addr <= 0xbfff) { - unsigned rom_addr = (prg_bank << 14) | (addr & 0x3fff); - return cartridge.prg_data[mirror(rom_addr, cartridge.prg_size)]; +uint8 BandaiFCG::prg_read(unsigned addr) { + if((addr & 0xc000) == 0x8000) { + addr = (prg_bank << 14) | (addr & 0x3fff); + return Mapper::prg_read(addr); } - if(addr >= 0xc000 && addr <= 0xffff) { - unsigned rom_addr = (0x0f << 14) | (addr & 0x3fff); - return cartridge.prg_data[mirror(rom_addr, cartridge.prg_size)]; + if((addr & 0xc000) == 0xc000) { + addr = (0x0f << 14) | (addr & 0x3fff); + return Mapper::prg_read(addr); } return cpu.mdr(); } -void BandaiFCG::prg_write(uint16 addr, uint8 data) { +void BandaiFCG::prg_write(unsigned addr, uint8 data) { if(addr >= 0x6000) { addr &= 0x0f; switch(addr) { @@ -62,25 +62,18 @@ void BandaiFCG::prg_write(uint16 addr, uint8 data) { } } -uint8 BandaiFCG::chr_read(uint16 addr) { - unsigned rom_addr = (chr_bank[addr >> 10] << 10) | (addr & 0x03ff); - return cartridge.chr_data[mirror(rom_addr, cartridge.chr_size)]; +uint8 BandaiFCG::chr_read(unsigned addr) { + if(addr & 0x2000) return ppu.ciram_read(ciram_addr(addr)); + + addr = (chr_bank[addr >> 10] << 10) | (addr & 0x03ff); + return Mapper::chr_read(addr); } -void BandaiFCG::chr_write(uint16 addr, uint8 data) { - if(cartridge.chr_ram == false) return; - unsigned rom_addr = (chr_bank[addr >> 10] << 10) | (addr & 0x03ff); - cartridge.chr_data[mirror(rom_addr, cartridge.chr_size)] = data; -} +void BandaiFCG::chr_write(unsigned addr, uint8 data) { + if(addr & 0x2000) return ppu.ciram_write(ciram_addr(addr), data); -uint8 BandaiFCG::ciram_read(uint13 addr) { - addr = ciram_addr(addr); - return ppu.ciram_read(addr); -} - -void BandaiFCG::ciram_write(uint13 addr, uint8 data) { - addr = ciram_addr(addr); - return ppu.ciram_write(addr, data); + addr = (chr_bank[addr >> 10] << 10) | (addr & 0x03ff); + Mapper::chr_write(addr, data); } void BandaiFCG::power() { @@ -96,8 +89,6 @@ void BandaiFCG::reset() { irq_latch = 0; } -// - unsigned BandaiFCG::ciram_addr(unsigned addr) const { switch(mirror_select & 0x03) { case 0: return ((addr & 0x0400) >> 0) | (addr & 0x03ff); //vertical mirroring @@ -108,8 +99,6 @@ unsigned BandaiFCG::ciram_addr(unsigned addr) const { throw; } -// - void BandaiFCG::serialize(serializer &s) { s.array(chr_bank); s.integer(prg_bank); diff --git a/bsnes/nes/mapper/bandai-fcg/bandai-fcg.hpp b/bsnes/nes/mapper/bandai-fcg/bandai-fcg.hpp index b39f224f..e1fd8b58 100755 --- a/bsnes/nes/mapper/bandai-fcg/bandai-fcg.hpp +++ b/bsnes/nes/mapper/bandai-fcg/bandai-fcg.hpp @@ -1,14 +1,11 @@ struct BandaiFCG : Mapper { void main(); - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); void power(); void reset(); diff --git a/bsnes/nes/mapper/cnrom/cnrom.cpp b/bsnes/nes/mapper/cnrom/cnrom.cpp index b96ec10d..df1c1e09 100755 --- a/bsnes/nes/mapper/cnrom/cnrom.cpp +++ b/bsnes/nes/mapper/cnrom/cnrom.cpp @@ -1,36 +1,32 @@ CNROM cnrom; -uint8 CNROM::prg_read(uint16 addr) { - if(addr & 0x8000) { - return cartridge.prg_data[mirror(addr & 0x7fff, cartridge.prg_size)]; - } - +uint8 CNROM::prg_read(unsigned addr) { + if(addr & 0x8000) return Mapper::prg_read(addr & 0x7fff); return cpu.mdr(); } -void CNROM::prg_write(uint16 addr, uint8 data) { +void CNROM::prg_write(unsigned addr, uint8 data) { if(addr & 0x8000) chr_bank = data & 0x03; } -uint8 CNROM::chr_read(uint16 addr) { - unsigned chr_addr = (chr_bank * 0x2000) + (addr & 0x1fff); - return cartridge.chr_data[mirror(chr_addr, cartridge.chr_size)]; +uint8 CNROM::chr_read(unsigned addr) { + if(addr & 0x2000) { + if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); + return ppu.ciram_read(addr & 0x07ff); + } + + addr = (chr_bank * 0x2000) + (addr & 0x1fff); + return Mapper::chr_read(addr); } -void CNROM::chr_write(uint16 addr, uint8 data) { - if(cartridge.chr_ram == false) return; - unsigned chr_addr = (chr_bank * 0x2000) + (addr & 0x1fff); - cartridge.chr_data[mirror(chr_addr, cartridge.chr_size)] = data; -} +void CNROM::chr_write(unsigned addr, uint8 data) { + if(addr & 0x2000) { + if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); + return ppu.ciram_write(addr & 0x07ff, data); + } -uint8 CNROM::ciram_read(uint13 addr) { - if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); - return ppu.ciram_read(addr & 0x07ff); -} - -void CNROM::ciram_write(uint13 addr, uint8 data) { - if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); - return ppu.ciram_write(addr & 0x07ff, data); + addr = (chr_bank * 0x2000) + (addr & 0x1fff); + Mapper::chr_write(addr, data); } void CNROM::power() { diff --git a/bsnes/nes/mapper/cnrom/cnrom.hpp b/bsnes/nes/mapper/cnrom/cnrom.hpp index 60914625..af32d78f 100755 --- a/bsnes/nes/mapper/cnrom/cnrom.hpp +++ b/bsnes/nes/mapper/cnrom/cnrom.hpp @@ -1,12 +1,9 @@ struct CNROM : Mapper { - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); void power(); void reset(); diff --git a/bsnes/nes/mapper/mapper.cpp b/bsnes/nes/mapper/mapper.cpp index 0aa5e519..db6ba850 100755 --- a/bsnes/nes/mapper/mapper.cpp +++ b/bsnes/nes/mapper/mapper.cpp @@ -37,14 +37,23 @@ unsigned Mapper::mirror(unsigned addr, unsigned size) const { return base; } -uint8& Mapper::prg_data(unsigned addr) { +uint8 Mapper::prg_read(unsigned addr) { return cartridge.prg_data[mirror(addr, cartridge.prg_size)]; } -uint8& Mapper::chr_data(unsigned addr) { +void Mapper::prg_write(unsigned addr, uint8 data) { + cartridge.prg_data[mirror(addr, cartridge.prg_size)] = data; +} + +uint8 Mapper::chr_read(unsigned addr) { return cartridge.chr_data[mirror(addr, cartridge.chr_size)]; } +void Mapper::chr_write(unsigned addr, uint8 data) { + if(cartridge.chr_ram == false) return; + cartridge.chr_data[mirror(addr, cartridge.chr_size)] = data; +} + unsigned Mapper::ram_size() { return 0u; } diff --git a/bsnes/nes/mapper/mapper.hpp b/bsnes/nes/mapper/mapper.hpp index 6989e7a4..08e1ef69 100755 --- a/bsnes/nes/mapper/mapper.hpp +++ b/bsnes/nes/mapper/mapper.hpp @@ -4,17 +4,18 @@ namespace Mapper { virtual void tick(); unsigned mirror(unsigned addr, unsigned size) const; - uint8& prg_data(unsigned addr); - uint8& chr_data(unsigned addr); - virtual uint8 prg_read(uint16 addr) = 0; - virtual void prg_write(uint16 addr, uint8 data) = 0; + //note: Mapper::{prg,chr}_read() functions take literal ROM addresses; mirroring appropriately + //subclasses of Mapper take 16-bit bus addresses; decode them; and call Mapper read functions - virtual uint8 chr_read(uint16 addr) = 0; - virtual void chr_write(uint16 addr, uint8 data) = 0; + virtual uint8 prg_read(unsigned addr); + virtual void prg_write(unsigned addr, uint8 data); - virtual uint8 ciram_read(uint13 addr) = 0; - virtual void ciram_write(uint13 addr, uint8 data) = 0; + virtual uint8 chr_read(unsigned addr); + virtual void chr_write(unsigned addr, uint8 data); + + virtual uint8 ciram_read(uint13 addr) {} + virtual void ciram_write(uint13 addr, uint8 data) {} virtual unsigned ram_size(); virtual uint8* ram_data(); diff --git a/bsnes/nes/mapper/mmc1/mmc1.cpp b/bsnes/nes/mapper/mmc1/mmc1.cpp index ab282a4d..11a53149 100755 --- a/bsnes/nes/mapper/mmc1/mmc1.cpp +++ b/bsnes/nes/mapper/mmc1/mmc1.cpp @@ -66,41 +66,27 @@ bool MMC1::prg_ram_disable() const { return r[3] & 0x10; } -// - -uint8& MMC1::prg_data(unsigned addr) { - return cartridge.prg_data[mirror(addr, cartridge.prg_size)]; -} - -uint8& MMC1::chr_data(unsigned addr) { - return cartridge.chr_data[mirror(addr, cartridge.chr_size)]; -} - -// - -uint8 MMC1::prg_read(uint16 readaddr) { - unsigned addr = readaddr; - - if(addr >= 0x6000 && addr <= 0x7fff) { +uint8 MMC1::prg_read(unsigned addr) { + if((addr & 0xe000) == 0x6000) { if(prg_ram_disable() == false) return prg_ram[addr & 0x1fff]; return 0x00; } - if(addr >= 0x8000 && addr <= 0xffff) { + if(addr & 0x8000) { addr = prg_addr(addr & 0x4000) | (addr & 0x3fff); - return prg_data(addr); + return Mapper::prg_read(addr); } return cpu.mdr(); } -void MMC1::prg_write(uint16 addr, uint8 data) { - if(addr >= 0x6000 && addr <= 0x7fff) { +void MMC1::prg_write(unsigned addr, uint8 data) { + if((addr & 0xe000) == 0x6000) { if(prg_ram_disable() == false) prg_ram[addr & 0x1fff] = data; return; } - if(addr >= 0x8000 && addr <= 0xffff) { + if(addr & 0x8000) { if(data & 0x80) { shiftaddr = 0; r[0] |= 0x0c; @@ -116,60 +102,48 @@ void MMC1::prg_write(uint16 addr, uint8 data) { } } -// +uint8 MMC1::chr_read(unsigned addr) { + if(addr & 0x2000) { + return ppu.ciram_read(ciram_addr(addr)); + } -uint8 MMC1::chr_read(uint16 readaddr) { - unsigned addr = readaddr; prg_ex_select = addr & 0x1000; if(addr <= 0x0fff) { addr = chr_banklo() * 0x1000 + (addr & 0x0fff); - return chr_data(addr); + return Mapper::chr_read(addr); } if(addr <= 0x1fff) { addr = chr_bankhi() * 0x1000 + (addr & 0x0fff); - return chr_data(addr); + return Mapper::chr_read(addr); } throw; } -void MMC1::chr_write(uint16 readaddr, uint8 data) { - unsigned addr = readaddr; +void MMC1::chr_write(unsigned addr, uint8 data) { + if(addr & 0x2000) { + return ppu.ciram_write(ciram_addr(addr), data); + } + prg_ex_select = addr & 0x1000; if(addr <= 0x0fff) { if(cartridge.chr_ram == false) return; addr = chr_banklo() * 0x1000 + (addr & 0x0fff); - chr_data(addr) = data; - return; + return Mapper::chr_write(addr, data); } if(addr <= 0x1fff) { if(cartridge.chr_ram == false) return; addr = chr_bankhi() * 0x1000 + (addr & 0x0fff); - chr_data(addr) = data; - return; + return Mapper::chr_write(addr, data); } throw; } -// - -uint8 MMC1::ciram_read(uint13 addr) { - addr = ciram_addr(addr); - return ppu.ciram_read(addr); -} - -void MMC1::ciram_write(uint13 addr, uint8 data) { - addr = ciram_addr(addr); - return ppu.ciram_write(addr, data); -} - -// - unsigned MMC1::ram_size() { return 8192u; } @@ -178,8 +152,6 @@ uint8* MMC1::ram_data() { return prg_ram; } -// - void MMC1::power() { reset(); } @@ -195,8 +167,6 @@ void MMC1::reset() { r[3] = 0x00; } -// - void MMC1::serialize(serializer &s) { s.array(prg_ram); s.array(r); diff --git a/bsnes/nes/mapper/mmc1/mmc1.hpp b/bsnes/nes/mapper/mmc1/mmc1.hpp index 8eab1750..446270bf 100755 --- a/bsnes/nes/mapper/mmc1/mmc1.hpp +++ b/bsnes/nes/mapper/mmc1/mmc1.hpp @@ -1,12 +1,9 @@ struct MMC1 : Mapper { - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); unsigned ram_size(); uint8* ram_data(); @@ -32,9 +29,6 @@ private: unsigned chr_bankhi() const; unsigned prg_bank() const; bool prg_ram_disable() const; - - uint8& prg_data(unsigned addr); - uint8& chr_data(unsigned addr); }; extern MMC1 mmc1; diff --git a/bsnes/nes/mapper/mmc3/mmc3.cpp b/bsnes/nes/mapper/mmc3/mmc3.cpp index d6b3e2b9..d5a5c0f3 100755 --- a/bsnes/nes/mapper/mmc3/mmc3.cpp +++ b/bsnes/nes/mapper/mmc3/mmc3.cpp @@ -48,7 +48,7 @@ unsigned MMC3::prg_addr(uint16 addr) { throw; } -uint8 MMC3::prg_read(uint16 addr) { +uint8 MMC3::prg_read(unsigned addr) { if((addr & 0xe000) == 0x6000) { //$6000-7fff if(prg_ram_enable) { return prg_ram[addr & 0x1fff]; @@ -56,13 +56,13 @@ uint8 MMC3::prg_read(uint16 addr) { } if(addr & 0x8000) { //$8000-ffff - return prg_data(prg_addr(addr)); + return Mapper::prg_read(prg_addr(addr)); } return cpu.mdr(); } -void MMC3::prg_write(uint16 addr, uint8 data) { +void MMC3::prg_write(unsigned addr, uint8 data) { if((addr & 0xe000) == 0x6000) { //$6000-7fff if(prg_ram_enable && prg_ram_write_protect == false) { prg_ram[addr & 0x1fff] = data; @@ -138,33 +138,24 @@ unsigned MMC3::chr_addr(uint16 addr) { throw; } -uint8 MMC3::chr_read(uint16 addr) { +uint8 MMC3::chr_read(unsigned addr) { irq_test(addr); - return chr_data(chr_addr(addr)); + if(addr & 0x2000) return ppu.ciram_read(ciram_addr(addr)); + return Mapper::chr_read(chr_addr(addr)); } -void MMC3::chr_write(uint16 addr, uint8 data) { +void MMC3::chr_write(unsigned addr, uint8 data) { irq_test(addr); - if(cartridge.chr_ram == false) return; - chr_data(chr_addr(addr)) = data; + if(addr & 0x2000) return ppu.ciram_write(ciram_addr(addr), data); + return Mapper::chr_write(chr_addr(addr), data); } unsigned MMC3::ciram_addr(uint13 addr) { - irq_test(0x2000 | addr); if(mirror_select == 0) return ((addr & 0x0400) >> 0) | (addr & 0x03ff); if(mirror_select == 1) return ((addr & 0x0800) >> 1) | (addr & 0x03ff); throw; } -uint8 MMC3::ciram_read(uint13 addr) { - irq_test(0x2000 | addr); - return ppu.ciram_read(ciram_addr(addr)); -} - -void MMC3::ciram_write(uint13 addr, uint8 data) { - return ppu.ciram_write(ciram_addr(addr), data); -} - unsigned MMC3::ram_size() { return 8192u; } diff --git a/bsnes/nes/mapper/mmc3/mmc3.hpp b/bsnes/nes/mapper/mmc3/mmc3.hpp index 3b0038fa..d6394ff6 100755 --- a/bsnes/nes/mapper/mmc3/mmc3.hpp +++ b/bsnes/nes/mapper/mmc3/mmc3.hpp @@ -1,14 +1,11 @@ struct MMC3 : Mapper { void main(); - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); unsigned ram_size(); uint8* ram_data(); diff --git a/bsnes/nes/mapper/none/none.cpp b/bsnes/nes/mapper/none/none.cpp index 03c44386..a675da33 100755 --- a/bsnes/nes/mapper/none/none.cpp +++ b/bsnes/nes/mapper/none/none.cpp @@ -1,35 +1,27 @@ None none; -uint8 None::prg_read(uint16 addr) { - if(addr >= 0x8000 && addr <= 0xffff) { - addr &= 0x7fff; - if(addr >= cartridge.prg_size) addr &= cartridge.prg_size - 1; - return cartridge.prg_data[addr]; - } - +uint8 None::prg_read(unsigned addr) { + if(addr & 0x8000) return Mapper::prg_read(addr); return cpu.mdr(); } -void None::prg_write(uint16 addr, uint8 data) { +void None::prg_write(unsigned addr, uint8 data) { } -uint8 None::chr_read(uint16 addr) { - return cartridge.chr_data[addr & 0x1fff]; +uint8 None::chr_read(unsigned addr) { + if(addr & 0x2000) { + if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); + return ppu.ciram_read(addr & 0x07ff); + } + return Mapper::chr_read(addr); } -void None::chr_write(uint16 addr, uint8 data) { - if(cartridge.chr_ram == false) return; - cartridge.chr_data[addr & 0x1fff] = data; -} - -uint8 None::ciram_read(uint13 addr) { - if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); - return ppu.ciram_read(addr & 0x07ff); -} - -void None::ciram_write(uint13 addr, uint8 data) { - if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); - return ppu.ciram_write(addr & 0x07ff, data); +void None::chr_write(unsigned addr, uint8 data) { + if(addr & 0x2000) { + if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); + return ppu.ciram_write(addr & 0x07ff, data); + } + return Mapper::chr_write(addr, data); } void None::power() { diff --git a/bsnes/nes/mapper/none/none.hpp b/bsnes/nes/mapper/none/none.hpp index 60a22e4b..957e501c 100755 --- a/bsnes/nes/mapper/none/none.hpp +++ b/bsnes/nes/mapper/none/none.hpp @@ -1,12 +1,9 @@ struct None : Mapper { - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); void power(); void reset(); diff --git a/bsnes/nes/mapper/uorom/uorom.cpp b/bsnes/nes/mapper/uorom/uorom.cpp index bff2be93..65d9f5a0 100755 --- a/bsnes/nes/mapper/uorom/uorom.cpp +++ b/bsnes/nes/mapper/uorom/uorom.cpp @@ -1,36 +1,35 @@ UOROM uorom; -uint8 UOROM::prg_read(uint16 addr) { +uint8 UOROM::prg_read(unsigned addr) { if((addr & 0xc000) == 0x8000) { - return prg_data((prg_bank << 14) | (addr & 0x3fff)); + return Mapper::prg_read((prg_bank << 14) | (addr & 0x3fff)); } if((addr & 0xc000) == 0xc000) { - return prg_data((0x0f << 14) | (addr & 0x3fff)); + return Mapper::prg_read((0x0f << 14) | (addr & 0x3fff)); } } -void UOROM::prg_write(uint16 addr, uint8 data) { +void UOROM::prg_write(unsigned addr, uint8 data) { if(addr & 0x8000) prg_bank = data & 0x0f; } -uint8 UOROM::chr_read(uint16 addr) { - return chr_data(addr); +uint8 UOROM::chr_read(unsigned addr) { + if(addr & 0x2000) { + if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); + return ppu.ciram_read(addr); + } + + return Mapper::chr_read(addr); } -void UOROM::chr_write(uint16 addr, uint8 data) { - if(cartridge.chr_ram == false) return; - chr_data(addr) = data; -} +void UOROM::chr_write(unsigned addr, uint8 data) { + if(addr & 0x2000) { + if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); + return ppu.ciram_write(addr, data); + } -uint8 UOROM::ciram_read(uint13 addr) { - if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); - return ppu.ciram_read(addr); -} - -void UOROM::ciram_write(uint13 addr, uint8 data) { - if(cartridge.mirroring == 0) addr = ((addr & 0x0800) >> 1) | (addr & 0x03ff); - return ppu.ciram_write(addr, data); + return Mapper::chr_write(addr, data); } void UOROM::power() { diff --git a/bsnes/nes/mapper/uorom/uorom.hpp b/bsnes/nes/mapper/uorom/uorom.hpp index ec06cb67..1c36c039 100755 --- a/bsnes/nes/mapper/uorom/uorom.hpp +++ b/bsnes/nes/mapper/uorom/uorom.hpp @@ -1,12 +1,9 @@ struct UOROM : Mapper { - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); void power(); void reset(); diff --git a/bsnes/nes/mapper/vrc6/vrc6.cpp b/bsnes/nes/mapper/vrc6/vrc6.cpp index 152e8468..7b1553f0 100755 --- a/bsnes/nes/mapper/vrc6/vrc6.cpp +++ b/bsnes/nes/mapper/vrc6/vrc6.cpp @@ -1,45 +1,24 @@ VRC6 vrc6; -// - void VRC6::Pulse::clock() { if(--divider == 0) { - divider = frequency; + divider = frequency + 1; cycle++; - output = (mode == 1 || cycle < duty) ? volume : (uint4)0; + output = (mode == 1 || cycle > duty) ? volume : (uint4)0; } if(enable == false) output = 0; } -void VRC6::Pulse::serialize(serializer &s) { - s.integer(mode); - s.integer(duty); - s.integer(volume); - s.integer(enable); - s.integer(frequency); - - s.integer(divider); - s.integer(cycle); - s.integer(output); -} - -VRC6::Pulse::Pulse() { - for(unsigned n = 0; n < 16; n++) { - dac[n] = -15360 + (n * 2048); - } -} - -// - void VRC6::Sawtooth::clock() { if(--divider == 0) { - divider = frequency; - if(phase == 0) { - phase = 0; - accumulator = 0; - } else if((phase & 1) == 0) { + divider = frequency + 1; + if(++phase == 0) { accumulator += rate; + if(++stage == 7) { + stage = 0; + accumulator = 0; + } } } @@ -47,25 +26,6 @@ void VRC6::Sawtooth::clock() { if(enable == false) output = 0; } -void VRC6::Sawtooth::serialize(serializer &s) { - s.integer(rate); - s.integer(enable); - s.integer(frequency); - - s.integer(divider); - s.integer(phase); - s.integer(accumulator); - s.integer(output); -} - -VRC6::Sawtooth::Sawtooth() { - for(unsigned n = 0; n < 32; n++) { - dac[n] = -15872 + (n * 1024); - } -} - -// - void VRC6::main() { while(true) { if(scheduler.sync == Scheduler::SynchronizeMode::All) { @@ -95,45 +55,39 @@ void VRC6::main() { } } } + cpu.set_irq_line(irq_line); pulse1.clock(); pulse2.clock(); sawtooth.clock(); + signed output = (pulse1.output + pulse2.output + sawtooth.output) << 7; + apu.set_sample(-output); - signed output = 0; - output += pulse1.dac[ pulse1.output]; - output += pulse2.dac[ pulse2.output]; - output += sawtooth.dac[sawtooth.output]; - output /= 6; //div by 3 for channel count; div that by 2 to match NES volume intensity - output = sclamp<16>(output); - - apu.set_sample(output); - cpu.set_irq_line(irq_line); tick(); } } -uint8 VRC6::prg_read(uint16 addr) { +uint8 VRC6::prg_read(unsigned addr) { if((addr & 0xe000) == 0x6000) { return prg_ram[addr & 0x1fff]; } if((addr & 0xc000) == 0x8000) { - return prg_data((prg_bank[0] << 14) | (addr & 0x3fff)); + return Mapper::prg_read((prg_bank[0] << 14) | (addr & 0x3fff)); } if((addr & 0xe000) == 0xc000) { - return prg_data((prg_bank[1] << 13) | (addr & 0x1fff)); + return Mapper::prg_read((prg_bank[1] << 13) | (addr & 0x1fff)); } if((addr & 0xe000) == 0xe000) { - return prg_data((0xff << 13) | (addr & 0x1fff)); + return Mapper::prg_read((0xff << 13) | (addr & 0x1fff)); } return cpu.mdr(); } -void VRC6::prg_write(uint16 addr, uint8 data) { +void VRC6::prg_write(unsigned addr, uint8 data) { if((addr & 0xe000) == 0x6000) { prg_ram[addr & 0x1fff] = data; return; @@ -228,15 +182,18 @@ void VRC6::prg_write(uint16 addr, uint8 data) { } } -uint8 VRC6::chr_read(uint16 addr) { +uint8 VRC6::chr_read(unsigned addr) { + if(addr & 0x2000) return ppu.ciram_read(ciram_addr(addr)); + unsigned bank = chr_bank[(addr >> 10) & 7]; - return chr_data((bank << 10) | (addr & 0x03ff)); + return Mapper::chr_read((bank << 10) | (addr & 0x03ff)); } -void VRC6::chr_write(uint16 addr, uint8 data) { - if(cartridge.chr_ram == false) return; +void VRC6::chr_write(unsigned addr, uint8 data) { + if(addr & 0x2000) return ppu.ciram_write(ciram_addr(addr), data); + unsigned bank = chr_bank[(addr >> 10) & 7]; - chr_data((bank << 10) | (addr & 0x03ff)) = data; + Mapper::chr_write((bank << 10) | (addr & 0x03ff), data); } unsigned VRC6::ciram_addr(unsigned addr) const { @@ -248,14 +205,6 @@ unsigned VRC6::ciram_addr(unsigned addr) const { } } -uint8 VRC6::ciram_read(uint13 addr) { - return ppu.ciram_read(ciram_addr(addr)); -} - -void VRC6::ciram_write(uint13 addr, uint8 data) { - return ppu.ciram_write(ciram_addr(addr), data); -} - unsigned VRC6::ram_size() { return 8192u; } @@ -297,7 +246,7 @@ void VRC6::reset() { pulse1.enable = 0; pulse1.frequency = 0; - pulse1.divider = 0; + pulse1.divider = 1; pulse1.cycle = 0; pulse1.output = 0; @@ -307,7 +256,7 @@ void VRC6::reset() { pulse2.enable = 0; pulse2.frequency = 0; - pulse2.divider = 0; + pulse2.divider = 1; pulse2.cycle = 0; pulse2.output = 0; @@ -315,8 +264,9 @@ void VRC6::reset() { sawtooth.enable = 0; sawtooth.frequency = 0; - sawtooth.divider = 0; + sawtooth.divider = 1; sawtooth.phase = 0; + sawtooth.stage = 0; sawtooth.accumulator = 0; sawtooth.output = 0; } @@ -340,3 +290,27 @@ void VRC6::serialize(serializer &s) { pulse2.serialize(s); sawtooth.serialize(s); } + +void VRC6::Pulse::serialize(serializer &s) { + s.integer(mode); + s.integer(duty); + s.integer(volume); + s.integer(enable); + s.integer(frequency); + + s.integer(divider); + s.integer(cycle); + s.integer(output); +} + +void VRC6::Sawtooth::serialize(serializer &s) { + s.integer(rate); + s.integer(enable); + s.integer(frequency); + + s.integer(divider); + s.integer(phase); + s.integer(stage); + s.integer(accumulator); + s.integer(output); +} diff --git a/bsnes/nes/mapper/vrc6/vrc6.hpp b/bsnes/nes/mapper/vrc6/vrc6.hpp index 8ffe4711..395b52f6 100755 --- a/bsnes/nes/mapper/vrc6/vrc6.hpp +++ b/bsnes/nes/mapper/vrc6/vrc6.hpp @@ -1,14 +1,11 @@ struct VRC6 : Mapper { void main(); - uint8 prg_read(uint16 addr); - void prg_write(uint16 addr, uint8 data); + uint8 prg_read(unsigned addr); + void prg_write(unsigned addr, uint8 data); - uint8 chr_read(uint16 addr); - void chr_write(uint16 addr, uint8 data); - - uint8 ciram_read(uint13 addr); - void ciram_write(uint13 addr, uint8 data); + uint8 chr_read(unsigned addr); + void chr_write(unsigned addr, uint8 data); unsigned ram_size(); uint8* ram_data(); @@ -46,11 +43,9 @@ private: uint12 divider; uint4 cycle; uint4 output; - int16 dac[16]; void clock(); void serialize(serializer&); - Pulse(); } pulse1, pulse2; struct Sawtooth { @@ -59,14 +54,13 @@ private: uint12 frequency; uint12 divider; - uint4 phase; + uint1 phase; + uint3 stage; uint8 accumulator; uint5 output; - int16 dac[32]; void clock(); void serialize(serializer&); - Sawtooth(); } sawtooth; unsigned ciram_addr(unsigned addr) const; diff --git a/bsnes/nes/ppu/ppu.cpp b/bsnes/nes/ppu/ppu.cpp index 7ac8582a..0d201211 100755 --- a/bsnes/nes/ppu/ppu.cpp +++ b/bsnes/nes/ppu/ppu.cpp @@ -114,10 +114,10 @@ uint8 PPU::read(uint16 addr) { status.bus_data = cartridge.chr_read(addr); } else if(addr <= 0x3eff) { result = status.bus_data; - status.bus_data = cartridge.ciram_read(addr); + status.bus_data = cartridge.chr_read(addr); } else if(addr <= 0x3fff) { result = cgram_read(addr); - status.bus_data = cartridge.ciram_read(addr); + status.bus_data = cartridge.chr_read(addr); } status.vaddr += status.vram_increment; break; @@ -179,7 +179,7 @@ void PPU::write(uint16 addr, uint8 data) { if(addr <= 0x1fff) { cartridge.chr_write(addr, data); } else if(addr <= 0x3eff) { - cartridge.ciram_write(addr, data); + cartridge.chr_write(addr, data); } else if(addr <= 0x3fff) { cgram_write(addr, data); } @@ -244,11 +244,6 @@ uint8 PPU::chr_load(uint16 addr) { return cartridge.chr_read(addr); } -uint8 PPU::ciram_load(uint16 addr) { - if(raster_enable() == false) return 0x00; - return cartridge.ciram_read(addr); -} - // void PPU::ly_increment() { @@ -295,6 +290,7 @@ void PPU::raster_pixel(unsigned x) { palette |= (attr & 3) << 2; } + if(status.bg_enable == false) palette = 0; if(status.bg_edge_enable == false && status.lx < 8) palette = 0; for(signed sprite = 7; sprite >= 0; sprite--) { @@ -367,7 +363,7 @@ void PPU::raster_scanline() { } for(unsigned tile = 0; tile < 32; tile++) { // 0-255 - unsigned nametable = ciram_load(status.vaddr & 0x0fff); + unsigned nametable = chr_load(0x2000 | (status.vaddr & 0x0fff)); unsigned tileaddr = status.bg_addr + (nametable << 4) + (scrolly() & 7); raster_pixel(0); tick(); @@ -375,7 +371,7 @@ void PPU::raster_scanline() { raster_pixel(1); tick(); - unsigned attribute = ciram_load(0x03c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); + unsigned attribute = chr_load(0x23c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); if(scrolly() & 16) attribute >>= 4; if(scrollx() & 16) attribute >>= 2; raster_pixel(2); @@ -411,13 +407,13 @@ void PPU::raster_scanline() { for(unsigned n = 0; n < 8; n++) raster.oam[n] = raster.soam[n]; for(unsigned sprite = 0; sprite < 8; sprite++) { //256-319 - unsigned nametable = ciram_load(status.vaddr & 0x0fff); + unsigned nametable = chr_load(0x2000 | (status.vaddr & 0x0fff)); tick(); if(raster_enable() && sprite == 0) status.vaddr = (status.vaddr & 0x7be0) | (status.taddr & 0x041f); //257 tick(); - unsigned attribute = ciram_load(0x03c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); + unsigned attribute = chr_load(0x23c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); unsigned tileaddr = (sprite_height() == 8) ? status.sprite_addr + raster.oam[sprite].tile * 16 : ((raster.oam[sprite].tile & ~1) * 16) + ((raster.oam[sprite].tile & 1) * 0x1000); @@ -441,12 +437,12 @@ void PPU::raster_scanline() { } for(unsigned tile = 0; tile < 2; tile++) { //320-335 - unsigned nametable = ciram_load(status.vaddr & 0x0fff); + unsigned nametable = chr_load(0x2000 | (status.vaddr & 0x0fff)); unsigned tileaddr = status.bg_addr + (nametable << 4) + (scrolly() & 7); tick(); tick(); - unsigned attribute = ciram_load(0x03c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); + unsigned attribute = chr_load(0x23c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); if(scrolly() & 16) attribute >>= 4; if(scrollx() & 16) attribute >>= 2; tick(); @@ -469,11 +465,11 @@ void PPU::raster_scanline() { } //336-339 - unsigned nametable = ciram_load(status.vaddr & 0x0fff); + unsigned nametable = chr_load(0x2000 | (status.vaddr & 0x0fff)); tick(); tick(); - unsigned attribute = ciram_load(0x03c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); + unsigned attribute = chr_load(0x23c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); tick(); tick(); @@ -483,107 +479,4 @@ void PPU::raster_scanline() { return ly_increment(); } -#if 0 - -//scanline-based PPU renderer - -void PPU::raster_scanline() { - if(raster_enable() == false || (status.ly >= 240 && status.ly <= 260)) { - return tick(341); - } - - uint32 *line = buffer + status.ly * 256; - - uint8 ioam[8][5]; - unsigned oamc = 0; - - unsigned sprite_height = status.sprite_size ? 16 : 8; - for(unsigned n = 0; n < 64; n++) { - unsigned y = oam[(n * 4) + 0] + 1; - if(status.ly < y || status.ly >= y + sprite_height) continue; - ioam[oamc][0] = y; - ioam[oamc][1] = oam[(n * 4) + 1]; - ioam[oamc][2] = oam[(n * 4) + 2]; - ioam[oamc][3] = oam[(n * 4) + 3]; - ioam[oamc][4] = n; - if(++oamc >= 8) break; - } - - for(unsigned x = 0; x < 256; x++) { - uint8 tile = cartridge.chr_read(0x2000 | (status.vaddr & 0x1fff)); - uint8 attr = cartridge.chr_read(0x23c0 | (status.vaddr & 0x0fc0) | ((scrolly() >> 5) << 3) | (scrollx() >> 5)); - - if(scrollx() & 16) attr >>= 2; - if(scrolly() & 16) attr >>= 4; - - unsigned tilex = (scrollx() + x) & 7; - - uint8 tdlo = cartridge.chr_read(status.bg_addr + (tile << 4) + 0 + (scrolly() & 7)); - uint8 tdhi = cartridge.chr_read(status.bg_addr + (tile << 4) + 8 + (scrolly() & 7)); - - if(tilex == 7) scrollx_increment(); - - unsigned mask = 0x80 >> tilex; - unsigned palette = 0; - if(status.bg_enable) { - if(status.bg_edge_enable == true || x >= 8) { - palette |= (tdlo & mask) ? 1 : 0; - palette |= (tdhi & mask) ? 2 : 0; - if(palette) palette |= (attr & 3) << 2; - } - } - - for(unsigned n = 0; n < oamc; n++) { - if(x < ioam[n][3] || x >= ioam[n][3] + 8) continue; - if(status.sprite_enable == false) continue; - if(status.sprite_edge_enable == false && x < 8) continue; - - unsigned spritex = x - ioam[n][3]; - unsigned spritey = status.ly - ioam[n][0]; - - unsigned addr = (sprite_height == 8) - ? status.sprite_addr + ioam[n][1] * 16 - : ((ioam[n][1] & ~1) * 16) + ((ioam[n][1] & 1) * 0x1000); - - if(ioam[n][2] & 0x80) spritey ^= (sprite_height - 1); - if(ioam[n][2] & 0x40) spritex ^= 7; - if(spritey & 8) spritey += 8; - - tdlo = cartridge.chr_read(addr + 0 + spritey); - tdhi = cartridge.chr_read(addr + 8 + spritey); - - mask = 0x80 >> spritex; - unsigned sprite_palette = 0; - sprite_palette |= (tdlo & mask) ? 1 : 0; - sprite_palette |= (tdhi & mask) ? 2 : 0; - if(sprite_palette == 0) continue; - - if(ioam[n][4] == 0) status.sprite_zero_hit = 1; - sprite_palette |= (ioam[n][2] & 3) << 2; - - bool priority = ioam[n][2] & 0x20; - if(priority == 0 || palette == 0) palette = 16 + sprite_palette; - break; - } - - *line++ = paletteRGB[cgram[palette]]; - } - - if(status.ly != 261) scrolly_increment(); - - tick(257); //257 - - if(raster_enable()) { - status.vaddr = (status.vaddr & 0x7be0) | (status.taddr & 0x041f); - } - - tick(47); //304 - - if(status.ly == 261) status.vaddr = status.taddr; - - tick(37); //341 -} - -#endif - } diff --git a/bsnes/nes/ppu/ppu.hpp b/bsnes/nes/ppu/ppu.hpp index 4b688fa7..9671098f 100755 --- a/bsnes/nes/ppu/ppu.hpp +++ b/bsnes/nes/ppu/ppu.hpp @@ -25,7 +25,6 @@ struct PPU : Processor { unsigned sprite_height() const; uint8 chr_load(uint16 addr); - uint8 ciram_load(uint16 addr); void ly_increment(); void scrollx_increment(); diff --git a/bsnes/ui/interface/interface.cpp b/bsnes/ui/interface/interface.cpp index de3d9442..fde7d33f 100755 --- a/bsnes/ui/interface/interface.cpp +++ b/bsnes/ui/interface/interface.cpp @@ -14,8 +14,8 @@ void Filter::render(const uint16_t *input, unsigned inputPitch, unsigned inputWi } Filter::Filter() { - data = new uint16_t[1024 * 1024]; - pitch = 1024 * sizeof(uint16_t); + data = new uint16_t[2048 * 2048]; + pitch = 2048 * sizeof(uint16_t); } Filter::~Filter() { diff --git a/bsnes/ui/main.cpp b/bsnes/ui/main.cpp index eb6ef0e3..2d2ee25b 100755 --- a/bsnes/ui/main.cpp +++ b/bsnes/ui/main.cpp @@ -41,7 +41,7 @@ Application::Application(int argc, char **argv) { inputManager = new InputManager; utility = new Utility; - title = "bsnes v082.22"; + title = "bsnes v082.23"; #if defined(PLATFORM_WIN) normalFont = "Tahoma, 8";