diff --git a/src/instruction.rs b/src/instruction.rs index 7671d2d..d108f5a 100644 --- a/src/instruction.rs +++ b/src/instruction.rs @@ -113,7 +113,7 @@ pub enum Instruction , TYA // Transfer Y to Accumulator..... | N. ...Z. A = Y } -pub enum AMOut { +pub enum OpInput { UseImplied, UseImmediate(u8), UseRelative(i8), @@ -149,24 +149,24 @@ fn arr_to_addr(arr: &[u8]) -> Address { impl AddressingMode { pub fn extra_bytes(self) -> AddressDiff { let x = match self { - Accumulator => 0, - Implied => 0, - Immediate => 1, - ZeroPage => 1, - ZeroPageX => 1, - ZeroPageY => 1, - Relative => 1, - Absolute => 2, - AbsoluteX => 2, - AbsoluteY => 2, - Indirect => 2, - IndexedIndirectX => 1, - IndirectIndexedY => 1, + AddressingMode::Accumulator => 0, + AddressingMode::Implied => 0, + AddressingMode::Immediate => 1, + AddressingMode::ZeroPage => 1, + AddressingMode::ZeroPageX => 1, + AddressingMode::ZeroPageY => 1, + AddressingMode::Relative => 1, + AddressingMode::Absolute => 2, + AddressingMode::AbsoluteX => 2, + AddressingMode::AbsoluteY => 2, + AddressingMode::Indirect => 2, + AddressingMode::IndexedIndirectX => 1, + AddressingMode::IndirectIndexedY => 1, }; AddressDiff(x) } - pub fn process(self, machine: &Machine, arr: &[u8]) -> AMOut { + pub fn process(self, machine: &Machine, arr: &[u8]) -> OpInput { debug_assert!({let AddressDiff(x) = self.extra_bytes(); arr.len() == x as uint}); @@ -177,60 +177,60 @@ impl AddressingMode { let memory = &machine.memory; match self { - Accumulator | Implied => { + AddressingMode::Accumulator | AddressingMode::Implied => { // Always the same -- no input - UseImplied + OpInput::UseImplied }, - Immediate => { + AddressingMode::Immediate => { // Use [u8, ..1] specified in instruction as input - UseImmediate(arr[0]) + OpInput::UseImmediate(arr[0]) }, - ZeroPage => { + AddressingMode::ZeroPage => { // Use [u8, ..1] from instruction // Interpret as zero page address // (Output: an 8-bit zero-page address) - UseAddress(Address(arr[0] as u16)) + OpInput::UseAddress(Address(arr[0] as u16)) }, - ZeroPageX => { + AddressingMode::ZeroPageX => { // Use [u8, ..1] from instruction // Add to X register (as u8 -- the final address is in 0-page) // (Output: an 8-bit zero-page address) - UseAddress(Address((arr[0] + x) as u16)) + OpInput::UseAddress(Address((arr[0] + x) as u16)) }, - ZeroPageY => { + AddressingMode::ZeroPageY => { // Use [u8, ..1] from instruction // Add to Y register (as u8 -- the final address is in 0-page) // (Output: an 8-bit zero-page address) - UseAddress(Address((arr[0] + y) as u16)) + OpInput::UseAddress(Address((arr[0] + y) as u16)) }, - Relative => { + AddressingMode::Relative => { // Use [u8, ..1] from instruction // (interpret as relative...) - UseRelative(arr[0] as i8) + OpInput::UseRelative(arr[0] as i8) }, - Absolute => { + AddressingMode::Absolute => { // Use [u8, ..2] from instruction as address // (Output: a 16-bit address) - UseAddress(arr_to_addr(arr)) + OpInput::UseAddress(arr_to_addr(arr)) }, - AbsoluteX => { + AddressingMode::AbsoluteX => { // Use [u8, ..2] from instruction as address, add X // (Output: a 16-bit address) - UseAddress(arr_to_addr(arr) + AddressDiff(x as i32)) + OpInput::UseAddress(arr_to_addr(arr) + AddressDiff(x as i32)) }, - AbsoluteY => { + AddressingMode::AbsoluteY => { // Use [u8, ..2] from instruction as address, add Y // (Output: a 16-bit address) - UseAddress(arr_to_addr(arr) + AddressDiff(y as i32)) + OpInput::UseAddress(arr_to_addr(arr) + AddressDiff(y as i32)) }, - Indirect => { + AddressingMode::Indirect => { // Use [u8, ..2] from instruction as an address. Interpret the // two bytes starting at that address as an address. // (Output: a 16-bit address) let slice = memory.get_slice(arr_to_addr(arr), AddressDiff(2)); - UseAddress(arr_to_addr(slice)) + OpInput::UseAddress(arr_to_addr(slice)) }, - IndexedIndirectX => { + AddressingMode::IndexedIndirectX => { // Use [u8, ..1] from instruction // Add to X register with 0-page wraparound, like ZeroPageX. // This is where the absolute (16-bit) target address is stored. @@ -238,9 +238,9 @@ impl AddressingMode { let start = arr[0] + x; let slice = memory.get_slice(Address(start as u16), AddressDiff(2)); - UseAddress(arr_to_addr(slice)) + OpInput::UseAddress(arr_to_addr(slice)) }, - IndirectIndexedY => { + AddressingMode::IndirectIndexedY => { // Use [u8, ..1] from instruction // This is where the absolute (16-bit) target address is stored. // Add Y register to this address to get the final address @@ -248,270 +248,270 @@ impl AddressingMode { let start = arr[0]; let slice = memory.get_slice(Address(start as u16), AddressDiff(2)); - UseAddress(arr_to_addr(slice) + AddressDiff(y as i32)) + OpInput::UseAddress(arr_to_addr(slice) + AddressDiff(y as i32)) }, } } } -pub type DecodedInstr = (Instruction, AMOut); +pub type DecodedInstr = (Instruction, OpInput); pub static OPCODES: [Option<(Instruction, AddressingMode)>, ..256] = [ -/*0x00*/ Some((BRK, Implied)), -/*0x01*/ Some((ORA, IndexedIndirectX)), +/*0x00*/ Some((Instruction::BRK, AddressingMode::Implied)), +/*0x01*/ Some((Instruction::ORA, AddressingMode::IndexedIndirectX)), /*0x02*/ None, /*0x03*/ None, /*0x04*/ None, -/*0x05*/ Some((ORA, ZeroPage)), -/*0x06*/ Some((ASL, ZeroPage)), +/*0x05*/ Some((Instruction::ORA, AddressingMode::ZeroPage)), +/*0x06*/ Some((Instruction::ASL, AddressingMode::ZeroPage)), /*0x07*/ None, -/*0x08*/ Some((PHP, Implied)), -/*0x09*/ Some((ORA, Immediate)), -/*0x0A*/ Some((ASL, Accumulator)), +/*0x08*/ Some((Instruction::PHP, AddressingMode::Implied)), +/*0x09*/ Some((Instruction::ORA, AddressingMode::Immediate)), +/*0x0A*/ Some((Instruction::ASL, AddressingMode::Accumulator)), /*0x0B*/ None, /*0x0C*/ None, -/*0x0D*/ Some((ORA, Absolute)), -/*0x0E*/ Some((ASL, Absolute)), +/*0x0D*/ Some((Instruction::ORA, AddressingMode::Absolute)), +/*0x0E*/ Some((Instruction::ASL, AddressingMode::Absolute)), /*0x0F*/ None, -/*0x10*/ Some((BPL, Relative)), -/*0x11*/ Some((ORA, IndirectIndexedY)), +/*0x10*/ Some((Instruction::BPL, AddressingMode::Relative)), +/*0x11*/ Some((Instruction::ORA, AddressingMode::IndirectIndexedY)), /*0x12*/ None, /*0x13*/ None, /*0x14*/ None, -/*0x15*/ Some((ORA, ZeroPageX)), -/*0x16*/ Some((ASL, ZeroPageX)), +/*0x15*/ Some((Instruction::ORA, AddressingMode::ZeroPageX)), +/*0x16*/ Some((Instruction::ASL, AddressingMode::ZeroPageX)), /*0x17*/ None, -/*0x18*/ Some((CLC, Implied)), -/*0x19*/ Some((ORA, AbsoluteY)), +/*0x18*/ Some((Instruction::CLC, AddressingMode::Implied)), +/*0x19*/ Some((Instruction::ORA, AddressingMode::AbsoluteY)), /*0x1A*/ None, /*0x1B*/ None, /*0x1C*/ None, -/*0x1D*/ Some((ORA, AbsoluteX)), -/*0x1E*/ Some((ASL, AbsoluteX)), +/*0x1D*/ Some((Instruction::ORA, AddressingMode::AbsoluteX)), +/*0x1E*/ Some((Instruction::ASL, AddressingMode::AbsoluteX)), /*0x1F*/ None, -/*0x20*/ Some((JSR, Absolute)), -/*0x21*/ Some((AND, IndexedIndirectX)), +/*0x20*/ Some((Instruction::JSR, AddressingMode::Absolute)), +/*0x21*/ Some((Instruction::AND, AddressingMode::IndexedIndirectX)), /*0x22*/ None, /*0x23*/ None, -/*0x24*/ Some((BIT, ZeroPage)), -/*0x25*/ Some((AND, ZeroPage)), -/*0x26*/ Some((ROL, ZeroPage)), +/*0x24*/ Some((Instruction::BIT, AddressingMode::ZeroPage)), +/*0x25*/ Some((Instruction::AND, AddressingMode::ZeroPage)), +/*0x26*/ Some((Instruction::ROL, AddressingMode::ZeroPage)), /*0x27*/ None, -/*0x28*/ Some((PLP, Implied)), -/*0x29*/ Some((AND, Immediate)), -/*0x2A*/ Some((ROL, Accumulator)), +/*0x28*/ Some((Instruction::PLP, AddressingMode::Implied)), +/*0x29*/ Some((Instruction::AND, AddressingMode::Immediate)), +/*0x2A*/ Some((Instruction::ROL, AddressingMode::Accumulator)), /*0x2B*/ None, -/*0x2C*/ Some((BIT, Absolute)), -/*0x2D*/ Some((AND, Absolute)), -/*0x2E*/ Some((ROL, Absolute)), +/*0x2C*/ Some((Instruction::BIT, AddressingMode::Absolute)), +/*0x2D*/ Some((Instruction::AND, AddressingMode::Absolute)), +/*0x2E*/ Some((Instruction::ROL, AddressingMode::Absolute)), /*0x2F*/ None, -/*0x30*/ Some((BMI, Relative)), -/*0x31*/ Some((AND, IndirectIndexedY)), +/*0x30*/ Some((Instruction::BMI, AddressingMode::Relative)), +/*0x31*/ Some((Instruction::AND, AddressingMode::IndirectIndexedY)), /*0x32*/ None, /*0x33*/ None, /*0x34*/ None, -/*0x35*/ Some((AND, ZeroPageX)), -/*0x36*/ Some((ROL, ZeroPageX)), +/*0x35*/ Some((Instruction::AND, AddressingMode::ZeroPageX)), +/*0x36*/ Some((Instruction::ROL, AddressingMode::ZeroPageX)), /*0x37*/ None, -/*0x38*/ Some((SEC, Implied)), -/*0x39*/ Some((AND, AbsoluteY)), +/*0x38*/ Some((Instruction::SEC, AddressingMode::Implied)), +/*0x39*/ Some((Instruction::AND, AddressingMode::AbsoluteY)), /*0x3A*/ None, /*0x3B*/ None, /*0x3C*/ None, -/*0x3D*/ Some((AND, AbsoluteX)), -/*0x3E*/ Some((ROL, AbsoluteX)), +/*0x3D*/ Some((Instruction::AND, AddressingMode::AbsoluteX)), +/*0x3E*/ Some((Instruction::ROL, AddressingMode::AbsoluteX)), /*0x3F*/ None, -/*0x40*/ Some((RTI, Implied)), -/*0x41*/ Some((EOR, IndexedIndirectX)), +/*0x40*/ Some((Instruction::RTI, AddressingMode::Implied)), +/*0x41*/ Some((Instruction::EOR, AddressingMode::IndexedIndirectX)), /*0x42*/ None, /*0x43*/ None, /*0x44*/ None, -/*0x45*/ Some((EOR, ZeroPage)), -/*0x46*/ Some((LSR, ZeroPage)), +/*0x45*/ Some((Instruction::EOR, AddressingMode::ZeroPage)), +/*0x46*/ Some((Instruction::LSR, AddressingMode::ZeroPage)), /*0x47*/ None, -/*0x48*/ Some((PHA, Implied)), -/*0x49*/ Some((EOR, Immediate)), -/*0x4A*/ Some((LSR, Accumulator)), +/*0x48*/ Some((Instruction::PHA, AddressingMode::Implied)), +/*0x49*/ Some((Instruction::EOR, AddressingMode::Immediate)), +/*0x4A*/ Some((Instruction::LSR, AddressingMode::Accumulator)), /*0x4B*/ None, -/*0x4C*/ Some((JMP, Absolute)), -/*0x4D*/ Some((EOR, Absolute)), -/*0x4E*/ Some((LSR, Absolute)), +/*0x4C*/ Some((Instruction::JMP, AddressingMode::Absolute)), +/*0x4D*/ Some((Instruction::EOR, AddressingMode::Absolute)), +/*0x4E*/ Some((Instruction::LSR, AddressingMode::Absolute)), /*0x4F*/ None, -/*0x50*/ Some((BVC, Relative)), -/*0x51*/ Some((EOR, IndirectIndexedY)), +/*0x50*/ Some((Instruction::BVC, AddressingMode::Relative)), +/*0x51*/ Some((Instruction::EOR, AddressingMode::IndirectIndexedY)), /*0x52*/ None, /*0x53*/ None, /*0x54*/ None, -/*0x55*/ Some((EOR, ZeroPageX)), -/*0x56*/ Some((LSR, ZeroPageX)), +/*0x55*/ Some((Instruction::EOR, AddressingMode::ZeroPageX)), +/*0x56*/ Some((Instruction::LSR, AddressingMode::ZeroPageX)), /*0x57*/ None, /*0x58*/ None, -/*0x59*/ Some((EOR, AbsoluteY)), +/*0x59*/ Some((Instruction::EOR, AddressingMode::AbsoluteY)), /*0x5A*/ None, /*0x5B*/ None, /*0x5C*/ None, -/*0x5D*/ Some((EOR, AbsoluteX)), -/*0x5E*/ Some((LSR, AbsoluteX)), +/*0x5D*/ Some((Instruction::EOR, AddressingMode::AbsoluteX)), +/*0x5E*/ Some((Instruction::LSR, AddressingMode::AbsoluteX)), /*0x5F*/ None, -/*0x60*/ Some((RTS, Implied)), -/*0x61*/ Some((ADC, IndexedIndirectX)), +/*0x60*/ Some((Instruction::RTS, AddressingMode::Implied)), +/*0x61*/ Some((Instruction::ADC, AddressingMode::IndexedIndirectX)), /*0x62*/ None, /*0x63*/ None, /*0x64*/ None, -/*0x65*/ Some((ADC, ZeroPage)), -/*0x66*/ Some((ROR, ZeroPage)), +/*0x65*/ Some((Instruction::ADC, AddressingMode::ZeroPage)), +/*0x66*/ Some((Instruction::ROR, AddressingMode::ZeroPage)), /*0x67*/ None, -/*0x68*/ Some((PLA, Implied)), -/*0x69*/ Some((ADC, Immediate)), -/*0x6A*/ Some((ROR, Accumulator)), +/*0x68*/ Some((Instruction::PLA, AddressingMode::Implied)), +/*0x69*/ Some((Instruction::ADC, AddressingMode::Immediate)), +/*0x6A*/ Some((Instruction::ROR, AddressingMode::Accumulator)), /*0x6B*/ None, -/*0x6C*/ Some((JMP, Indirect)), -/*0x6D*/ Some((ADC, Absolute)), -/*0x6E*/ Some((ROR, Absolute)), +/*0x6C*/ Some((Instruction::JMP, AddressingMode::Indirect)), +/*0x6D*/ Some((Instruction::ADC, AddressingMode::Absolute)), +/*0x6E*/ Some((Instruction::ROR, AddressingMode::Absolute)), /*0x6F*/ None, -/*0x70*/ Some((BVS, Relative)), -/*0x71*/ Some((ADC, IndirectIndexedY)), +/*0x70*/ Some((Instruction::BVS, AddressingMode::Relative)), +/*0x71*/ Some((Instruction::ADC, AddressingMode::IndirectIndexedY)), /*0x72*/ None, /*0x73*/ None, /*0x74*/ None, -/*0x75*/ Some((ADC, ZeroPageX)), -/*0x76*/ Some((ROR, ZeroPageX)), +/*0x75*/ Some((Instruction::ADC, AddressingMode::ZeroPageX)), +/*0x76*/ Some((Instruction::ROR, AddressingMode::ZeroPageX)), /*0x77*/ None, -/*0x78*/ Some((SEI, Implied)), -/*0x79*/ Some((ADC, AbsoluteY)), +/*0x78*/ Some((Instruction::SEI, AddressingMode::Implied)), +/*0x79*/ Some((Instruction::ADC, AddressingMode::AbsoluteY)), /*0x7A*/ None, /*0x7B*/ None, /*0x7C*/ None, -/*0x7D*/ Some((ADC, AbsoluteX)), -/*0x7E*/ Some((ROR, AbsoluteX)), +/*0x7D*/ Some((Instruction::ADC, AddressingMode::AbsoluteX)), +/*0x7E*/ Some((Instruction::ROR, AddressingMode::AbsoluteX)), /*0x7F*/ None, /*0x80*/ None, -/*0x81*/ Some((STA, IndexedIndirectX)), +/*0x81*/ Some((Instruction::STA, AddressingMode::IndexedIndirectX)), /*0x82*/ None, /*0x83*/ None, -/*0x84*/ Some((STY, ZeroPage)), -/*0x85*/ Some((STA, ZeroPage)), -/*0x86*/ Some((STX, ZeroPage)), +/*0x84*/ Some((Instruction::STY, AddressingMode::ZeroPage)), +/*0x85*/ Some((Instruction::STA, AddressingMode::ZeroPage)), +/*0x86*/ Some((Instruction::STX, AddressingMode::ZeroPage)), /*0x87*/ None, -/*0x88*/ Some((DEY, Implied)), +/*0x88*/ Some((Instruction::DEY, AddressingMode::Implied)), /*0x89*/ None, -/*0x8A*/ Some((TXA, Implied)), +/*0x8A*/ Some((Instruction::TXA, AddressingMode::Implied)), /*0x8B*/ None, -/*0x8C*/ Some((STY, Absolute)), -/*0x8D*/ Some((STA, Absolute)), -/*0x8E*/ Some((STX, Absolute)), +/*0x8C*/ Some((Instruction::STY, AddressingMode::Absolute)), +/*0x8D*/ Some((Instruction::STA, AddressingMode::Absolute)), +/*0x8E*/ Some((Instruction::STX, AddressingMode::Absolute)), /*0x8F*/ None, -/*0x90*/ Some((BCC, Relative)), -/*0x91*/ Some((STA, IndirectIndexedY)), +/*0x90*/ Some((Instruction::BCC, AddressingMode::Relative)), +/*0x91*/ Some((Instruction::STA, AddressingMode::IndirectIndexedY)), /*0x92*/ None, /*0x93*/ None, -/*0x94*/ Some((STY, ZeroPageX)), -/*0x95*/ Some((STA, ZeroPageX)), -/*0x96*/ Some((STX, ZeroPageY)), +/*0x94*/ Some((Instruction::STY, AddressingMode::ZeroPageX)), +/*0x95*/ Some((Instruction::STA, AddressingMode::ZeroPageX)), +/*0x96*/ Some((Instruction::STX, AddressingMode::ZeroPageY)), /*0x97*/ None, -/*0x98*/ Some((TYA, Implied)), -/*0x99*/ Some((STA, AbsoluteY)), -/*0x9A*/ Some((TXS, Implied)), +/*0x98*/ Some((Instruction::TYA, AddressingMode::Implied)), +/*0x99*/ Some((Instruction::STA, AddressingMode::AbsoluteY)), +/*0x9A*/ Some((Instruction::TXS, AddressingMode::Implied)), /*0x9B*/ None, /*0x9C*/ None, -/*0x9D*/ Some((STA, AbsoluteX)), +/*0x9D*/ Some((Instruction::STA, AddressingMode::AbsoluteX)), /*0x9E*/ None, /*0x9F*/ None, -/*0xA0*/ Some((LDY, Immediate)), -/*0xA1*/ Some((LDA, IndexedIndirectX)), -/*0xA2*/ Some((LDX, Immediate)), +/*0xA0*/ Some((Instruction::LDY, AddressingMode::Immediate)), +/*0xA1*/ Some((Instruction::LDA, AddressingMode::IndexedIndirectX)), +/*0xA2*/ Some((Instruction::LDX, AddressingMode::Immediate)), /*0xA3*/ None, -/*0xA4*/ Some((LDY, ZeroPage)), -/*0xA5*/ Some((LDA, ZeroPage)), -/*0xA6*/ Some((LDX, ZeroPage)), +/*0xA4*/ Some((Instruction::LDY, AddressingMode::ZeroPage)), +/*0xA5*/ Some((Instruction::LDA, AddressingMode::ZeroPage)), +/*0xA6*/ Some((Instruction::LDX, AddressingMode::ZeroPage)), /*0xA7*/ None, -/*0xA8*/ Some((TAY, Implied)), -/*0xA9*/ Some((LDA, Immediate)), -/*0xAA*/ Some((TAX, Implied)), +/*0xA8*/ Some((Instruction::TAY, AddressingMode::Implied)), +/*0xA9*/ Some((Instruction::LDA, AddressingMode::Immediate)), +/*0xAA*/ Some((Instruction::TAX, AddressingMode::Implied)), /*0xAB*/ None, -/*0xAC*/ Some((LDY, Absolute)), -/*0xAD*/ Some((LDA, Absolute)), -/*0xAE*/ Some((LDX, Absolute)), +/*0xAC*/ Some((Instruction::LDY, AddressingMode::Absolute)), +/*0xAD*/ Some((Instruction::LDA, AddressingMode::Absolute)), +/*0xAE*/ Some((Instruction::LDX, AddressingMode::Absolute)), /*0xAF*/ None, -/*0xB0*/ Some((BCS, Relative)), -/*0xB1*/ Some((LDA, IndirectIndexedY)), +/*0xB0*/ Some((Instruction::BCS, AddressingMode::Relative)), +/*0xB1*/ Some((Instruction::LDA, AddressingMode::IndirectIndexedY)), /*0xB2*/ None, /*0xB3*/ None, -/*0xB4*/ Some((LDY, ZeroPageX)), -/*0xB5*/ Some((LDA, ZeroPageX)), -/*0xB6*/ Some((LDX, ZeroPageY)), +/*0xB4*/ Some((Instruction::LDY, AddressingMode::ZeroPageX)), +/*0xB5*/ Some((Instruction::LDA, AddressingMode::ZeroPageX)), +/*0xB6*/ Some((Instruction::LDX, AddressingMode::ZeroPageY)), /*0xB7*/ None, -/*0xB8*/ Some((CLV, Implied)), -/*0xB9*/ Some((LDA, AbsoluteY)), -/*0xBA*/ Some((TSX, Implied)), +/*0xB8*/ Some((Instruction::CLV, AddressingMode::Implied)), +/*0xB9*/ Some((Instruction::LDA, AddressingMode::AbsoluteY)), +/*0xBA*/ Some((Instruction::TSX, AddressingMode::Implied)), /*0xBB*/ None, -/*0xBC*/ Some((LDY, AbsoluteX)), -/*0xBD*/ Some((LDA, AbsoluteX)), -/*0xBE*/ Some((LDX, AbsoluteY)), +/*0xBC*/ Some((Instruction::LDY, AddressingMode::AbsoluteX)), +/*0xBD*/ Some((Instruction::LDA, AddressingMode::AbsoluteX)), +/*0xBE*/ Some((Instruction::LDX, AddressingMode::AbsoluteY)), /*0xBF*/ None, -/*0xC0*/ Some((CPY, Immediate)), -/*0xC1*/ Some((CMP, IndexedIndirectX)), +/*0xC0*/ Some((Instruction::CPY, AddressingMode::Immediate)), +/*0xC1*/ Some((Instruction::CMP, AddressingMode::IndexedIndirectX)), /*0xC2*/ None, /*0xC3*/ None, -/*0xC4*/ Some((CPY, ZeroPage)), -/*0xC5*/ Some((CMP, ZeroPage)), -/*0xC6*/ Some((DEC, ZeroPage)), +/*0xC4*/ Some((Instruction::CPY, AddressingMode::ZeroPage)), +/*0xC5*/ Some((Instruction::CMP, AddressingMode::ZeroPage)), +/*0xC6*/ Some((Instruction::DEC, AddressingMode::ZeroPage)), /*0xC7*/ None, -/*0xC8*/ Some((INY, Implied)), -/*0xC9*/ Some((CMP, Immediate)), -/*0xCA*/ Some((DEX, Implied)), +/*0xC8*/ Some((Instruction::INY, AddressingMode::Implied)), +/*0xC9*/ Some((Instruction::CMP, AddressingMode::Immediate)), +/*0xCA*/ Some((Instruction::DEX, AddressingMode::Implied)), /*0xCB*/ None, -/*0xCC*/ Some((CPY, Absolute)), -/*0xCD*/ Some((CMP, Absolute)), -/*0xCE*/ Some((DEC, Absolute)), +/*0xCC*/ Some((Instruction::CPY, AddressingMode::Absolute)), +/*0xCD*/ Some((Instruction::CMP, AddressingMode::Absolute)), +/*0xCE*/ Some((Instruction::DEC, AddressingMode::Absolute)), /*0xCF*/ None, -/*0xD0*/ Some((BNE, Relative)), -/*0xD1*/ Some((CMP, IndirectIndexedY)), +/*0xD0*/ Some((Instruction::BNE, AddressingMode::Relative)), +/*0xD1*/ Some((Instruction::CMP, AddressingMode::IndirectIndexedY)), /*0xD2*/ None, /*0xD3*/ None, /*0xD4*/ None, -/*0xD5*/ Some((CMP, ZeroPageX)), -/*0xD6*/ Some((DEC, ZeroPageX)), +/*0xD5*/ Some((Instruction::CMP, AddressingMode::ZeroPageX)), +/*0xD6*/ Some((Instruction::DEC, AddressingMode::ZeroPageX)), /*0xD7*/ None, -/*0xD8*/ Some((CLD, Implied)), -/*0xD9*/ Some((CMP, AbsoluteY)), +/*0xD8*/ Some((Instruction::CLD, AddressingMode::Implied)), +/*0xD9*/ Some((Instruction::CMP, AddressingMode::AbsoluteY)), /*0xDA*/ None, /*0xDB*/ None, /*0xDC*/ None, -/*0xDD*/ Some((CMP, AbsoluteX)), -/*0xDE*/ Some((DEC, AbsoluteX)), +/*0xDD*/ Some((Instruction::CMP, AddressingMode::AbsoluteX)), +/*0xDE*/ Some((Instruction::DEC, AddressingMode::AbsoluteX)), /*0xDF*/ None, -/*0xE0*/ Some((CPX, Immediate)), -/*0xE1*/ Some((SBC, IndexedIndirectX)), +/*0xE0*/ Some((Instruction::CPX, AddressingMode::Immediate)), +/*0xE1*/ Some((Instruction::SBC, AddressingMode::IndexedIndirectX)), /*0xE2*/ None, /*0xE3*/ None, -/*0xE4*/ Some((CPX, ZeroPage)), -/*0xE5*/ Some((SBC, ZeroPage)), -/*0xE6*/ Some((INC, ZeroPage)), +/*0xE4*/ Some((Instruction::CPX, AddressingMode::ZeroPage)), +/*0xE5*/ Some((Instruction::SBC, AddressingMode::ZeroPage)), +/*0xE6*/ Some((Instruction::INC, AddressingMode::ZeroPage)), /*0xE7*/ None, -/*0xE8*/ Some((INX, Implied)), -/*0xE9*/ Some((SBC, Immediate)), -/*0xEA*/ Some((NOP, Implied)), +/*0xE8*/ Some((Instruction::INX, AddressingMode::Implied)), +/*0xE9*/ Some((Instruction::SBC, AddressingMode::Immediate)), +/*0xEA*/ Some((Instruction::NOP, AddressingMode::Implied)), /*0xEB*/ None, -/*0xEC*/ Some((CPX, Absolute)), -/*0xED*/ Some((SBC, Absolute)), -/*0xEE*/ Some((INC, Absolute)), +/*0xEC*/ Some((Instruction::CPX, AddressingMode::Absolute)), +/*0xED*/ Some((Instruction::SBC, AddressingMode::Absolute)), +/*0xEE*/ Some((Instruction::INC, AddressingMode::Absolute)), /*0xEF*/ None, -/*0xF0*/ Some((BEQ, Relative)), -/*0xF1*/ Some((SBC, IndirectIndexedY)), +/*0xF0*/ Some((Instruction::BEQ, AddressingMode::Relative)), +/*0xF1*/ Some((Instruction::SBC, AddressingMode::IndirectIndexedY)), /*0xF2*/ None, /*0xF3*/ None, /*0xF4*/ None, -/*0xF5*/ Some((SBC, ZeroPageX)), -/*0xF6*/ Some((INC, ZeroPageX)), +/*0xF5*/ Some((Instruction::SBC, AddressingMode::ZeroPageX)), +/*0xF6*/ Some((Instruction::INC, AddressingMode::ZeroPageX)), /*0xF7*/ None, -/*0xF8*/ Some((SED, Implied)), -/*0xF9*/ Some((SBC, AbsoluteY)), +/*0xF8*/ Some((Instruction::SED, AddressingMode::Implied)), +/*0xF9*/ Some((Instruction::SBC, AddressingMode::AbsoluteY)), /*0xFA*/ None, /*0xFB*/ None, /*0xFC*/ None, -/*0xFD*/ Some((SBC, AbsoluteX)), -/*0xFE*/ Some((INC, AbsoluteX)), +/*0xFD*/ Some((Instruction::SBC, AddressingMode::AbsoluteX)), +/*0xFE*/ Some((Instruction::INC, AddressingMode::AbsoluteX)), /*0xFF*/ None, ]; diff --git a/src/machine.rs b/src/machine.rs index 94d2c24..a9f3e01 100644 --- a/src/machine.rs +++ b/src/machine.rs @@ -29,7 +29,7 @@ use std; use address::{Address, AddressDiff}; use instruction; -use instruction::{DecodedInstr}; +use instruction::{DecodedInstr, Instruction, OpInput}; use memory::Memory; use registers::{ Registers, StackPointer, Status, StatusArgs }; use registers::{ PS_NEGATIVE, PS_DECIMAL_MODE, PS_OVERFLOW, PS_ZERO, PS_CARRY, @@ -78,25 +78,25 @@ impl Machine { pub fn execute_instruction(&mut self, decoded_instr: DecodedInstr) { match decoded_instr { - (instruction::ADC, instruction::UseImmediate(val)) => { + (Instruction::ADC, OpInput::UseImmediate(val)) => { debug!("add with carry immediate: {}", val); self.add_with_carry(val as i8); } - (instruction::ADC, instruction::UseAddress(addr)) => { + (Instruction::ADC, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr) as i8; debug!("add with carry. address: {}. value: {}", addr, val); self.add_with_carry(val); } - (instruction::AND, instruction::UseImmediate(val)) => { + (Instruction::AND, OpInput::UseImmediate(val)) => { self.and(val as i8); } - (instruction::AND, instruction::UseAddress(addr)) => { + (Instruction::AND, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr) as i8; self.and(val as i8); } - (instruction::ASL, instruction::UseImplied) => { + (Instruction::ASL, OpInput::UseImplied) => { // Accumulator mode let mut val = self.registers.accumulator as u8; Machine::shift_left_with_flags(&mut val, @@ -104,31 +104,31 @@ impl Machine { self.registers.accumulator = val as i8; } - (instruction::ASL, instruction::UseAddress(addr)) => { + (Instruction::ASL, OpInput::UseAddress(addr)) => { Machine::shift_left_with_flags( self.memory.get_byte_mut_ref(addr), &mut self.registers.status); } - (instruction::BCC, instruction::UseRelative(rel)) => { + (Instruction::BCC, OpInput::UseRelative(rel)) => { let addr = self.registers.program_counter + AddressDiff(rel as i32); self.branch_if_carry_clear(addr); } - (instruction::BCS, instruction::UseRelative(rel)) => { + (Instruction::BCS, OpInput::UseRelative(rel)) => { let addr = self.registers.program_counter + AddressDiff(rel as i32); self.branch_if_carry_set(addr); } - (instruction::BEQ, instruction::UseRelative(rel)) => { + (Instruction::BEQ, OpInput::UseRelative(rel)) => { let addr = self.registers.program_counter + AddressDiff(rel as i32); self.branch_if_equal(addr); } - (instruction::BIT, instruction::UseAddress(addr)) => { + (Instruction::BIT, OpInput::UseAddress(addr)) => { let a: u8 = self.registers.accumulator as u8; let m: u8 = self.memory.get_byte(addr); let res = a & m; @@ -150,163 +150,163 @@ impl Machine { ..StatusArgs::none() } )); } - (instruction::BMI, instruction::UseRelative(rel)) => { + (Instruction::BMI, OpInput::UseRelative(rel)) => { let addr = self.registers.program_counter + AddressDiff(rel as i32); debug!("branch if minus relative. address: {}", addr); self.branch_if_minus(addr); } - (instruction::BPL, instruction::UseRelative(rel)) => { + (Instruction::BPL, OpInput::UseRelative(rel)) => { let addr = self.registers.program_counter + AddressDiff(rel as i32); self.branch_if_positive(addr); } - (instruction::BVC, instruction::UseRelative(rel)) => { + (Instruction::BVC, OpInput::UseRelative(rel)) => { let addr = self.registers.program_counter + AddressDiff(rel as i32); self.branch_if_overflow_clear(addr); } - (instruction::BVS, instruction::UseRelative(rel)) => { + (Instruction::BVS, OpInput::UseRelative(rel)) => { let addr = self.registers.program_counter + AddressDiff(rel as i32); self.branch_if_overflow_set(addr); } - (instruction::CLC, instruction::UseImplied) => { + (Instruction::CLC, OpInput::UseImplied) => { self.registers.status.and(!PS_CARRY); } - (instruction::CLD, instruction::UseImplied) => { + (Instruction::CLD, OpInput::UseImplied) => { self.registers.status.and(!PS_DECIMAL_MODE); } - (instruction::CLI, instruction::UseImplied) => { + (Instruction::CLI, OpInput::UseImplied) => { self.registers.status.and(!PS_DISABLE_INTERRUPTS); } - (instruction::CLV, instruction::UseImplied) => { + (Instruction::CLV, OpInput::UseImplied) => { self.registers.status.and(!PS_OVERFLOW); } - (instruction::CMP, instruction::UseImmediate(val)) => { + (Instruction::CMP, OpInput::UseImmediate(val)) => { self.compare_with_a_register(val); } - (instruction::CMP, instruction::UseAddress(addr)) => { + (Instruction::CMP, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr); self.compare_with_a_register(val); } - (instruction::CPX, instruction::UseImmediate(val)) => { + (Instruction::CPX, OpInput::UseImmediate(val)) => { self.compare_with_x_register(val); } - (instruction::CPX, instruction::UseAddress(addr)) => { + (Instruction::CPX, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr); self.compare_with_x_register(val); } - (instruction::CPY, instruction::UseImmediate(val)) => { + (Instruction::CPY, OpInput::UseImmediate(val)) => { self.compare_with_y_register(val); } - (instruction::CPY, instruction::UseAddress(addr)) => { + (Instruction::CPY, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr); self.compare_with_y_register(val); } - (instruction::DEC, instruction::UseAddress(addr)) => { + (Instruction::DEC, OpInput::UseAddress(addr)) => { self.decrement_memory(addr) } - (instruction::DEX, instruction::UseImplied) => { + (Instruction::DEX, OpInput::UseImplied) => { self.dec_x(); } - (instruction::EOR, instruction::UseImmediate(val)) => { + (Instruction::EOR, OpInput::UseImmediate(val)) => { self.exclusive_or(val); } - (instruction::EOR, instruction::UseAddress(addr)) => { + (Instruction::EOR, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr); self.exclusive_or(val); } - (instruction::INC, instruction::UseAddress(addr)) => { + (Instruction::INC, OpInput::UseAddress(addr)) => { let m = self.memory.get_byte(addr); let m = m + 1; self.memory.set_byte(addr, m); let i = m as i8; Machine::set_flags_from_i8(&mut self.registers.status, i); } - (instruction::INX, instruction::UseImplied) => { + (Instruction::INX, OpInput::UseImplied) => { let x = self.registers.index_x + 1; self.load_x_register(x); } - (instruction::INY, instruction::UseImplied) => { + (Instruction::INY, OpInput::UseImplied) => { let y = self.registers.index_y + 1; self.load_y_register(y); } - (instruction::JMP, instruction::UseAddress(addr)) => { + (Instruction::JMP, OpInput::UseAddress(addr)) => { self.jump(addr) } - (instruction::LDA, instruction::UseImmediate(val)) => { + (Instruction::LDA, OpInput::UseImmediate(val)) => { debug!("load A immediate: {}", val); self.load_accumulator(val as i8); } - (instruction::LDA, instruction::UseAddress(addr)) => { + (Instruction::LDA, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr); debug!("load A. address: {}. value: {}", addr, val); self.load_accumulator(val as i8); } - (instruction::LDX, instruction::UseImmediate(val)) => { + (Instruction::LDX, OpInput::UseImmediate(val)) => { debug!("load X immediate: {}", val); self.load_x_register(val as i8); } - (instruction::LDX, instruction::UseAddress(addr)) => { + (Instruction::LDX, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr); debug!("load X. address: {}. value: {}", addr, val); self.load_x_register(val as i8); } - (instruction::LDY, instruction::UseImmediate(val)) => { + (Instruction::LDY, OpInput::UseImmediate(val)) => { debug!("load Y immediate: {}", val); self.load_y_register(val as i8); } - (instruction::LDY, instruction::UseAddress(addr)) => { + (Instruction::LDY, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr); debug!("load Y. address: {}. value: {}", addr, val); self.load_y_register(val as i8); } - (instruction::LSR, instruction::UseImplied) => { + (Instruction::LSR, OpInput::UseImplied) => { // Accumulator mode let mut val = self.registers.accumulator as u8; Machine::shift_right_with_flags(&mut val, &mut self.registers.status); self.registers.accumulator = val as i8; } - (instruction::LSR, instruction::UseAddress(addr)) => { + (Instruction::LSR, OpInput::UseAddress(addr)) => { Machine::shift_right_with_flags( self.memory.get_byte_mut_ref(addr), &mut self.registers.status); } - (instruction::PHA, instruction::UseImplied) => { + (Instruction::PHA, OpInput::UseImplied) => { // Push accumulator let val = self.registers.accumulator as u8; self.push_on_stack(val); } - (instruction::PHP, instruction::UseImplied) => { + (Instruction::PHP, OpInput::UseImplied) => { // Push status let val = self.registers.status.bits(); self.push_on_stack(val); } - (instruction::PLA, instruction::UseImplied) => { + (Instruction::PLA, OpInput::UseImplied) => { // Pull accumulator let val: u8 = self.pull_from_stack(); self.registers.accumulator = val as i8; } - (instruction::PLP, instruction::UseImplied) => { + (Instruction::PLP, OpInput::UseImplied) => { // Pull status let val: u8 = self.pull_from_stack(); // The `truncate` here won't do anything because we have a @@ -315,92 +315,92 @@ impl Machine { self.registers.status = Status::from_bits_truncate(val); } - (instruction::ROL, instruction::UseImplied) => { + (Instruction::ROL, OpInput::UseImplied) => { // Accumulator mode let mut val = self.registers.accumulator as u8; Machine::rotate_left_with_flags(&mut val, &mut self.registers.status); self.registers.accumulator = val as i8; } - (instruction::ROL, instruction::UseAddress(addr)) => { + (Instruction::ROL, OpInput::UseAddress(addr)) => { Machine::rotate_left_with_flags( self.memory.get_byte_mut_ref(addr), &mut self.registers.status); } - (instruction::ROR, instruction::UseImplied) => { + (Instruction::ROR, OpInput::UseImplied) => { // Accumulator mode let mut val = self.registers.accumulator as u8; Machine::rotate_right_with_flags(&mut val, &mut self.registers.status); self.registers.accumulator = val as i8; } - (instruction::ROR, instruction::UseAddress(addr)) => { + (Instruction::ROR, OpInput::UseAddress(addr)) => { Machine::rotate_right_with_flags( self.memory.get_byte_mut_ref(addr), &mut self.registers.status); } - (instruction::SBC, instruction::UseImmediate(val)) => { + (Instruction::SBC, OpInput::UseImmediate(val)) => { debug!("subtract with carry immediate: {}", val); self.subtract_with_carry(val as i8); } - (instruction::SBC, instruction::UseAddress(addr)) => { + (Instruction::SBC, OpInput::UseAddress(addr)) => { let val = self.memory.get_byte(addr) as i8; debug!("subtract with carry. address: {}. value: {}", addr, val); self.subtract_with_carry(val); } - (instruction::SEC, instruction::UseImplied) => { + (Instruction::SEC, OpInput::UseImplied) => { self.registers.status.or(PS_CARRY); } - (instruction::SED, instruction::UseImplied) => { + (Instruction::SED, OpInput::UseImplied) => { self.registers.status.or(PS_DECIMAL_MODE); } - (instruction::SEI, instruction::UseImplied) => { + (Instruction::SEI, OpInput::UseImplied) => { self.registers.status.or(PS_DISABLE_INTERRUPTS); } - (instruction::STA, instruction::UseAddress(addr)) => { + (Instruction::STA, OpInput::UseAddress(addr)) => { self.memory.set_byte(addr, self.registers.accumulator as u8); } - (instruction::STX, instruction::UseAddress(addr)) => { + (Instruction::STX, OpInput::UseAddress(addr)) => { self.memory.set_byte(addr, self.registers.index_x as u8); } - (instruction::STY, instruction::UseAddress(addr)) => { + (Instruction::STY, OpInput::UseAddress(addr)) => { self.memory.set_byte(addr, self.registers.index_y as u8); } - (instruction::TAX, instruction::UseImplied) => { + (Instruction::TAX, OpInput::UseImplied) => { let val = self.registers.accumulator; self.load_x_register(val); } - (instruction::TAY, instruction::UseImplied) => { + (Instruction::TAY, OpInput::UseImplied) => { let val = self.registers.accumulator; self.load_y_register(val); } - (instruction::TSX, instruction::UseImplied) => { + (Instruction::TSX, OpInput::UseImplied) => { let StackPointer(val) = self.registers.stack_pointer; let val = val as i8; self.load_x_register(val); } - (instruction::TXA, instruction::UseImplied) => { + (Instruction::TXA, OpInput::UseImplied) => { let val = self.registers.index_x; self.load_accumulator(val); } - (instruction::TXS, instruction::UseImplied) => { + (Instruction::TXS, OpInput::UseImplied) => { // Note that this is the only 'transfer' instruction that does // NOT set the zero and negative flags. (Because the target // is the stack pointer) let val = self.registers.index_x; self.registers.stack_pointer = StackPointer(val as u8); } - (instruction::TYA, instruction::UseImplied) => { + (Instruction::TYA, OpInput::UseImplied) => { let val = self.registers.index_y; self.load_accumulator(val); } - (instruction::NOP, instruction::UseImplied) => { + (Instruction::NOP, OpInput::UseImplied) => { debug!("NOP instruction"); } (_, _) => { @@ -828,7 +828,7 @@ fn and_test() { fn subtract_with_carry_test() { let mut machine = Machine::new(); - machine.execute_instruction((instruction::SEC, instruction::UseImplied)); + machine.execute_instruction((Instruction::SEC, OpInput::UseImplied)); machine.registers.accumulator = 0; machine.subtract_with_carry(1); @@ -838,7 +838,7 @@ fn subtract_with_carry_test() { assert_eq!(machine.registers.status.contains(PS_NEGATIVE), true); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), false); - machine.execute_instruction((instruction::SEC, instruction::UseImplied)); + machine.execute_instruction((Instruction::SEC, OpInput::UseImplied)); machine.registers.accumulator = -128; machine.subtract_with_carry(1); assert_eq!(machine.registers.accumulator, 127); @@ -847,7 +847,7 @@ fn subtract_with_carry_test() { assert_eq!(machine.registers.status.contains(PS_NEGATIVE), false); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), true); - machine.execute_instruction((instruction::SEC, instruction::UseImplied)); + machine.execute_instruction((Instruction::SEC, OpInput::UseImplied)); machine.registers.accumulator = 127; machine.subtract_with_carry(-1); assert_eq!(machine.registers.accumulator, -128); @@ -856,7 +856,7 @@ fn subtract_with_carry_test() { assert_eq!(machine.registers.status.contains(PS_NEGATIVE), true); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), true); - machine.execute_instruction((instruction::CLC, instruction::UseImplied)); + machine.execute_instruction((Instruction::CLC, OpInput::UseImplied)); machine.registers.accumulator = -64; machine.subtract_with_carry(64); assert_eq!(machine.registers.accumulator, 127); @@ -865,7 +865,7 @@ fn subtract_with_carry_test() { assert_eq!(machine.registers.status.contains(PS_NEGATIVE), false); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), true); - machine.execute_instruction((instruction::SEC, instruction::UseImplied)); + machine.execute_instruction((Instruction::SEC, OpInput::UseImplied)); machine.registers.accumulator = 0; machine.subtract_with_carry(-128); assert_eq!(machine.registers.accumulator, -128); @@ -874,7 +874,7 @@ fn subtract_with_carry_test() { assert_eq!(machine.registers.status.contains(PS_NEGATIVE), true); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), true); - machine.execute_instruction((instruction::CLC, instruction::UseImplied)); + machine.execute_instruction((Instruction::CLC, OpInput::UseImplied)); machine.registers.accumulator = 0; machine.subtract_with_carry(127); assert_eq!(machine.registers.accumulator, -128); @@ -919,40 +919,40 @@ fn logical_shift_right_test() { // Testing UseImplied version (which targets the accumulator) only, for now let mut machine = Machine::new(); - machine.execute_instruction((instruction::LDA, - instruction::UseImmediate(0))); - machine.execute_instruction((instruction::LSR, - instruction::UseImplied)); + machine.execute_instruction((Instruction::LDA, + OpInput::UseImmediate(0))); + machine.execute_instruction((Instruction::LSR, + OpInput::UseImplied)); assert_eq!(machine.registers.accumulator, 0); assert_eq!(machine.registers.status.contains(PS_CARRY), false); assert_eq!(machine.registers.status.contains(PS_ZERO), true); assert_eq!(machine.registers.status.contains(PS_NEGATIVE), false); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), false); - machine.execute_instruction((instruction::LDA, - instruction::UseImmediate(1))); - machine.execute_instruction((instruction::LSR, - instruction::UseImplied)); + machine.execute_instruction((Instruction::LDA, + OpInput::UseImmediate(1))); + machine.execute_instruction((Instruction::LSR, + OpInput::UseImplied)); assert_eq!(machine.registers.accumulator, 0); assert_eq!(machine.registers.status.contains(PS_CARRY), true); assert_eq!(machine.registers.status.contains(PS_ZERO), true); assert_eq!(machine.registers.status.contains(PS_NEGATIVE), false); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), false); - machine.execute_instruction((instruction::LDA, - instruction::UseImmediate(255))); - machine.execute_instruction((instruction::LSR, - instruction::UseImplied)); + machine.execute_instruction((Instruction::LDA, + OpInput::UseImmediate(255))); + machine.execute_instruction((Instruction::LSR, + OpInput::UseImplied)); assert_eq!(machine.registers.accumulator, 0x7F); assert_eq!(machine.registers.status.contains(PS_CARRY), true); assert_eq!(machine.registers.status.contains(PS_ZERO), false); assert_eq!(machine.registers.status.contains(PS_NEGATIVE), false); assert_eq!(machine.registers.status.contains(PS_OVERFLOW), false); - machine.execute_instruction((instruction::LDA, - instruction::UseImmediate(254))); - machine.execute_instruction((instruction::LSR, - instruction::UseImplied)); + machine.execute_instruction((Instruction::LDA, + OpInput::UseImmediate(254))); + machine.execute_instruction((Instruction::LSR, + OpInput::UseImplied)); assert_eq!(machine.registers.accumulator, 0x7F); assert_eq!(machine.registers.status.contains(PS_CARRY), false); assert_eq!(machine.registers.status.contains(PS_ZERO), false); @@ -1018,11 +1018,11 @@ fn jump_test() { fn branch_if_carry_clear_test() { let mut machine = Machine::new(); - machine.execute_instruction((instruction::SEC, instruction::UseImplied)); + machine.execute_instruction((Instruction::SEC, OpInput::UseImplied)); machine.branch_if_carry_clear(Address(0xABCD)); assert_eq!(machine.registers.program_counter, Address(0)); - machine.execute_instruction((instruction::CLC, instruction::UseImplied)); + machine.execute_instruction((Instruction::CLC, OpInput::UseImplied)); machine.branch_if_carry_clear(Address(0xABCD)); assert_eq!(machine.registers.program_counter, Address(0xABCD)); } @@ -1031,11 +1031,11 @@ fn branch_if_carry_clear_test() { fn branch_if_carry_set_test() { let mut machine = Machine::new(); - machine.execute_instruction((instruction::CLC, instruction::UseImplied)); + machine.execute_instruction((Instruction::CLC, OpInput::UseImplied)); machine.branch_if_carry_set(Address(0xABCD)); assert_eq!(machine.registers.program_counter, Address(0)); - machine.execute_instruction((instruction::SEC, instruction::UseImplied)); + machine.execute_instruction((Instruction::SEC, OpInput::UseImplied)); machine.branch_if_carry_set(Address(0xABCD)); assert_eq!(machine.registers.program_counter, Address(0xABCD)); } @@ -1113,14 +1113,15 @@ fn branch_if_overflow_set_test() { assert_eq!(machine.registers.program_counter, Address(0xABCD)); } +#[cfg(test)] fn compare_test_helper( compare: |&mut Machine, u8|, - load_instruction: instruction::Instruction + load_instruction: Instruction ) { let mut machine = Machine::new(); machine.execute_instruction( - (load_instruction, instruction::UseImmediate(127)) + (load_instruction, OpInput::UseImmediate(127)) ); compare(&mut machine, 127); @@ -1130,7 +1131,7 @@ fn compare_test_helper( machine.execute_instruction( - (load_instruction, instruction::UseImmediate(127)) + (load_instruction, OpInput::UseImmediate(127)) ); compare(&mut machine, 1); @@ -1140,7 +1141,7 @@ fn compare_test_helper( machine.execute_instruction( - (load_instruction, instruction::UseImmediate(1)) + (load_instruction, OpInput::UseImmediate(1)) ); compare(&mut machine, 2); @@ -1150,7 +1151,7 @@ fn compare_test_helper( machine.execute_instruction( - (load_instruction, instruction::UseImmediate(20)) + (load_instruction, OpInput::UseImmediate(20)) ); compare(&mut machine, -50); @@ -1160,7 +1161,7 @@ fn compare_test_helper( machine.execute_instruction( - (load_instruction, instruction::UseImmediate(1)) + (load_instruction, OpInput::UseImmediate(1)) ); compare(&mut machine, -1); @@ -1170,7 +1171,7 @@ fn compare_test_helper( machine.execute_instruction( - (load_instruction, instruction::UseImmediate(127)) + (load_instruction, OpInput::UseImmediate(127)) ); compare(&mut machine, -128); @@ -1185,7 +1186,7 @@ fn compare_with_a_register_test() { |machine: &mut Machine, val: u8| { machine.compare_with_a_register(val); }, - instruction::LDA + Instruction::LDA ); } @@ -1195,7 +1196,7 @@ fn compare_with_x_register_test() { |machine: &mut Machine, val: u8| { machine.compare_with_x_register(val); }, - instruction::LDX + Instruction::LDX ); } @@ -1205,7 +1206,7 @@ fn compare_with_y_register_test() { |machine: &mut Machine, val: u8| { machine.compare_with_y_register(val); }, - instruction::LDY + Instruction::LDY ); } @@ -1216,7 +1217,7 @@ fn exclusive_or_test() { for a_before in range(0u8, 255u8) { for val in range(0u8, 255u8) { machine.execute_instruction( - (instruction::LDA, instruction::UseImmediate(a_before)) + (Instruction::LDA, OpInput::UseImmediate(a_before)) ); machine.exclusive_or(val); @@ -1237,4 +1238,4 @@ fn exclusive_or_test() { } } } -} \ No newline at end of file +}