Skip to main content

vihaco_cpu/execute/values/
bitwise.rs

1// SPDX-FileCopyrightText: 2026 The vihaco Authors
2// SPDX-License-Identifier: MIT
3
4use crate::{CPU, cpu};
5use vihaco_runtime::{Execute, PopFromStack, PushToStack};
6
7impl Execute<cpu::ShlI32> for CPU {
8    type Message = PopFromStack<(i32, u32)>;
9    type Effect = PushToStack<(i32,)>;
10    type Error = eyre::Report;
11
12    fn execute(
13        &mut self,
14        _: &cpu::ShlI32,
15        PopFromStack((lhs, rhs)): Self::Message,
16    ) -> eyre::Result<Self::Effect> {
17        Ok(PushToStack((lhs.wrapping_shl(rhs & 31),)))
18    }
19}
20
21impl Execute<cpu::ShlI64> for CPU {
22    type Message = PopFromStack<(i64, u32)>;
23    type Effect = PushToStack<(i64,)>;
24    type Error = eyre::Report;
25
26    fn execute(
27        &mut self,
28        _: &cpu::ShlI64,
29        PopFromStack((lhs, rhs)): Self::Message,
30    ) -> eyre::Result<Self::Effect> {
31        Ok(PushToStack((lhs.wrapping_shl(rhs & 63),)))
32    }
33}
34
35impl Execute<cpu::ShlU32> for CPU {
36    type Message = PopFromStack<(u32, u32)>;
37    type Effect = PushToStack<(u32,)>;
38    type Error = eyre::Report;
39
40    fn execute(
41        &mut self,
42        _: &cpu::ShlU32,
43        PopFromStack((lhs, rhs)): Self::Message,
44    ) -> eyre::Result<Self::Effect> {
45        Ok(PushToStack((lhs.wrapping_shl(rhs & 31),)))
46    }
47}
48
49impl Execute<cpu::ShlU64> for CPU {
50    type Message = PopFromStack<(u64, u32)>;
51    type Effect = PushToStack<(u64,)>;
52    type Error = eyre::Report;
53
54    fn execute(
55        &mut self,
56        _: &cpu::ShlU64,
57        PopFromStack((lhs, rhs)): Self::Message,
58    ) -> eyre::Result<Self::Effect> {
59        Ok(PushToStack((lhs.wrapping_shl(rhs & 63),)))
60    }
61}
62
63impl Execute<cpu::ShrI32> for CPU {
64    type Message = PopFromStack<(i32, u32)>;
65    type Effect = PushToStack<(i32,)>;
66    type Error = eyre::Report;
67
68    fn execute(
69        &mut self,
70        _: &cpu::ShrI32,
71        PopFromStack((lhs, rhs)): Self::Message,
72    ) -> eyre::Result<Self::Effect> {
73        Ok(PushToStack((lhs.wrapping_shr(rhs & 31),)))
74    }
75}
76
77impl Execute<cpu::ShrI64> for CPU {
78    type Message = PopFromStack<(i64, u32)>;
79    type Effect = PushToStack<(i64,)>;
80    type Error = eyre::Report;
81
82    fn execute(
83        &mut self,
84        _: &cpu::ShrI64,
85        PopFromStack((lhs, rhs)): Self::Message,
86    ) -> eyre::Result<Self::Effect> {
87        Ok(PushToStack((lhs.wrapping_shr(rhs & 63),)))
88    }
89}
90
91impl Execute<cpu::ShrU32> for CPU {
92    type Message = PopFromStack<(u32, u32)>;
93    type Effect = PushToStack<(u32,)>;
94    type Error = eyre::Report;
95
96    fn execute(
97        &mut self,
98        _: &cpu::ShrU32,
99        PopFromStack((lhs, rhs)): Self::Message,
100    ) -> eyre::Result<Self::Effect> {
101        Ok(PushToStack((lhs.wrapping_shr(rhs & 31),)))
102    }
103}
104
105impl Execute<cpu::ShrU64> for CPU {
106    type Message = PopFromStack<(u64, u32)>;
107    type Effect = PushToStack<(u64,)>;
108    type Error = eyre::Report;
109
110    fn execute(
111        &mut self,
112        _: &cpu::ShrU64,
113        PopFromStack((lhs, rhs)): Self::Message,
114    ) -> eyre::Result<Self::Effect> {
115        Ok(PushToStack((lhs.wrapping_shr(rhs & 63),)))
116    }
117}
118
119impl Execute<cpu::RolI32> for CPU {
120    type Message = PopFromStack<(i32, u32)>;
121    type Effect = PushToStack<(i32,)>;
122    type Error = eyre::Report;
123
124    fn execute(
125        &mut self,
126        _: &cpu::RolI32,
127        PopFromStack((lhs, rhs)): Self::Message,
128    ) -> eyre::Result<Self::Effect> {
129        Ok(PushToStack((lhs.rotate_left(rhs),)))
130    }
131}
132
133impl Execute<cpu::RolI64> for CPU {
134    type Message = PopFromStack<(i64, u32)>;
135    type Effect = PushToStack<(i64,)>;
136    type Error = eyre::Report;
137
138    fn execute(
139        &mut self,
140        _: &cpu::RolI64,
141        PopFromStack((lhs, rhs)): Self::Message,
142    ) -> eyre::Result<Self::Effect> {
143        Ok(PushToStack((lhs.rotate_left(rhs),)))
144    }
145}
146
147impl Execute<cpu::RolU32> for CPU {
148    type Message = PopFromStack<(u32, u32)>;
149    type Effect = PushToStack<(u32,)>;
150    type Error = eyre::Report;
151
152    fn execute(
153        &mut self,
154        _: &cpu::RolU32,
155        PopFromStack((lhs, rhs)): Self::Message,
156    ) -> eyre::Result<Self::Effect> {
157        Ok(PushToStack((lhs.rotate_left(rhs),)))
158    }
159}
160
161impl Execute<cpu::RolU64> for CPU {
162    type Message = PopFromStack<(u64, u32)>;
163    type Effect = PushToStack<(u64,)>;
164    type Error = eyre::Report;
165
166    fn execute(
167        &mut self,
168        _: &cpu::RolU64,
169        PopFromStack((lhs, rhs)): Self::Message,
170    ) -> eyre::Result<Self::Effect> {
171        Ok(PushToStack((lhs.rotate_left(rhs),)))
172    }
173}
174
175impl Execute<cpu::RorI32> for CPU {
176    type Message = PopFromStack<(i32, u32)>;
177    type Effect = PushToStack<(i32,)>;
178    type Error = eyre::Report;
179
180    fn execute(
181        &mut self,
182        _: &cpu::RorI32,
183        PopFromStack((lhs, rhs)): Self::Message,
184    ) -> eyre::Result<Self::Effect> {
185        Ok(PushToStack((lhs.rotate_right(rhs),)))
186    }
187}
188
189impl Execute<cpu::RorI64> for CPU {
190    type Message = PopFromStack<(i64, u32)>;
191    type Effect = PushToStack<(i64,)>;
192    type Error = eyre::Report;
193
194    fn execute(
195        &mut self,
196        _: &cpu::RorI64,
197        PopFromStack((lhs, rhs)): Self::Message,
198    ) -> eyre::Result<Self::Effect> {
199        Ok(PushToStack((lhs.rotate_right(rhs),)))
200    }
201}
202
203impl Execute<cpu::RorU32> for CPU {
204    type Message = PopFromStack<(u32, u32)>;
205    type Effect = PushToStack<(u32,)>;
206    type Error = eyre::Report;
207
208    fn execute(
209        &mut self,
210        _: &cpu::RorU32,
211        PopFromStack((lhs, rhs)): Self::Message,
212    ) -> eyre::Result<Self::Effect> {
213        Ok(PushToStack((lhs.rotate_right(rhs),)))
214    }
215}
216
217impl Execute<cpu::RorU64> for CPU {
218    type Message = PopFromStack<(u64, u32)>;
219    type Effect = PushToStack<(u64,)>;
220    type Error = eyre::Report;
221
222    fn execute(
223        &mut self,
224        _: &cpu::RorU64,
225        PopFromStack((lhs, rhs)): Self::Message,
226    ) -> eyre::Result<Self::Effect> {
227        Ok(PushToStack((lhs.rotate_right(rhs),)))
228    }
229}
230
231impl Execute<cpu::BitAndI32> for CPU {
232    type Message = PopFromStack<(i32, i32)>;
233    type Effect = PushToStack<(i32,)>;
234    type Error = eyre::Report;
235
236    fn execute(
237        &mut self,
238        _: &cpu::BitAndI32,
239        PopFromStack((lhs, rhs)): Self::Message,
240    ) -> eyre::Result<Self::Effect> {
241        Ok(PushToStack((lhs & rhs,)))
242    }
243}
244
245impl Execute<cpu::BitAndI64> for CPU {
246    type Message = PopFromStack<(i64, i64)>;
247    type Effect = PushToStack<(i64,)>;
248    type Error = eyre::Report;
249
250    fn execute(
251        &mut self,
252        _: &cpu::BitAndI64,
253        PopFromStack((lhs, rhs)): Self::Message,
254    ) -> eyre::Result<Self::Effect> {
255        Ok(PushToStack((lhs & rhs,)))
256    }
257}
258
259impl Execute<cpu::BitAndU32> for CPU {
260    type Message = PopFromStack<(u32, u32)>;
261    type Effect = PushToStack<(u32,)>;
262    type Error = eyre::Report;
263
264    fn execute(
265        &mut self,
266        _: &cpu::BitAndU32,
267        PopFromStack((lhs, rhs)): Self::Message,
268    ) -> eyre::Result<Self::Effect> {
269        Ok(PushToStack((lhs & rhs,)))
270    }
271}
272
273impl Execute<cpu::BitAndU64> for CPU {
274    type Message = PopFromStack<(u64, u64)>;
275    type Effect = PushToStack<(u64,)>;
276    type Error = eyre::Report;
277
278    fn execute(
279        &mut self,
280        _: &cpu::BitAndU64,
281        PopFromStack((lhs, rhs)): Self::Message,
282    ) -> eyre::Result<Self::Effect> {
283        Ok(PushToStack((lhs & rhs,)))
284    }
285}
286
287impl Execute<cpu::BitOrI32> for CPU {
288    type Message = PopFromStack<(i32, i32)>;
289    type Effect = PushToStack<(i32,)>;
290    type Error = eyre::Report;
291
292    fn execute(
293        &mut self,
294        _: &cpu::BitOrI32,
295        PopFromStack((lhs, rhs)): Self::Message,
296    ) -> eyre::Result<Self::Effect> {
297        Ok(PushToStack((lhs | rhs,)))
298    }
299}
300
301impl Execute<cpu::BitOrI64> for CPU {
302    type Message = PopFromStack<(i64, i64)>;
303    type Effect = PushToStack<(i64,)>;
304    type Error = eyre::Report;
305
306    fn execute(
307        &mut self,
308        _: &cpu::BitOrI64,
309        PopFromStack((lhs, rhs)): Self::Message,
310    ) -> eyre::Result<Self::Effect> {
311        Ok(PushToStack((lhs | rhs,)))
312    }
313}
314
315impl Execute<cpu::BitOrU32> for CPU {
316    type Message = PopFromStack<(u32, u32)>;
317    type Effect = PushToStack<(u32,)>;
318    type Error = eyre::Report;
319
320    fn execute(
321        &mut self,
322        _: &cpu::BitOrU32,
323        PopFromStack((lhs, rhs)): Self::Message,
324    ) -> eyre::Result<Self::Effect> {
325        Ok(PushToStack((lhs | rhs,)))
326    }
327}
328
329impl Execute<cpu::BitOrU64> for CPU {
330    type Message = PopFromStack<(u64, u64)>;
331    type Effect = PushToStack<(u64,)>;
332    type Error = eyre::Report;
333
334    fn execute(
335        &mut self,
336        _: &cpu::BitOrU64,
337        PopFromStack((lhs, rhs)): Self::Message,
338    ) -> eyre::Result<Self::Effect> {
339        Ok(PushToStack((lhs | rhs,)))
340    }
341}
342
343impl Execute<cpu::BitXorI32> for CPU {
344    type Message = PopFromStack<(i32, i32)>;
345    type Effect = PushToStack<(i32,)>;
346    type Error = eyre::Report;
347
348    fn execute(
349        &mut self,
350        _: &cpu::BitXorI32,
351        PopFromStack((lhs, rhs)): Self::Message,
352    ) -> eyre::Result<Self::Effect> {
353        Ok(PushToStack((lhs ^ rhs,)))
354    }
355}
356
357impl Execute<cpu::BitXorI64> for CPU {
358    type Message = PopFromStack<(i64, i64)>;
359    type Effect = PushToStack<(i64,)>;
360    type Error = eyre::Report;
361
362    fn execute(
363        &mut self,
364        _: &cpu::BitXorI64,
365        PopFromStack((lhs, rhs)): Self::Message,
366    ) -> eyre::Result<Self::Effect> {
367        Ok(PushToStack((lhs ^ rhs,)))
368    }
369}
370
371impl Execute<cpu::BitXorU32> for CPU {
372    type Message = PopFromStack<(u32, u32)>;
373    type Effect = PushToStack<(u32,)>;
374    type Error = eyre::Report;
375
376    fn execute(
377        &mut self,
378        _: &cpu::BitXorU32,
379        PopFromStack((lhs, rhs)): Self::Message,
380    ) -> eyre::Result<Self::Effect> {
381        Ok(PushToStack((lhs ^ rhs,)))
382    }
383}
384
385impl Execute<cpu::BitXorU64> for CPU {
386    type Message = PopFromStack<(u64, u64)>;
387    type Effect = PushToStack<(u64,)>;
388    type Error = eyre::Report;
389
390    fn execute(
391        &mut self,
392        _: &cpu::BitXorU64,
393        PopFromStack((lhs, rhs)): Self::Message,
394    ) -> eyre::Result<Self::Effect> {
395        Ok(PushToStack((lhs ^ rhs,)))
396    }
397}