1#![no_std]
4
5extern crate alloc;
6
7use core::{error::Error, fmt};
8
9use alloc::boxed::Box;
10
11pub struct Report<E = Box<dyn Error>>(E);
13
14impl<E> Report<E>
15where
16 Self: From<E>,
17{
18 pub fn new(error: E) -> Self {
20 Self::from(error)
21 }
22}
23
24impl<E> From<E> for Report<E>
25where
26 E: Error,
27{
28 fn from(error: E) -> Self {
29 Self(error)
30 }
31}
32
33impl<E> fmt::Debug for Report<E>
35where
36 Self: fmt::Display,
37{
38 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
39 fmt::Display::fmt(self, f)
40 }
41}
42
43impl<E> fmt::Display for Report<E>
44where
45 E: Error,
46{
47 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
48 let mut error: &dyn Error = &self.0;
49
50 write!(f, "{error}")?;
51
52 if error.source().is_some() {
53 write!(f, "\n\nCaused by:")?;
54
55 let mut index = 0;
56 while let Some(cause) = error.source() {
57 write!(f, "\n{index: >4}: {cause}")?;
58 error = cause;
59 index += 1;
60 }
61 }
62
63 Ok(())
64 }
65}