Jelajahi Sumber

sdk: implemented get_system_time for use inside wasm

aggstam 3 tahun lalu
induk
melakukan
fc6c6e6551
5 mengubah file dengan 68 tambahan dan 0 penghapusan
  1. 9 0
      src/runtime/import/util.rs
  2. 5 0
      src/runtime/vm_runtime.rs
  3. 6 0
      src/sdk/src/error.rs
  4. 3 0
      src/sdk/src/lib.rs
  5. 45 0
      src/sdk/src/util.rs

+ 9 - 0
src/runtime/import/util.rs

@@ -16,6 +16,8 @@
  * along with this program.  If not, see <https://www.gnu.org/licenses/>.
  * along with this program.  If not, see <https://www.gnu.org/licenses/>.
  */
  */
 
 
+use std::time::SystemTime;
+
 use log::error;
 use log::error;
 use wasmer::{FunctionEnvMut, WasmPtr};
 use wasmer::{FunctionEnvMut, WasmPtr};
 
 
@@ -148,3 +150,10 @@ pub(crate) fn get_object_size(ctx: FunctionEnvMut<Env>, idx: u32) -> i64 {
     let obj = &objects[idx as usize];
     let obj = &objects[idx as usize];
     obj.len() as i64
     obj.len() as i64
 }
 }
+
+pub(crate) fn get_system_time() -> i64 {
+    match SystemTime::now().duration_since(SystemTime::UNIX_EPOCH) {
+        Ok(t) => t.as_secs() as i64,
+        Err(_) => -1,
+    }
+}

+ 5 - 0
src/runtime/vm_runtime.rs

@@ -253,6 +253,11 @@ impl Runtime {
                     &ctx,
                     &ctx,
                     import::merkle::merkle_add,
                     import::merkle::merkle_add,
                 ),
                 ),
+
+                "get_system_time_" => Function::new_typed(
+                    &mut store,
+                    import::util::get_system_time,
+                ),
             }
             }
         };
         };
 
 

+ 6 - 0
src/sdk/src/error.rs

@@ -80,6 +80,9 @@ pub enum ContractError {
 
 
     #[error("SMT: Path nodes are not consistent")]
     #[error("SMT: Path nodes are not consistent")]
     SmtInvalidPathNodes,
     SmtInvalidPathNodes,
+
+    #[error("Error retrieving system time")]
+    GetSystemTimeFailed,
 }
 }
 
 
 /// Builtin return values occupy the upper 32 bits
 /// Builtin return values occupy the upper 32 bits
@@ -107,6 +110,7 @@ pub const INVALID_FUNCTION: i64 = to_builtin!(15);
 pub const DB_DEL_FAILED: i64 = to_builtin!(16);
 pub const DB_DEL_FAILED: i64 = to_builtin!(16);
 pub const SMT_INVALID_LEAF: i64 = to_builtin!(17);
 pub const SMT_INVALID_LEAF: i64 = to_builtin!(17);
 pub const SMT_INVALID_PATH_NODES: i64 = to_builtin!(18);
 pub const SMT_INVALID_PATH_NODES: i64 = to_builtin!(18);
+pub const GET_SYSTEM_TIME_FAILED: i64 = to_builtin!(19);
 
 
 impl From<ContractError> for i64 {
 impl From<ContractError> for i64 {
     fn from(err: ContractError) -> Self {
     fn from(err: ContractError) -> Self {
@@ -128,6 +132,7 @@ impl From<ContractError> for i64 {
             ContractError::DbDelFailed => DB_DEL_FAILED,
             ContractError::DbDelFailed => DB_DEL_FAILED,
             ContractError::SmtInvalidLeaf => SMT_INVALID_LEAF,
             ContractError::SmtInvalidLeaf => SMT_INVALID_LEAF,
             ContractError::SmtInvalidPathNodes => SMT_INVALID_PATH_NODES,
             ContractError::SmtInvalidPathNodes => SMT_INVALID_PATH_NODES,
+            ContractError::GetSystemTimeFailed => GET_SYSTEM_TIME_FAILED,
             ContractError::Custom(error) => {
             ContractError::Custom(error) => {
                 if error == 0 {
                 if error == 0 {
                     CUSTOM_ZERO
                     CUSTOM_ZERO
@@ -160,6 +165,7 @@ impl From<i64> for ContractError {
             DB_DEL_FAILED => Self::DbDelFailed,
             DB_DEL_FAILED => Self::DbDelFailed,
             SMT_INVALID_LEAF => Self::SmtInvalidLeaf,
             SMT_INVALID_LEAF => Self::SmtInvalidLeaf,
             SMT_INVALID_PATH_NODES => Self::SmtInvalidPathNodes,
             SMT_INVALID_PATH_NODES => Self::SmtInvalidPathNodes,
+            GET_SYSTEM_TIME_FAILED => Self::GetSystemTimeFailed,
             _ => Self::Custom(error as u32),
             _ => Self::Custom(error as u32),
         }
         }
     }
     }

+ 3 - 0
src/sdk/src/lib.rs

@@ -41,3 +41,6 @@ pub use merkle::merkle_add;
 /// Transaction structure
 /// Transaction structure
 pub mod tx;
 pub mod tx;
 pub use tx::ContractCall;
 pub use tx::ContractCall;
+
+/// Utility functions
+pub mod util;

+ 45 - 0
src/sdk/src/util.rs

@@ -0,0 +1,45 @@
+/* This file is part of DarkFi (https://dark.fi)
+ *
+ * Copyright (C) 2020-2023 Dyne.org foundation
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <https://www.gnu.org/licenses/>.
+ */
+
+use super::error::{ContractError, GenericResult};
+
+pub const GET_SYSTEM_TIME_FAILED: i64 = -1;
+
+/// Everyone can call this. Will return current system timestamp.
+///
+/// ```
+/// timestamp = get_system_time();
+/// ```
+pub fn get_system_time() -> GenericResult<i64> {
+    unsafe {
+        let ret = get_system_time_();
+
+        if ret < 0 {
+            match ret {
+                GET_SYSTEM_TIME_FAILED => return Err(ContractError::GetSystemTimeFailed),
+                _ => unimplemented!(),
+            }
+        }
+
+        Ok(ret)
+    }
+}
+
+extern "C" {
+    fn get_system_time_() -> i64;
+}