Skip to main content

move_neovm/bytecode/
types.rs

1//! Move bytecode type definitions.
2
3/// Move bytecode version
4#[derive(Debug, Clone, Copy)]
5pub struct BytecodeVersion(pub u32);
6
7/// A parsed Move module
8#[derive(Debug, Clone)]
9pub struct MoveModule {
10    /// Module version
11    pub version: BytecodeVersion,
12    /// Module name
13    pub name: String,
14    /// Identifier table offset
15    pub identifiers_offset: u32,
16    /// Identifier table count
17    pub identifiers_count: u32,
18    /// Struct table offset
19    pub struct_defs_offset: u32,
20    /// Struct table count
21    pub struct_defs_count: u32,
22    /// Function handle offset (unused placeholder)
23    pub _function_handles_offset: u32,
24    /// Function handle count (unused placeholder)
25    pub _function_handles_count: u32,
26    /// Function table offset
27    pub function_defs_offset: u32,
28    /// Function table count
29    pub function_defs_count: u32,
30    /// Struct definitions
31    pub structs: Vec<StructDef>,
32    /// Function definitions
33    pub functions: Vec<FunctionDef>,
34}
35
36/// Ability flags attached to a struct definition
37#[derive(Debug, Clone, Copy, Default)]
38pub struct AbilitySet {
39    pub copy: bool,
40    pub drop: bool,
41    pub store: bool,
42    pub key: bool,
43}
44
45impl AbilitySet {
46    pub fn is_resource(&self) -> bool {
47        self.key
48    }
49}
50
51/// A struct (or resource) definition
52#[derive(Debug, Clone)]
53pub struct StructDef {
54    /// Struct name (fully-qualified or simple)
55    pub name: String,
56    /// Ability set declared on the struct
57    pub abilities: AbilitySet,
58    /// Field definitions
59    pub fields: Vec<FieldDef>,
60}
61
62/// A field definition
63#[derive(Debug, Clone)]
64pub struct FieldDef {
65    /// Field name
66    pub name: String,
67    /// Field type
68    pub type_tag: TypeTag,
69}
70
71/// A function definition
72#[derive(Debug, Clone)]
73pub struct FunctionDef {
74    /// Function name
75    pub name: String,
76    /// Is this a public function?
77    pub is_public: bool,
78    /// Is this an entry function?
79    pub is_entry: bool,
80    /// Parameter types
81    pub parameters: Vec<TypeTag>,
82    /// Return types
83    pub returns: Vec<TypeTag>,
84    /// Local slot layout (parameters are always the first locals)
85    pub locals: Vec<TypeTag>,
86    /// Function body (opcodes)
87    pub code: Vec<MoveOpcode>,
88}
89
90/// Move type tags
91#[derive(Debug, Clone)]
92pub enum TypeTag {
93    Bool,
94    U8,
95    U64,
96    U128,
97    U256,
98    Address,
99    Signer,
100    Vector(Box<TypeTag>),
101    Struct(String),
102    Reference(Box<TypeTag>),
103    MutableReference(Box<TypeTag>),
104}
105
106impl TypeTag {
107    /// Convert to WASM-compatible representation
108    pub fn to_wasm_type(&self) -> &'static str {
109        match self {
110            TypeTag::Bool => "i32",
111            TypeTag::U8 => "i32",
112            TypeTag::U64 => "i64",
113            TypeTag::U128 => "i64",      // Requires multi-word handling
114            TypeTag::U256 => "i64",      // Requires multi-word handling
115            TypeTag::Address => "i32",   // Pointer to 32-byte array
116            TypeTag::Signer => "i32",    // Pointer to signer data
117            TypeTag::Vector(_) => "i32", // Pointer to vector
118            TypeTag::Struct(_) => "i32", // Pointer to struct
119            TypeTag::Reference(_) => "i32",
120            TypeTag::MutableReference(_) => "i32",
121        }
122    }
123}
124
125/// Move VM opcodes (simplified subset)
126#[derive(Debug, Clone)]
127pub enum MoveOpcode {
128    // Constants
129    LdU8(u8),
130    LdU64(u64),
131    LdU128(u128),
132    LdTrue,
133    LdFalse,
134    LdConst(u16), // Constant pool index
135
136    // Local operations
137    CopyLoc(u8),
138    MoveLoc(u8),
139    StLoc(u8),
140    MutBorrowLoc(u8),
141    ImmBorrowLoc(u8),
142
143    // Arithmetic
144    Add,
145    Sub,
146    Mul,
147    Div,
148    Mod,
149
150    // Comparison
151    Lt,
152    Gt,
153    Le,
154    Ge,
155    Eq,
156    Neq,
157
158    // Logical
159    And,
160    Or,
161    Not,
162
163    // Control flow
164    Branch(u16),
165    BrTrue(u16),
166    BrFalse(u16),
167    Call(u16), // Function index
168    Ret,
169    Abort,
170
171    // Resource operations
172    Pack(u16), // Struct index
173    Unpack(u16),
174    BorrowField(u16),
175    MutBorrowField(u16),
176    MoveFrom(u16), // Struct index
177    MoveTo(u16),
178    Exists(u16),
179    BorrowGlobal(u16),
180    MutBorrowGlobal(u16),
181
182    // Stack
183    Pop,
184
185    // Vector operations
186    VecPack(u16, u64),
187    VecLen(u16),
188    VecImmBorrow(u16),
189    VecMutBorrow(u16),
190    VecPushBack(u16),
191    VecPopBack(u16),
192
193    // Casting
194    CastU8,
195    CastU64,
196    CastU128,
197
198    // Nop (placeholder for unsupported)
199    Nop,
200}
201
202impl MoveOpcode {
203    /// Get opcode byte value
204    pub fn opcode_byte(&self) -> u8 {
205        match self {
206            MoveOpcode::Pop => 0x01,
207            MoveOpcode::Ret => 0x02,
208            MoveOpcode::BrTrue(_) => 0x03,
209            MoveOpcode::BrFalse(_) => 0x04,
210            MoveOpcode::Branch(_) => 0x05,
211            MoveOpcode::LdU8(_) => 0x06,
212            MoveOpcode::LdU64(_) => 0x07,
213            MoveOpcode::LdU128(_) => 0x08,
214            MoveOpcode::CastU8 => 0x09,
215            MoveOpcode::CastU64 => 0x0A,
216            MoveOpcode::CastU128 => 0x0B,
217            MoveOpcode::LdConst(_) => 0x0C,
218            MoveOpcode::LdTrue => 0x0D,
219            MoveOpcode::LdFalse => 0x0E,
220            MoveOpcode::CopyLoc(_) => 0x0F,
221            MoveOpcode::MoveLoc(_) => 0x10,
222            MoveOpcode::StLoc(_) => 0x11,
223            MoveOpcode::MutBorrowLoc(_) => 0x12,
224            MoveOpcode::ImmBorrowLoc(_) => 0x13,
225            MoveOpcode::MutBorrowField(_) => 0x14,
226            MoveOpcode::BorrowField(_) => 0x15,
227            MoveOpcode::Call(_) => 0x16,
228            MoveOpcode::Pack(_) => 0x17,
229            MoveOpcode::Unpack(_) => 0x18,
230            MoveOpcode::Add => 0x22,
231            MoveOpcode::Sub => 0x23,
232            MoveOpcode::Mul => 0x24,
233            MoveOpcode::Mod => 0x25,
234            MoveOpcode::Div => 0x26,
235            MoveOpcode::Lt => 0x32,
236            MoveOpcode::Gt => 0x33,
237            MoveOpcode::Le => 0x34,
238            MoveOpcode::Ge => 0x35,
239            MoveOpcode::And => 0x40,
240            MoveOpcode::Or => 0x41,
241            MoveOpcode::Not => 0x42,
242            MoveOpcode::Eq => 0x43,
243            MoveOpcode::Neq => 0x44,
244            MoveOpcode::Abort => 0x45,
245            MoveOpcode::Exists(_) => 0x50,
246            MoveOpcode::BorrowGlobal(_) => 0x51,
247            MoveOpcode::MutBorrowGlobal(_) => 0x52,
248            MoveOpcode::MoveFrom(_) => 0x53,
249            MoveOpcode::MoveTo(_) => 0x54,
250            MoveOpcode::VecPack(_, _) => 0x60,
251            MoveOpcode::VecLen(_) => 0x61,
252            MoveOpcode::VecImmBorrow(_) => 0x62,
253            MoveOpcode::VecMutBorrow(_) => 0x63,
254            MoveOpcode::VecPushBack(_) => 0x64,
255            MoveOpcode::VecPopBack(_) => 0x65,
256            MoveOpcode::Nop => 0x00,
257        }
258    }
259}