1use crate::value::*;
6
7const DEFAULT_CAPACITY: usize = 256;
8
9pub struct Stack {
10 vec: Vec<GosValue>,
11}
12
13impl Stack {
14 #[inline]
15 pub fn new() -> Stack {
16 Stack {
17 vec: vec![GosValue::new_nil(ValueType::Void); DEFAULT_CAPACITY],
18 }
19 }
20
21 #[inline]
22 pub fn with_vec(v: Vec<GosValue>) -> Stack {
23 let mut s = Stack { vec: v };
24 s.set_min_size(DEFAULT_CAPACITY);
25 s
26 }
27
28 #[inline]
29 pub fn get(&self, index: OpIndex) -> &GosValue {
30 unsafe { self.vec.get_unchecked(index as usize) }
31 }
32
33 #[inline]
34 pub fn get_mut(&mut self, index: OpIndex) -> &mut GosValue {
35 unsafe { self.vec.get_unchecked_mut(index as usize) }
36 }
37
38 #[inline]
39 pub fn set(&mut self, index: OpIndex, val: GosValue) {
40 *self.get_mut(index) = val;
41 }
42
43 #[inline]
44 pub fn read<'a>(&'a self, i: OpIndex, sb: OpIndex, consts: &'a [GosValue]) -> &'a GosValue {
45 if i >= 0 {
46 &self.get(i + sb)
47 } else {
48 &consts[(-i - 1) as usize]
49 }
50 }
51
52 #[inline]
53 pub(crate) fn read_and_op(
54 &self,
55 lhs: &ValueData,
56 t: ValueType,
57 op: Opcode,
58 rhs: OpIndex,
59 sb: OpIndex,
60 consts: &[GosValue],
61 ) -> GosValue {
62 let d = match op {
63 Opcode::INC => lhs.inc(t),
64 Opcode::DEC => lhs.dec(t),
65 Opcode::ADD => lhs.binary_op_add(self.read(rhs, sb, consts).data(), t),
66 Opcode::SUB => lhs.binary_op_sub(self.read(rhs, sb, consts).data(), t),
67 Opcode::MUL => lhs.binary_op_mul(self.read(rhs, sb, consts).data(), t),
68 Opcode::QUO => lhs.binary_op_quo(self.read(rhs, sb, consts).data(), t),
69 Opcode::REM => lhs.binary_op_rem(self.read(rhs, sb, consts).data(), t),
70 Opcode::AND => lhs.binary_op_and(self.read(rhs, sb, consts).data(), t),
71 Opcode::OR => lhs.binary_op_or(self.read(rhs, sb, consts).data(), t),
72 Opcode::XOR => lhs.binary_op_xor(self.read(rhs, sb, consts).data(), t),
73 Opcode::AND_NOT => lhs.binary_op_and_not(self.read(rhs, sb, consts).data(), t),
74 Opcode::SHL => lhs.binary_op_shl(self.read(rhs, sb, consts).data().as_uint32(), t),
75 Opcode::SHR => lhs.binary_op_shr(self.read(rhs, sb, consts).data().as_uint32(), t),
76 _ => {
77 dbg!(op);
78 unreachable!();
79 }
80 };
81 GosValue::new(t, d)
82 }
83
84 #[inline]
85 pub fn set_min_size(&mut self, size: usize) {
86 if size > self.vec.len() {
87 self.vec.resize(size, GosValue::new_nil(ValueType::Void))
88 }
89 }
90
91 #[inline]
92 pub fn set_vec(&mut self, index: OpIndex, mut vec: Vec<GosValue>) {
93 let begin = index as usize;
94 let new_len = begin + vec.len();
95 self.set_min_size(new_len);
96 self.vec[begin..new_len].swap_with_slice(&mut vec);
97 }
98
99 #[inline]
100 pub fn move_vec(&mut self, begin: OpIndex, end: OpIndex) -> Vec<GosValue> {
101 let b = begin as usize;
102 let e = end as usize;
103 let mut defaults = vec![GosValue::new_nil(ValueType::Void); e - b];
104 self.vec[b..e].swap_with_slice(&mut defaults[..]);
105 defaults
106 }
107
108 #[inline]
109 pub fn get_bool(&mut self, index: OpIndex) -> bool {
110 *self.get_data(index).as_bool()
111 }
112
113 #[inline]
114 pub fn set_bool(&mut self, index: OpIndex, b: bool) {
115 *self.get_data_mut(index) = ValueData::new_bool(b);
116 }
117
118 #[inline]
119 pub fn get_int(&mut self, index: OpIndex) -> isize {
120 *self.get_data(index).as_int()
121 }
122
123 #[inline]
124 pub fn set_int(&mut self, index: OpIndex, i: isize) {
125 *self.get_data_mut(index) = ValueData::new_int(i);
126 }
127
128 #[inline]
129 pub(crate) fn get_data(&self, index: OpIndex) -> &ValueData {
130 self.get(index).data()
131 }
132
133 #[inline]
134 pub(crate) fn get_data_mut(&mut self, index: OpIndex) -> &mut ValueData {
135 unsafe { self.get_mut(index).data_mut() }
136 }
137}
138
139impl std::fmt::Debug for Stack {
140 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
141 write!(f, "{:#?}", &self.vec[..16])
142 }
143}
144
145pub struct RangeStack {
147 maps: Vec<GosMapIter<'static>>,
148 slices: Vec<SliceEnumIter<'static, AnyElem>>,
149 strings: Vec<StringEnumIter<'static>>,
150}
151
152impl RangeStack {
153 pub fn new() -> RangeStack {
154 RangeStack {
155 maps: vec![],
156 slices: vec![],
157 strings: vec![],
158 }
159 }
160
161 pub(crate) fn range_init(
169 &mut self,
170 target: &GosValue,
171 typ: ValueType,
172 arr_caller: &Box<dyn Dispatcher>,
173 ) -> RuntimeResult<()> {
174 match typ {
175 ValueType::Map => {
176 let map = target.as_non_nil_map()?.0.borrow_data();
177 let iter = unsafe { std::mem::transmute(map.iter()) };
178 self.maps.push(iter);
179 }
180 ValueType::Array | ValueType::Slice => {
181 let iter = arr_caller.array_slice_iter(&target)?;
182 self.slices.push(iter);
183 }
184 ValueType::String => {
185 let iter =
186 unsafe { std::mem::transmute(target.as_string().as_str().chars().enumerate()) };
187 self.strings.push(iter);
188 }
189 _ => unreachable!(),
190 }
191 Ok(())
192 }
193
194 pub(crate) fn range_body(
195 &mut self,
196 typ: ValueType,
197 arr_caller: &Box<dyn Dispatcher>,
198 stack: &mut Stack,
199 index_key: OpIndex,
200 index_val: OpIndex,
201 ) -> bool {
202 match typ {
203 ValueType::Map => match self.maps.last_mut().unwrap().next() {
204 Some((k, v)) => {
205 stack.set(index_key, k.clone());
206 stack.set(index_val, v.clone());
207 false
208 }
209 None => {
210 self.maps.pop();
211 true
212 }
213 },
214 ValueType::Array | ValueType::Slice => {
215 match arr_caller.array_slice_next(self.slices.last_mut().unwrap()) {
216 Some((k, v)) => {
217 stack.set(index_key, (k as isize).into());
218 stack.set(index_val, v);
219 false
220 }
221 None => {
222 self.slices.pop();
223 true
224 }
225 }
226 }
227 ValueType::String => match self.strings.last_mut().unwrap().next() {
228 Some((k, v)) => {
229 stack.set(index_key, (k as isize).into());
230 stack.set(index_val, (v as isize).into());
231 false
232 }
233 None => {
234 self.strings.pop();
235 true
236 }
237 },
238 _ => unreachable!(),
239 }
240 }
241}