1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
|
/* -*- Mode: rust; rust-indent-offset: 4 -*- */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
use std::fmt;
/// Helper macro to create an Error that knows which file and line it occurred
/// on. Can optionally have some extra information as a String.
#[macro_export]
macro_rules! error_here {
($error_type:expr) => {
Error::new($error_type, file!(), line!(), None)
};
($error_type:expr, $info:expr) => {
Error::new($error_type, file!(), line!(), Some($info))
};
}
/// Error type for identifying errors in this crate. Use the error_here! macro
/// to instantiate.
#[derive(Debug)]
pub struct Error {
typ: ErrorType,
file: &'static str,
line: u32,
info: Option<String>,
}
impl Error {
pub fn new(typ: ErrorType, file: &'static str, line: u32, info: Option<String>) -> Error {
Error {
typ,
file,
line,
info,
}
}
}
impl fmt::Display for Error {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
if let Some(info) = &self.info {
write!(f, "{} at {}:{} ({})", self.typ, self.file, self.line, info)
} else {
write!(f, "{} at {}:{}", self.typ, self.file, self.line)
}
}
}
impl Clone for Error {
fn clone(&self) -> Self {
Error {
typ: self.typ,
file: self.file,
line: self.line,
info: self.info.as_ref().cloned(),
}
}
fn clone_from(&mut self, source: &Self) {
self.typ = source.typ;
self.file = source.file;
self.line = source.line;
self.info = source.info.as_ref().cloned();
}
}
#[derive(Copy, Clone, Debug)]
pub enum ErrorType {
/// An error in an external library or resource.
ExternalError,
/// Unexpected extra input (e.g. in an ASN.1 encoding).
ExtraInput,
/// Invalid argument.
InvalidArgument,
/// Invalid data input.
InvalidInput,
/// An internal library failure (e.g. an expected invariant failed).
LibraryFailure,
/// Truncated input (e.g. in an ASN.1 encoding).
TruncatedInput,
/// Unsupported input.
UnsupportedInput,
/// A given value could not be represented in the type used for it.
ValueTooLarge,
}
impl fmt::Display for ErrorType {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let error_type_str = match self {
ErrorType::ExternalError => "ExternalError",
ErrorType::ExtraInput => "ExtraInput",
ErrorType::InvalidArgument => "InvalidArgument",
ErrorType::InvalidInput => "InvalidInput",
ErrorType::LibraryFailure => "LibraryFailure",
ErrorType::TruncatedInput => "TruncatedInput",
ErrorType::UnsupportedInput => "UnsupportedInput",
ErrorType::ValueTooLarge => "ValueTooLarge",
};
write!(f, "{}", error_type_str)
}
}
|