1use casper_types::bytesrepr::Error as BytesReprError;
2use casper_types::{CLType, CLValueError};
3use core::any::Any;
4
5use crate::arithmetic::ArithmeticsError;
6use crate::prelude::*;
7use crate::VmError::Serialization;
8
9#[repr(u16)]
11#[derive(Clone, Debug, PartialEq)]
12pub enum OdraError {
13 ExecutionError(ExecutionError),
15 VmError(VmError)
17}
18
19impl OdraError {
20 pub fn code(&self) -> u16 {
22 match self {
23 OdraError::ExecutionError(e) => e.code(),
24 OdraError::VmError(_e) => 0
25 }
26 }
27
28 pub fn user(code: u16) -> Self {
30 if code >= ExecutionError::UserErrorTooHigh.code() {
31 ExecutionError::UserErrorTooHigh.into()
32 } else {
33 ExecutionError::User(code).into()
34 }
35 }
36}
37
38impl From<ArithmeticsError> for ExecutionError {
39 fn from(error: ArithmeticsError) -> Self {
40 match error {
41 ArithmeticsError::AdditionOverflow => Self::AdditionOverflow,
42 ArithmeticsError::SubtractingOverflow => Self::SubtractionOverflow,
43 ArithmeticsError::ConversionError => Self::ConversionError
44 }
45 }
46}
47
48impl From<ArithmeticsError> for OdraError {
49 fn from(error: ArithmeticsError) -> Self {
50 Into::<ExecutionError>::into(error).into()
51 }
52}
53
54impl From<Box<dyn Any + Send>> for OdraError {
55 fn from(_: Box<dyn Any + Send>) -> Self {
56 OdraError::VmError(VmError::Panic)
57 }
58}
59
60impl From<casper_types::bytesrepr::Error> for ExecutionError {
61 fn from(error: casper_types::bytesrepr::Error) -> Self {
62 match error {
63 casper_types::bytesrepr::Error::EarlyEndOfStream => Self::EarlyEndOfStream,
64 casper_types::bytesrepr::Error::Formatting => Self::Formatting,
65 casper_types::bytesrepr::Error::LeftOverBytes => Self::LeftOverBytes,
66 casper_types::bytesrepr::Error::OutOfMemory => Self::OutOfMemory,
67 casper_types::bytesrepr::Error::NotRepresentable => Self::NotRepresentable,
68 casper_types::bytesrepr::Error::ExceededRecursionDepth => Self::ExceededRecursionDepth,
69 _ => Self::Formatting
70 }
71 }
72}
73
74#[repr(u16)]
84#[derive(Clone, Copy, Debug, PartialEq)]
85pub enum ExecutionError {
86 UnwrapError = 1,
88 UnexpectedError = 2,
90 AdditionOverflow = 100,
92 SubtractionOverflow = 101,
94 NonPayable = 102,
96 TransferToContract = 103,
98 ReentrantCall = 104,
100 ContractAlreadyInstalled = 105,
102 UnknownConstructor = 106,
104 NativeTransferError = 107,
106 IndexOutOfBounds = 108,
108 ZeroAddress = 109,
110 AddressCreationFailed = 110,
112 EarlyEndOfStream = 111,
114 Formatting = 112,
116 LeftOverBytes = 113,
118 OutOfMemory = 114,
120 NotRepresentable = 115,
122 ExceededRecursionDepth = 116,
124 KeyNotFound = 117,
126 CouldNotDeserializeSignature = 118,
128 TypeMismatch = 119,
130 CouldNotSignMessage = 120,
132 EmptyDictionaryName = 121,
134 MissingArg = 122,
136 MissingAddress = 123,
138 OutOfGas = 124,
140 MainPurseError = 125,
142 ConversionError = 126,
144 ContractDeploymentError = 127,
146 CannotExtractCallerInfo = 128,
148 MaxUserError = 64535,
150 UserErrorTooHigh = 64536,
152 User(u16)
154}
155
156impl ExecutionError {
157 pub fn code(&self) -> u16 {
159 unsafe {
160 match self {
161 ExecutionError::User(code) => *code,
162 ExecutionError::MaxUserError => 64535,
163 ExecutionError::UserErrorTooHigh => 64536,
164 _ => ExecutionError::UserErrorTooHigh.code() + *(self as *const Self as *const u16)
165 }
166 }
167 }
168}
169
170impl From<ExecutionError> for OdraError {
171 fn from(error: ExecutionError) -> Self {
172 Self::ExecutionError(error)
173 }
174}
175
176#[derive(Clone, Debug, PartialEq, Eq)]
178pub enum VmError {
179 Serialization,
181 Deserialization,
183 BalanceExceeded,
185 NoSuchMethod(String),
187 InvalidContractAddress,
189 InvalidContext,
191 TypeMismatch {
193 expected: CLType,
195 found: CLType
197 },
198 Other(String),
200 Panic
202}
203
204pub enum CollectionError {
206 IndexOutOfBounds
208}
209
210impl From<CollectionError> for ExecutionError {
211 fn from(error: CollectionError) -> Self {
212 match error {
213 CollectionError::IndexOutOfBounds => Self::IndexOutOfBounds
214 }
215 }
216}
217
218impl From<CollectionError> for OdraError {
219 fn from(error: CollectionError) -> Self {
220 Into::<ExecutionError>::into(error).into()
221 }
222}
223
224#[derive(Clone, Debug, PartialEq)]
226pub enum AddressError {
227 ZeroAddress,
229 AddressCreationError
231}
232
233impl From<AddressError> for ExecutionError {
234 fn from(error: AddressError) -> Self {
235 match error {
236 AddressError::ZeroAddress => Self::ZeroAddress,
237 AddressError::AddressCreationError => Self::AddressCreationFailed
238 }
239 }
240}
241
242impl From<AddressError> for OdraError {
243 fn from(error: AddressError) -> Self {
244 Into::<ExecutionError>::into(error).into()
245 }
246}
247
248#[derive(Debug, PartialEq, Eq, PartialOrd)]
250pub enum EventError {
251 UnexpectedType(String),
253 IndexOutOfBounds,
255 Formatting,
257 Parsing,
259 CouldntExtractName,
261 CouldntExtractEventData,
263 ContractDoesntSupportEvents,
265 TriedToQueryEventForNonContract
267}
268
269pub type OdraResult<T> = Result<T, OdraError>;
271
272impl From<CLValueError> for OdraError {
273 fn from(error: CLValueError) -> Self {
274 match error {
275 CLValueError::Serialization(_) => OdraError::VmError(Serialization),
276 CLValueError::Type(cl_type_mismatch) => OdraError::VmError(VmError::TypeMismatch {
277 expected: cl_type_mismatch.expected.clone(),
278 found: cl_type_mismatch.found.clone()
279 })
280 }
281 }
282}
283
284impl From<BytesReprError> for OdraError {
285 fn from(error: BytesReprError) -> Self {
286 match error {
287 BytesReprError::EarlyEndOfStream => ExecutionError::EarlyEndOfStream,
288 BytesReprError::Formatting => ExecutionError::Formatting,
289 BytesReprError::LeftOverBytes => ExecutionError::LeftOverBytes,
290 BytesReprError::OutOfMemory => ExecutionError::OutOfMemory,
291 BytesReprError::NotRepresentable => ExecutionError::NotRepresentable,
292 BytesReprError::ExceededRecursionDepth => ExecutionError::ExceededRecursionDepth,
293 _ => ExecutionError::Formatting
294 }
295 .into()
296 }
297}
298
299impl From<anyhow::Error> for OdraError {
300 fn from(value: anyhow::Error) -> Self {
301 OdraError::VmError(VmError::Other(value.to_string()))
302 }
303}