diff --git a/src/vm/mod.rs b/src/vm/mod.rs index 76f97e7..65c38fb 100644 --- a/src/vm/mod.rs +++ b/src/vm/mod.rs @@ -1,3 +1,4 @@ +use crate::vm::utils::output_handler::OutputHandler; use std::fmt::Debug; use std::rc::Rc; @@ -7,6 +8,7 @@ mod value; mod block; pub(crate) mod opcodes; +mod utils; mod virtual_machine; #[derive(Debug, Clone, PartialEq)] @@ -28,6 +30,7 @@ pub struct VirtualMachine { ip: usize, stack: Vec, block: Option>, + output_handler: Box, } #[derive(Debug)] diff --git a/src/vm/utils/mod.rs b/src/vm/utils/mod.rs new file mode 100644 index 0000000..1e813a8 --- /dev/null +++ b/src/vm/utils/mod.rs @@ -0,0 +1 @@ +pub(crate) mod output_handler; diff --git a/src/vm/utils/output_handler.rs b/src/vm/utils/output_handler.rs new file mode 100644 index 0000000..9672f1e --- /dev/null +++ b/src/vm/utils/output_handler.rs @@ -0,0 +1,13 @@ +use crate::vm::Value; + +pub(crate) trait OutputHandler { + fn println(&self, value: Value); +} + +pub(crate) struct ConsoleOutputHandler {} + +impl OutputHandler for ConsoleOutputHandler { + fn println(&self, value: Value) { + println!("{}", value); + } +} diff --git a/src/vm/virtual_machine.rs b/src/vm/virtual_machine.rs index f5fb158..7fd6057 100644 --- a/src/vm/virtual_machine.rs +++ b/src/vm/virtual_machine.rs @@ -1,5 +1,6 @@ use crate::compiler::Compiler; use crate::vm::opcodes::OpCode; +use crate::vm::utils::output_handler::ConsoleOutputHandler; use crate::vm::{Block, Result, Value, VirtualMachine}; use std::rc::Rc; @@ -11,6 +12,7 @@ impl VirtualMachine { ip: 0, stack: Vec::new(), block: None, + output_handler: Box::new(ConsoleOutputHandler {}), } } @@ -137,7 +139,7 @@ impl VirtualMachine { } OpCode::Print => { let value = self.pop(); - println!("{}", value); + self.output_handler.println(value); } OpCode::Pop => { self.pop(); @@ -214,11 +216,7 @@ mod tests { block.write_op_code(super::OpCode::Divide, 0); block.write_op_code(super::OpCode::Return, 0); - let mut vm = super::VirtualMachine { - ip: 0, - stack: Vec::new(), - block: None, - }; + let mut vm = super::VirtualMachine::new(); let result = vm.run(&block); assert_eq!(super::Result::Ok, result); @@ -248,6 +246,7 @@ mod tests { assert_eq!(super::Result::Ok, result); } + #[test] fn can_run_multi_line_statements() { let program = r#"