commit 36d910f5b7e3ad8280fae94d5513244225595789
parent 70bd0819463984cfaacab1087f70f491907611f1
Author: Ryan Jeffrey <ryan@ryanmj.xyz>
Date: Wed, 9 Nov 2022 22:21:50 -0800
Complete data path
Diffstat:
6 files changed, 239 insertions(+), 26 deletions(-)
diff --git a/src/cpu.rs b/src/cpu.rs
@@ -403,7 +403,7 @@ impl ProcessorStatusWord {
impl fmt::Display for ProcessorStatusWord {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
- write!(f, "0x{:x}", self.0)
+ write!(f, "{:03x}", self.0)
}
}
diff --git a/src/data_path.rs b/src/data_path.rs
@@ -18,14 +18,10 @@ use config::Config;
use cpu::{OutputPins, ProcessorStatusWord, RegisterFile, SIZEOF_INSTRUCTION};
use instruction::*;
use memory::Memory;
-use shifter;
+use shifter::Shifter;
use std::fmt;
use util::Result;
-use crate::shifter::Shifter;
-
-pub type MicroOp = fn(dp: &mut DataPath);
-
pub struct SCCBits {
pub z: bool,
pub n: bool,
@@ -381,9 +377,36 @@ impl DataPath {
// Callr
long = true;
immediate = true;
+
+ result = InstructionCycle {
+ 0: [
+ noop,
+ noop,
+ |dp: &mut DataPath| -> () {
+ dp.callr_step3();
+ },
+ noop,
+ |dp: &mut DataPath| -> () {
+ dp.commit_callr();
+ },
+ ],
+ };
}
12 => {
// Jmpx
+ result = InstructionCycle {
+ 0: [
+ noop,
+ noop,
+ |dp: &mut DataPath| -> () {
+ dp.jmpx_step3();
+ },
+ noop,
+ |dp: &mut DataPath| -> () {
+ dp.commit_jmpx();
+ },
+ ],
+ };
}
13 => {
// Jmpr
@@ -421,6 +444,26 @@ impl DataPath {
result
}
+ fn callr_step3(&mut self) {
+ // Calculate value and send it to dest.
+ let eff_addr = self.alu.add();
+
+ self.dst_latch = eff_addr;
+ }
+
+ fn jmpx_step3(&mut self) {
+ //
+ }
+
+ fn commit_jmpx(&mut self) {
+ //
+ self.nxtpc = self.dst_latch;
+ }
+
+ fn commit_callr(&mut self) {
+ //
+ }
+
pub fn current_instruction_is_memory(&self) -> bool {
self.control2.memory
}
@@ -437,6 +480,58 @@ impl DataPath {
self.psw.set_cc_neg(self.dst_latch & SIGN_BIT_LOC != 0);
}
}
+
+ pub fn decode_source_registers(&self) -> (u8, u8) {
+ (self.rs1_1, self.rs2_1)
+ }
+
+ pub fn execute_source_registers(&self) -> (u8, u8) {
+ (self.rs1_2, self.rs2_2)
+ }
+
+ pub fn decode_destination_register(&self) -> u8 {
+ self.rd1
+ }
+
+ pub fn execute_destination_register(&self) -> u8 {
+ self.rd2
+ }
+
+ pub fn commit_destination_register(&self) -> u8 {
+ self.rd3
+ }
+
+ pub fn decode_rd(&self) -> u8 {
+ self.rd1
+ }
+
+ pub fn execute_rd(&self) -> u8 {
+ self.rd2
+ }
+
+ pub fn bar(&self) -> u8 {
+ self.bar
+ }
+
+ pub fn imm(&self) -> u32 {
+ self.imm
+ }
+
+ pub fn execute_op(&self) -> u8 {
+ self.op1
+ }
+
+ pub fn register_file(&self) -> &RegisterFile {
+ &self.regs
+ }
+
+ pub fn psw(&self) -> ProcessorStatusWord {
+ self.psw.clone()
+ }
+
+ pub fn shifter(&self) -> Shifter {
+ self.shifter
+ }
}
impl Control {
diff --git a/src/debug_window.rs b/src/debug_window.rs
@@ -132,7 +132,7 @@ impl<'a> Drawable for DebugWindow<'a> {
Phase::Four => "φ₄",
Phase::Interrupt => "φᵢ",
},
- Rect::new(1400, 0, 50, 50),
+ Rect::new(1550, 0, 50, 50),
OBJ_DEFAULT_COLOR,
)?;
@@ -186,7 +186,7 @@ impl<'a> Drawable for DebugWindow<'a> {
self.draw_lines(
&[
(400, 525, 1275, 525),
- (815, 525, 815, 425),
+ (815, 525, 815, 450),
(850, 525, 850, 575),
(850, 575, 875, 575),
],
@@ -198,18 +198,20 @@ impl<'a> Drawable for DebugWindow<'a> {
&[
(400, 640, 850, 640),
(850, 640, 850, 750),
+ (805, 640, 805, 450),
(850, 750, 875, 750),
],
OBJ_DEFAULT_COLOR,
)?;
-
self.draw_static_str("busR", Rect::new(410, 645, 50, 25), OBJ_DEFAULT_COLOR)?;
// busL
self.draw_lines(
&[
(400, 760, 600, 760),
- (600, 760, 810, 500),
- (810, 500, 810, 425),
+ (600, 760, 790, 550),
+ (790, 550, 790, 350),
+ (790, 350, 825, 350),
+ (825, 350, 825, 325),
],
OBJ_DEFAULT_COLOR,
)?;
@@ -235,9 +237,22 @@ impl<'a> Drawable for DebugWindow<'a> {
self.draw_static_str("RD", Rect::new(125, 125, 50, 50), OBJ_DEFAULT_COLOR)?;
// busext to RD
self.pane.canvas.line(150, 50, 150, 75, OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("R{:02}", dp.decode_rd()),
+ Rect::new(125, 75, 50, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
+
+ // Source register latches
+ let (rs1, rs2) = dp.decode_source_registers();
// RS1
self.draw_rect(Rect::new(50, 200, 100, 50), OBJ_DEFAULT_COLOR)?;
self.draw_static_str("RS1", Rect::new(75, 250, 50, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("R{:02}", rs1),
+ Rect::new(75, 200, 50, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
// busext to RS1
self.draw_line((75, 50, 75, 200), OBJ_DEFAULT_COLOR)?;
// RD to RS1
@@ -247,6 +262,11 @@ impl<'a> Drawable for DebugWindow<'a> {
// RS2
self.draw_rect(Rect::new(175, 200, 100, 50), OBJ_DEFAULT_COLOR)?;
self.draw_static_str("RS2", Rect::new(200, 250, 50, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("R{:02}", rs2),
+ Rect::new(200, 200, 50, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
// busext to RS2
self.draw_line((250, 50, 250, 200), OBJ_DEFAULT_COLOR)?;
// RD to RS2
@@ -257,8 +277,16 @@ impl<'a> Drawable for DebugWindow<'a> {
// PSW register
self.draw_rect(Rect::new(300, 200, 125, 75), OBJ_DEFAULT_COLOR)?;
self.draw_static_str("PSW", Rect::new(325, 275, 75, 50), OBJ_DEFAULT_COLOR)?;
- // busB to PSW
- self.draw_line((310, 700, 310, 275), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("{}", dp.psw()),
+ Rect::new(325, 225, 75, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
+ // busB to PSW and SHam
+ self.draw_lines(
+ &[(310, 700, 310, 275), (310, 325, 500, 325)],
+ OBJ_DEFAULT_COLOR,
+ )?;
// PSW to register file
self.draw_line((300, 250, 290, 250), OBJ_DEFAULT_COLOR)?;
self.draw_line((290, 250, 290, 475), OBJ_DEFAULT_COLOR)?;
@@ -266,23 +294,46 @@ impl<'a> Drawable for DebugWindow<'a> {
// imm
self.draw_rect(Rect::new(800, 100, 100, 50), OBJ_DEFAULT_COLOR)?;
self.draw_static_str("IMM", Rect::new(910, 100, 75, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("{:05x}", dp.imm()),
+ Rect::new(810, 100, 75, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
// busEXT to imm
self.draw_line((825, 50, 825, 100), OBJ_DEFAULT_COLOR)?;
// dimm
self.draw_rect(Rect::new(800, 250, 250, 75), OBJ_DEFAULT_COLOR)?;
self.draw_static_str("DIn/DIMM", Rect::new(900, 325, 150, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("{:08x}", dp.imm()),
+ Rect::new(800, 255, 250, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
// busEXT to dimm
self.draw_line((1000, 50, 1000, 250), OBJ_DEFAULT_COLOR)?;
- // imm to dimm
- self.draw_line((825, 150, 825, 250), OBJ_DEFAULT_COLOR)?;
+ // imm to dimm and SHAM
+ self.draw_lines(
+ &[
+ (825, 150, 825, 250),
+ (825, 175, 475, 175),
+ (475, 175, 475, 315),
+ (475, 315, 500, 315),
+ ],
+ OBJ_DEFAULT_COLOR,
+ )?;
// op
self.draw_rect(Rect::new(1100, 125, 50, 50), OBJ_DEFAULT_COLOR)?;
self.draw_static_str("OP", Rect::new(1100, 175, 50, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("{:02x}", dp.execute_op()),
+ Rect::new(1100, 125, 50, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
// busext to op
self.draw_line((1125, 50, 1125, 125), OBJ_DEFAULT_COLOR)?;
// Shifter
self.draw_rect(Rect::new(600, 500, 175, 300), OBJ_DEFAULT_COLOR)?;
- self.draw_static_str("Shifter", Rect::new(600, 450, 100, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_static_str("Shifter", Rect::new(600, 800, 100, 50), OBJ_DEFAULT_COLOR)?;
self.draw_circle((690, 650, 50), OBJ_DEFAULT_COLOR)?;
// ALU
@@ -294,16 +345,65 @@ impl<'a> Drawable for DebugWindow<'a> {
self.draw_static_str("ALU", Rect::new(900, 450, 75, 50), OBJ_DEFAULT_COLOR)?;
// AI (ALU input latch)
self.draw_rect(Rect::new(875, 500, 25, 120), OBJ_DEFAULT_COLOR)?;
- self.draw_static_str("BAR", Rect::new(825, 450, 50, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_static_str("AI", Rect::new(825, 450, 50, 50), OBJ_DEFAULT_COLOR)?;
// BI (ALU input latch)
self.draw_rect(Rect::new(875, 680, 25, 120), OBJ_DEFAULT_COLOR)?;
self.draw_static_str("BI", Rect::new(825, 800, 50, 50), OBJ_DEFAULT_COLOR)?;
// BAR
- self.draw_rect(Rect::new(800, 400, 25, 25), OBJ_DEFAULT_COLOR)?;
- self.draw_static_str("BAR", Rect::new(830, 400, 75, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_rect(Rect::new(800, 400, 50, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_static_str("BAR", Rect::new(855, 400, 75, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("{:02x}", dp.bar()),
+ Rect::new(800, 400, 50, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
+ // Bar to SHam
+ self.draw_lines(
+ &[
+ (810, 400, 810, 380),
+ (810, 380, 475, 380),
+ (475, 380, 475, 340),
+ (475, 340, 500, 340),
+ ],
+ OBJ_DEFAULT_COLOR,
+ )?;
+ // Busout
+ self.draw_lines(
+ &[
+ (1050, 750, 1450, 750),
+ (1450, 750, 1450, 50),
+ (1050, 525, 1050, 750),
+ ],
+ OBJ_DEFAULT_COLOR,
+ )?;
+ self.draw_static_str("busOUT", Rect::new(1400, 750, 100, 50), OBJ_DEFAULT_COLOR)?;
+ // PADS (pins in/out)
+ self.draw_rect(Rect::new(1300, 25, 100, 100), OBJ_DEFAULT_COLOR)?;
+ self.draw_static_str("PADS", Rect::new(1300, 125, 100, 50), OBJ_DEFAULT_COLOR)?;
+
+ // SDEC and SHAM
+ self.draw_rects(
+ &[Rect::new(550, 300, 150, 50), Rect::new(500, 300, 50, 50)],
+ OBJ_DEFAULT_COLOR,
+ )?;
+ self.draw_static_str("SHam", Rect::new(500, 250, 75, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_static_str("SDec", Rect::new(650, 250, 75, 50), OBJ_DEFAULT_COLOR)?;
+ self.draw_string(
+ &format!("{:02x}", dp.shifter().s_ham),
+ Rect::new(500, 300, 50, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
+ self.draw_string(
+ &format!("{:02x}", dp.shifter().s_dec),
+ Rect::new(600, 300, 50, 50),
+ OBJ_DEFAULT_COLOR,
+ )?;
+ // Connect SDec to Shifter
+ self.draw_line((600, 350, 700, 600), OBJ_DEFAULT_COLOR)?;
// Draw the debug window.
self.pane.canvas.present();
+
Ok(())
}
diff --git a/src/instruction.rs b/src/instruction.rs
@@ -36,7 +36,7 @@ pub const SIGN_BIT_LOC: u32 = 0x80000000;
// Enums and structs.
-pub struct InstructionCycle([fn(dp: &mut DataPath); 4]);
+pub struct InstructionCycle(pub [fn(dp: &mut DataPath); 5]);
pub fn noop(dp: &mut DataPath) {}
@@ -588,12 +588,12 @@ impl fmt::Display for Conditional {
}
impl InstructionCycle {
- pub fn new(steps: [fn(dp: &mut DataPath); 4]) -> Self {
+ pub fn new(steps: [fn(dp: &mut DataPath); 5]) -> Self {
Self { 0: steps }
}
pub fn noop_cycle() -> Self {
- Self { 0: [noop; 4] }
+ Self { 0: [noop; 5] }
}
}
diff --git a/src/shifter.rs b/src/shifter.rs
@@ -23,6 +23,8 @@ pub struct Shifter {
pub src: u32,
/// Amount to shift the input.
pub s_ham: u8,
+ /// Shift decoder value. Contains the amount to shift by.
+ pub s_dec: u8,
}
// Impls.
@@ -30,7 +32,11 @@ pub struct Shifter {
impl Shifter {
/// Create a 0'd out shifter.
pub fn new() -> Self {
- Self { src: 0, s_ham: 0 }
+ Self {
+ src: 0,
+ s_ham: 0,
+ s_dec: 0,
+ }
}
/// Left shift `src` by `s_ham` bits.
pub fn shift_left(&self) -> u32 {
@@ -45,7 +51,7 @@ impl Shifter {
impl fmt::Display for Shifter {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
- write!(f, "{}, {}", self.src, self.s_ham,)
+ write!(f, "{}, {}, {}", self.src, self.s_ham, self.s_dec)
}
}
@@ -53,8 +59,8 @@ impl fmt::Debug for Shifter {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(
f,
- "Input register: {}, SHam latch: {}",
- self.src, self.s_ham,
+ "Input register: {}, SHam latch: {}, SDEC amount: {}",
+ self.src, self.s_ham, self.s_dec
)
}
}
diff --git a/src/system.rs b/src/system.rs
@@ -135,4 +135,16 @@ impl System {
Phase::Interrupt => Phase::One,
};
}
+
+ pub fn clock(&self) -> &Clock {
+ &self.clock
+ }
+
+ pub fn data_path(&self) -> &DataPath {
+ &self.data_path
+ }
+
+ pub fn phase(&self) -> Phase {
+ self.phase.clone()
+ }
}