use datasize::DataSize;
use thiserror::Error;
use casper_hashing::Digest;
use casper_types::{bytesrepr, system::mint, ApiError, ProtocolVersion};
use crate::{
core::{
engine_state::{genesis::GenesisError, upgrade::ProtocolUpgradeError},
execution,
runtime::stack,
},
shared::wasm_prep,
storage::{self, error::db::DbError, global_state::CommitError},
};
#[derive(Clone, Error, Debug)]
pub enum Error {
#[error("Root not found: {0}")]
RootNotFound(Digest),
#[error("Invalid protocol version: {0}")]
InvalidProtocolVersion(ProtocolVersion),
#[error("{0:?}")]
Genesis(Box<GenesisError>),
#[error("Wasm preprocessing error: {0}")]
WasmPreprocessing(#[from] wasm_prep::PreprocessingError),
#[error("Wasm serialization error: {0:?}")]
WasmSerialization(#[from] parity_wasm::SerializationError),
#[error(transparent)]
Exec(execution::Error),
#[error("Storage error: {0}")]
Storage(#[from] storage::error::Error),
#[error("Authorization failure: not authorized.")]
Authorization,
#[error("Insufficient payment")]
InsufficientPayment,
#[error("Gas conversion overflow")]
GasConversionOverflow,
#[error("Deploy error")]
Deploy,
#[error("Payment finalization error")]
Finalization,
#[error("Bytesrepr error: {0}")]
Bytesrepr(String),
#[error("Mint error: {0}")]
Mint(String),
#[error("Unsupported key type")]
InvalidKeyVariant,
#[error("Protocol upgrade error: {0}")]
ProtocolUpgrade(ProtocolUpgradeError),
#[error("Unsupported deploy item variant: {0}")]
InvalidDeployItemVariant(String),
#[error(transparent)]
CommitError(#[from] CommitError),
#[error("Missing SystemContractRegistry")]
MissingSystemContractRegistry,
#[error("Missing system contract hash: {0}")]
MissingSystemContractHash(String),
#[error("Runtime stack overflow")]
RuntimeStackOverflow,
}
impl Error {
pub fn reverter(api_error: impl Into<ApiError>) -> Error {
Error::Exec(execution::Error::Revert(api_error.into()))
}
}
impl From<execution::Error> for Error {
fn from(error: execution::Error) -> Self {
match error {
execution::Error::WasmPreprocessing(preprocessing_error) => {
Error::WasmPreprocessing(preprocessing_error)
}
_ => Error::Exec(error),
}
}
}
impl From<bytesrepr::Error> for Error {
fn from(error: bytesrepr::Error) -> Self {
Error::Bytesrepr(format!("{}", error))
}
}
impl From<lmdb::Error> for Error {
fn from(error: lmdb::Error) -> Self {
Error::Storage(storage::error::Error::Db(DbError::Lmdb(error)))
}
}
impl From<mint::Error> for Error {
fn from(error: mint::Error) -> Self {
Error::Mint(format!("{}", error))
}
}
impl From<GenesisError> for Error {
fn from(genesis_error: GenesisError) -> Self {
Self::Genesis(Box::new(genesis_error))
}
}
impl From<stack::RuntimeStackOverflow> for Error {
fn from(_: stack::RuntimeStackOverflow) -> Self {
Self::RuntimeStackOverflow
}
}
impl DataSize for Error {
const IS_DYNAMIC: bool = true;
const STATIC_HEAP_SIZE: usize = 0;
#[inline]
fn estimate_heap_size(&self) -> usize {
12 }
}