#![allow(dead_code)]
#[derive(Debug, Clone, Copy, Default)]
pub struct ProcessorStatus(pub u8);
impl ProcessorStatus {
pub fn new() -> Self {
ProcessorStatus(0)
}
pub fn carry_flag(&self) -> bool {
self.0 & 0b0000_0001 != 0
}
pub fn set_carry_flag(&mut self) {
let mask = 0b0000_0001;
self.0 |= mask;
}
pub fn clear_carry_flag(&mut self) {
let mask = 0b1111_1110;
self.0 &= mask;
}
pub fn zero_flag(&self) -> bool {
self.0 & 0b0000_0010 != 0
}
pub fn set_zero_flag(&mut self) {
let mask = 0b0000_0010;
self.0 |= mask;
}
pub fn clear_zero_flag(&mut self) {
let mask = 0b1111_1101;
self.0 &= mask;
}
pub fn interrupt_disable_flag(&self) -> bool {
self.0 & 0b0000_0100 != 0
}
pub fn set_interrupt_disable_flag(&mut self) {
let mask = 0b0000_0100;
self.0 |= mask;
}
pub fn clear_interrupt_disable_flag(&mut self) {
let mask = 0b1111_1011;
self.0 &= mask;
}
pub fn decimal_flag(&self) -> bool {
self.0 & 0b0000_1000 != 0
}
pub fn set_decimal_flag(&mut self) {
let mask = 0b0000_1000;
self.0 |= mask;
}
pub fn clear_decimal_flag(&mut self) {
let mask = 0b1111_0111;
self.0 &= mask;
}
pub fn break_flag(&self) -> bool {
self.0 & 0b0001_0000 != 0
}
pub fn set_break_flag(&mut self) {
let mask = 0b0001_0000;
self.0 |= mask;
}
pub fn clear_break_flag(&mut self) {
let mask = 0b1110_1111;
self.0 &= mask;
}
pub fn bit_5_flag(&self) -> bool {
self.0 & 0b0010_0000 != 0
}
pub fn set_bit_5_flag(&mut self) {
let mask = 0b0010_0000;
self.0 |= mask;
}
pub fn clear_bit_5_flag(&mut self) {
let mask = 0b1101_1111;
self.0 &= mask;
}
pub fn overflow_flag(&self) -> bool {
self.0 & 0b0100_0000 != 0
}
pub fn set_overflow_flag(&mut self) {
let mask = 0b0100_0000;
self.0 |= mask;
}
pub fn clear_overflow_flag(&mut self) {
let mask = 0b1011_1111;
self.0 &= mask;
}
pub fn negative_flag(&self) -> bool {
self.0 & 0b1000_0000 != 0
}
pub fn set_negative_flag(&mut self) {
let mask = 0b1000_0000;
self.0 |= mask;
}
pub fn clear_negative_flag(&mut self) {
let mask = 0b0111_1111;
self.0 &= mask;
}
}
#[cfg(test)]
mod test {
use super::*;
#[test]
fn test_carry() {
let mut flag_reg = ProcessorStatus::new();
assert!(!flag_reg.carry_flag());
flag_reg.set_carry_flag();
assert!(flag_reg.carry_flag());
flag_reg.clear_carry_flag();
assert!(!flag_reg.carry_flag());
}
#[test]
fn test_zero() {
let mut flag_reg = ProcessorStatus::new();
assert!(!flag_reg.zero_flag());
flag_reg.set_zero_flag();
assert!(flag_reg.zero_flag());
flag_reg.clear_zero_flag();
assert!(!flag_reg.zero_flag());
}
#[test]
fn test_interrupt_disable() {
let mut flag_reg = ProcessorStatus::new();
assert!(!flag_reg.interrupt_disable_flag());
flag_reg.set_interrupt_disable_flag();
assert!(flag_reg.interrupt_disable_flag());
flag_reg.clear_interrupt_disable_flag();
assert!(!flag_reg.interrupt_disable_flag());
}
#[test]
fn test_decimal() {
let mut flag_reg = ProcessorStatus::new();
assert!(!flag_reg.decimal_flag());
flag_reg.set_decimal_flag();
assert!(flag_reg.decimal_flag());
flag_reg.clear_decimal_flag();
assert!(!flag_reg.decimal_flag());
}
#[test]
fn test_overflow() {
let mut flag_reg = ProcessorStatus::new();
assert!(!flag_reg.overflow_flag());
flag_reg.set_overflow_flag();
assert!(flag_reg.overflow_flag());
flag_reg.clear_overflow_flag();
assert!(!flag_reg.overflow_flag());
}
#[test]
fn test_neg() {
let mut flag_reg = ProcessorStatus::new();
assert!(!flag_reg.negative_flag());
flag_reg.set_negative_flag();
assert!(flag_reg.negative_flag());
flag_reg.clear_negative_flag();
assert!(!flag_reg.negative_flag());
}
}