summaryrefslogtreecommitdiff
path: root/src/stack.rs
diff options
context:
space:
mode:
authorBen Bridle <bridle.benjamin@gmail.com>2024-09-30 12:28:24 +1300
committerBen Bridle <bridle.benjamin@gmail.com>2024-09-30 15:00:01 +1300
commitf4f129a75208ccf5d6a19b1cb81c56d4d95fd61f (patch)
treeb3b95f78edeb2cc48ccf207069631468b2705d55 /src/stack.rs
parentf5986d0a37dd8c2526432e5e5e3af7083840447d (diff)
downloadbedrock-core-f4f129a75208ccf5d6a19b1cb81c56d4d95fd61f.zip
Make Bedrock parametric over devices
The core Bedrock struct is now parametric over individual Device structs, rather than over a single DeviceBus. This change was made so that devices can be implemented separately to one another. The implementation of the evaluate method has also been changed to make it potentially slightly more efficient, by replacing pop-then-push combinations with get operations.
Diffstat (limited to 'src/stack.rs')
-rw-r--r--src/stack.rs73
1 files changed, 14 insertions, 59 deletions
diff --git a/src/stack.rs b/src/stack.rs
index 2862b72..ab18cca 100644
--- a/src/stack.rs
+++ b/src/stack.rs
@@ -11,6 +11,10 @@ impl Stack {
}
}
+ pub fn reset(&mut self) {
+ self.sp = 0;
+ }
+
pub fn push_u8(&mut self, val: u8) {
self.mem[self.sp as usize] = val;
self.sp = self.sp.wrapping_add(1);
@@ -22,67 +26,18 @@ impl Stack {
}
pub fn push_u16(&mut self, val: u16) {
- let [byte_high, byte_low] = u16::to_be_bytes(val);
- self.push_u8(byte_high);
- self.push_u8(byte_low);
+ let [high, low] = u16::to_be_bytes(val);
+ self.mem[self.sp as usize] = high;
+ self.sp = self.sp.wrapping_add(1);
+ self.mem[self.sp as usize] = low;
+ self.sp = self.sp.wrapping_add(1);
}
pub fn pop_u16(&mut self) -> u16 {
- self.sp = self.sp.wrapping_sub(1);
- let byte_low = self.mem[self.sp as usize];
- self.sp = self.sp.wrapping_sub(1);
- let byte_high = self.mem[self.sp as usize];
- u16::from_be_bytes([byte_high, byte_low])
- }
-
- pub fn get_u8(&mut self) -> u8 {
- self.mem[self.sp.wrapping_sub(1) as usize]
- }
-
- pub fn get_u16(&mut self) -> u16 {
- let byte_low = self.mem[self.sp.wrapping_sub(1) as usize];
- let byte_high = self.mem[self.sp.wrapping_sub(2) as usize];
- u16::from_be_bytes([byte_high, byte_low])
- }
-
- pub fn reset(&mut self) {
- self.mem.fill(0);
- self.sp = 0;
- }
-}
-
-use std::ops::Not;
-
-impl Stack {
- pub fn inc_u8(&mut self) {
- let sp = self.sp.wrapping_sub(1) as usize;
- self.mem[sp] = self.mem[sp].wrapping_add(1);
- }
-
- pub fn dec_u8(&mut self) {
- let sp = self.sp.wrapping_sub(1) as usize;
- self.mem[sp] = self.mem[sp].wrapping_sub(1);
- }
-
- pub fn not_u8(&mut self) {
- let sp = self.sp.wrapping_sub(1) as usize;
- self.mem[sp] = self.mem[sp].not();
- }
-
- pub fn not_u16(&mut self) {
- let sp = self.sp.wrapping_sub(1) as usize;
- self.mem[sp] = self.mem[sp].not();
- let sp = self.sp.wrapping_sub(2) as usize;
- self.mem[sp] = self.mem[sp].not();
- }
-
- pub fn tal_u8(&mut self) {
- let sp = self.sp.wrapping_sub(1) as usize;
- self.mem[sp] = self.mem[sp].count_ones() as u8;
- }
-
- pub fn rev_u8(&mut self) {
- let sp = self.sp.wrapping_sub(1) as usize;
- self.mem[sp] = self.mem[sp].reverse_bits();
+ self.sp = self.sp.wrapping_sub(1);
+ let low = self.mem[self.sp as usize];
+ self.sp = self.sp.wrapping_sub(1);
+ let high = self.mem[self.sp as usize];
+ u16::from_be_bytes([high, low])
}
}