Couple bugfixes, integration tests ported

This commit is contained in:
2022-04-17 23:35:48 -05:00
parent df111ce55b
commit 05c1be2e94
16 changed files with 436 additions and 48 deletions
+33 -22
View File
@@ -32,6 +32,12 @@ impl PeekPoke for CPU {
}
}
impl Default for CPU {
fn default() -> Self {
Self::new(Memory::default())
}
}
impl CPU {
pub fn new(memory: Memory) -> Self {
Self {
@@ -270,6 +276,33 @@ impl CPU {
pub fn running(&self) -> bool {
!self.halted
}
pub fn run_to_halt(&mut self) {
self.start();
while !self.halted && self.pc < 1100 {
self.tick()
}
}
pub fn get_stack(&self) -> Vec<Word> {
let mut v = Vec::new();
let mut curr = Word::from(256);
while curr < self.dp {
v.push(self.memory.peek24(curr));
curr += 3
}
v
}
pub fn get_call(&self) -> Vec<Word> {
let mut v = Vec::new();
let mut curr = Word::from(1024);
while curr > self.sp {
curr -= 3;
v.push(self.memory.peek24(curr));
}
v
}
}
impl Opcode {
@@ -305,28 +338,6 @@ mod tests {
use super::*;
use Opcode::*;
impl CPU {
fn get_stack(&self) -> Vec<Word> {
let mut v = Vec::new();
let mut curr = Word::from(256);
while curr < self.dp {
v.push(self.memory.peek24(curr));
curr += 3
}
v
}
fn get_call(&self) -> Vec<Word> {
let mut v = Vec::new();
let mut curr = Word::from(1024);
while curr > self.sp {
curr -= 3;
v.push(self.memory.peek24(curr));
}
v
}
}
fn predicate_opcode_test<P, Q>(opcode: Opcode, given: P, pred: Q)
where
P: FnOnce(&mut CPU),
+5 -1
View File
@@ -1,4 +1,8 @@
pub mod cpu;
pub mod memory;
pub mod opcodes;
pub mod word;
pub mod word;
pub use cpu::CPU;
pub use memory::Memory;
pub use word::Word;
+20
View File
@@ -20,6 +20,26 @@ impl<R: Rng> From<R> for Memory {
}
}
impl Memory {
/// Create a memory containing the given contents (probably code) starting at `0x400` (the
/// starting address for code). The rest of the memory is zeroes.
/// ```
/// # use crate::vcore::memory::PeekPokeExt;
/// # use crate::vcore::Word;
/// # use crate::vcore::Memory;
/// let mem = Memory::with_program(vec![0x02, 0x12, 0x34]);
/// assert_eq!(mem.peek8(Word::from(0x400)), 0x02);
/// assert_eq!(mem.peek8(Word::from(0x401)), 0x12); // etc
/// ```
pub fn with_program<T: IntoIterator<Item = u8>>(code: T) -> Memory {
let mut m = Memory::default();
for (addr, byte) in code.into_iter().enumerate() {
m.poke8(addr + 0x400, byte)
}
m
}
}
impl std::ops::Index<Word> for Memory {
type Output = u8;
fn index(&self, index: Word) -> &Self::Output {
+7
View File
@@ -1,3 +1,5 @@
use std::fmt::{Display, Formatter};
// 128k, the amount of memory in a standard Vulcan machine
pub const MEM_SIZE: u32 = 128 * 1024;
@@ -45,6 +47,11 @@ impl From<Word> for u32 {
}
}
impl Display for Word {
fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
write!(f, "{}", i32::from(*self))
}
}
#[test]
fn to_from_u32() {
assert_eq!(u32::from(Word::from(0x123456u32)), 0x123456u32);