Skip to content

Commit

Permalink
Add (failing) Klaus test
Browse files Browse the repository at this point in the history
  • Loading branch information
breqdev committed Nov 22, 2023
1 parent f1595eb commit 196336b
Show file tree
Hide file tree
Showing 2 changed files with 41 additions and 14 deletions.
2 changes: 1 addition & 1 deletion src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ fn main() {
let system = match args.system {
SystemArg::Basic => BasicSystemBuilder::build(romfile.unwrap(), (), platform.provider()),
SystemArg::Easy => Easy6502SystemBuilder::build(romfile.unwrap(), (), platform.provider()),
SystemArg::Klaus => KlausSystemBuilder::build(romfile.unwrap(), (), platform.provider()),
SystemArg::Klaus => KlausSystemBuilder::build(romfile.unwrap(), None, platform.provider()),
SystemArg::Pet => PetSystemBuilder::build(
PetSystemRoms::from_disk(),
PetSystemConfig { mapping },
Expand Down
53 changes: 40 additions & 13 deletions src/systems/klaus.rs
Original file line number Diff line number Diff line change
@@ -1,44 +1,47 @@
use instant::{Duration, Instant};
use instant::Duration;

use crate::cpu::Mos6502;
use crate::memory::BlockMemory;
use crate::platform::{PlatformProvider, WindowConfig};
use crate::roms::RomFile;
use crate::systems::System;
use std::cell::Cell;
use std::rc::Rc;
use std::sync::Arc;

use super::SystemBuilder;

/// A factory for creating a system that runs Klaus Dormann's 6502 CPU test suite.
pub struct KlausSystemBuilder;

impl SystemBuilder<KlausSystem, RomFile, ()> for KlausSystemBuilder {
fn build(rom: RomFile, _config: (), _platform: Arc<dyn PlatformProvider>) -> Box<dyn System> {
impl SystemBuilder<KlausSystem, RomFile, Option<Rc<Cell<u16>>>> for KlausSystemBuilder {
fn build(
rom: RomFile,
config: Option<Rc<Cell<u16>>>,
_platform: Arc<dyn PlatformProvider>,
) -> Box<dyn System> {
let rom = BlockMemory::from_file(0x10000, rom);
let mut cpu = Mos6502::new(Box::new(rom));

cpu.registers.pc.load(0x0400);

Box::new(KlausSystem {
cpu,
last_report: Instant::now(),
})
Box::new(KlausSystem { cpu, pc: config })
}
}

/// A system used to run Klaus Dormann's 6502 CPU test suite.
pub struct KlausSystem {
cpu: Mos6502,
last_report: Instant,
pc: Option<Rc<Cell<u16>>>,
}

impl System for KlausSystem {
fn tick(&mut self) -> Duration {
if self.last_report.elapsed().as_secs() > 1 {
println!("PC: {:04x}", self.cpu.registers.pc.address());
self.last_report = Instant::now();
};
Duration::from_secs_f64(1.0 / 1_000_000.0) * self.cpu.tick().into()
self.cpu.tick();
if let Some(pc) = &self.pc {
pc.set(self.cpu.registers.pc.address());
}
Duration::ZERO
}

fn reset(&mut self) {
Expand All @@ -47,3 +50,27 @@ impl System for KlausSystem {

fn render(&mut self, _framebuffer: &mut [u8], _window: WindowConfig) {}
}

#[cfg(test)]
mod tests {
use crate::{
platform::{Platform, TextPlatform},
roms::DiskLoadable,
};

use super::*;

#[test]
fn test_klaus() {
let roms = RomFile::from_file("bin/klaus.bin");
let platform = TextPlatform::new();
let pc = Rc::new(Cell::new(0));
let mut system = KlausSystemBuilder::build(roms, Some(pc.clone()), platform.provider());

for _ in 0..=100000000 {
system.tick();
}

assert_eq!(pc.get(), 0x3469);
}
}

0 comments on commit 196336b

Please sign in to comment.