brainpreter/core/
program.rs

1use super::instruction::Instruction;
2
3// Struct for the program (a series of instructions)
4pub struct Program {
5    
6    instr:Vec<Instruction>,
7    ptr:usize,
8
9}
10
11impl Program {
12
13    // Function to create and return a new program
14    pub fn new() -> Program {
15
16        Program {
17
18            instr:Vec::<Instruction>::new(),
19            ptr:0,
20
21        }
22
23    }
24
25    // Function to increase the pointer
26    pub fn inc_ptr(&mut self) -> bool {
27
28        if self.ptr < self.instr.len() - 1 {
29            self.ptr += 1;
30            return true;
31        }
32
33        false
34
35    }
36
37    // Function to decrease the pointer
38    #[allow(unused)]
39    pub fn dec_ptr(&mut self) -> bool {
40
41        if self.ptr > 0 {
42            self.ptr -= 1;
43            return true;
44        }
45
46        false
47
48    }
49
50    // Function to move the pointer
51    pub fn set_ptr(&mut self, pos:usize) -> bool {
52
53        if pos >= self.get_size() {
54            return false;
55        }
56
57        self.ptr = pos;
58
59        true
60
61    }
62
63    // Function to get the current instruction (if a program is already loaded and the instruction exists)
64    pub fn get(&self) -> Option<Instruction> {
65
66        if self.instr.len() > 0 { Option::Some(self.instr[self.ptr]) } else { Option::None }
67
68    }
69
70    // Function to increase the pointer and get the instruction
71    #[allow(unused)]
72    pub fn get_next(&mut self) -> Option<Instruction> {
73
74        if self.inc_ptr() { self.get() } else { Option::None }
75
76    }
77
78    // Function to decrease the pointer and get the instruction
79    #[allow(unused)]
80    pub fn get_prev(&mut self) -> Option<Instruction> {
81
82        if self.dec_ptr() { self.get() } else { Option::None }
83
84    }
85
86    // Function to get an instruction
87    #[allow(unused)]
88    pub fn get_at(&self, p:usize) -> Option<Instruction> {
89
90        if p >= (0 as usize) && p < self.instr.len() { Option::Some(self.instr[p]) } else { Option::None }
91
92    }
93
94    // Function to add a new instruction at the end of the program
95    pub fn push(&mut self, i:Instruction) -> &mut Program {
96
97        self.instr.push(i);
98
99        self
100
101    }
102
103    // Function to remove the last instruction from the program (if exists)
104    #[allow(unused)]
105    pub fn pop(&mut self) -> bool {
106        
107        return match self.instr.pop() {
108
109            Some(_) => {
110                
111                if self.ptr >= self.instr.len() {
112                    if self.ptr > 0 {
113                        self.ptr -= 1;
114                    }
115                }
116
117                true
118
119            }
120
121            None => false
122
123        }
124
125    }
126
127    // Function to clear the program and set pointer to 0
128    #[allow(unused)]
129    pub fn clear(&mut self) -> &mut Program {
130
131        self.instr.clear();
132        self.ptr = 0;
133
134        self
135
136    }
137    
138    // Function to reset the pointer (set to 0)
139    #[allow(unused)]
140    pub fn reset_ptr(&mut self) -> &mut Program {
141
142        self.ptr = 0;
143
144        self
145
146    }
147
148    // Function to update a specific instruction
149    pub fn update_instr(&mut self, pos:usize, new_instr:Instruction) -> bool {
150
151        if self.instr.len() == 0 || pos >= self.instr.len() {
152            return false;
153        }
154
155        self.instr[pos] = new_instr;
156
157        return true;
158
159    }
160
161    // Function to get program's size
162    pub fn get_size(&self) -> usize {
163
164        self.instr.len()
165
166    }
167
168}