mirror of
https://github.com/bsnes-emu/bsnes.git
synced 2025-02-22 06:02:28 +01:00
byuu says: Changelog: - I caved on the `samples[] = {0.0}` thing, but I'm very unhappy about it - if it's really invalid C++, then GCC needs to stop accepting it in strict `-std=c++14` mode - Emulator::Interface::Information::resettable is gone - Emulator::Interface::reset() is gone - FC, SFC, MD cores updated to remove soft reset behavior - split GameBoy::Interface into GameBoyInterface, GameBoyColorInterface - split WonderSwan::Interface into WonderSwanInterface, WonderSwanColorInterface - PCE: fixed off-by-one scanline error [hex_usr] - PCE: temporary hack to prevent crashing when VDS is set to < 2 - hiro: Cocoa: removed (u)int(#) constants; converted (u)int(#) types to (u)int_(#)t types - icarus: replaced usage of unique with strip instead (so we don't mess up frameworks on macOS) - libco: added macOS-specific section marker [Ryphecha] So ... the major news this time is the removal of the soft reset behavior. This is a major!! change that results in a 100KiB diff file, and it's very prone to accidental mistakes!! If anyone is up for testing, or even better -- looking over the code changes between v102r01 and v102r02 and looking for any issues, please do so. Ideally we'll want to test every NES mapper type and every SNES coprocessor type by loading said games and power cycling to make sure the games are all cleanly resetting. It's too big of a change for me to cover there not being any issues on my own, but this is truly critical code, so yeah ... please help if you can. We technically lose a bit of hardware documentation here. The soft reset events do all kinds of interesting things in all kinds of different chips -- or at least they do on the SNES. This is obviously not ideal. But in the process of removing these portions of code, I found a few mistakes I had made previously. It simplifies resetting the system state a lot when not trying to have all the power() functions call the reset() functions to share partial functionality. In the future, the goal will be to come up with a way to add back in the soft reset behavior via keyboard binding as with the Master System core. What's going to have to happen is that the key binding will have to send a "reset pulse" to every emulated chip, and those chips are going to have to act independently to power() instead of reusing functionality. We'll get there eventually, but there's many things of vastly greater importance to work on right now, so it'll be a while. The information isn't lost ... we'll just have to pull it out of v102 when we are ready. Note that I left the SNES reset vector simulation code in, even though it's not possible to trigger, for the time being. Also ... the Super Game Boy core is still disconnected. To be honest, it totally slipped my mind when I released v102 that it wasn't connected again yet. This one's going to be pretty tricky to be honest. I'm thinking about making a third GameBoy::Interface class just for SGB, and coming up with some way of bypassing platform-> calls when in this mode.
244 lines
4.8 KiB
C++
244 lines
4.8 KiB
C++
struct CPU : Processor::R65816, Thread, PPUcounter {
|
|
auto interruptPending() const -> bool override;
|
|
auto pio() const -> uint8;
|
|
auto joylatch() const -> bool;
|
|
|
|
CPU();
|
|
|
|
auto readPort(uint2 port) const -> uint8;
|
|
auto writePort(uint2 port, uint8 data) -> void;
|
|
|
|
static auto Enter() -> void;
|
|
auto main() -> void;
|
|
auto load(Markup::Node) -> bool;
|
|
auto power() -> void;
|
|
|
|
//dma.cpp
|
|
auto dmaStep(uint clocks) -> void;
|
|
auto dmaTransferValid(uint8 bbus, uint24 abus) -> bool;
|
|
auto dmaAddressValid(uint24 abus) -> bool;
|
|
auto dmaRead(uint24 abus) -> uint8;
|
|
auto dmaWrite(bool valid, uint addr = 0, uint8 data = 0) -> void;
|
|
auto dmaTransfer(bool direction, uint8 bbus, uint24 abus) -> void;
|
|
|
|
inline auto dmaAddressB(uint n, uint channel) -> uint8;
|
|
inline auto dmaAddress(uint n) -> uint24;
|
|
inline auto hdmaAddress(uint n) -> uint24;
|
|
inline auto hdmaIndirectAddress(uint n) -> uint24;
|
|
|
|
inline auto dmaEnabledChannels() -> uint;
|
|
inline auto hdmaActive(uint n) -> bool;
|
|
inline auto hdmaActiveAfter(uint s) -> bool;
|
|
inline auto hdmaEnabledChannels() -> uint;
|
|
inline auto hdmaActiveChannels() -> uint;
|
|
|
|
auto dmaRun() -> void;
|
|
auto hdmaUpdate(uint n) -> void;
|
|
auto hdmaRun() -> void;
|
|
auto hdmaInitReset() -> void;
|
|
auto hdmaInit() -> void;
|
|
|
|
//memory.cpp
|
|
auto idle() -> void override;
|
|
auto read(uint24 addr) -> uint8 override;
|
|
auto write(uint24 addr, uint8 data) -> void override;
|
|
alwaysinline auto speed(uint24 addr) const -> uint;
|
|
auto readDisassembler(uint24 addr) -> uint8 override;
|
|
|
|
//io.cpp
|
|
auto readAPU(uint24 addr, uint8 data) -> uint8;
|
|
auto readCPU(uint24 addr, uint8 data) -> uint8;
|
|
auto readDMA(uint24 addr, uint8 data) -> uint8;
|
|
auto writeAPU(uint24 addr, uint8 data) -> void;
|
|
auto writeCPU(uint24 addr, uint8 data) -> void;
|
|
auto writeDMA(uint24 addr, uint8 data) -> void;
|
|
|
|
//timing.cpp
|
|
auto dmaCounter() const -> uint;
|
|
|
|
auto step(uint clocks) -> void;
|
|
auto scanline() -> void;
|
|
|
|
alwaysinline auto aluEdge() -> void;
|
|
alwaysinline auto dmaEdge() -> void;
|
|
alwaysinline auto lastCycle() -> void;
|
|
|
|
//irq.cpp
|
|
alwaysinline auto pollInterrupts() -> void;
|
|
auto nmitimenUpdate(uint8 data) -> void;
|
|
auto rdnmi() -> bool;
|
|
auto timeup() -> bool;
|
|
|
|
alwaysinline auto nmiTest() -> bool;
|
|
alwaysinline auto irqTest() -> bool;
|
|
|
|
//joypad.cpp
|
|
auto stepAutoJoypadPoll() -> void;
|
|
|
|
//serialization.cpp
|
|
auto serialize(serializer&) -> void;
|
|
|
|
uint8 wram[128 * 1024];
|
|
vector<Thread*> coprocessors;
|
|
vector<Thread*> peripherals;
|
|
|
|
private:
|
|
uint version = 2; //allowed: 1, 2
|
|
|
|
struct Status {
|
|
bool interruptPending;
|
|
|
|
uint clockCount;
|
|
uint lineClocks;
|
|
|
|
//timing
|
|
bool irqLock;
|
|
|
|
uint dramRefreshPosition;
|
|
bool dramRefreshed;
|
|
|
|
uint hdmaInitPosition;
|
|
bool hdmaInitTriggered;
|
|
|
|
uint hdmaPosition;
|
|
bool hdmaTriggered;
|
|
|
|
bool nmiValid;
|
|
bool nmiLine;
|
|
bool nmiTransition;
|
|
bool nmiPending;
|
|
bool nmiHold;
|
|
|
|
bool irqValid;
|
|
bool irqLine;
|
|
bool irqTransition;
|
|
bool irqPending;
|
|
bool irqHold;
|
|
|
|
bool powerPending;
|
|
bool resetPending;
|
|
|
|
//DMA
|
|
bool dmaActive;
|
|
uint dmaCounter;
|
|
uint dmaClocks;
|
|
bool dmaPending;
|
|
bool hdmaPending;
|
|
bool hdmaMode; //0 = init, 1 = run
|
|
|
|
//auto joypad polling
|
|
bool autoJoypadActive;
|
|
bool autoJoypadLatch;
|
|
uint autoJoypadCounter;
|
|
uint autoJoypadClock;
|
|
} status;
|
|
|
|
struct IO {
|
|
//$2140-217f
|
|
uint8 port[4];
|
|
|
|
//$2181-$2183
|
|
uint17 wramAddress;
|
|
|
|
//$4016-$4017
|
|
bool joypadStrobeLatch;
|
|
|
|
//$4200
|
|
bool nmiEnabled;
|
|
bool hirqEnabled;
|
|
bool virqEnabled;
|
|
bool autoJoypadPoll;
|
|
|
|
//$4201
|
|
uint8 pio;
|
|
|
|
//$4202-$4203
|
|
uint8 wrmpya;
|
|
uint8 wrmpyb;
|
|
|
|
//$4204-$4206
|
|
uint16 wrdiva;
|
|
uint8 wrdivb;
|
|
|
|
//$4207-$420a
|
|
uint9 hirqPos;
|
|
uint9 virqPos;
|
|
|
|
//$420d
|
|
uint romSpeed;
|
|
|
|
//$4214-$4217
|
|
uint16 rddiv;
|
|
uint16 rdmpy;
|
|
|
|
//$4218-$421f
|
|
uint16 joy1;
|
|
uint16 joy2;
|
|
uint16 joy3;
|
|
uint16 joy4;
|
|
} io;
|
|
|
|
struct ALU {
|
|
uint mpyctr;
|
|
uint divctr;
|
|
uint shift;
|
|
} alu;
|
|
|
|
struct Channel {
|
|
//$420b
|
|
bool dmaEnabled;
|
|
|
|
//$420c
|
|
bool hdmaEnabled;
|
|
|
|
//$43x0
|
|
bool direction;
|
|
bool indirect;
|
|
bool unused;
|
|
bool reverseTransfer;
|
|
bool fixedTransfer;
|
|
uint3 transferMode;
|
|
|
|
//$43x1
|
|
uint8 targetAddress;
|
|
|
|
//$43x2-$43x3
|
|
uint16 sourceAddress;
|
|
|
|
//$43x4
|
|
uint8 sourceBank;
|
|
|
|
//$43x5-$43x6
|
|
union {
|
|
uint16 transferSize;
|
|
uint16 indirectAddress;
|
|
};
|
|
|
|
//$43x7
|
|
uint8 indirectBank;
|
|
|
|
//$43x8-$43x9
|
|
uint16 hdmaAddress;
|
|
|
|
//$43xa
|
|
uint8 lineCounter;
|
|
|
|
//$43xb/$43xf
|
|
uint8 unknown;
|
|
|
|
//internal state
|
|
bool hdmaCompleted;
|
|
bool hdmaDoTransfer;
|
|
|
|
Channel() : transferSize(0) {}
|
|
} channel[8];
|
|
|
|
struct Pipe {
|
|
bool valid;
|
|
uint addr;
|
|
uint8 data;
|
|
} pipe;
|
|
};
|
|
|
|
extern CPU cpu;
|