1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
#[derive(Debug)] pub enum Error { DynamicLoading(ckb_std::dynamic_loading::Error), ValidationFunctionNotFound, ValidateFailure(i32), } use ckb_std::dynamic_loading::{CKBDLContext, Symbol}; type Validate = unsafe extern "C" fn(args: *const u8, len: u64) -> i32; const VALIDATE: &[u8; 8] = b"validate"; pub struct DynLock { validate: Symbol<Validate>, } impl DynLock { pub fn load<T>(context: &mut CKBDLContext<T>, code_hash: &[u8]) -> Result<Self, Error> { let lock = context.load(code_hash).map_err(Error::DynamicLoading)?; let validate: Symbol<Validate> = unsafe { lock.get(VALIDATE) .ok_or_else(|| Error::ValidationFunctionNotFound)? }; Ok(DynLock { validate }) } pub fn validate(&self, args: &[u8], args_size: u64) -> Result<(), Error> { let f = &self.validate; let error_code = unsafe { f(args.as_ptr(), args_size) }; if error_code != 0 { return Err(Error::ValidateFailure(error_code)); } Ok(()) } }