entrypoint.rs (1768B)
1 use std::{mem::size_of, slice::from_raw_parts}; 2 3 /// Success exit code for contract 4 pub const SUCCESS: u64 = 0; 5 6 /// This macro is used to flag the contract entrypoint function. 7 /// All contracts must provide such a function and accept a payload. 8 /// 9 /// The payload is a slice of u8 prepended with a little-endian u64 10 /// that tells the slice's length. 11 #[macro_export] 12 macro_rules! entrypoint { 13 ($process_instruction:ident) => { 14 /// # Safety 15 #[no_mangle] 16 pub unsafe extern "C" fn entrypoint(input: *mut u8) -> u64 { 17 let instruction_data = $crate::entrypoint::deserialize(input); 18 19 match $process_instruction(&instruction_data) { 20 Ok(()) => $crate::entrypoint::SUCCESS, 21 Err(e) => e.into(), 22 } 23 } 24 }; 25 } 26 27 /// Deserialize a given payload in `entrypoint` 28 /// # Safety 29 pub unsafe fn deserialize<'a>(input: *mut u8) -> &'a [u8] { 30 let mut offset: usize = 0; 31 32 let instruction_data_len = *(input.add(offset) as *const u64) as usize; 33 offset += size_of::<u64>(); 34 35 let instruction_data = { from_raw_parts(input.add(offset), instruction_data_len) }; 36 37 instruction_data 38 } 39 40 /// Allocate a piece of memory in the wasm VM 41 #[no_mangle] 42 #[cfg(target_arch = "wasm32")] 43 extern "C" fn __drkruntime_mem_alloc(size: usize) -> *mut u8 { 44 let align = std::mem::align_of::<usize>(); 45 46 if let Ok(layout) = std::alloc::Layout::from_size_align(size, align) { 47 unsafe { 48 if layout.size() > 0 { 49 let ptr = std::alloc::alloc(layout); 50 if !ptr.is_null() { 51 return ptr 52 } 53 } else { 54 return align as *mut u8 55 } 56 } 57 } 58 59 std::process::abort(); 60 }