miden_stdlib_sys/intrinsics/
word.rs

1use core::ops::{Index, IndexMut};
2
3use super::felt::Felt;
4use crate::felt;
5
6#[derive(Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Debug)]
7#[repr(C, align(16))]
8pub struct Word {
9    pub inner: (Felt, Felt, Felt, Felt),
10}
11impl Word {
12    pub const fn new(word: [Felt; 4]) -> Self {
13        Self {
14            inner: (word[0], word[1], word[2], word[3]),
15        }
16    }
17
18    pub fn reverse(&self) -> Word {
19        // This is workaround for the https://github.com/0xMiden/compiler/issues/596 to avoid
20        // i64.rotl op in the compiled Wasm
21        let mut arr: [Felt; 4] = self.into();
22        arr.reverse();
23        arr.into()
24    }
25}
26impl From<[Felt; 4]> for Word {
27    fn from(word: [Felt; 4]) -> Self {
28        Self {
29            inner: (word[0], word[1], word[2], word[3]),
30        }
31    }
32}
33impl From<Word> for [Felt; 4] {
34    #[inline(always)]
35    fn from(word: Word) -> Self {
36        [word.inner.0, word.inner.1, word.inner.2, word.inner.3]
37    }
38}
39impl From<&Word> for [Felt; 4] {
40    #[inline(always)]
41    fn from(word: &Word) -> Self {
42        [word.inner.0, word.inner.1, word.inner.2, word.inner.3]
43    }
44}
45impl From<Felt> for Word {
46    fn from(value: Felt) -> Self {
47        Word {
48            inner: (felt!(0), felt!(0), felt!(0), value),
49        }
50    }
51}
52impl From<Word> for Felt {
53    fn from(value: Word) -> Self {
54        value.inner.3
55    }
56}
57impl Index<usize> for Word {
58    type Output = Felt;
59
60    #[inline(always)]
61    fn index(&self, index: usize) -> &Self::Output {
62        match index {
63            0 => &self.inner.0,
64            1 => &self.inner.1,
65            2 => &self.inner.2,
66            3 => &self.inner.3,
67            _ => unreachable!(),
68        }
69    }
70}
71impl IndexMut<usize> for Word {
72    #[inline(always)]
73    fn index_mut(&mut self, index: usize) -> &mut Self::Output {
74        match index {
75            0 => &mut self.inner.0,
76            1 => &mut self.inner.1,
77            2 => &mut self.inner.2,
78            3 => &mut self.inner.3,
79            _ => unreachable!(),
80        }
81    }
82}
83
84impl AsRef<Word> for Word {
85    fn as_ref(&self) -> &Word {
86        self
87    }
88}