Skip to main content

solar_codegen/mir/
types.rs

1//! MIR type system.
2
3use std::fmt;
4
5/// Types used in MIR.
6#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
7pub enum MirType {
8    /// Unsigned integer with a given bit width (8, 16, 32, ..., 256).
9    UInt(u16),
10    /// Signed integer with a given bit width.
11    Int(u16),
12    /// Boolean type.
13    Bool,
14    /// Address type (20 bytes).
15    Address,
16    /// Fixed-size byte array.
17    FixedBytes(u8),
18    /// Memory pointer.
19    MemPtr,
20    /// Storage pointer.
21    StoragePtr,
22    /// Calldata pointer.
23    CalldataPtr,
24    /// Function type.
25    Function,
26    /// Void/unit type (for functions that don't return).
27    Void,
28}
29
30impl MirType {
31    /// Returns the size in bytes for this type on the stack.
32    #[must_use]
33    pub const fn stack_size(&self) -> usize {
34        match self {
35            Self::Bool => 1,
36            Self::UInt(bits) | Self::Int(bits) => (*bits as usize).div_ceil(8),
37            Self::Address => 20,
38            Self::FixedBytes(n) => *n as usize,
39            Self::MemPtr | Self::StoragePtr | Self::CalldataPtr => 32,
40            Self::Function => 24,
41            Self::Void => 0,
42        }
43    }
44
45    /// Returns true if this type fits in a single EVM word (32 bytes).
46    #[must_use]
47    pub const fn fits_in_word(&self) -> bool {
48        self.stack_size() <= 32
49    }
50
51    /// Returns the uint256 type.
52    #[must_use]
53    pub const fn uint256() -> Self {
54        Self::UInt(256)
55    }
56
57    /// Returns the int256 type.
58    #[must_use]
59    pub const fn int256() -> Self {
60        Self::Int(256)
61    }
62
63    /// Returns the bytes32 type.
64    #[must_use]
65    pub const fn bytes32() -> Self {
66        Self::FixedBytes(32)
67    }
68}
69
70impl fmt::Display for MirType {
71    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
72        match self {
73            Self::UInt(bits) => write!(f, "u{bits}"),
74            Self::Int(bits) => write!(f, "i{bits}"),
75            Self::Bool => write!(f, "bool"),
76            Self::Address => write!(f, "address"),
77            Self::FixedBytes(n) => write!(f, "bytes{n}"),
78            Self::MemPtr => write!(f, "memptr"),
79            Self::StoragePtr => write!(f, "storageptr"),
80            Self::CalldataPtr => write!(f, "calldataptr"),
81            Self::Function => write!(f, "function"),
82            Self::Void => write!(f, "void"),
83        }
84    }
85}