mirror of
https://github.com/darkrenaissance/darkfi.git
synced 2026-01-09 14:48:08 -05:00
535 lines
13 KiB
Rust
535 lines
13 KiB
Rust
// Hello developer. Please add your error to the according subsection
|
|
// that is commented, or make a new subsection. Keep it clean.
|
|
|
|
/// Main result type used throughout the codebase.
|
|
pub type Result<T> = std::result::Result<T, Error>;
|
|
|
|
/// Result type used in transaction verifications
|
|
pub type VerifyResult<T> = std::result::Result<T, VerifyFailed>;
|
|
|
|
/// Result type used in the Client module
|
|
pub type ClientResult<T> = std::result::Result<T, ClientFailed>;
|
|
|
|
/// General library errors used throughout the codebase.
|
|
#[derive(Debug, Clone, thiserror::Error)]
|
|
pub enum Error {
|
|
// ==============
|
|
// Parsing errors
|
|
// ==============
|
|
#[error("Parse failed: {0}")]
|
|
ParseFailed(&'static str),
|
|
|
|
#[error(transparent)]
|
|
ParseIntError(#[from] std::num::ParseIntError),
|
|
|
|
#[error(transparent)]
|
|
ParseFloatError(#[from] std::num::ParseFloatError),
|
|
|
|
#[cfg(feature = "url")]
|
|
#[error(transparent)]
|
|
UrlParseError(#[from] url::ParseError),
|
|
|
|
#[error("URL parse error: {0}")]
|
|
UrlParse(String),
|
|
|
|
#[error(transparent)]
|
|
AddrParseError(#[from] std::net::AddrParseError),
|
|
|
|
#[error("Could not parse token parameter")]
|
|
TokenParseError,
|
|
|
|
#[error(transparent)]
|
|
TryFromSliceError(#[from] std::array::TryFromSliceError),
|
|
|
|
// ===============
|
|
// Encoding errors
|
|
// ===============
|
|
#[error("decode failed: {0}")]
|
|
DecodeError(&'static str),
|
|
|
|
#[error("encode failed: {0}")]
|
|
EncodeError(&'static str),
|
|
|
|
#[error("VarInt was encoded in a non-minimal way")]
|
|
NonMinimalVarInt,
|
|
|
|
#[error(transparent)]
|
|
Utf8Error(#[from] std::string::FromUtf8Error),
|
|
|
|
#[error(transparent)]
|
|
StrUtf8Error(#[from] std::str::Utf8Error),
|
|
|
|
#[cfg(feature = "serde_json")]
|
|
#[error("serde_json error: {0}")]
|
|
SerdeJsonError(String),
|
|
|
|
#[cfg(feature = "toml")]
|
|
#[error(transparent)]
|
|
TomlDeserializeError(#[from] toml::de::Error),
|
|
|
|
#[cfg(feature = "bs58")]
|
|
#[error(transparent)]
|
|
Bs58DecodeError(#[from] bs58::decode::Error),
|
|
|
|
#[cfg(feature = "hex")]
|
|
#[error(transparent)]
|
|
HexDecodeError(#[from] hex::FromHexError),
|
|
|
|
#[error("Bad operation type byte")]
|
|
BadOperationType,
|
|
|
|
// ======================
|
|
// Network-related errors
|
|
// ======================
|
|
#[error("Unsupported network transport: {0}")]
|
|
UnsupportedTransport(String),
|
|
|
|
#[error("Unsupported network transport upgrade: {0}")]
|
|
UnsupportedTransportUpgrade(String),
|
|
|
|
#[error("Connection failed")]
|
|
ConnectFailed,
|
|
|
|
#[error("Timeout Error")]
|
|
TimeoutError,
|
|
|
|
#[error("Connection timed out")]
|
|
ConnectTimeout,
|
|
|
|
#[error("Channel stopped")]
|
|
ChannelStopped,
|
|
|
|
#[error("Channel timed out")]
|
|
ChannelTimeout,
|
|
|
|
#[error("Network service stopped")]
|
|
NetworkServiceStopped,
|
|
|
|
#[error("Create listener bound to {0} failed")]
|
|
BindFailed(String),
|
|
|
|
#[error("Accept a new incoming connection from the listener {0} failed")]
|
|
AcceptConnectionFailed(String),
|
|
|
|
#[error("Accept a new tls connection from the listener {0} failed")]
|
|
AcceptTlsConnectionFailed(String),
|
|
|
|
#[error("Network operation failed")]
|
|
NetworkOperationFailed,
|
|
|
|
#[error("Malformed packet")]
|
|
MalformedPacket,
|
|
|
|
#[error("Socks proxy error: {0}")]
|
|
SocksError(String),
|
|
|
|
#[error("No Socks5 URL found")]
|
|
NoSocks5UrlFound,
|
|
|
|
#[error("No URL found")]
|
|
NoUrlFound,
|
|
|
|
#[cfg(feature = "tungstenite")]
|
|
#[error("tungstenite error: {0}")]
|
|
TungsteniteError(String),
|
|
|
|
#[error("Tor error: {0}")]
|
|
TorError(String),
|
|
|
|
#[error("Node is not connected to other nodes.")]
|
|
NetworkNotConnected,
|
|
|
|
// =============
|
|
// Crypto errors
|
|
// =============
|
|
#[cfg(feature = "halo2_proofs")]
|
|
#[error("halo2 plonk error: {0}")]
|
|
PlonkError(String),
|
|
|
|
#[error("Unable to decrypt mint note: {0}")]
|
|
NoteDecryptionFailed(String),
|
|
|
|
#[error("No keypair file detected")]
|
|
KeypairPathNotFound,
|
|
|
|
#[error("Failed converting bytes to PublicKey")]
|
|
PublicKeyFromBytes,
|
|
|
|
#[error("Failed converting bytes to SecretKey")]
|
|
SecretKeyFromBytes,
|
|
|
|
#[error("Failed converting b58 string to PublicKey")]
|
|
PublicKeyFromStr,
|
|
|
|
#[error("Failed converting bs58 string to SecretKey")]
|
|
SecretKeyFromStr,
|
|
|
|
#[error("Invalid DarkFi address")]
|
|
InvalidAddress,
|
|
|
|
#[cfg(feature = "futures-rustls")]
|
|
#[error(transparent)]
|
|
RustlsError(#[from] futures_rustls::rustls::Error),
|
|
|
|
#[cfg(feature = "futures-rustls")]
|
|
#[error("Invalid DNS Name {0}")]
|
|
RustlsInvalidDns(String),
|
|
|
|
// =======================
|
|
// Protocol-related errors
|
|
// =======================
|
|
#[error("Unsupported chain")]
|
|
UnsupportedChain,
|
|
|
|
#[error("Unsupported token")]
|
|
UnsupportedToken,
|
|
|
|
#[error("Unsupported coin network")]
|
|
UnsupportedCoinNetwork,
|
|
|
|
#[error("Raft error: {0}")]
|
|
RaftError(String),
|
|
|
|
#[error("JSON-RPC error: {0}")]
|
|
JsonRpcError(String),
|
|
|
|
// ===============
|
|
// Database errors
|
|
// ===============
|
|
#[cfg(feature = "sqlx")]
|
|
#[error("Sqlx error: {0}")]
|
|
SqlxError(String),
|
|
|
|
#[cfg(feature = "sled")]
|
|
#[error(transparent)]
|
|
SledError(#[from] sled::Error),
|
|
|
|
#[error("Transaction {0} not found in database")]
|
|
TransactionNotFound(String),
|
|
|
|
#[error("Header {0} not found in database")]
|
|
HeaderNotFound(String),
|
|
|
|
#[error("Block {0} not found in database")]
|
|
BlockNotFound(String),
|
|
|
|
#[error("Block in slot {0} not found in database")]
|
|
SlotNotFound(u64),
|
|
|
|
#[error("Block {0} metadata not found in database")]
|
|
BlockMetadataNotFound(String),
|
|
|
|
// =============
|
|
// Wallet errors
|
|
// =============
|
|
#[error("Wallet password is empty")]
|
|
WalletEmptyPassword,
|
|
|
|
#[error("Merkle tree already exists in wallet")]
|
|
WalletTreeExists,
|
|
|
|
#[error("Wallet insufficient balance")]
|
|
WalletInsufficientBalance,
|
|
|
|
// ===================
|
|
// wasm runtime errors
|
|
// ===================
|
|
#[cfg(feature = "wasm-runtime")]
|
|
#[error("Wasmer compile error: {0}")]
|
|
WasmerCompileError(String),
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
#[error("Wasmer export error: {0}")]
|
|
WasmerExportError(String),
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
#[error("Wasmer runtime error: {0}")]
|
|
WasmerRuntimeError(String),
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
#[error("Wasmer instantiation error: {0}")]
|
|
WasmerInstantiationError(String),
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
#[error("wasm runtime out of memory")]
|
|
WasmerOomError,
|
|
|
|
// ====================
|
|
// Miscellaneous errors
|
|
// ====================
|
|
#[error("IO error: {0}")]
|
|
Io(std::io::ErrorKind),
|
|
|
|
#[error("Infallible error: {0}")]
|
|
InfallibleError(String),
|
|
|
|
#[cfg(feature = "smol")]
|
|
#[error("async_channel sender error: {0}")]
|
|
AsyncChannelSendError(String),
|
|
|
|
#[cfg(feature = "smol")]
|
|
#[error("async_channel receiver error: {0}")]
|
|
AsyncChannelRecvError(String),
|
|
|
|
#[error("SetLogger (log crate) failed: {0}")]
|
|
SetLoggerError(String),
|
|
|
|
#[error("ValueIsNotObject")]
|
|
ValueIsNotObject,
|
|
|
|
#[error("No config file detected")]
|
|
ConfigNotFound,
|
|
|
|
#[error("Invalid config file detected")]
|
|
ConfigInvalid,
|
|
|
|
#[error("Failed decoding bincode: {0}")]
|
|
ZkasDecoderError(String),
|
|
|
|
#[cfg(feature = "util")]
|
|
#[error("System clock is not correct!")]
|
|
InvalidClock,
|
|
|
|
#[error("Unsupported OS")]
|
|
UnsupportedOS,
|
|
|
|
#[error("System clock went backwards")]
|
|
BackwardsTime(std::time::SystemTimeError),
|
|
|
|
// ==============================================
|
|
// Wrappers for other error types in this library
|
|
// ==============================================
|
|
#[error(transparent)]
|
|
VerifyFailed(#[from] VerifyFailed),
|
|
|
|
#[error(transparent)]
|
|
ClientFailed(#[from] ClientFailed),
|
|
|
|
//=============
|
|
// clock
|
|
//=============
|
|
#[error("clock out of sync with peers: {0}")]
|
|
ClockOutOfSync(String),
|
|
|
|
// ==============
|
|
// DHT errors
|
|
// ==============
|
|
// FIXME: This is out of context, be specific when writing errors.
|
|
#[error("Did not find key")]
|
|
UnknownKey,
|
|
|
|
// Catch-all
|
|
#[error("{0}")]
|
|
Custom(String),
|
|
}
|
|
|
|
/// Transaction verification errors
|
|
#[derive(Debug, Clone, thiserror::Error)]
|
|
pub enum VerifyFailed {
|
|
#[error("Transaction has no inputs")]
|
|
LackingInputs,
|
|
|
|
#[error("Transaction has no outputs")]
|
|
LackingOutputs,
|
|
|
|
#[error("Invalid cashier/faucet public key for clear input {0}")]
|
|
InvalidCashierOrFaucetKey(usize),
|
|
|
|
#[error("Invalid Merkle root for input {0}")]
|
|
InvalidMerkle(usize),
|
|
|
|
#[error("Nullifier already exists for input {0}")]
|
|
NullifierExists(usize),
|
|
|
|
#[error("Invalid signature for input {0}")]
|
|
InputSignature(usize),
|
|
|
|
#[error("Invalid signature for clear input {0}")]
|
|
ClearInputSignature(usize),
|
|
|
|
#[error("Token commitments in inputs or outputs to not match")]
|
|
TokenMismatch,
|
|
|
|
#[error("Money in does not match money out (value commitments)")]
|
|
MissingFunds,
|
|
|
|
#[error("Mint proof verification failure for input {0}")]
|
|
MintProof(usize),
|
|
|
|
#[error("Burn proof verification failure for input {0}")]
|
|
BurnProof(usize),
|
|
|
|
#[error("Failed verifying zk proofs: {0}")]
|
|
ProofVerifyFailed(String),
|
|
|
|
#[error("Internal error: {0}")]
|
|
InternalError(String),
|
|
}
|
|
|
|
/// Client module errors
|
|
#[derive(Debug, Clone, thiserror::Error)]
|
|
pub enum ClientFailed {
|
|
#[error("IO error: {0}")]
|
|
Io(std::io::ErrorKind),
|
|
|
|
#[error("Not enough value: {0}")]
|
|
NotEnoughValue(u64),
|
|
|
|
#[error("Invalid address: {0}")]
|
|
InvalidAddress(String),
|
|
|
|
#[error("Invalid amount: {0}")]
|
|
InvalidAmount(u64),
|
|
|
|
#[error("Internal error: {0}")]
|
|
InternalError(String),
|
|
|
|
#[error("Verify error: {0}")]
|
|
VerifyError(String),
|
|
}
|
|
|
|
impl From<Error> for VerifyFailed {
|
|
fn from(err: Error) -> Self {
|
|
Self::InternalError(err.to_string())
|
|
}
|
|
}
|
|
|
|
impl From<Error> for ClientFailed {
|
|
fn from(err: Error) -> Self {
|
|
Self::InternalError(err.to_string())
|
|
}
|
|
}
|
|
|
|
impl From<VerifyFailed> for ClientFailed {
|
|
fn from(err: VerifyFailed) -> Self {
|
|
Self::VerifyError(err.to_string())
|
|
}
|
|
}
|
|
|
|
impl From<std::io::Error> for ClientFailed {
|
|
fn from(err: std::io::Error) -> Self {
|
|
Self::Io(err.kind())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "async-std")]
|
|
impl From<async_std::future::TimeoutError> for Error {
|
|
fn from(_err: async_std::future::TimeoutError) -> Self {
|
|
Self::TimeoutError
|
|
}
|
|
}
|
|
|
|
impl From<std::io::Error> for Error {
|
|
fn from(err: std::io::Error) -> Self {
|
|
Self::Io(err.kind())
|
|
}
|
|
}
|
|
|
|
impl From<std::time::SystemTimeError> for Error {
|
|
fn from(err: std::time::SystemTimeError) -> Self {
|
|
Self::BackwardsTime(err)
|
|
}
|
|
}
|
|
|
|
impl From<std::convert::Infallible> for Error {
|
|
fn from(err: std::convert::Infallible) -> Self {
|
|
Self::InfallibleError(err.to_string())
|
|
}
|
|
}
|
|
|
|
impl From<()> for Error {
|
|
fn from(_err: ()) -> Self {
|
|
Self::InfallibleError("Infallible".into())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "smol")]
|
|
impl<T> From<smol::channel::SendError<T>> for Error {
|
|
fn from(err: smol::channel::SendError<T>) -> Self {
|
|
Self::AsyncChannelSendError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "smol")]
|
|
impl From<smol::channel::RecvError> for Error {
|
|
fn from(err: smol::channel::RecvError) -> Self {
|
|
Self::AsyncChannelRecvError(err.to_string())
|
|
}
|
|
}
|
|
|
|
impl From<log::SetLoggerError> for Error {
|
|
fn from(err: log::SetLoggerError) -> Self {
|
|
Self::SetLoggerError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "sqlx")]
|
|
impl From<sqlx::error::Error> for Error {
|
|
fn from(err: sqlx::error::Error) -> Self {
|
|
Self::SqlxError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "halo2_proofs")]
|
|
impl From<halo2_proofs::plonk::Error> for Error {
|
|
fn from(err: halo2_proofs::plonk::Error) -> Self {
|
|
Self::PlonkError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "tungstenite")]
|
|
impl From<tungstenite::Error> for Error {
|
|
fn from(err: tungstenite::Error) -> Self {
|
|
Self::TungsteniteError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "futures-rustls")]
|
|
impl From<futures_rustls::rustls::client::InvalidDnsNameError> for Error {
|
|
fn from(err: futures_rustls::rustls::client::InvalidDnsNameError) -> Self {
|
|
Self::RustlsInvalidDns(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "serde_json")]
|
|
impl From<serde_json::Error> for Error {
|
|
fn from(err: serde_json::Error) -> Self {
|
|
Self::SerdeJsonError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "fast-socks5")]
|
|
impl From<fast_socks5::SocksError> for Error {
|
|
fn from(err: fast_socks5::SocksError) -> Self {
|
|
Self::SocksError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
impl From<wasmer::CompileError> for Error {
|
|
fn from(err: wasmer::CompileError) -> Self {
|
|
Self::WasmerCompileError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
impl From<wasmer::ExportError> for Error {
|
|
fn from(err: wasmer::ExportError) -> Self {
|
|
Self::WasmerExportError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
impl From<wasmer::RuntimeError> for Error {
|
|
fn from(err: wasmer::RuntimeError) -> Self {
|
|
Self::WasmerRuntimeError(err.to_string())
|
|
}
|
|
}
|
|
|
|
#[cfg(feature = "wasm-runtime")]
|
|
impl From<wasmer::InstantiationError> for Error {
|
|
fn from(err: wasmer::InstantiationError) -> Self {
|
|
Self::WasmerInstantiationError(err.to_string())
|
|
}
|
|
}
|