1use std::{
2 fmt,
3 fmt::Display,
4};
5
6use failure::{
7 Context,
8 Fail,
9 Backtrace,
10};
11
12#[derive(Debug)]
13pub struct RustepError {
14 inner: Context<RustepErrorKind>
15}
16
17#[derive(Copy, Clone, Eq, PartialEq, Debug, Fail)]
18pub enum RustepErrorKind {
19 #[fail(display = "Unsupported ELF class value {}", _0)]
20 UnsupportedElfClass(u8),
21 #[fail(display = "Parsing error")]
22 Parse,
23 #[fail(display = "Not enough byte, {} bytes needed", _0)]
24 Incomplete(usize),
25 #[fail(display = "Not enough byte, unknown bytes needed")]
26 IncompleteUnknown,
27 #[fail(display = "Segment type {} not resolved", _0)]
28 SegmentType(u64),
29 #[fail(display = "Section type {} not resolved", _0)]
30 SectionType(u64),
31 #[fail(display = "Segment flag {} invalid", _0)]
32 SegmentFlag(u64),
33 #[fail(display = "Section flag {} invalid", _0)]
34 SectionFlag(u64),
35 #[fail(display = "Unknown elf type {}", _0)]
36 ElfType(u64),
37 #[fail(display = "Unknown elf machine {}", _0)]
38 ElfMachine(u64),
39 #[fail(display = "Not an Elf file")]
40 NotElf,
41}
42
43impl Fail for RustepError {
44 fn cause(&self) -> Option<&Fail> {
45 self.inner.cause()
46 }
47
48 fn backtrace(&self) -> Option<&Backtrace> {
49 self.inner.backtrace()
50 }
51}
52
53impl Display for RustepError {
54 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
55 Display::fmt(&self.inner, f)
56 }
57}
58
59impl RustepError {
60 pub fn kind(&self) -> RustepErrorKind {
61 *self.inner.get_context()
62 }
63}
64
65impl From<RustepErrorKind> for RustepError {
66 fn from(kind: RustepErrorKind) -> RustepError {
67 RustepError { inner: Context::new(kind) }
68 }
69}
70
71impl From<Context<RustepErrorKind>> for RustepError {
72 fn from(inner: Context<RustepErrorKind>) -> RustepError {
73 RustepError { inner: inner }
74 }
75}
76
77macro_rules! nom_try {
91
92 ($arg:expr) => {
93 match $arg {
94 Done(_i, res) => {
95 res
96 },
97 Error(e) => {
98 Err(format_err!("Parse Error {}", e.to_string()).context(RustepErrorKind::Parse))?
99 },
100 Incomplete(needed) => {
101 match needed {
102 Size(s) => Err(RustepErrorKind::Incomplete(s))?,
103 Unknown => Err(RustepErrorKind::IncompleteUnknown)?,
104 }
105 }
106 }
107 }
108}