anyhow/
error.rs

1use crate::backtrace::Backtrace;
2use crate::chain::Chain;
3#[cfg(any(feature = "std", not(anyhow_no_core_error), anyhow_no_ptr_addr_of))]
4use crate::ptr::Mut;
5use crate::ptr::{Own, Ref};
6use crate::{Error, StdError};
7use alloc::boxed::Box;
8use core::any::TypeId;
9#[cfg(error_generic_member_access)]
10use core::error::{self, Request};
11use core::fmt::{self, Debug, Display};
12use core::mem::ManuallyDrop;
13#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
14use core::ops::{Deref, DerefMut};
15#[cfg(not(anyhow_no_core_unwind_safe))]
16use core::panic::{RefUnwindSafe, UnwindSafe};
17#[cfg(not(anyhow_no_ptr_addr_of))]
18use core::ptr;
19use core::ptr::NonNull;
20#[cfg(all(feature = "std", anyhow_no_core_unwind_safe))]
21use std::panic::{RefUnwindSafe, UnwindSafe};
22
23impl Error {
24    /// Create a new error object from any error type.
25    ///
26    /// The error type must be threadsafe and `'static`, so that the `Error`
27    /// will be as well.
28    ///
29    /// If the error type does not provide a backtrace, a backtrace will be
30    /// created here to ensure that a backtrace exists.
31    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
32    #[cold]
33    #[must_use]
34    pub fn new<E>(error: E) -> Self
35    where
36        E: StdError + Send + Sync + 'static,
37    {
38        let backtrace = backtrace_if_absent!(&error);
39        Error::construct_from_std(error, backtrace)
40    }
41
42    /// Create a new error object from a printable error message.
43    ///
44    /// If the argument implements std::error::Error, prefer `Error::new`
45    /// instead which preserves the underlying error's cause chain and
46    /// backtrace. If the argument may or may not implement std::error::Error
47    /// now or in the future, use `anyhow!(err)` which handles either way
48    /// correctly.
49    ///
50    /// `Error::msg("...")` is equivalent to `anyhow!("...")` but occasionally
51    /// convenient in places where a function is preferable over a macro, such
52    /// as iterator or stream combinators:
53    ///
54    /// ```
55    /// # mod ffi {
56    /// #     pub struct Input;
57    /// #     pub struct Output;
58    /// #     pub async fn do_some_work(_: Input) -> Result<Output, &'static str> {
59    /// #         unimplemented!()
60    /// #     }
61    /// # }
62    /// #
63    /// # use ffi::{Input, Output};
64    /// #
65    /// use anyhow::{Error, Result};
66    /// use futures::stream::{Stream, StreamExt, TryStreamExt};
67    ///
68    /// async fn demo<S>(stream: S) -> Result<Vec<Output>>
69    /// where
70    ///     S: Stream<Item = Input>,
71    /// {
72    ///     stream
73    ///         .then(ffi::do_some_work) // returns Result<Output, &str>
74    ///         .map_err(Error::msg)
75    ///         .try_collect()
76    ///         .await
77    /// }
78    /// ```
79    #[cold]
80    #[must_use]
81    pub fn msg<M>(message: M) -> Self
82    where
83        M: Display + Debug + Send + Sync + 'static,
84    {
85        Error::construct_from_adhoc(message, backtrace!())
86    }
87
88    /// Construct an error object from a type-erased standard library error.
89    ///
90    /// This is mostly useful for interop with other error libraries.
91    ///
92    /// # Example
93    ///
94    /// Here is a skeleton of a library that provides its own error abstraction.
95    /// The pair of `From` impls provide bidirectional support for `?`
96    /// conversion between `Report` and `anyhow::Error`.
97    ///
98    /// ```
99    /// use std::error::Error as StdError;
100    ///
101    /// pub struct Report {/* ... */}
102    ///
103    /// impl<E> From<E> for Report
104    /// where
105    ///     E: Into<anyhow::Error>,
106    ///     Result<(), E>: anyhow::Context<(), E>,
107    /// {
108    ///     fn from(error: E) -> Self {
109    ///         let anyhow_error: anyhow::Error = error.into();
110    ///         let boxed_error: Box<dyn StdError + Send + Sync + 'static> = anyhow_error.into();
111    ///         Report::from_boxed(boxed_error)
112    ///     }
113    /// }
114    ///
115    /// impl From<Report> for anyhow::Error {
116    ///     fn from(report: Report) -> Self {
117    ///         let boxed_error: Box<dyn StdError + Send + Sync + 'static> = report.into_boxed();
118    ///         anyhow::Error::from_boxed(boxed_error)
119    ///     }
120    /// }
121    ///
122    /// impl Report {
123    ///     fn from_boxed(boxed_error: Box<dyn StdError + Send + Sync + 'static>) -> Self {
124    ///         todo!()
125    ///     }
126    ///     fn into_boxed(self) -> Box<dyn StdError + Send + Sync + 'static> {
127    ///         todo!()
128    ///     }
129    /// }
130    ///
131    /// // Example usage: can use `?` in both directions.
132    /// fn a() -> anyhow::Result<()> {
133    ///     b()?;
134    ///     Ok(())
135    /// }
136    /// fn b() -> Result<(), Report> {
137    ///     a()?;
138    ///     Ok(())
139    /// }
140    /// ```
141    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
142    #[cold]
143    #[must_use]
144    pub fn from_boxed(boxed_error: Box<dyn StdError + Send + Sync + 'static>) -> Self {
145        let backtrace = backtrace_if_absent!(&*boxed_error);
146        Error::construct_from_boxed(boxed_error, backtrace)
147    }
148
149    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
150    #[cold]
151    pub(crate) fn construct_from_std<E>(error: E, backtrace: Option<Backtrace>) -> Self
152    where
153        E: StdError + Send + Sync + 'static,
154    {
155        let vtable = &ErrorVTable {
156            object_drop: object_drop::<E>,
157            object_ref: object_ref::<E>,
158            #[cfg(anyhow_no_ptr_addr_of)]
159            object_mut: object_mut::<E>,
160            object_boxed: object_boxed::<E>,
161            object_downcast: object_downcast::<E>,
162            #[cfg(anyhow_no_ptr_addr_of)]
163            object_downcast_mut: object_downcast_mut::<E>,
164            object_drop_rest: object_drop_front::<E>,
165            #[cfg(all(
166                not(error_generic_member_access),
167                any(std_backtrace, feature = "backtrace")
168            ))]
169            object_backtrace: no_backtrace,
170        };
171
172        // Safety: passing vtable that operates on the right type E.
173        unsafe { Error::construct(error, vtable, backtrace) }
174    }
175
176    #[cold]
177    pub(crate) fn construct_from_adhoc<M>(message: M, backtrace: Option<Backtrace>) -> Self
178    where
179        M: Display + Debug + Send + Sync + 'static,
180    {
181        use crate::wrapper::MessageError;
182        let error: MessageError<M> = MessageError(message);
183        let vtable = &ErrorVTable {
184            object_drop: object_drop::<MessageError<M>>,
185            object_ref: object_ref::<MessageError<M>>,
186            #[cfg(all(any(feature = "std", not(anyhow_no_core_error)), anyhow_no_ptr_addr_of))]
187            object_mut: object_mut::<MessageError<M>>,
188            object_boxed: object_boxed::<MessageError<M>>,
189            object_downcast: object_downcast::<M>,
190            #[cfg(anyhow_no_ptr_addr_of)]
191            object_downcast_mut: object_downcast_mut::<M>,
192            object_drop_rest: object_drop_front::<M>,
193            #[cfg(all(
194                not(error_generic_member_access),
195                any(std_backtrace, feature = "backtrace")
196            ))]
197            object_backtrace: no_backtrace,
198        };
199
200        // Safety: MessageError is repr(transparent) so it is okay for the
201        // vtable to allow casting the MessageError<M> to M.
202        unsafe { Error::construct(error, vtable, backtrace) }
203    }
204
205    #[cold]
206    pub(crate) fn construct_from_display<M>(message: M, backtrace: Option<Backtrace>) -> Self
207    where
208        M: Display + Send + Sync + 'static,
209    {
210        use crate::wrapper::DisplayError;
211        let error: DisplayError<M> = DisplayError(message);
212        let vtable = &ErrorVTable {
213            object_drop: object_drop::<DisplayError<M>>,
214            object_ref: object_ref::<DisplayError<M>>,
215            #[cfg(all(any(feature = "std", not(anyhow_no_core_error)), anyhow_no_ptr_addr_of))]
216            object_mut: object_mut::<DisplayError<M>>,
217            object_boxed: object_boxed::<DisplayError<M>>,
218            object_downcast: object_downcast::<M>,
219            #[cfg(anyhow_no_ptr_addr_of)]
220            object_downcast_mut: object_downcast_mut::<M>,
221            object_drop_rest: object_drop_front::<M>,
222            #[cfg(all(
223                not(error_generic_member_access),
224                any(std_backtrace, feature = "backtrace")
225            ))]
226            object_backtrace: no_backtrace,
227        };
228
229        // Safety: DisplayError is repr(transparent) so it is okay for the
230        // vtable to allow casting the DisplayError<M> to M.
231        unsafe { Error::construct(error, vtable, backtrace) }
232    }
233
234    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
235    #[cold]
236    pub(crate) fn construct_from_context<C, E>(
237        context: C,
238        error: E,
239        backtrace: Option<Backtrace>,
240    ) -> Self
241    where
242        C: Display + Send + Sync + 'static,
243        E: StdError + Send + Sync + 'static,
244    {
245        let error: ContextError<C, E> = ContextError { context, error };
246
247        let vtable = &ErrorVTable {
248            object_drop: object_drop::<ContextError<C, E>>,
249            object_ref: object_ref::<ContextError<C, E>>,
250            #[cfg(anyhow_no_ptr_addr_of)]
251            object_mut: object_mut::<ContextError<C, E>>,
252            object_boxed: object_boxed::<ContextError<C, E>>,
253            object_downcast: context_downcast::<C, E>,
254            #[cfg(anyhow_no_ptr_addr_of)]
255            object_downcast_mut: context_downcast_mut::<C, E>,
256            object_drop_rest: context_drop_rest::<C, E>,
257            #[cfg(all(
258                not(error_generic_member_access),
259                any(std_backtrace, feature = "backtrace")
260            ))]
261            object_backtrace: no_backtrace,
262        };
263
264        // Safety: passing vtable that operates on the right type.
265        unsafe { Error::construct(error, vtable, backtrace) }
266    }
267
268    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
269    #[cold]
270    pub(crate) fn construct_from_boxed(
271        error: Box<dyn StdError + Send + Sync>,
272        backtrace: Option<Backtrace>,
273    ) -> Self {
274        use crate::wrapper::BoxedError;
275        let error = BoxedError(error);
276        let vtable = &ErrorVTable {
277            object_drop: object_drop::<BoxedError>,
278            object_ref: object_ref::<BoxedError>,
279            #[cfg(anyhow_no_ptr_addr_of)]
280            object_mut: object_mut::<BoxedError>,
281            object_boxed: object_boxed::<BoxedError>,
282            object_downcast: object_downcast::<Box<dyn StdError + Send + Sync>>,
283            #[cfg(anyhow_no_ptr_addr_of)]
284            object_downcast_mut: object_downcast_mut::<Box<dyn StdError + Send + Sync>>,
285            object_drop_rest: object_drop_front::<Box<dyn StdError + Send + Sync>>,
286            #[cfg(all(
287                not(error_generic_member_access),
288                any(std_backtrace, feature = "backtrace")
289            ))]
290            object_backtrace: no_backtrace,
291        };
292
293        // Safety: BoxedError is repr(transparent) so it is okay for the vtable
294        // to allow casting to Box<dyn StdError + Send + Sync>.
295        unsafe { Error::construct(error, vtable, backtrace) }
296    }
297
298    // Takes backtrace as argument rather than capturing it here so that the
299    // user sees one fewer layer of wrapping noise in the backtrace.
300    //
301    // Unsafe because the given vtable must have sensible behavior on the error
302    // value of type E.
303    #[cold]
304    unsafe fn construct<E>(
305        error: E,
306        vtable: &'static ErrorVTable,
307        backtrace: Option<Backtrace>,
308    ) -> Self
309    where
310        E: StdError + Send + Sync + 'static,
311    {
312        let inner: Box<ErrorImpl<E>> = Box::new(ErrorImpl {
313            vtable,
314            backtrace,
315            _object: error,
316        });
317        // Erase the concrete type of E from the compile-time type system. This
318        // is equivalent to the safe unsize coercion from Box<ErrorImpl<E>> to
319        // Box<ErrorImpl<dyn StdError + Send + Sync + 'static>> except that the
320        // result is a thin pointer. The necessary behavior for manipulating the
321        // underlying ErrorImpl<E> is preserved in the vtable provided by the
322        // caller rather than a builtin fat pointer vtable.
323        let inner = Own::new(inner).cast::<ErrorImpl>();
324        Error { inner }
325    }
326
327    /// Wrap the error value with additional context.
328    ///
329    /// For attaching context to a `Result` as it is propagated, the
330    /// [`Context`][crate::Context] extension trait may be more convenient than
331    /// this function.
332    ///
333    /// The primary reason to use `error.context(...)` instead of
334    /// `result.context(...)` via the `Context` trait would be if the context
335    /// needs to depend on some data held by the underlying error:
336    ///
337    /// ```
338    /// # use std::fmt::{self, Debug, Display};
339    /// #
340    /// # type T = ();
341    /// #
342    /// # impl std::error::Error for ParseError {}
343    /// # impl Debug for ParseError {
344    /// #     fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
345    /// #         unimplemented!()
346    /// #     }
347    /// # }
348    /// # impl Display for ParseError {
349    /// #     fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
350    /// #         unimplemented!()
351    /// #     }
352    /// # }
353    /// #
354    /// use anyhow::Result;
355    /// use std::fs::File;
356    /// use std::path::Path;
357    ///
358    /// struct ParseError {
359    ///     line: usize,
360    ///     column: usize,
361    /// }
362    ///
363    /// fn parse_impl(file: File) -> Result<T, ParseError> {
364    ///     # const IGNORE: &str = stringify! {
365    ///     ...
366    ///     # };
367    ///     # unimplemented!()
368    /// }
369    ///
370    /// pub fn parse(path: impl AsRef<Path>) -> Result<T> {
371    ///     let file = File::open(&path)?;
372    ///     parse_impl(file).map_err(|error| {
373    ///         let context = format!(
374    ///             "only the first {} lines of {} are valid",
375    ///             error.line, path.as_ref().display(),
376    ///         );
377    ///         anyhow::Error::new(error).context(context)
378    ///     })
379    /// }
380    /// ```
381    #[cold]
382    #[must_use]
383    pub fn context<C>(self, context: C) -> Self
384    where
385        C: Display + Send + Sync + 'static,
386    {
387        let error: ContextError<C, Error> = ContextError {
388            context,
389            error: self,
390        };
391
392        let vtable = &ErrorVTable {
393            object_drop: object_drop::<ContextError<C, Error>>,
394            object_ref: object_ref::<ContextError<C, Error>>,
395            #[cfg(all(any(feature = "std", not(anyhow_no_core_error)), anyhow_no_ptr_addr_of))]
396            object_mut: object_mut::<ContextError<C, Error>>,
397            object_boxed: object_boxed::<ContextError<C, Error>>,
398            object_downcast: context_chain_downcast::<C>,
399            #[cfg(anyhow_no_ptr_addr_of)]
400            object_downcast_mut: context_chain_downcast_mut::<C>,
401            object_drop_rest: context_chain_drop_rest::<C>,
402            #[cfg(all(
403                not(error_generic_member_access),
404                any(std_backtrace, feature = "backtrace")
405            ))]
406            object_backtrace: context_backtrace::<C>,
407        };
408
409        // As the cause is anyhow::Error, we already have a backtrace for it.
410        let backtrace = None;
411
412        // Safety: passing vtable that operates on the right type.
413        unsafe { Error::construct(error, vtable, backtrace) }
414    }
415
416    /// Get the backtrace for this Error.
417    ///
418    /// In order for the backtrace to be meaningful, one of the two environment
419    /// variables `RUST_LIB_BACKTRACE=1` or `RUST_BACKTRACE=1` must be defined
420    /// and `RUST_LIB_BACKTRACE` must not be `0`. Backtraces are somewhat
421    /// expensive to capture in Rust, so we don't necessarily want to be
422    /// capturing them all over the place all the time.
423    ///
424    /// - If you want panics and errors to both have backtraces, set
425    ///   `RUST_BACKTRACE=1`;
426    /// - If you want only errors to have backtraces, set
427    ///   `RUST_LIB_BACKTRACE=1`;
428    /// - If you want only panics to have backtraces, set `RUST_BACKTRACE=1` and
429    ///   `RUST_LIB_BACKTRACE=0`.
430    ///
431    /// # Stability
432    ///
433    /// Standard library backtraces are only available when using Rust &ge;
434    /// 1.65. On older compilers, this function is only available if the crate's
435    /// "backtrace" feature is enabled, and will use the `backtrace` crate as
436    /// the underlying backtrace implementation. The return type of this
437    /// function on old compilers is `&(impl Debug + Display)`.
438    ///
439    /// ```toml
440    /// [dependencies]
441    /// anyhow = { version = "1.0", features = ["backtrace"] }
442    /// ```
443    #[cfg(any(std_backtrace, feature = "backtrace"))]
444    pub fn backtrace(&self) -> &impl_backtrace!() {
445        unsafe { ErrorImpl::backtrace(self.inner.by_ref()) }
446    }
447
448    /// An iterator of the chain of source errors contained by this Error.
449    ///
450    /// This iterator will visit every error in the cause chain of this error
451    /// object, beginning with the error that this error object was created
452    /// from.
453    ///
454    /// # Example
455    ///
456    /// ```
457    /// use anyhow::Error;
458    /// use std::io;
459    ///
460    /// pub fn underlying_io_error_kind(error: &Error) -> Option<io::ErrorKind> {
461    ///     for cause in error.chain() {
462    ///         if let Some(io_error) = cause.downcast_ref::<io::Error>() {
463    ///             return Some(io_error.kind());
464    ///         }
465    ///     }
466    ///     None
467    /// }
468    /// ```
469    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
470    #[cold]
471    pub fn chain(&self) -> Chain {
472        unsafe { ErrorImpl::chain(self.inner.by_ref()) }
473    }
474
475    /// The lowest level cause of this error &mdash; this error's cause's
476    /// cause's cause etc.
477    ///
478    /// The root cause is the last error in the iterator produced by
479    /// [`chain()`][Error::chain].
480    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
481    #[allow(clippy::double_ended_iterator_last)]
482    pub fn root_cause(&self) -> &(dyn StdError + 'static) {
483        self.chain().last().unwrap()
484    }
485
486    /// Returns true if `E` is the type held by this error object.
487    ///
488    /// For errors with context, this method returns true if `E` matches the
489    /// type of the context `C` **or** the type of the error on which the
490    /// context has been attached. For details about the interaction between
491    /// context and downcasting, [see here].
492    ///
493    /// [see here]: crate::Context#effect-on-downcasting
494    pub fn is<E>(&self) -> bool
495    where
496        E: Display + Debug + Send + Sync + 'static,
497    {
498        self.downcast_ref::<E>().is_some()
499    }
500
501    /// Attempt to downcast the error object to a concrete type.
502    pub fn downcast<E>(mut self) -> Result<E, Self>
503    where
504        E: Display + Debug + Send + Sync + 'static,
505    {
506        let target = TypeId::of::<E>();
507        let inner = self.inner.by_mut();
508        unsafe {
509            // Use vtable to find NonNull<()> which points to a value of type E
510            // somewhere inside the data structure.
511            #[cfg(not(anyhow_no_ptr_addr_of))]
512            let addr = match (vtable(inner.ptr).object_downcast)(inner.by_ref(), target) {
513                Some(addr) => addr.by_mut().extend(),
514                None => return Err(self),
515            };
516            #[cfg(anyhow_no_ptr_addr_of)]
517            let addr = match (vtable(inner.ptr).object_downcast_mut)(inner, target) {
518                Some(addr) => addr.extend(),
519                None => return Err(self),
520            };
521
522            // Prepare to read E out of the data structure. We'll drop the rest
523            // of the data structure separately so that E is not dropped.
524            let outer = ManuallyDrop::new(self);
525
526            // Read E from where the vtable found it.
527            let error = addr.cast::<E>().read();
528
529            // Drop rest of the data structure outside of E.
530            (vtable(outer.inner.ptr).object_drop_rest)(outer.inner, target);
531
532            Ok(error)
533        }
534    }
535
536    /// Downcast this error object by reference.
537    ///
538    /// # Example
539    ///
540    /// ```
541    /// # use anyhow::anyhow;
542    /// # use std::fmt::{self, Display};
543    /// # use std::task::Poll;
544    /// #
545    /// # #[derive(Debug)]
546    /// # enum DataStoreError {
547    /// #     Censored(()),
548    /// # }
549    /// #
550    /// # impl Display for DataStoreError {
551    /// #     fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
552    /// #         unimplemented!()
553    /// #     }
554    /// # }
555    /// #
556    /// # impl std::error::Error for DataStoreError {}
557    /// #
558    /// # const REDACTED_CONTENT: () = ();
559    /// #
560    /// # let error = anyhow!("...");
561    /// # let root_cause = &error;
562    /// #
563    /// # let ret =
564    /// // If the error was caused by redaction, then return a tombstone instead
565    /// // of the content.
566    /// match root_cause.downcast_ref::<DataStoreError>() {
567    ///     Some(DataStoreError::Censored(_)) => Ok(Poll::Ready(REDACTED_CONTENT)),
568    ///     None => Err(error),
569    /// }
570    /// # ;
571    /// ```
572    pub fn downcast_ref<E>(&self) -> Option<&E>
573    where
574        E: Display + Debug + Send + Sync + 'static,
575    {
576        let target = TypeId::of::<E>();
577        unsafe {
578            // Use vtable to find NonNull<()> which points to a value of type E
579            // somewhere inside the data structure.
580            let addr = (vtable(self.inner.ptr).object_downcast)(self.inner.by_ref(), target)?;
581            Some(addr.cast::<E>().deref())
582        }
583    }
584
585    /// Downcast this error object by mutable reference.
586    pub fn downcast_mut<E>(&mut self) -> Option<&mut E>
587    where
588        E: Display + Debug + Send + Sync + 'static,
589    {
590        let target = TypeId::of::<E>();
591        unsafe {
592            // Use vtable to find NonNull<()> which points to a value of type E
593            // somewhere inside the data structure.
594
595            #[cfg(not(anyhow_no_ptr_addr_of))]
596            let addr =
597                (vtable(self.inner.ptr).object_downcast)(self.inner.by_ref(), target)?.by_mut();
598
599            #[cfg(anyhow_no_ptr_addr_of)]
600            let addr = (vtable(self.inner.ptr).object_downcast_mut)(self.inner.by_mut(), target)?;
601
602            Some(addr.cast::<E>().deref_mut())
603        }
604    }
605
606    #[cfg(error_generic_member_access)]
607    pub(crate) fn provide<'a>(&'a self, request: &mut Request<'a>) {
608        unsafe { ErrorImpl::provide(self.inner.by_ref(), request) }
609    }
610
611    // Called by thiserror when you have `#[source] anyhow::Error`. This provide
612    // implementation includes the anyhow::Error's Backtrace if any, unlike
613    // deref'ing to dyn Error where the provide implementation would include
614    // only the original error's Backtrace from before it got wrapped into an
615    // anyhow::Error.
616    #[cfg(error_generic_member_access)]
617    #[doc(hidden)]
618    pub fn thiserror_provide<'a>(&'a self, request: &mut Request<'a>) {
619        Self::provide(self, request);
620    }
621}
622
623#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
624impl<E> From<E> for Error
625where
626    E: StdError + Send + Sync + 'static,
627{
628    #[cold]
629    fn from(error: E) -> Self {
630        let backtrace = backtrace_if_absent!(&error);
631        Error::construct_from_std(error, backtrace)
632    }
633}
634
635#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
636impl Deref for Error {
637    type Target = dyn StdError + Send + Sync + 'static;
638
639    fn deref(&self) -> &Self::Target {
640        unsafe { ErrorImpl::error(self.inner.by_ref()) }
641    }
642}
643
644#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
645impl DerefMut for Error {
646    fn deref_mut(&mut self) -> &mut Self::Target {
647        unsafe { ErrorImpl::error_mut(self.inner.by_mut()) }
648    }
649}
650
651impl Display for Error {
652    fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
653        unsafe { ErrorImpl::display(self.inner.by_ref(), formatter) }
654    }
655}
656
657impl Debug for Error {
658    fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
659        unsafe { ErrorImpl::debug(self.inner.by_ref(), formatter) }
660    }
661}
662
663impl Drop for Error {
664    fn drop(&mut self) {
665        unsafe {
666            // Invoke the vtable's drop behavior.
667            (vtable(self.inner.ptr).object_drop)(self.inner);
668        }
669    }
670}
671
672struct ErrorVTable {
673    object_drop: unsafe fn(Own<ErrorImpl>),
674    object_ref: unsafe fn(Ref<ErrorImpl>) -> Ref<dyn StdError + Send + Sync + 'static>,
675    #[cfg(all(any(feature = "std", not(anyhow_no_core_error)), anyhow_no_ptr_addr_of))]
676    object_mut: unsafe fn(Mut<ErrorImpl>) -> &mut (dyn StdError + Send + Sync + 'static),
677    object_boxed: unsafe fn(Own<ErrorImpl>) -> Box<dyn StdError + Send + Sync + 'static>,
678    object_downcast: unsafe fn(Ref<ErrorImpl>, TypeId) -> Option<Ref<()>>,
679    #[cfg(anyhow_no_ptr_addr_of)]
680    object_downcast_mut: unsafe fn(Mut<ErrorImpl>, TypeId) -> Option<Mut<()>>,
681    object_drop_rest: unsafe fn(Own<ErrorImpl>, TypeId),
682    #[cfg(all(
683        not(error_generic_member_access),
684        any(std_backtrace, feature = "backtrace")
685    ))]
686    object_backtrace: unsafe fn(Ref<ErrorImpl>) -> Option<&Backtrace>,
687}
688
689// Safety: requires layout of *e to match ErrorImpl<E>.
690unsafe fn object_drop<E>(e: Own<ErrorImpl>) {
691    // Cast back to ErrorImpl<E> so that the allocator receives the correct
692    // Layout to deallocate the Box's memory.
693    let unerased_own = e.cast::<ErrorImpl<E>>();
694    drop(unsafe { unerased_own.boxed() });
695}
696
697// Safety: requires layout of *e to match ErrorImpl<E>.
698unsafe fn object_drop_front<E>(e: Own<ErrorImpl>, target: TypeId) {
699    // Drop the fields of ErrorImpl other than E as well as the Box allocation,
700    // without dropping E itself. This is used by downcast after doing a
701    // ptr::read to take ownership of the E.
702    let _ = target;
703    let unerased_own = e.cast::<ErrorImpl<ManuallyDrop<E>>>();
704    drop(unsafe { unerased_own.boxed() });
705}
706
707// Safety: requires layout of *e to match ErrorImpl<E>.
708unsafe fn object_ref<E>(e: Ref<ErrorImpl>) -> Ref<dyn StdError + Send + Sync + 'static>
709where
710    E: StdError + Send + Sync + 'static,
711{
712    // Attach E's native StdError vtable onto a pointer to self._object.
713
714    let unerased_ref = e.cast::<ErrorImpl<E>>();
715
716    #[cfg(not(anyhow_no_ptr_addr_of))]
717    return Ref::from_raw(unsafe {
718        NonNull::new_unchecked(ptr::addr_of!((*unerased_ref.as_ptr())._object) as *mut E)
719    });
720
721    #[cfg(anyhow_no_ptr_addr_of)]
722    return Ref::new(unsafe { &unerased_ref.deref()._object });
723}
724
725// Safety: requires layout of *e to match ErrorImpl<E>, and for `e` to be derived
726// from a `&mut`
727#[cfg(all(any(feature = "std", not(anyhow_no_core_error)), anyhow_no_ptr_addr_of))]
728unsafe fn object_mut<E>(e: Mut<ErrorImpl>) -> &mut (dyn StdError + Send + Sync + 'static)
729where
730    E: StdError + Send + Sync + 'static,
731{
732    // Attach E's native StdError vtable onto a pointer to self._object.
733    let unerased_mut = e.cast::<ErrorImpl<E>>();
734    unsafe { &mut unerased_mut.deref_mut()._object }
735}
736
737// Safety: requires layout of *e to match ErrorImpl<E>.
738unsafe fn object_boxed<E>(e: Own<ErrorImpl>) -> Box<dyn StdError + Send + Sync + 'static>
739where
740    E: StdError + Send + Sync + 'static,
741{
742    // Attach ErrorImpl<E>'s native StdError vtable. The StdError impl is below.
743    let unerased_own = e.cast::<ErrorImpl<E>>();
744    unsafe { unerased_own.boxed() }
745}
746
747// Safety: requires layout of *e to match ErrorImpl<E>.
748unsafe fn object_downcast<E>(e: Ref<ErrorImpl>, target: TypeId) -> Option<Ref<()>>
749where
750    E: 'static,
751{
752    if TypeId::of::<E>() == target {
753        // Caller is looking for an E pointer and e is ErrorImpl<E>, take a
754        // pointer to its E field.
755
756        let unerased_ref = e.cast::<ErrorImpl<E>>();
757
758        #[cfg(not(anyhow_no_ptr_addr_of))]
759        return Some(
760            Ref::from_raw(unsafe {
761                NonNull::new_unchecked(ptr::addr_of!((*unerased_ref.as_ptr())._object) as *mut E)
762            })
763            .cast::<()>(),
764        );
765
766        #[cfg(anyhow_no_ptr_addr_of)]
767        return Some(Ref::new(unsafe { &unerased_ref.deref()._object }).cast::<()>());
768    } else {
769        None
770    }
771}
772
773// Safety: requires layout of *e to match ErrorImpl<E>.
774#[cfg(anyhow_no_ptr_addr_of)]
775unsafe fn object_downcast_mut<E>(e: Mut<ErrorImpl>, target: TypeId) -> Option<Mut<()>>
776where
777    E: 'static,
778{
779    if TypeId::of::<E>() == target {
780        // Caller is looking for an E pointer and e is ErrorImpl<E>, take a
781        // pointer to its E field.
782        let unerased_mut = e.cast::<ErrorImpl<E>>();
783        let unerased = unsafe { unerased_mut.deref_mut() };
784        Some(Mut::new(&mut unerased._object).cast::<()>())
785    } else {
786        None
787    }
788}
789
790#[cfg(all(
791    not(error_generic_member_access),
792    any(std_backtrace, feature = "backtrace")
793))]
794fn no_backtrace(e: Ref<ErrorImpl>) -> Option<&Backtrace> {
795    let _ = e;
796    None
797}
798
799// Safety: requires layout of *e to match ErrorImpl<ContextError<C, E>>.
800#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
801unsafe fn context_downcast<C, E>(e: Ref<ErrorImpl>, target: TypeId) -> Option<Ref<()>>
802where
803    C: 'static,
804    E: 'static,
805{
806    if TypeId::of::<C>() == target {
807        let unerased_ref = e.cast::<ErrorImpl<ContextError<C, E>>>();
808        let unerased = unsafe { unerased_ref.deref() };
809        Some(Ref::new(&unerased._object.context).cast::<()>())
810    } else if TypeId::of::<E>() == target {
811        let unerased_ref = e.cast::<ErrorImpl<ContextError<C, E>>>();
812        let unerased = unsafe { unerased_ref.deref() };
813        Some(Ref::new(&unerased._object.error).cast::<()>())
814    } else {
815        None
816    }
817}
818
819// Safety: requires layout of *e to match ErrorImpl<ContextError<C, E>>.
820#[cfg(all(feature = "std", anyhow_no_ptr_addr_of))]
821unsafe fn context_downcast_mut<C, E>(e: Mut<ErrorImpl>, target: TypeId) -> Option<Mut<()>>
822where
823    C: 'static,
824    E: 'static,
825{
826    if TypeId::of::<C>() == target {
827        let unerased_mut = e.cast::<ErrorImpl<ContextError<C, E>>>();
828        let unerased = unsafe { unerased_mut.deref_mut() };
829        Some(Mut::new(&mut unerased._object.context).cast::<()>())
830    } else if TypeId::of::<E>() == target {
831        let unerased_mut = e.cast::<ErrorImpl<ContextError<C, E>>>();
832        let unerased = unsafe { unerased_mut.deref_mut() };
833        Some(Mut::new(&mut unerased._object.error).cast::<()>())
834    } else {
835        None
836    }
837}
838
839// Safety: requires layout of *e to match ErrorImpl<ContextError<C, E>>.
840#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
841unsafe fn context_drop_rest<C, E>(e: Own<ErrorImpl>, target: TypeId)
842where
843    C: 'static,
844    E: 'static,
845{
846    // Called after downcasting by value to either the C or the E and doing a
847    // ptr::read to take ownership of that value.
848    if TypeId::of::<C>() == target {
849        let unerased_own = e.cast::<ErrorImpl<ContextError<ManuallyDrop<C>, E>>>();
850        drop(unsafe { unerased_own.boxed() });
851    } else {
852        let unerased_own = e.cast::<ErrorImpl<ContextError<C, ManuallyDrop<E>>>>();
853        drop(unsafe { unerased_own.boxed() });
854    }
855}
856
857// Safety: requires layout of *e to match ErrorImpl<ContextError<C, Error>>.
858unsafe fn context_chain_downcast<C>(e: Ref<ErrorImpl>, target: TypeId) -> Option<Ref<()>>
859where
860    C: 'static,
861{
862    let unerased_ref = e.cast::<ErrorImpl<ContextError<C, Error>>>();
863    let unerased = unsafe { unerased_ref.deref() };
864    if TypeId::of::<C>() == target {
865        Some(Ref::new(&unerased._object.context).cast::<()>())
866    } else {
867        // Recurse down the context chain per the inner error's vtable.
868        let source = &unerased._object.error;
869        unsafe { (vtable(source.inner.ptr).object_downcast)(source.inner.by_ref(), target) }
870    }
871}
872
873// Safety: requires layout of *e to match ErrorImpl<ContextError<C, Error>>.
874#[cfg(anyhow_no_ptr_addr_of)]
875unsafe fn context_chain_downcast_mut<C>(e: Mut<ErrorImpl>, target: TypeId) -> Option<Mut<()>>
876where
877    C: 'static,
878{
879    let unerased_mut = e.cast::<ErrorImpl<ContextError<C, Error>>>();
880    let unerased = unsafe { unerased_mut.deref_mut() };
881    if TypeId::of::<C>() == target {
882        Some(Mut::new(&mut unerased._object.context).cast::<()>())
883    } else {
884        // Recurse down the context chain per the inner error's vtable.
885        let source = &mut unerased._object.error;
886        unsafe { (vtable(source.inner.ptr).object_downcast_mut)(source.inner.by_mut(), target) }
887    }
888}
889
890// Safety: requires layout of *e to match ErrorImpl<ContextError<C, Error>>.
891unsafe fn context_chain_drop_rest<C>(e: Own<ErrorImpl>, target: TypeId)
892where
893    C: 'static,
894{
895    // Called after downcasting by value to either the C or one of the causes
896    // and doing a ptr::read to take ownership of that value.
897    if TypeId::of::<C>() == target {
898        let unerased_own = e.cast::<ErrorImpl<ContextError<ManuallyDrop<C>, Error>>>();
899        // Drop the entire rest of the data structure rooted in the next Error.
900        drop(unsafe { unerased_own.boxed() });
901    } else {
902        let unerased_own = e.cast::<ErrorImpl<ContextError<C, ManuallyDrop<Error>>>>();
903        let unerased = unsafe { unerased_own.boxed() };
904        // Read the Own<ErrorImpl> from the next error.
905        let inner = unerased._object.error.inner;
906        drop(unerased);
907        let vtable = unsafe { vtable(inner.ptr) };
908        // Recursively drop the next error using the same target typeid.
909        unsafe { (vtable.object_drop_rest)(inner, target) };
910    }
911}
912
913// Safety: requires layout of *e to match ErrorImpl<ContextError<C, Error>>.
914#[cfg(all(
915    not(error_generic_member_access),
916    any(std_backtrace, feature = "backtrace")
917))]
918#[allow(clippy::unnecessary_wraps)]
919unsafe fn context_backtrace<C>(e: Ref<ErrorImpl>) -> Option<&Backtrace>
920where
921    C: 'static,
922{
923    let unerased_ref = e.cast::<ErrorImpl<ContextError<C, Error>>>();
924    let unerased = unsafe { unerased_ref.deref() };
925    let backtrace = unsafe { ErrorImpl::backtrace(unerased._object.error.inner.by_ref()) };
926    Some(backtrace)
927}
928
929// NOTE: If working with `ErrorImpl<()>`, references should be avoided in favor
930// of raw pointers and `NonNull`.
931// repr C to ensure that E remains in the final position.
932#[repr(C)]
933pub(crate) struct ErrorImpl<E = ()> {
934    vtable: &'static ErrorVTable,
935    backtrace: Option<Backtrace>,
936    // NOTE: Don't use directly. Use only through vtable. Erased type may have
937    // different alignment.
938    _object: E,
939}
940
941// Reads the vtable out of `p`. This is the same as `p.as_ref().vtable`, but
942// avoids converting `p` into a reference.
943unsafe fn vtable(p: NonNull<ErrorImpl>) -> &'static ErrorVTable {
944    // NOTE: This assumes that `ErrorVTable` is the first field of ErrorImpl.
945    unsafe { *(p.as_ptr() as *const &'static ErrorVTable) }
946}
947
948// repr C to ensure that ContextError<C, E> has the same layout as
949// ContextError<ManuallyDrop<C>, E> and ContextError<C, ManuallyDrop<E>>.
950#[repr(C)]
951pub(crate) struct ContextError<C, E> {
952    pub context: C,
953    pub error: E,
954}
955
956impl<E> ErrorImpl<E> {
957    fn erase(&self) -> Ref<ErrorImpl> {
958        // Erase the concrete type of E but preserve the vtable in self.vtable
959        // for manipulating the resulting thin pointer. This is analogous to an
960        // unsize coercion.
961        Ref::new(self).cast::<ErrorImpl>()
962    }
963}
964
965impl ErrorImpl {
966    pub(crate) unsafe fn error(this: Ref<Self>) -> &(dyn StdError + Send + Sync + 'static) {
967        // Use vtable to attach E's native StdError vtable for the right
968        // original type E.
969        unsafe { (vtable(this.ptr).object_ref)(this).deref() }
970    }
971
972    #[cfg(any(feature = "std", not(anyhow_no_core_error)))]
973    pub(crate) unsafe fn error_mut(this: Mut<Self>) -> &mut (dyn StdError + Send + Sync + 'static) {
974        // Use vtable to attach E's native StdError vtable for the right
975        // original type E.
976
977        #[cfg(not(anyhow_no_ptr_addr_of))]
978        return unsafe {
979            (vtable(this.ptr).object_ref)(this.by_ref())
980                .by_mut()
981                .deref_mut()
982        };
983
984        #[cfg(anyhow_no_ptr_addr_of)]
985        return unsafe { (vtable(this.ptr).object_mut)(this) };
986    }
987
988    #[cfg(any(std_backtrace, feature = "backtrace"))]
989    pub(crate) unsafe fn backtrace(this: Ref<Self>) -> &Backtrace {
990        // This unwrap can only panic if the underlying error's backtrace method
991        // is nondeterministic, which would only happen in maliciously
992        // constructed code.
993        unsafe { this.deref() }
994            .backtrace
995            .as_ref()
996            .or_else(|| {
997                #[cfg(error_generic_member_access)]
998                return error::request_ref::<Backtrace>(unsafe { Self::error(this) });
999                #[cfg(not(error_generic_member_access))]
1000                return unsafe { (vtable(this.ptr).object_backtrace)(this) };
1001            })
1002            .expect("backtrace capture failed")
1003    }
1004
1005    #[cfg(error_generic_member_access)]
1006    unsafe fn provide<'a>(this: Ref<'a, Self>, request: &mut Request<'a>) {
1007        if let Some(backtrace) = unsafe { &this.deref().backtrace } {
1008            request.provide_ref(backtrace);
1009        }
1010        unsafe { Self::error(this) }.provide(request);
1011    }
1012
1013    #[cold]
1014    pub(crate) unsafe fn chain(this: Ref<Self>) -> Chain {
1015        Chain::new(unsafe { Self::error(this) })
1016    }
1017}
1018
1019impl<E> StdError for ErrorImpl<E>
1020where
1021    E: StdError,
1022{
1023    fn source(&self) -> Option<&(dyn StdError + 'static)> {
1024        unsafe { ErrorImpl::error(self.erase()).source() }
1025    }
1026
1027    #[cfg(error_generic_member_access)]
1028    fn provide<'a>(&'a self, request: &mut Request<'a>) {
1029        unsafe { ErrorImpl::provide(self.erase(), request) }
1030    }
1031}
1032
1033impl<E> Debug for ErrorImpl<E>
1034where
1035    E: Debug,
1036{
1037    fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
1038        unsafe { ErrorImpl::debug(self.erase(), formatter) }
1039    }
1040}
1041
1042impl<E> Display for ErrorImpl<E>
1043where
1044    E: Display,
1045{
1046    fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
1047        unsafe { Display::fmt(ErrorImpl::error(self.erase()), formatter) }
1048    }
1049}
1050
1051impl From<Error> for Box<dyn StdError + Send + Sync + 'static> {
1052    #[cold]
1053    fn from(error: Error) -> Self {
1054        let outer = ManuallyDrop::new(error);
1055        unsafe {
1056            // Use vtable to attach ErrorImpl<E>'s native StdError vtable for
1057            // the right original type E.
1058            (vtable(outer.inner.ptr).object_boxed)(outer.inner)
1059        }
1060    }
1061}
1062
1063impl From<Error> for Box<dyn StdError + Send + 'static> {
1064    fn from(error: Error) -> Self {
1065        Box::<dyn StdError + Send + Sync>::from(error)
1066    }
1067}
1068
1069impl From<Error> for Box<dyn StdError + 'static> {
1070    fn from(error: Error) -> Self {
1071        Box::<dyn StdError + Send + Sync>::from(error)
1072    }
1073}
1074
1075#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
1076impl AsRef<dyn StdError + Send + Sync> for Error {
1077    fn as_ref(&self) -> &(dyn StdError + Send + Sync + 'static) {
1078        &**self
1079    }
1080}
1081
1082#[cfg(any(feature = "std", not(anyhow_no_core_error)))]
1083impl AsRef<dyn StdError> for Error {
1084    fn as_ref(&self) -> &(dyn StdError + 'static) {
1085        &**self
1086    }
1087}
1088
1089#[cfg(any(feature = "std", not(anyhow_no_core_unwind_safe)))]
1090impl UnwindSafe for Error {}
1091
1092#[cfg(any(feature = "std", not(anyhow_no_core_unwind_safe)))]
1093impl RefUnwindSafe for Error {}