1
0
mirror of https://github.com/mre/mos6502.git synced 2024-11-25 02:33:26 +00:00

x and y are now unsigned and there's less casting all over

This commit is contained in:
Sam M W 2022-10-20 09:42:17 +01:00
parent 41b9b19be2
commit 665ee4193d
2 changed files with 42 additions and 24 deletions

View File

@ -212,7 +212,7 @@ impl CPU {
(Instruction::DEY, OpInput::UseImplied) => { (Instruction::DEY, OpInput::UseImplied) => {
let mut r = u8::from_ne_bytes(self.registers.index_y.to_ne_bytes()); let mut r = u8::from_ne_bytes(self.registers.index_y.to_ne_bytes());
self.decrement(&mut r); self.decrement(&mut r);
self.load_y_register(i8::from_ne_bytes(r.to_ne_bytes())); self.load_y_register(r);
} }
(Instruction::DEX, OpInput::UseImplied) => { (Instruction::DEX, OpInput::UseImplied) => {
@ -257,22 +257,22 @@ impl CPU {
(Instruction::LDX, OpInput::UseImmediate(val)) => { (Instruction::LDX, OpInput::UseImmediate(val)) => {
debug!("load X immediate: {}", val); debug!("load X immediate: {}", val);
self.load_x_register(val as i8); self.load_x_register(val);
} }
(Instruction::LDX, OpInput::UseAddress(addr)) => { (Instruction::LDX, OpInput::UseAddress(addr)) => {
let val = self.memory.get_byte(addr); let val = self.memory.get_byte(addr);
debug!("load X. address: {:?}. value: {}", addr, val); debug!("load X. address: {:?}. value: {}", addr, val);
self.load_x_register(val as i8); self.load_x_register(val);
} }
(Instruction::LDY, OpInput::UseImmediate(val)) => { (Instruction::LDY, OpInput::UseImmediate(val)) => {
debug!("load Y immediate: {}", val); debug!("load Y immediate: {}", val);
self.load_y_register(val as i8); self.load_y_register(val);
} }
(Instruction::LDY, OpInput::UseAddress(addr)) => { (Instruction::LDY, OpInput::UseAddress(addr)) => {
let val = self.memory.get_byte(addr); let val = self.memory.get_byte(addr);
debug!("load Y. address: {:?}. value: {}", addr, val); debug!("load Y. address: {:?}. value: {}", addr, val);
self.load_y_register(val as i8); self.load_y_register(val);
} }
(Instruction::LSR, OpInput::UseImplied) => { (Instruction::LSR, OpInput::UseImplied) => {
@ -377,20 +377,19 @@ impl CPU {
(Instruction::TAX, OpInput::UseImplied) => { (Instruction::TAX, OpInput::UseImplied) => {
let val = self.registers.accumulator; let val = self.registers.accumulator;
self.load_x_register(val); self.load_x_register(val as u8);
} }
(Instruction::TAY, OpInput::UseImplied) => { (Instruction::TAY, OpInput::UseImplied) => {
let val = self.registers.accumulator; let val = self.registers.accumulator;
self.load_y_register(val); self.load_y_register(val as u8);
} }
(Instruction::TSX, OpInput::UseImplied) => { (Instruction::TSX, OpInput::UseImplied) => {
let StackPointer(val) = self.registers.stack_pointer; let StackPointer(val) = self.registers.stack_pointer;
let val = val as i8;
self.load_x_register(val); self.load_x_register(val);
} }
(Instruction::TXA, OpInput::UseImplied) => { (Instruction::TXA, OpInput::UseImplied) => {
let val = self.registers.index_x; let val = self.registers.index_x;
self.load_accumulator(val); self.load_accumulator(val as i8);
} }
(Instruction::TXS, OpInput::UseImplied) => { (Instruction::TXS, OpInput::UseImplied) => {
// Note that this is the only 'transfer' instruction that does // Note that this is the only 'transfer' instruction that does
@ -401,7 +400,7 @@ impl CPU {
} }
(Instruction::TYA, OpInput::UseImplied) => { (Instruction::TYA, OpInput::UseImplied) => {
let val = self.registers.index_y; let val = self.registers.index_y;
self.load_accumulator(val); self.load_accumulator(val as i8);
} }
(Instruction::NOP, OpInput::UseImplied) => { (Instruction::NOP, OpInput::UseImplied) => {
@ -436,6 +435,20 @@ impl CPU {
); );
} }
fn set_flags_from_u8(status: &mut Status, value: u8) {
let is_zero = value == 0;
let is_negative = value > 127;
status.set_with_mask(
Status::PS_ZERO | Status::PS_NEGATIVE,
Status::new(StatusArgs {
zero: is_zero,
negative: is_negative,
..StatusArgs::none()
}),
);
}
fn shift_left_with_flags(p_val: &mut u8, status: &mut Status) { fn shift_left_with_flags(p_val: &mut u8, status: &mut Status) {
let mask = 1 << 7; let mask = 1 << 7;
let is_bit_7_set = (*p_val & mask) == mask; let is_bit_7_set = (*p_val & mask) == mask;
@ -497,21 +510,26 @@ impl CPU {
CPU::set_flags_from_i8(status, *p_val as i8); CPU::set_flags_from_i8(status, *p_val as i8);
} }
fn set_u8_with_flags(mem: &mut u8, status: &mut Status, value: u8) {
*mem = value;
CPU::set_flags_from_u8(status, value);
}
fn set_i8_with_flags(mem: &mut i8, status: &mut Status, value: i8) { fn set_i8_with_flags(mem: &mut i8, status: &mut Status, value: i8) {
*mem = value; *mem = value;
CPU::set_flags_from_i8(status, value); CPU::set_flags_from_i8(status, value);
} }
fn load_x_register(&mut self, value: i8) { fn load_x_register(&mut self, value: u8) {
CPU::set_i8_with_flags( CPU::set_u8_with_flags(
&mut self.registers.index_x, &mut self.registers.index_x,
&mut self.registers.status, &mut self.registers.status,
value, value,
); );
} }
fn load_y_register(&mut self, value: i8) { fn load_y_register(&mut self, value: u8) {
CPU::set_i8_with_flags( CPU::set_u8_with_flags(
&mut self.registers.index_y, &mut self.registers.index_y,
&mut self.registers.status, &mut self.registers.status,
value, value,
@ -692,7 +710,7 @@ impl CPU {
fn dec_x(&mut self) { fn dec_x(&mut self) {
let mut r = u8::from_ne_bytes(self.registers.index_x.to_ne_bytes()); let mut r = u8::from_ne_bytes(self.registers.index_x.to_ne_bytes());
self.decrement(&mut r); self.decrement(&mut r);
self.load_x_register(i8::from_ne_bytes(r.to_ne_bytes())); self.load_x_register(r);
} }
fn jump(&mut self, addr: Address) { fn jump(&mut self, addr: Address) {
@ -778,12 +796,12 @@ impl CPU {
debug!("compare_with_x_register"); debug!("compare_with_x_register");
let x = self.registers.index_x; let x = self.registers.index_x;
self.compare(x, val); self.compare(x as i8, val);
} }
fn compare_with_y_register(&mut self, val: u8) { fn compare_with_y_register(&mut self, val: u8) {
let y = self.registers.index_y; let y = self.registers.index_y;
self.compare(y, val); self.compare(y as i8, val);
} }
fn exclusive_or(&mut self, val: u8) { fn exclusive_or(&mut self, val: u8) {
@ -1083,7 +1101,7 @@ mod tests {
#[test] #[test]
fn decrement_x_test() { fn decrement_x_test() {
let mut cpu = CPU::new(); let mut cpu = CPU::new();
cpu.registers.index_x = -128; cpu.registers.index_x = 0x80;
cpu.execute_instruction((Instruction::DEX, OpInput::UseImplied)); cpu.execute_instruction((Instruction::DEX, OpInput::UseImplied));
assert_eq!(cpu.registers.index_x, 127); assert_eq!(cpu.registers.index_x, 127);
assert!(!cpu.registers.status.contains(Status::PS_ZERO)); assert!(!cpu.registers.status.contains(Status::PS_ZERO));
@ -1093,7 +1111,7 @@ mod tests {
#[test] #[test]
fn decrement_y_test() { fn decrement_y_test() {
let mut cpu = CPU::new(); let mut cpu = CPU::new();
cpu.registers.index_y = -128; cpu.registers.index_y = 0x80;
cpu.execute_instruction((Instruction::DEY, OpInput::UseImplied)); cpu.execute_instruction((Instruction::DEY, OpInput::UseImplied));
assert_eq!(cpu.registers.index_y, 127); assert_eq!(cpu.registers.index_y, 127);
assert!(!cpu.registers.status.contains(Status::PS_ZERO)); assert!(!cpu.registers.status.contains(Status::PS_ZERO));
@ -1143,14 +1161,14 @@ mod tests {
let mut cpu = CPU::new(); let mut cpu = CPU::new();
cpu.dec_x(); cpu.dec_x();
assert_eq!(cpu.registers.index_x, -1); assert_eq!(cpu.registers.index_x, 0xff);
assert!(!cpu.registers.status.contains(Status::PS_CARRY)); assert!(!cpu.registers.status.contains(Status::PS_CARRY));
assert!(!cpu.registers.status.contains(Status::PS_ZERO)); assert!(!cpu.registers.status.contains(Status::PS_ZERO));
assert!(cpu.registers.status.contains(Status::PS_NEGATIVE)); assert!(cpu.registers.status.contains(Status::PS_NEGATIVE));
assert!(!cpu.registers.status.contains(Status::PS_OVERFLOW)); assert!(!cpu.registers.status.contains(Status::PS_OVERFLOW));
cpu.dec_x(); cpu.dec_x();
assert_eq!(cpu.registers.index_x, -2); assert_eq!(cpu.registers.index_x, 0xfe);
assert!(!cpu.registers.status.contains(Status::PS_CARRY)); assert!(!cpu.registers.status.contains(Status::PS_CARRY));
assert!(!cpu.registers.status.contains(Status::PS_ZERO)); assert!(!cpu.registers.status.contains(Status::PS_ZERO));
assert!(cpu.registers.status.contains(Status::PS_NEGATIVE)); assert!(cpu.registers.status.contains(Status::PS_NEGATIVE));
@ -1176,7 +1194,7 @@ mod tests {
assert!(!cpu.registers.status.contains(Status::PS_OVERFLOW)); assert!(!cpu.registers.status.contains(Status::PS_OVERFLOW));
cpu.dec_x(); cpu.dec_x();
assert_eq!(cpu.registers.index_x, -1); assert_eq!(cpu.registers.index_x, 0xff);
assert!(!cpu.registers.status.contains(Status::PS_CARRY)); assert!(!cpu.registers.status.contains(Status::PS_CARRY));
assert!(!cpu.registers.status.contains(Status::PS_ZERO)); assert!(!cpu.registers.status.contains(Status::PS_ZERO));
assert!(cpu.registers.status.contains(Status::PS_NEGATIVE)); assert!(cpu.registers.status.contains(Status::PS_NEGATIVE));

View File

@ -163,8 +163,8 @@ impl StackPointer {
#[derive(Copy, Clone, PartialEq, Eq, Debug)] #[derive(Copy, Clone, PartialEq, Eq, Debug)]
pub struct Registers { pub struct Registers {
pub accumulator: i8, pub accumulator: i8,
pub index_x: i8, pub index_x: u8,
pub index_y: i8, pub index_y: u8,
pub stack_pointer: StackPointer, pub stack_pointer: StackPointer,
pub program_counter: Address, pub program_counter: Address,
pub status: Status, pub status: Status,