Krolyxon
Commit 798ac8c

Branches

Tags

Refs →

bench51798ac8c

refactor the cpu logic to cpu module

Author
krolxon
Date
2026-01-04 18:47 +0530
Parent
4809d71
Commit
798ac8ce75e2784e9e412f9ea7778b80b077c1dd

+118 −116

2 files changed

  1. M src/cpu.rs +113 −0
  2. M src/main.rs +5 −116
M src/cpu.rs View
@@ -1,3 +1,5 @@
1+use crate::memory::{self, Memory};
2+
13 #[derive(Default)]
24 #[derive(Debug)]
35 pub struct CPU{
@@ -19,4 +21,115 @@ impl CPU {
1921 pub fn inc_cp(&mut self) {
2022 self.pc += 1;
2123 }
24+
25+ pub fn halt(&mut self) {
26+ self.halted = true;
27+ }
28+
29+ pub fn mov(&mut self, mem: &mut Memory) {
30+ let reg = mem.read(self.pc); self.inc_cp();
31+ let val = mem.read(self.pc); self.inc_cp();
32+
33+ match reg {
34+ 0 => self.a = val,
35+ 1 => self.b = val,
36+ 2 => self.c = val,
37+ 3 => self.d = val,
38+ _ => {}
39+ }
40+ }
41+
42+ pub fn add(&mut self, mem:&mut Memory) {
43+
44+ let dest = mem.read(self.pc); self.pc += 1;
45+ let src = mem.read(self.pc); self.pc += 1;
46+
47+ let (result, carry) = match (dest, src) {
48+ // What the fuck do these tuples mean?
49+ // so basically they are the numbers assigned to register
50+ // 0 => A, 1 => B ....
51+ // so when it is (0, 0), it basically says add the
52+ // value of register B into register A,
53+ // thats exactly whats replicated in the code below
54+ (0, 0) => self.a.overflowing_add(self.a),
55+ (0, 1) => self.a.overflowing_add(self.b),
56+ (0, 2) => self.a.overflowing_add(self.c),
57+ (0, 3) => self.a.overflowing_add(self.d),
58+
59+ (1, 0) => self.b.overflowing_add(self.a),
60+ (1, 1) => self.b.overflowing_add(self.b),
61+ (1, 2) => self.b.overflowing_add(self.c),
62+ (1, 3) => self.b.overflowing_add(self.d),
63+
64+ (2, 0) => self.c.overflowing_add(self.a),
65+ (2, 1) => self.c.overflowing_add(self.b),
66+ (2, 2) => self.c.overflowing_add(self.c),
67+ (2, 3) => self.c.overflowing_add(self.d),
68+
69+ (3, 0) => self.d.overflowing_add(self.a),
70+ (3, 1) => self.d.overflowing_add(self.b),
71+ (3, 2) => self.d.overflowing_add(self.c),
72+ (3, 3) => self.d.overflowing_add(self.d),
73+
74+ _ => (0, false),
75+ };
76+
77+ match dest {
78+ 0 => self.a = result,
79+ 1 => self.b = result,
80+ 2 => self.c = result,
81+ 3 => self.d = result,
82+ _ => {}
83+ }
84+
85+ self.zero = result == 0;
86+ self.carry = carry;
87+ }
88+
89+ pub fn sub(&mut self, mem: &mut Memory) {
90+ let dest = mem.read(self.pc); self.pc += 1;
91+ let src = mem.read(self.pc); self.pc += 1;
92+
93+ let (result, borrow) = match (dest, src) {
94+ // What the fuck do these tuples mean?
95+ // so basically they are the numbers assigned to register
96+ // 0 => A, 1 => B ....
97+ // so when it is (0, 0), it basically says add the
98+ // value of register B into register A,
99+ // thats exactly whats replicated in the code below
100+ (0, 0) => self.a.overflowing_sub(self.a),
101+ (0, 1) => self.a.overflowing_sub(self.b),
102+ (0, 2) => self.a.overflowing_sub(self.c),
103+ (0, 3) => self.a.overflowing_sub(self.d),
104+
105+ (1, 0) => self.b.overflowing_sub(self.a),
106+ (1, 1) => self.b.overflowing_sub(self.b),
107+ (1, 2) => self.b.overflowing_sub(self.c),
108+ (1, 3) => self.b.overflowing_sub(self.d),
109+
110+ (2, 0) => self.c.overflowing_sub(self.a),
111+ (2, 1) => self.c.overflowing_sub(self.b),
112+ (2, 2) => self.c.overflowing_sub(self.c),
113+ (2, 3) => self.c.overflowing_sub(self.d),
114+
115+ (3, 0) => self.d.overflowing_sub(self.a),
116+ (3, 1) => self.d.overflowing_sub(self.b),
117+ (3, 2) => self.d.overflowing_sub(self.c),
118+ (3, 3) => self.d.overflowing_sub(self.d),
119+
120+ _ => (0, false),
121+ };
122+
123+ match dest {
124+ 0 => self.a = result,
125+ 1 => self.b = result,
126+ 2 => self.c = result,
127+ 3 => self.d = result,
128+ _ => {}
129+ }
130+
131+ self.zero = result == 0;
132+ self.carry = borrow;
133+ }
134+
22135 }
M src/main.rs View
@@ -20,7 +20,7 @@ fn main() {
2020 // b = 2
2121 mem.write(0x0003, Instruction::MOV as u8);
2222 mem.write(0x0004, 1);
23− mem.write(0x0005, 10);
23+ mem.write(0x0005, 1);
2424
2525 // a = a + b
2626 mem.write(0x0006, Instruction::SUB as u8);
@@ -40,123 +40,12 @@ fn main() {
4040 cpu.inc_cp();
4141
4242 match opcode {
43− x if x == Instruction::MOV as u8 => {
44− let reg = mem.read(cpu.pc); cpu.inc_cp();
45− let val = mem.read(cpu.pc); cpu.inc_cp();
46−
47− match reg {
48− 0 => cpu.a = val,
49− 1 => cpu.b = val,
50− 2 => cpu.c = val,
51− 3 => cpu.d = val,
52− _ => {}
53− }
54− }
55−
56− x if x == Instruction::ADD as u8 => {
57− let dest = mem.read(cpu.pc); cpu.pc += 1;
58− let src = mem.read(cpu.pc); cpu.pc += 1;
59−
60− let (result, carry) = match (dest, src) {
61− // What the fuck do these tuples mean?
62− // so basically they are the numbers assigned to register
63− // 0 => A, 1 => B ....
64− // so when it is (0, 0), it basically says add the
65− // value of register B into register A,
66− // thats exactly whats replicated in the code below
67− (0, 0) => cpu.a.overflowing_add(cpu.a),
68− (0, 1) => cpu.a.overflowing_add(cpu.b),
69− (0, 2) => cpu.a.overflowing_add(cpu.c),
70− (0, 3) => cpu.a.overflowing_add(cpu.d),
71−
72− (1, 0) => cpu.b.overflowing_add(cpu.a),
73− (1, 1) => cpu.b.overflowing_add(cpu.b),
74− (1, 2) => cpu.b.overflowing_add(cpu.c),
75− (1, 3) => cpu.b.overflowing_add(cpu.d),
76−
77− (2, 0) => cpu.c.overflowing_add(cpu.a),
78− (2, 1) => cpu.c.overflowing_add(cpu.b),
79− (2, 2) => cpu.c.overflowing_add(cpu.c),
80− (2, 3) => cpu.c.overflowing_add(cpu.d),
81−
82− (3, 0) => cpu.d.overflowing_add(cpu.a),
83− (3, 1) => cpu.d.overflowing_add(cpu.b),
84− (3, 2) => cpu.d.overflowing_add(cpu.c),
85− (3, 3) => cpu.d.overflowing_add(cpu.d),
86−
87− _ => (0, false),
88− };
89−
90−
91−
92− match dest {
93− 0 => cpu.a = result,
94− 1 => cpu.b = result,
95− 2 => cpu.c = result,
96− 3 => cpu.d = result,
97− _ => {}
98− }
99−
100− cpu.zero = result == 0;
101− cpu.carry = carry;
102− }
103− x if x == Instruction::SUB as u8 => {
104− let dest = mem.read(cpu.pc); cpu.pc += 1;
105− let src = mem.read(cpu.pc); cpu.pc += 1;
106−
107− let (result, borrow) = match (dest, src) {
108− // What the fuck do these tuples mean?
109− // so basically they are the numbers assigned to register
110− // 0 => A, 1 => B ....
111− // so when it is (0, 0), it basically says add the
112− // value of register B into register A,
113− // thats exactly whats replicated in the code below
114− (0, 0) => cpu.a.overflowing_sub(cpu.a),
115− (0, 1) => cpu.a.overflowing_sub(cpu.b),
116− (0, 2) => cpu.a.overflowing_sub(cpu.c),
117− (0, 3) => cpu.a.overflowing_sub(cpu.d),
118−
119− (1, 0) => cpu.b.overflowing_sub(cpu.a),
120− (1, 1) => cpu.b.overflowing_sub(cpu.b),
121− (1, 2) => cpu.b.overflowing_sub(cpu.c),
122− (1, 3) => cpu.b.overflowing_sub(cpu.d),
123−
124− (2, 0) => cpu.c.overflowing_sub(cpu.a),
125− (2, 1) => cpu.c.overflowing_sub(cpu.b),
126− (2, 2) => cpu.c.overflowing_sub(cpu.c),
127− (2, 3) => cpu.c.overflowing_sub(cpu.d),
128−
129− (3, 0) => cpu.d.overflowing_sub(cpu.a),
130− (3, 1) => cpu.d.overflowing_sub(cpu.b),
131− (3, 2) => cpu.d.overflowing_sub(cpu.c),
132− (3, 3) => cpu.d.overflowing_sub(cpu.d),
133−
134− _ => (0, false),
135− };
136−
137−
138−
139− match dest {
140− 0 => cpu.a = result,
141− 1 => cpu.b = result,
142− 2 => cpu.c = result,
143− 3 => cpu.d = result,
144− _ => {}
145− }
146−
147− cpu.zero = result == 0;
148− cpu.carry = borrow;
149− }
150−
151−
43+ x if x == Instruction::MOV as u8 => cpu.mov(&mut mem),
44+ x if x == Instruction::ADD as u8 => cpu.add(&mut mem),
45+ x if x == Instruction::SUB as u8 => cpu.sub(&mut mem),
15246 x if x == Instruction::JMP as u8 => {}
153−
15447 x if x == Instruction::JZ as u8 => {}
155−
156− x if x == Instruction::HLT as u8 => {
157− cpu.halted = true;
158− }
159−
48+ x if x == Instruction::HLT as u8 => cpu.halt(),
16049 _ => panic!("Unknown opcode {:02X}", opcode),
16150 }
16251 }