ic_dbms_api/memory/
error.rs1use std::array::TryFromSliceError;
2
3use candid::CandidType;
4use serde::{Deserialize, Serialize};
5use thiserror::Error;
6
7use crate::memory::{MSize, Page, PageOffset};
8
9#[derive(Debug, Error, CandidType, Deserialize, Serialize)]
11pub enum MemoryError {
12 #[error("Data too large for page (page size: {page_size}, requested: {requested})")]
14 DataTooLarge { page_size: u64, requested: u64 },
15 #[error("Failed to decode data from bytes: {0}")]
17 DecodeError(DecodeError),
18 #[error("Failed to allocate a new page")]
20 FailedToAllocatePage,
21 #[error("Stable memory access out of bounds")]
23 OutOfBounds,
24 #[error(
26 "Tried to write out of the allocated page (page: {page}, offset: {offset}, data size: {data_size}, page size: {page_size})"
27 )]
28 SegmentationFault {
29 page: Page,
30 offset: PageOffset,
31 data_size: MSize,
32 page_size: u64,
33 },
34 #[error("Failed to grow stable memory: {0}")]
36 StableMemoryError(String),
37}
38
39impl From<ic_cdk::stable::StableMemoryError> for MemoryError {
40 fn from(err: ic_cdk::stable::StableMemoryError) -> Self {
41 MemoryError::StableMemoryError(err.to_string())
42 }
43}
44
45impl From<TryFromSliceError> for MemoryError {
46 fn from(err: TryFromSliceError) -> Self {
47 MemoryError::DecodeError(DecodeError::from(err))
48 }
49}
50
51impl From<std::string::FromUtf8Error> for MemoryError {
52 fn from(err: std::string::FromUtf8Error) -> Self {
53 MemoryError::DecodeError(DecodeError::from(err))
54 }
55}
56
57impl From<candid::types::principal::PrincipalError> for MemoryError {
58 fn from(err: candid::types::principal::PrincipalError) -> Self {
59 MemoryError::DecodeError(DecodeError::from(err))
60 }
61}
62
63impl From<uuid::Error> for MemoryError {
64 fn from(err: uuid::Error) -> Self {
65 MemoryError::DecodeError(DecodeError::from(err))
66 }
67}
68
69#[derive(Debug, Error, CandidType, Deserialize, Serialize)]
71pub enum DecodeError {
72 #[error("Bad raw record header")]
74 BadRawRecordHeader,
75 #[error("Principal error: {0}")]
77 PrincipalError(String),
78 #[error("Failed to convert from slice: {0}")]
80 TryFromSliceError(String),
81 #[error("Failed to convert from UTF-8 string: {0}")]
83 Utf8Error(String),
84 #[error("Data too short to decode")]
86 TooShort,
87 #[error("UUID error: {0}")]
89 UuidError(String),
90}
91
92impl From<uuid::Error> for DecodeError {
93 fn from(err: uuid::Error) -> Self {
94 DecodeError::UuidError(err.to_string())
95 }
96}
97
98impl From<std::string::FromUtf8Error> for DecodeError {
99 fn from(err: std::string::FromUtf8Error) -> Self {
100 DecodeError::Utf8Error(err.to_string())
101 }
102}
103
104impl From<TryFromSliceError> for DecodeError {
105 fn from(err: TryFromSliceError) -> Self {
106 DecodeError::TryFromSliceError(err.to_string())
107 }
108}
109
110impl From<candid::types::principal::PrincipalError> for DecodeError {
111 fn from(err: candid::types::principal::PrincipalError) -> Self {
112 DecodeError::PrincipalError(err.to_string())
113 }
114}
115
116#[cfg(test)]
117mod tests {
118
119 use super::*;
120
121 #[test]
122 fn test_memory_error_display() {
123 let error = MemoryError::DataTooLarge {
124 page_size: 1024,
125 requested: 2048,
126 };
127 assert_eq!(
128 format!("{}", error),
129 "Data too large for page (page size: 1024, requested: 2048)"
130 );
131 }
132
133 #[test]
134 fn test_decode_error_display() {
135 let error = DecodeError::BadRawRecordHeader;
136 assert_eq!(format!("{}", error), "Bad raw record header");
137 }
138}