mirror of
https://github.com/FranLMSP/snes.git
synced 2026-08-03 08:30:01 -04:00
WIP check interrupts
This commit is contained in:
@@ -34,9 +34,9 @@ impl CPU {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if self.registers.is_cpu_waiting_interrupt {
|
if self.registers.is_cpu_waiting_interrupt {
|
||||||
// TODO: check for interrupts here
|
self.check_interrupts(bus);
|
||||||
let (bytes, cycles) = cycles::increment_cycles_while_stopped();
|
let (_, cycles) = cycles::increment_cycles_while_stopped();
|
||||||
self.registers.increment_pc(bytes); self.registers.cycles += cycles;
|
self.registers.cycles += cycles;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if self.registers.is_moving {
|
if self.registers.is_moving {
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
use super::{interface::CPU, instructions::{phk::PHK, CPUInstruction, php::PHP, push_common}};
|
use super::{instructions::{phk::PHK, php::PHP, push_common, CPUInstruction}, interface::CPU, internal_registers::RDNMI};
|
||||||
use crate::cpu::bus::Bus;
|
use crate::cpu::bus::Bus;
|
||||||
|
|
||||||
|
|
||||||
@@ -38,13 +38,6 @@ impl CPU {
|
|||||||
self.registers.is_cpu_stopped = false;
|
self.registers.is_cpu_stopped = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_vector_from_interrupts(&self) -> Option<Vector> {
|
|
||||||
if self.registers.get_irq_disable_flag() {
|
|
||||||
return None;
|
|
||||||
}
|
|
||||||
Some(Vector::Reset)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn push_emulation_interrupt(&mut self, bus: &mut Bus) {
|
fn push_emulation_interrupt(&mut self, bus: &mut Bus) {
|
||||||
if !self.registers.emulation_mode {
|
if !self.registers.emulation_mode {
|
||||||
PHK{}.execute(&mut self.registers, bus);
|
PHK{}.execute(&mut self.registers, bus);
|
||||||
@@ -57,14 +50,22 @@ impl CPU {
|
|||||||
PHP{}.execute(&mut self.registers, bus);
|
PHP{}.execute(&mut self.registers, bus);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn handle_interrupts(&mut self, bus: &mut Bus) {
|
fn handle_interrupt(&mut self, bus: &mut Bus, vector: Vector) {
|
||||||
self.push_emulation_interrupt(bus);
|
self.push_emulation_interrupt(bus);
|
||||||
if let Some(vector) = self.get_vector_from_interrupts() {
|
|
||||||
let effective_vector = vector.get_base_address();
|
let effective_vector = vector.get_base_address();
|
||||||
self.registers.pc = effective_vector as u16;
|
self.registers.pc = effective_vector as u16;
|
||||||
self.registers.pbr = (effective_vector >> 16) as u8;
|
self.registers.pbr = (effective_vector >> 16) as u8;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn check_interrupts(&mut self, bus: &mut Bus) {
|
||||||
|
let rdnmi_byte = bus.read(RDNMI as u32);
|
||||||
|
if rdnmi_byte >> 7 != 0 {
|
||||||
|
self.registers.is_cpu_waiting_interrupt = false;
|
||||||
|
self.handle_interrupt(bus, Vector::NMI);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ use super::registers::PPURegisters;
|
|||||||
pub struct PPU {
|
pub struct PPU {
|
||||||
framebuffer: Vec<u8>,
|
framebuffer: Vec<u8>,
|
||||||
pub registers: PPURegisters,
|
pub registers: PPURegisters,
|
||||||
|
was_vblank_nmi_set: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl PPU {
|
impl PPU {
|
||||||
@@ -10,6 +11,7 @@ impl PPU {
|
|||||||
Self {
|
Self {
|
||||||
framebuffer: vec![],
|
framebuffer: vec![],
|
||||||
registers: PPURegisters::new(),
|
registers: PPURegisters::new(),
|
||||||
|
was_vblank_nmi_set: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -28,10 +30,12 @@ impl PPU {
|
|||||||
if self.registers.h_count > 339 {
|
if self.registers.h_count > 339 {
|
||||||
self.registers.h_count = 0;
|
self.registers.h_count = 0;
|
||||||
self.registers.v_count += 1;
|
self.registers.v_count += 1;
|
||||||
if self.registers.v_count > 224 {
|
if self.registers.v_count > 224 && !self.was_vblank_nmi_set {
|
||||||
self.registers.vblank_nmi = true;
|
self.registers.vblank_nmi = true;
|
||||||
|
self.was_vblank_nmi_set = true;
|
||||||
}
|
}
|
||||||
if self.registers.v_count > 261 {
|
if self.registers.v_count > 261 {
|
||||||
|
self.was_vblank_nmi_set = false;
|
||||||
self.registers.v_count = 0;
|
self.registers.v_count = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user