void S9xSA1Reset () { SA1Registers.PB = 0; SA1Registers.PC = Memory.FillRAM [0x2203] | (Memory.FillRAM [0x2204] << 8); SA1Registers.D.W = 0; SA1Registers.DB = 0; SA1Registers.SH = 1; SA1Registers.SL = 0xFF; SA1Registers.XH = 0; SA1Registers.YH = 0; SA1Registers.P.W = 0; SA1.ShiftedPB = 0; SA1.ShiftedDB = 0; SA1SetFlags (MemoryFlag | IndexFlag | IRQ | Emulation); SA1ClearFlags (Decimal); SA1.WaitingForInterrupt = FALSE; SA1.PC = NULL; SA1.PCBase = NULL; S9xSA1SetPCBase (SA1Registers.PC); SA1.S9xOpcodes = S9xSA1OpcodesM1X1; S9xSA1UnpackStatus(); S9xSA1FixCycles (); SA1.WaitCounter = 3; SA1.Executing = TRUE; SA1.BWRAM = Memory.SRAM; Memory.FillRAM [0x2225] = 0; }
void S9xFixSA1AfterSnapshotLoad () { bool useOldMethod = (SA1.Executing == 2); if(useOldMethod) { SA1.ShiftedPB = (uint32) SA1Registers.PB << 16; SA1.ShiftedDB = (uint32) SA1Registers.DB << 16; } S9xSA1SetPCBase (SA1.ShiftedPB + SA1Registers.PC); if(useOldMethod) S9xSA1UnpackStatus (); S9xSA1FixCycles (); if(useOldMethod) SA1.VirtualBitmapFormat = (Memory.FillRAM [0x223f] & 0x80) ? 2 : 4; Memory.BWRAM = Memory.SRAM + (Memory.FillRAM [0x2224] & 7) * 0x2000; S9xSA1SetBWRAMMemMap (Memory.FillRAM [0x2225]); if(useOldMethod) { SA1.Waiting = (Memory.FillRAM [0x2200] & 0x60) != 0; SA1.Executing = !SA1.Waiting; } }
void S9xSA1MainLoop () { int i; #if 0 if (SA1.Flags & NMI_FLAG) { SA1.Flags &= ~NMI_FLAG; if (SA1.WaitingForInterrupt) { SA1.WaitingForInterrupt = FALSE; SA1Registers.PCw++; } S9xSA1Opcode_NMI (); } #endif if (SA1.Flags & IRQ_FLAG) { if (SA1.IRQActive) { if (SA1.WaitingForInterrupt) { SA1.WaitingForInterrupt = FALSE; SA1Registers.PCw++; } if (!SA1CheckFlag (IRQ)) S9xSA1Opcode_IRQ (); } else SA1.Flags &= ~IRQ_FLAG; } for (i = 0; i < 3 && SA1.Executing; i++) { #ifdef DEBUGGER if (SA1.Flags & TRACE_FLAG){ S9xSA1Trace(); } #endif #ifdef CPU_SHUTDOWN SA1.PBPCAtOpcodeStart = SA1Registers.PBPC; #endif register uint8 Op; register struct SOpcodes *Opcodes; if(SA1.PCBase){ SA1OpenBus = Op = SA1.PCBase[Registers.PCw]; Opcodes = SA1.S9xOpcodes; } else { Op = S9xSA1GetByte(Registers.PBPC); Opcodes = S9xOpcodesSlow; } if((SA1Registers.PCw&MEMMAP_MASK)+SA1.S9xOpLengths[Op]>=MEMMAP_BLOCK_SIZE){ uint32 oldPC = SA1Registers.PBPC; S9xSA1SetPCBase(SA1Registers.PBPC); SA1Registers.PBPC = oldPC; Opcodes = S9xSA1OpcodesSlow; } Registers.PCw++; (*Opcodes[Op].S9xOpcode) (); } }
void S9xSA1PostLoadState (void) { SA1.ShiftedPB = (uint32) SA1Registers.PB << 16; SA1.ShiftedDB = (uint32) SA1Registers.DB << 16; S9xSA1SetPCBase(SA1Registers.PBPC); S9xSA1UnpackStatus(); S9xSA1FixCycles(); SA1.VirtualBitmapFormat = (Memory.FillRAM[0x223f] & 0x80) ? 2 : 4; Memory.BWRAM = Memory.SRAM + (Memory.FillRAM[0x2224] & 7) * 0x2000; S9xSA1SetBWRAMMemMap(Memory.FillRAM[0x2225]); }
void S9xSA1MainLoop (void) { if (Memory.FillRAM[0x2200] & 0x60) { SA1.Cycles += 6; // FIXME S9xSA1UpdateTimer(); return; } // SA-1 NMI if ((Memory.FillRAM[0x2200] & 0x10) && !(Memory.FillRAM[0x220b] & 0x10)) { Memory.FillRAM[0x2301] |= 0x10; Memory.FillRAM[0x220b] |= 0x10; if (SA1.WaitingForInterrupt) { SA1.WaitingForInterrupt = FALSE; SA1Registers.PCw++; } S9xSA1Opcode_NMI(); } else if (!SA1CheckFlag(IRQ)) { // SA-1 Timer IRQ if ((Memory.FillRAM[0x220a] & 0x40) && !(Memory.FillRAM[0x220b] & 0x40)) { Memory.FillRAM[0x2301] |= 0x40; if (SA1.WaitingForInterrupt) { SA1.WaitingForInterrupt = FALSE; SA1Registers.PCw++; } S9xSA1Opcode_IRQ(); } else // SA-1 DMA IRQ if ((Memory.FillRAM[0x220a] & 0x20) && !(Memory.FillRAM[0x220b] & 0x20)) { Memory.FillRAM[0x2301] |= 0x20; if (SA1.WaitingForInterrupt) { SA1.WaitingForInterrupt = FALSE; SA1Registers.PCw++; } S9xSA1Opcode_IRQ(); } else // SA-1 IRQ if ((Memory.FillRAM[0x2200] & 0x80) && !(Memory.FillRAM[0x220b] & 0x80)) { Memory.FillRAM[0x2301] |= 0x80; if (SA1.WaitingForInterrupt) { SA1.WaitingForInterrupt = FALSE; SA1Registers.PCw++; } S9xSA1Opcode_IRQ(); } } for (int i = 0; i < 3 && !(Memory.FillRAM[0x2200] & 0x60); i++) { #ifdef DEBUGGER if (SA1.Flags & TRACE_FLAG) S9xSA1Trace(); #endif register uint8 Op; register Opcode *Opcodes; if (SA1.PCBase) { SA1OpenBus = Op = SA1.PCBase[Registers.PCw]; Opcodes = SA1.S9xOpcodes; } else { Op = S9xSA1GetByte(Registers.PBPC); Opcodes = S9xOpcodesSlow; } if ((SA1Registers.PCw & MEMMAP_MASK) + SA1.S9xOpLengths[Op] >= MEMMAP_BLOCK_SIZE) { uint32 oldPC = SA1Registers.PBPC; S9xSA1SetPCBase(SA1Registers.PBPC); SA1Registers.PBPC = oldPC; Opcodes = S9xSA1OpcodesSlow; } Registers.PCw++; Opcodes[Op](); } S9xSA1UpdateTimer(); }