CPU cycling and disassembling
This commit is contained in:
parent
3685fc6595
commit
77c7e66b9b
281
Cargo.lock
generated
281
Cargo.lock
generated
@ -13,4 +13,285 @@ name = "core"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"simplelog",
|
||||
"strum",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "deranged"
|
||||
version = "0.3.11"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4"
|
||||
dependencies = [
|
||||
"powerfmt",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "heck"
|
||||
version = "0.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea"
|
||||
|
||||
[[package]]
|
||||
name = "itoa"
|
||||
version = "1.0.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d75a2a4b1b190afb6f5425f10f6a8f959d2ea0b9c2b1d79553551850539e4674"
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.169"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b5aba8db14291edd000dfcc4d620c7ebfb122c613afb886ca8803fa4e128a20a"
|
||||
|
||||
[[package]]
|
||||
name = "log"
|
||||
version = "0.4.25"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "04cbf5b083de1c7e0222a7a51dbfdba1cbe1c6ab0b15e29fff3f6c077fd9cd9f"
|
||||
|
||||
[[package]]
|
||||
name = "num-conv"
|
||||
version = "0.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9"
|
||||
|
||||
[[package]]
|
||||
name = "num_threads"
|
||||
version = "0.1.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5c7398b9c8b70908f6371f47ed36737907c87c52af34c268fed0bf0ceb92ead9"
|
||||
dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "paris"
|
||||
version = "1.5.15"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8fecab3723493c7851f292cb060f3ee1c42f19b8d749345d0d7eaf3fd19aa62d"
|
||||
|
||||
[[package]]
|
||||
name = "powerfmt"
|
||||
version = "0.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "439ee305def115ba05938db6eb1644ff94165c5ab5e9420d1c1bcedbba909391"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.93"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "60946a68e5f9d28b0dc1c21bb8a97ee7d018a8b322fa57838ba31cc878e22d99"
|
||||
dependencies = [
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quote"
|
||||
version = "1.0.38"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0e4dccaaaf89514f546c693ddc140f729f958c247918a13380cccc6078391acc"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustversion"
|
||||
version = "1.0.19"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f7c45b9784283f1b2e7fb61b42047c2fd678ef0960d4f6f1eba131594cc369d4"
|
||||
|
||||
[[package]]
|
||||
name = "serde"
|
||||
version = "1.0.217"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "02fc4265df13d6fa1d00ecff087228cc0a2b5f3c0e87e258d8b94a156e984c70"
|
||||
dependencies = [
|
||||
"serde_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_derive"
|
||||
version = "1.0.217"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5a9bf7cf98d04a2b28aead066b7496853d4779c9cc183c440dbac457641e19a0"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "simplelog"
|
||||
version = "0.12.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "16257adbfaef1ee58b1363bdc0664c9b8e1e30aed86049635fb5f147d065a9c0"
|
||||
dependencies = [
|
||||
"log",
|
||||
"paris",
|
||||
"termcolor",
|
||||
"time",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "strum"
|
||||
version = "0.26.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8fec0f0aef304996cf250b31b5a10dee7980c85da9d759361292b8bca5a18f06"
|
||||
dependencies = [
|
||||
"strum_macros",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "strum_macros"
|
||||
version = "0.26.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4c6bee85a5a24955dc440386795aa378cd9cf82acd5f764469152d2270e581be"
|
||||
dependencies = [
|
||||
"heck",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"rustversion",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.96"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d5d0adab1ae378d7f53bdebc67a39f1f151407ef230f0ce2883572f5d8985c80"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "termcolor"
|
||||
version = "1.4.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "06794f8f6c5c898b3275aebefa6b8a1cb24cd2c6c79397ab15774837a0bc5755"
|
||||
dependencies = [
|
||||
"winapi-util",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "time"
|
||||
version = "0.3.37"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "35e7868883861bd0e56d9ac6efcaaca0d6d5d82a2a7ec8209ff492c07cf37b21"
|
||||
dependencies = [
|
||||
"deranged",
|
||||
"itoa",
|
||||
"libc",
|
||||
"num-conv",
|
||||
"num_threads",
|
||||
"powerfmt",
|
||||
"serde",
|
||||
"time-core",
|
||||
"time-macros",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "time-core"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3"
|
||||
|
||||
[[package]]
|
||||
name = "time-macros"
|
||||
version = "0.2.19"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2834e6017e3e5e4b9834939793b282bc03b37a3336245fa820e35e233e2a85de"
|
||||
dependencies = [
|
||||
"num-conv",
|
||||
"time-core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "unicode-ident"
|
||||
version = "1.0.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "adb9e6ca4f869e1180728b7950e35922a7fc6397f7b641499e8f3ef06e50dc83"
|
||||
|
||||
[[package]]
|
||||
name = "winapi-util"
|
||||
version = "0.1.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cf221c93e13a30d793f7645a0e7762c55d169dbb0a49671918a2319d289b10bb"
|
||||
dependencies = [
|
||||
"windows-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.59.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1e38bc4d79ed67fd075bcc251a1c39b32a1776bbe92e5bef1f0bf1f8c531853b"
|
||||
dependencies = [
|
||||
"windows-targets",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-targets"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9b724f72796e036ab90c1021d4780d4d3d648aca59e491e6b98e725b84e99973"
|
||||
dependencies = [
|
||||
"windows_aarch64_gnullvm",
|
||||
"windows_aarch64_msvc",
|
||||
"windows_i686_gnu",
|
||||
"windows_i686_gnullvm",
|
||||
"windows_i686_msvc",
|
||||
"windows_x86_64_gnu",
|
||||
"windows_x86_64_gnullvm",
|
||||
"windows_x86_64_msvc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8e9b5ad5ab802e97eb8e295ac6720e509ee4c243f69d781394014ebfe8bbfa0b"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnullvm"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec"
|
||||
|
@ -7,3 +7,5 @@ edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
bitflags = "2.7.0"
|
||||
simplelog = { version = "^0.12.0", features = ["paris"] }
|
||||
strum = { version = "0.26", features = ["derive"] }
|
||||
|
48
core/src/cpu/disassembler.rs
Normal file
48
core/src/cpu/disassembler.rs
Normal file
@ -0,0 +1,48 @@
|
||||
use crate::cpu::op::AddressingMode::*;
|
||||
use crate::cpu::op::{AddressingMode, Instruction};
|
||||
use crate::cpu::Cpu;
|
||||
|
||||
impl Cpu {
|
||||
pub fn disassemble_next_instr(&self) {
|
||||
let registers = self.registers;
|
||||
let op_code = self.memory_bus.get_byte(registers.pc);
|
||||
|
||||
let instr: Instruction = Self::INSTRUCTIONS[op_code];
|
||||
let operation = instr.op().to_string();
|
||||
let addr_mode = self.disassemble_addr_mode(instr.addr_mode());
|
||||
|
||||
dbg!(
|
||||
"DIS {:#04x} - {:#02x} {:?} {:?} - A {:#02x}, X {:#02x}, Y {:#02x}, SP: {:#02x}, F: {:#02x}",
|
||||
op_code,
|
||||
registers.pc,
|
||||
operation,
|
||||
addr_mode,
|
||||
registers.a,
|
||||
registers.x,
|
||||
registers.y,
|
||||
registers.sp,
|
||||
registers.status
|
||||
);
|
||||
}
|
||||
|
||||
fn disassemble_addr_mode(&self, addr_mode: AddressingMode, pc: u16) -> String {
|
||||
let word_peek = self.memory_bus.get_word(pc);
|
||||
let byte_peek = (word_peek & 0xFF) as u8;
|
||||
|
||||
match addr_mode {
|
||||
ZP0 => format!("${:#02x}", byte_peek),
|
||||
ZPX => format!("${:#02x},x", byte_peek),
|
||||
ZPY => format!("${:#02x},x", byte_peek),
|
||||
ABS => format!("${:#04x}", word_peek),
|
||||
ABX => format!("${:#04x},x", word_peek),
|
||||
ABY => format!("${:#04x},y", word_peek),
|
||||
IND => format!("(${:#04x})", word_peek),
|
||||
IDX => format!("(${:#02x},x)", word_peek),
|
||||
IDY => format!("(${:#02x}),y", word_peek),
|
||||
REL => format!("#${:#04x}", word_peek),
|
||||
ACC => String::from('A'),
|
||||
IMP => String::from(""),
|
||||
IMM => format!("{:#02x}", byte_peek),
|
||||
}
|
||||
}
|
||||
}
|
@ -1,7 +1,9 @@
|
||||
mod disassembler;
|
||||
mod op;
|
||||
mod operations;
|
||||
|
||||
use crate::memory::MemoryBus;
|
||||
use crate::Clock;
|
||||
use bitflags::bitflags;
|
||||
|
||||
const STACK_ADDR: u16 = 0x0100;
|
||||
@ -14,6 +16,9 @@ struct Cpu<'a> {
|
||||
/// The memory bus accessible by the CPU
|
||||
memory_bus: &'a MemoryBus,
|
||||
|
||||
/// The number of cycles ran on the CPU
|
||||
cycle: u32,
|
||||
|
||||
/// The amount of cycles the CPU will be busy for (won't execute any instruction)
|
||||
busy_cycle_count: u16,
|
||||
|
||||
@ -25,6 +30,7 @@ struct Cpu<'a> {
|
||||
}
|
||||
|
||||
/// Represents the registers of the 6502 CPU
|
||||
#[derive(Copy, Clone)]
|
||||
struct CpuRegisters {
|
||||
/// The program counter
|
||||
pc: u16,
|
||||
@ -137,6 +143,7 @@ impl Cpu {
|
||||
status: 0x04,
|
||||
},
|
||||
memory_bus,
|
||||
cycle: 0,
|
||||
busy_cycle_count: 0,
|
||||
oam_dma_triggered: false,
|
||||
nmi_requested: false,
|
||||
@ -232,3 +239,22 @@ impl CpuInternals for Cpu {
|
||||
self.registers.pc = pc;
|
||||
}
|
||||
}
|
||||
|
||||
impl Clock for Cpu {
|
||||
fn cycle(&mut self) {
|
||||
self.cycle += 1;
|
||||
|
||||
if self.busy_cycle_count > 0 {
|
||||
self.busy_cycle_count -= 1;
|
||||
return;
|
||||
}
|
||||
|
||||
self.disassemble_next_instr();
|
||||
|
||||
let op_code = self.program_get_next_byte();
|
||||
let instr = Self::INSTRUCTIONS[op_code];
|
||||
|
||||
self.busy_cycle_count = instr.cycles();
|
||||
self.exec_instruction(instr);
|
||||
}
|
||||
}
|
||||
|
@ -1,12 +1,12 @@
|
||||
// From https://github.com/lukexor/tetanes/blob/main/tetanes-core/src/cpu/instr.rs
|
||||
#[derive(Default, Copy, Clone, Debug, PartialEq, Eq)]
|
||||
#[derive(Default, Copy, Clone, Debug, PartialEq, Eq, strum::Display)]
|
||||
#[rustfmt::skip]
|
||||
pub enum OperationType {
|
||||
ADC, AND, ASL, BCC, BCS, BEQ, BIT, BMI, BNE, BPL, BRK, BVC, BVS, CLC, CLD, CLI, CLV, CMP, CPX,
|
||||
CPY, DEC, DEX, DEY, EOR, INC, INX, INY, JMP, JSR, LDA, LDX, LDY, LSR, NOP, ORA, PHA, PHP, PLA,
|
||||
PLP, ROL, ROR, RTI, RTS, SBC, SEC, SED, SEI, STA, STX, STY, TAX, TAY, TSX, TXA, TXS, TYA,
|
||||
// "Unofficial" opcodes
|
||||
SKB, IGN, ISB, DCP, SBX, LAS, LAX, AHX, SAX, ANE, SHX, RRA, TAS, SHY, ARR, SRE, ALR, RLA, ANC,
|
||||
ISB, DCP, SBX, LAS, LAX, AHX, SAX, ANE, SHX, RRA, TAS, SHY, ARR, SRE, ALR, RLA, ANC,
|
||||
SLO, #[default] STP
|
||||
}
|
||||
|
||||
@ -24,11 +24,10 @@ pub enum AddressingMode {
|
||||
use crate::cpu::{Cpu, CpuInternals};
|
||||
use AddressingMode::{ABS, ABX, ABY, ACC, IDX, IDY, IMM, IMP, IND, REL, ZP0, ZPX, ZPY};
|
||||
use OperationType::{
|
||||
ADC, AHX, ALR, ANC, AND, ARR, ASL, SBX, BCC, BCS, BEQ, BIT, BMI, BNE, BPL, BRK, BVC, BVS, CLC,
|
||||
CLD, CLI, CLV, CMP, CPX, CPY, DCP, DEC, DEX, DEY, EOR, IGN, INC, INX, INY, ISB, JMP, JSR, LAS,
|
||||
LAX, LDA, LDX, LDY, LSR, NOP, ORA, PHA, PHP, PLA, PLP, RLA, ROL, ROR, RRA, RTI, RTS, SAX, SBC,
|
||||
SEC, SED, SEI, SKB, SLO, SRE, STA, STX, STY, SHX, SHY, TAS, TAX, TAY, TSX, TXA, TXS, TYA, ANE,
|
||||
STP,
|
||||
ADC, AHX, ALR, ANC, AND, ANE, ARR, ASL, BCC, BCS, BEQ, BIT, BMI, BNE, BPL, BRK, BVC, BVS, CLC,
|
||||
CLD, CLI, CLV, CMP, CPX, CPY, DCP, DEC, DEX, DEY, EOR, INC, INX, INY, ISB, JMP, JSR, LAS, LAX,
|
||||
LDA, LDX, LDY, LSR, NOP, ORA, PHA, PHP, PLA, PLP, RLA, ROL, ROR, RRA, RTI, RTS, SAX, SBC, SBX,
|
||||
SEC, SED, SEI, SHX, SHY, SLO, SRE, STA, STP, STX, STY, TAS, TAX, TAY, TSX, TXA, TXS, TYA,
|
||||
};
|
||||
|
||||
/// CPU Instruction.
|
||||
@ -62,7 +61,7 @@ enum OperandType {
|
||||
pub struct Operand {
|
||||
operand_type: OperandType,
|
||||
pub value: u16,
|
||||
is_page_crossing: bool,
|
||||
pub is_page_crossing: bool,
|
||||
}
|
||||
|
||||
impl Operand {
|
||||
@ -103,21 +102,21 @@ impl Cpu {
|
||||
#[rustfmt::skip]
|
||||
pub const INSTRUCTIONS: [Instruction; 256] = [
|
||||
Instruction(0x00, IMM, BRK, 7), Instruction(0x01, IDX, ORA, 6), Instruction(0x02, IMP, STP, 2), Instruction(0x03, IDX, SLO, 8), Instruction(0x04, ZP0, NOP, 3), Instruction(0x05, ZP0, ORA, 3), Instruction(0x06, ZP0, ASL, 5), Instruction(0x07, ZP0, SLO, 5), Instruction(0x08, IMP, PHP, 3), Instruction(0x09, IMM, ORA, 2), Instruction(0x0A, ACC, ASL, 2), Instruction(0x0B, IMM, ANC, 2), Instruction(0x0C, ABS, NOP, 4), Instruction(0x0D, ABS, ORA, 4), Instruction(0x0E, ABS, ASL, 6), Instruction(0x0F, ABS, SLO, 6),
|
||||
Instruction(0x10, REL, BPL, 2), Instruction(0x11, IDY, ORA, 5), Instruction(0x12, IMP, STP, 2), Instruction(0x13, IDY, SLO, 8), Instruction(0x14, ZPX, NOP, 4), Instruction(0x15, ZPX, ORA, 4), Instruction(0x16, ZPX, ASL, 6), Instruction(0x17, ZPX, SLO, 6), Instruction(0x18, IMP, CLC, 2), Instruction(0x19, ABY, ORA, 4), Instruction(0x1A, IMP, NOP, 2), Instruction(0x1B, ABY, SLO, 7), Instruction(0x1C, ABX, IGN, 4), Instruction(0x1D, ABX, ORA, 4), Instruction(0x1E, ABX, ASL, 7), Instruction(0x1F, ABX, SLO, 7),
|
||||
Instruction(0x10, REL, BPL, 2), Instruction(0x11, IDY, ORA, 5), Instruction(0x12, IMP, STP, 2), Instruction(0x13, IDY, SLO, 8), Instruction(0x14, ZPX, NOP, 4), Instruction(0x15, ZPX, ORA, 4), Instruction(0x16, ZPX, ASL, 6), Instruction(0x17, ZPX, SLO, 6), Instruction(0x18, IMP, CLC, 2), Instruction(0x19, ABY, ORA, 4), Instruction(0x1A, IMP, NOP, 2), Instruction(0x1B, ABY, SLO, 7), Instruction(0x1C, ABX, NOP, 4), Instruction(0x1D, ABX, ORA, 4), Instruction(0x1E, ABX, ASL, 7), Instruction(0x1F, ABX, SLO, 7),
|
||||
Instruction(0x20, ABS, JSR, 6), Instruction(0x21, IDX, AND, 6), Instruction(0x22, IMP, STP, 2), Instruction(0x23, IDX, RLA, 8), Instruction(0x24, ZP0, BIT, 3), Instruction(0x25, ZP0, AND, 3), Instruction(0x26, ZP0, ROL, 5), Instruction(0x27, ZP0, RLA, 5), Instruction(0x28, IMP, PLP, 4), Instruction(0x29, IMM, AND, 2), Instruction(0x2A, ACC, ROL, 2), Instruction(0x2B, IMM, ANC, 2), Instruction(0x2C, ABS, BIT, 4), Instruction(0x2D, ABS, AND, 4), Instruction(0x2E, ABS, ROL, 6), Instruction(0x2F, ABS, RLA, 6),
|
||||
Instruction(0x30, REL, BMI, 2), Instruction(0x31, IDY, AND, 5), Instruction(0x32, IMP, STP, 2), Instruction(0x33, IDY, RLA, 8), Instruction(0x34, ZPX, NOP, 4), Instruction(0x35, ZPX, AND, 4), Instruction(0x36, ZPX, ROL, 6), Instruction(0x37, ZPX, RLA, 6), Instruction(0x38, IMP, SEC, 2), Instruction(0x39, ABY, AND, 4), Instruction(0x3A, IMP, NOP, 2), Instruction(0x3B, ABY, RLA, 7), Instruction(0x3C, ABX, IGN, 4), Instruction(0x3D, ABX, AND, 4), Instruction(0x3E, ABX, ROL, 7), Instruction(0x3F, ABX, RLA, 7),
|
||||
Instruction(0x30, REL, BMI, 2), Instruction(0x31, IDY, AND, 5), Instruction(0x32, IMP, STP, 2), Instruction(0x33, IDY, RLA, 8), Instruction(0x34, ZPX, NOP, 4), Instruction(0x35, ZPX, AND, 4), Instruction(0x36, ZPX, ROL, 6), Instruction(0x37, ZPX, RLA, 6), Instruction(0x38, IMP, SEC, 2), Instruction(0x39, ABY, AND, 4), Instruction(0x3A, IMP, NOP, 2), Instruction(0x3B, ABY, RLA, 7), Instruction(0x3C, ABX, NOP, 4), Instruction(0x3D, ABX, AND, 4), Instruction(0x3E, ABX, ROL, 7), Instruction(0x3F, ABX, RLA, 7),
|
||||
Instruction(0x40, IMP, RTI, 6), Instruction(0x41, IDX, EOR, 6), Instruction(0x42, IMP, STP, 2), Instruction(0x43, IDX, SRE, 8), Instruction(0x44, ZP0, NOP, 3), Instruction(0x45, ZP0, EOR, 3), Instruction(0x46, ZP0, LSR, 5), Instruction(0x47, ZP0, SRE, 5), Instruction(0x48, IMP, PHA, 3), Instruction(0x49, IMM, EOR, 2), Instruction(0x4A, ACC, LSR, 2), Instruction(0x4B, IMM, ALR, 2), Instruction(0x4C, ABS, JMP, 3), Instruction(0x4D, ABS, EOR, 4), Instruction(0x4E, ABS, LSR, 6), Instruction(0x4F, ABS, SRE, 6),
|
||||
Instruction(0x50, REL, BVC, 2), Instruction(0x51, IDY, EOR, 5), Instruction(0x52, IMP, STP, 2), Instruction(0x53, IDY, SRE, 8), Instruction(0x54, ZPX, NOP, 4), Instruction(0x55, ZPX, EOR, 4), Instruction(0x56, ZPX, LSR, 6), Instruction(0x57, ZPX, SRE, 6), Instruction(0x58, IMP, CLI, 2), Instruction(0x59, ABY, EOR, 4), Instruction(0x5A, IMP, NOP, 2), Instruction(0x5B, ABY, SRE, 7), Instruction(0x5C, ABX, IGN, 4), Instruction(0x5D, ABX, EOR, 4), Instruction(0x5E, ABX, LSR, 7), Instruction(0x5F, ABX, SRE, 7),
|
||||
Instruction(0x50, REL, BVC, 2), Instruction(0x51, IDY, EOR, 5), Instruction(0x52, IMP, STP, 2), Instruction(0x53, IDY, SRE, 8), Instruction(0x54, ZPX, NOP, 4), Instruction(0x55, ZPX, EOR, 4), Instruction(0x56, ZPX, LSR, 6), Instruction(0x57, ZPX, SRE, 6), Instruction(0x58, IMP, CLI, 2), Instruction(0x59, ABY, EOR, 4), Instruction(0x5A, IMP, NOP, 2), Instruction(0x5B, ABY, SRE, 7), Instruction(0x5C, ABX, NOP, 4), Instruction(0x5D, ABX, EOR, 4), Instruction(0x5E, ABX, LSR, 7), Instruction(0x5F, ABX, SRE, 7),
|
||||
Instruction(0x60, IMP, RTS, 6), Instruction(0x61, IDX, ADC, 6), Instruction(0x62, IMP, STP, 2), Instruction(0x63, IDX, RRA, 8), Instruction(0x64, ZP0, NOP, 3), Instruction(0x65, ZP0, ADC, 3), Instruction(0x66, ZP0, ROR, 5), Instruction(0x67, ZP0, RRA, 5), Instruction(0x68, IMP, PLA, 4), Instruction(0x69, IMM, ADC, 2), Instruction(0x6A, ACC, ROR, 2), Instruction(0x6B, IMM, ARR, 2), Instruction(0x6C, IND, JMP, 5), Instruction(0x6D, ABS, ADC, 4), Instruction(0x6E, ABS, ROR, 6), Instruction(0x6F, ABS, RRA, 6),
|
||||
Instruction(0x70, REL, BVS, 2), Instruction(0x71, IDY, ADC, 5), Instruction(0x72, IMP, STP, 2), Instruction(0x73, IDY, RRA, 8), Instruction(0x74, ZPX, NOP, 4), Instruction(0x75, ZPX, ADC, 4), Instruction(0x76, ZPX, ROR, 6), Instruction(0x77, ZPX, RRA, 6), Instruction(0x78, IMP, SEI, 2), Instruction(0x79, ABY, ADC, 4), Instruction(0x7A, IMP, NOP, 2), Instruction(0x7B, ABY, RRA, 7), Instruction(0x7C, ABX, IGN, 4), Instruction(0x7D, ABX, ADC, 4), Instruction(0x7E, ABX, ROR, 7), Instruction(0x7F, ABX, RRA, 7),
|
||||
Instruction(0x80, IMM, SKB, 2), Instruction(0x81, IDX, STA, 6), Instruction(0x82, IMM, SKB, 2), Instruction(0x83, IDX, SAX, 6), Instruction(0x84, ZP0, STY, 3), Instruction(0x85, ZP0, STA, 3), Instruction(0x86, ZP0, STX, 3), Instruction(0x87, ZP0, SAX, 3), Instruction(0x88, IMP, DEY, 2), Instruction(0x89, IMM, SKB, 2), Instruction(0x8A, IMP, TXA, 2), Instruction(0x8B, IMM, ANE, 2), Instruction(0x8C, ABS, STY, 4), Instruction(0x8D, ABS, STA, 4), Instruction(0x8E, ABS, STX, 4), Instruction(0x8F, ABS, SAX, 4),
|
||||
Instruction(0x70, REL, BVS, 2), Instruction(0x71, IDY, ADC, 5), Instruction(0x72, IMP, STP, 2), Instruction(0x73, IDY, RRA, 8), Instruction(0x74, ZPX, NOP, 4), Instruction(0x75, ZPX, ADC, 4), Instruction(0x76, ZPX, ROR, 6), Instruction(0x77, ZPX, RRA, 6), Instruction(0x78, IMP, SEI, 2), Instruction(0x79, ABY, ADC, 4), Instruction(0x7A, IMP, NOP, 2), Instruction(0x7B, ABY, RRA, 7), Instruction(0x7C, ABX, NOP, 4), Instruction(0x7D, ABX, ADC, 4), Instruction(0x7E, ABX, ROR, 7), Instruction(0x7F, ABX, RRA, 7),
|
||||
Instruction(0x80, IMM, NOP, 2), Instruction(0x81, IDX, STA, 6), Instruction(0x82, IMM, NOP, 2), Instruction(0x83, IDX, SAX, 6), Instruction(0x84, ZP0, STY, 3), Instruction(0x85, ZP0, STA, 3), Instruction(0x86, ZP0, STX, 3), Instruction(0x87, ZP0, SAX, 3), Instruction(0x88, IMP, DEY, 2), Instruction(0x89, IMM, NOP, 2), Instruction(0x8A, IMP, TXA, 2), Instruction(0x8B, IMM, ANE, 2), Instruction(0x8C, ABS, STY, 4), Instruction(0x8D, ABS, STA, 4), Instruction(0x8E, ABS, STX, 4), Instruction(0x8F, ABS, SAX, 4),
|
||||
Instruction(0x90, REL, BCC, 2), Instruction(0x91, IDY, STA, 6), Instruction(0x92, IMP, STP, 2), Instruction(0x93, IDY, AHX, 6), Instruction(0x94, ZPX, STY, 4), Instruction(0x95, ZPX, STA, 4), Instruction(0x96, ZPY, STX, 4), Instruction(0x97, ZPY, SAX, 4), Instruction(0x98, IMP, TYA, 2), Instruction(0x99, ABY, STA, 5), Instruction(0x9A, IMP, TXS, 2), Instruction(0x9B, ABY, TAS, 5), Instruction(0x9C, ABX, SHY, 5), Instruction(0x9D, ABX, STA, 5), Instruction(0x9E, ABY, SHX, 5), Instruction(0x9F, ABY, AHX, 5),
|
||||
Instruction(0xA0, IMM, LDY, 2), Instruction(0xA1, IDX, LDA, 6), Instruction(0xA2, IMM, LDX, 2), Instruction(0xA3, IDX, LAX, 6), Instruction(0xA4, ZP0, LDY, 3), Instruction(0xA5, ZP0, LDA, 3), Instruction(0xA6, ZP0, LDX, 3), Instruction(0xA7, ZP0, LAX, 3), Instruction(0xA8, IMP, TAY, 2), Instruction(0xA9, IMM, LDA, 2), Instruction(0xAA, IMP, TAX, 2), Instruction(0xAB, IMM, LAX, 2), Instruction(0xAC, ABS, LDY, 4), Instruction(0xAD, ABS, LDA, 4), Instruction(0xAE, ABS, LDX, 4), Instruction(0xAF, ABS, LAX, 4),
|
||||
Instruction(0xB0, REL, BCS, 2), Instruction(0xB1, IDY, LDA, 5), Instruction(0xB2, IMP, STP, 2), Instruction(0xB3, IDY, LAX, 5), Instruction(0xB4, ZPX, LDY, 4), Instruction(0xB5, ZPX, LDA, 4), Instruction(0xB6, ZPY, LDX, 4), Instruction(0xB7, ZPY, LAX, 4), Instruction(0xB8, IMP, CLV, 2), Instruction(0xB9, ABY, LDA, 4), Instruction(0xBA, IMP, TSX, 2), Instruction(0xBB, ABY, LAS, 4), Instruction(0xBC, ABX, LDY, 4), Instruction(0xBD, ABX, LDA, 4), Instruction(0xBE, ABY, LDX, 4), Instruction(0xBF, ABY, LAX, 4),
|
||||
Instruction(0xC0, IMM, CPY, 2), Instruction(0xC1, IDX, CMP, 6), Instruction(0xC2, IMM, SKB, 2), Instruction(0xC3, IDX, DCP, 8), Instruction(0xC4, ZP0, CPY, 3), Instruction(0xC5, ZP0, CMP, 3), Instruction(0xC6, ZP0, DEC, 5), Instruction(0xC7, ZP0, DCP, 5), Instruction(0xC8, IMP, INY, 2), Instruction(0xC9, IMM, CMP, 2), Instruction(0xCA, IMP, DEX, 2), Instruction(0xCB, IMM, SBX, 2), Instruction(0xCC, ABS, CPY, 4), Instruction(0xCD, ABS, CMP, 4), Instruction(0xCE, ABS, DEC, 6), Instruction(0xCF, ABS, DCP, 6),
|
||||
Instruction(0xD0, REL, BNE, 2), Instruction(0xD1, IDY, CMP, 5), Instruction(0xD2, IMP, STP, 2), Instruction(0xD3, IDY, DCP, 8), Instruction(0xD4, ZPX, NOP, 4), Instruction(0xD5, ZPX, CMP, 4), Instruction(0xD6, ZPX, DEC, 6), Instruction(0xD7, ZPX, DCP, 6), Instruction(0xD8, IMP, CLD, 2), Instruction(0xD9, ABY, CMP, 4), Instruction(0xDA, IMP, NOP, 2), Instruction(0xDB, ABY, DCP, 7), Instruction(0xDC, ABX, IGN, 4), Instruction(0xDD, ABX, CMP, 4), Instruction(0xDE, ABX, DEC, 7), Instruction(0xDF, ABX, DCP, 7),
|
||||
Instruction(0xE0, IMM, CPX, 2), Instruction(0xE1, IDX, SBC, 6), Instruction(0xE2, IMM, SKB, 2), Instruction(0xE3, IDX, ISB, 8), Instruction(0xE4, ZP0, CPX, 3), Instruction(0xE5, ZP0, SBC, 3), Instruction(0xE6, ZP0, INC, 5), Instruction(0xE7, ZP0, ISB, 5), Instruction(0xE8, IMP, INX, 2), Instruction(0xE9, IMM, SBC, 2), Instruction(0xEA, IMP, NOP, 2), Instruction(0xEB, IMM, SBC, 2), Instruction(0xEC, ABS, CPX, 4), Instruction(0xED, ABS, SBC, 4), Instruction(0xEE, ABS, INC, 6), Instruction(0xEF, ABS, ISB, 6),
|
||||
Instruction(0xF0, REL, BEQ, 2), Instruction(0xF1, IDY, SBC, 5), Instruction(0xF2, IMP, STP, 2), Instruction(0xF3, IDY, ISB, 8), Instruction(0xF4, ZPX, NOP, 4), Instruction(0xF5, ZPX, SBC, 4), Instruction(0xF6, ZPX, INC, 6), Instruction(0xF7, ZPX, ISB, 6), Instruction(0xF8, IMP, SED, 2), Instruction(0xF9, ABY, SBC, 4), Instruction(0xFA, IMP, NOP, 2), Instruction(0xFB, ABY, ISB, 7), Instruction(0xFC, ABX, IGN, 4), Instruction(0xFD, ABX, SBC, 4), Instruction(0xFE, ABX, INC, 7), Instruction(0xFF, ABX, ISB, 7),
|
||||
Instruction(0xC0, IMM, CPY, 2), Instruction(0xC1, IDX, CMP, 6), Instruction(0xC2, IMM, NOP, 2), Instruction(0xC3, IDX, DCP, 8), Instruction(0xC4, ZP0, CPY, 3), Instruction(0xC5, ZP0, CMP, 3), Instruction(0xC6, ZP0, DEC, 5), Instruction(0xC7, ZP0, DCP, 5), Instruction(0xC8, IMP, INY, 2), Instruction(0xC9, IMM, CMP, 2), Instruction(0xCA, IMP, DEX, 2), Instruction(0xCB, IMM, SBX, 2), Instruction(0xCC, ABS, CPY, 4), Instruction(0xCD, ABS, CMP, 4), Instruction(0xCE, ABS, DEC, 6), Instruction(0xCF, ABS, DCP, 6),
|
||||
Instruction(0xD0, REL, BNE, 2), Instruction(0xD1, IDY, CMP, 5), Instruction(0xD2, IMP, STP, 2), Instruction(0xD3, IDY, DCP, 8), Instruction(0xD4, ZPX, NOP, 4), Instruction(0xD5, ZPX, CMP, 4), Instruction(0xD6, ZPX, DEC, 6), Instruction(0xD7, ZPX, DCP, 6), Instruction(0xD8, IMP, CLD, 2), Instruction(0xD9, ABY, CMP, 4), Instruction(0xDA, IMP, NOP, 2), Instruction(0xDB, ABY, DCP, 7), Instruction(0xDC, ABX, NOP, 4), Instruction(0xDD, ABX, CMP, 4), Instruction(0xDE, ABX, DEC, 7), Instruction(0xDF, ABX, DCP, 7),
|
||||
Instruction(0xE0, IMM, CPX, 2), Instruction(0xE1, IDX, SBC, 6), Instruction(0xE2, IMM, NOP, 2), Instruction(0xE3, IDX, ISB, 8), Instruction(0xE4, ZP0, CPX, 3), Instruction(0xE5, ZP0, SBC, 3), Instruction(0xE6, ZP0, INC, 5), Instruction(0xE7, ZP0, ISB, 5), Instruction(0xE8, IMP, INX, 2), Instruction(0xE9, IMM, SBC, 2), Instruction(0xEA, IMP, NOP, 2), Instruction(0xEB, IMM, SBC, 2), Instruction(0xEC, ABS, CPX, 4), Instruction(0xED, ABS, SBC, 4), Instruction(0xEE, ABS, INC, 6), Instruction(0xEF, ABS, ISB, 6),
|
||||
Instruction(0xF0, REL, BEQ, 2), Instruction(0xF1, IDY, SBC, 5), Instruction(0xF2, IMP, STP, 2), Instruction(0xF3, IDY, ISB, 8), Instruction(0xF4, ZPX, NOP, 4), Instruction(0xF5, ZPX, SBC, 4), Instruction(0xF6, ZPX, INC, 6), Instruction(0xF7, ZPX, ISB, 6), Instruction(0xF8, IMP, SED, 2), Instruction(0xF9, ABY, SBC, 4), Instruction(0xFA, IMP, NOP, 2), Instruction(0xFB, ABY, ISB, 7), Instruction(0xFC, ABX, NOP, 4), Instruction(0xFD, ABX, SBC, 4), Instruction(0xFE, ABX, INC, 7), Instruction(0xFF, ABX, ISB, 7),
|
||||
];
|
||||
|
||||
pub fn read_next_instruction(&mut self) -> Instruction {
|
||||
|
@ -10,6 +10,10 @@ fn is_sign_overflow(val1: u8, val2: u8, result: u8) -> bool {
|
||||
impl Cpu {
|
||||
pub fn exec_instruction(&mut self, instr: Instruction) {
|
||||
let operand = self.operand_decode(instr.addr_mode());
|
||||
if operand.is_page_crossing {
|
||||
self.busy_cycle_count += 1;
|
||||
}
|
||||
|
||||
match instr.op() {
|
||||
OperationType::ADC => self.op_adc(operand),
|
||||
OperationType::AND => self.op_and(operand),
|
||||
@ -67,8 +71,6 @@ impl Cpu {
|
||||
OperationType::TXA => self.op_txa(operand),
|
||||
OperationType::TXS => self.op_txs(operand),
|
||||
OperationType::TYA => self.op_tya(operand),
|
||||
OperationType::SKB => {}
|
||||
OperationType::IGN => {}
|
||||
OperationType::ISB => self.op_isc(operand),
|
||||
OperationType::DCP => self.op_dcp(operand),
|
||||
OperationType::SBX => self.op_sbx(operand),
|
||||
@ -141,7 +143,7 @@ impl Cpu {
|
||||
}
|
||||
}
|
||||
|
||||
self.busy_cycle_count = cycle_count;
|
||||
self.busy_cycle_count += cycle_count;
|
||||
}
|
||||
|
||||
fn set_common_flags(&mut self, result: u8) {
|
||||
|
@ -1,13 +1,7 @@
|
||||
mod cpu;
|
||||
mod memory;
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn it_works() {
|
||||
let result = add(2, 2);
|
||||
assert_eq!(result, 4);
|
||||
}
|
||||
pub trait Clock {
|
||||
/// Run a clock cycle
|
||||
fn cycle(&mut self);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user