private void Cycle(bool noPpu) { _apuCatchCycles += _apuCyclesPerMaster * 2; if (_joypadStrobe) { _joypad1Val = _joypad1State; _joypad2Val = _joypad2State; } if (_hdmaTimer > 0) { _hdmaTimer -= 2; } else if (_dmaBusy) { HandleDma(); } else if (XPos < 536 || XPos >= 576) { CpuCycle(); } if (YPos == _vTimer && _vIrqEnabled) { if (!_hIrqEnabled) { if (XPos == 0) { _inIrq = true; CPU.IrqWanted = true; } } else { if (XPos == _hTimer * 4) { _inIrq = true; CPU.IrqWanted = true; } } } else if (XPos == _hTimer * 4 && _hIrqEnabled && !_vIrqEnabled) { _inIrq = true; CPU.IrqWanted = true; } if (XPos == 1024) { _inHblank = true; if (!_inVblank) { HandleHdma(); } } else if (XPos == 0) { _inHblank = false; PPU.CheckOverscan(YPos); } else if (XPos == 512 && !noPpu) { PPU.RenderLine(YPos); } if (YPos == (PPU.FrameOverscan ? 240 : 225) && XPos == 0) { _inNmi = true; _inVblank = true; if (_autoJoyRead) { _autoJoyBusy = true; _autoJoyTimer = 4224; DoAutoJoyRead(); } if (_nmiEnabled) { CPU.NmiWanted = true; } } else if (YPos == 0 && XPos == 0) { _inNmi = false; _inVblank = false; InitHdma(); } if (_autoJoyBusy) { _autoJoyTimer -= 2; if (_autoJoyTimer == 0) { _autoJoyBusy = false; } } XPos += 2; if (XPos == 1364) { XPos = 0; YPos++; if (YPos == 262) { CatchUpApu(); YPos = 0; } } }