commit 5f8ad66aa984f882f4c2d8926c9e15e26f6d5825
parent e4fae9954d20225831248af32972253a3577d25f
Author: parazyd <parazyd@dyne.org>
Date: Tue, 8 Mar 2022 23:32:59 +0100
sdk: Clean up errors.
Diffstat:
2 files changed, 39 insertions(+), 21 deletions(-)
diff --git a/drk-sdk/Cargo.toml b/drk-sdk/Cargo.toml
@@ -4,4 +4,5 @@ version = "0.1.0"
edition = "2021"
[dependencies]
+borsh = "0.9.3"
thiserror = "1.0.30"
diff --git a/drk-sdk/src/error.rs b/drk-sdk/src/error.rs
@@ -1,51 +1,68 @@
+use borsh::maybestd::io::Error as BorshIoError;
use std::result::Result as ResultGeneric;
pub type ContractResult = ResultGeneric<(), ContractError>;
#[derive(Debug, thiserror::Error)]
-#[repr(C)]
pub enum ContractError {
+ /// Allows on-chain programs to implement contract-specific error types and
+ /// see them returned by the runtime. A contract-specific error may be any
+ /// type that is represented as or serialized to an u32 inteter.
+ #[error("Custom contract error: {0:#x}")]
+ Custom(u32),
+
#[error("Internal error")]
Internal,
-
#[error("Out of memory")]
OutOfMemory,
+ #[error("IO error: {0}")]
+ BorshIoError(String),
+}
- #[error("IO error")]
- Io,
-
- #[error("Custom contract error: {0:#x}")]
- Custom(u32),
+/// Builtin return values occupy the upper 32 bits
+const BUILTIN_BIT_SHIFT: usize = 32;
+macro_rules! to_builtin {
+ ($error:expr) => {
+ ($error as u64) << BUILTIN_BIT_SHIFT
+ };
}
-pub const INTERNAL_ERROR: u64 = 1;
-pub const OUT_OF_MEMORY: u64 = 2;
-pub const IO_ERROR: u64 = 3;
+pub const CUSTOM_ZERO: u64 = to_builtin!(1);
+pub const INTERNAL_ERROR: u64 = to_builtin!(2);
+pub const OUT_OF_MEMORY: u64 = to_builtin!(3);
+pub const BORSH_IO_ERROR: u64 = to_builtin!(4);
impl From<ContractError> for u64 {
fn from(err: ContractError) -> Self {
match err {
ContractError::Internal => INTERNAL_ERROR,
ContractError::OutOfMemory => OUT_OF_MEMORY,
- ContractError::Io => IO_ERROR,
- ContractError::Custom(e) => e.into(),
+ ContractError::BorshIoError(_) => BORSH_IO_ERROR,
+ ContractError::Custom(error) => {
+ if error == 0 {
+ CUSTOM_ZERO
+ } else {
+ error as u64
+ }
+ }
}
}
}
impl From<u64> for ContractError {
- fn from(err: u64) -> Self {
- match err {
- INTERNAL_ERROR => ContractError::Internal,
- OUT_OF_MEMORY => ContractError::OutOfMemory,
- IO_ERROR => ContractError::Io,
- e => ContractError::Custom(e.try_into().unwrap()),
+ fn from(error: u64) -> Self {
+ match error {
+ CUSTOM_ZERO => Self::Custom(0),
+ INTERNAL_ERROR => Self::Internal,
+ OUT_OF_MEMORY => Self::OutOfMemory,
+ BORSH_IO_ERROR => Self::BorshIoError("Unknown".to_string()),
+ _ => Self::Custom(error as u32),
}
}
}
-impl From<std::io::Error> for ContractError {
- fn from(_: std::io::Error) -> Self {
- Self::Io
+impl From<BorshIoError> for ContractError {
+ fn from(error: BorshIoError) -> Self {
+ Self::BorshIoError(format!("{}", error))
}
}