1use alloc::boxed::Box;
2#[cfg(feature = "std")]
3use core::ops::{Deref, DerefMut};
4#[cfg(not(anyhow_no_ptr_addr_of))]
5use core::ptr;
6use core::{
7 any::TypeId,
8 fmt::{self, Debug, Display},
9 mem::ManuallyDrop,
10 ptr::NonNull,
11};
12#[cfg(error_generic_member_access)]
13use std::error::{self, Request};
14
15#[cfg(any(feature = "std", anyhow_no_ptr_addr_of))]
16use crate::ptr::Mut;
17use crate::{
18 Error, StdError,
19 backtrace::Backtrace,
20 chain::Chain,
21 ptr::{Own, Ref},
22};
23
24impl Error {
25 #[cfg(feature = "std")]
33 #[cfg_attr(docsrs, doc(cfg(feature = "std")))]
34 #[cold]
35 #[must_use]
36 pub fn new<E>(error: E) -> Self
37 where
38 E: StdError + Send + Sync + 'static,
39 {
40 let backtrace = backtrace_if_absent!(&error);
41 Error::from_std(error, backtrace)
42 }
43
44 #[cold]
82 #[must_use]
83 pub fn msg<M>(message: M) -> Self
84 where
85 M: Display + Debug + Send + Sync + 'static,
86 {
87 Error::from_adhoc(message, backtrace!())
88 }
89
90 #[cfg(feature = "std")]
91 #[cold]
92 pub(crate) fn from_std<E>(error: E, backtrace: Option<Backtrace>) -> Self
93 where
94 E: StdError + Send + Sync + 'static,
95 {
96 let vtable = &ErrorVTable {
97 object_drop: object_drop::<E>,
98 object_ref: object_ref::<E>,
99 #[cfg(anyhow_no_ptr_addr_of)]
100 object_mut: object_mut::<E>,
101 object_boxed: object_boxed::<E>,
102 object_downcast: object_downcast::<E>,
103 #[cfg(anyhow_no_ptr_addr_of)]
104 object_downcast_mut: object_downcast_mut::<E>,
105 object_drop_rest: object_drop_front::<E>,
106 #[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
107 object_backtrace: no_backtrace,
108 };
109
110 unsafe { Error::construct(error, vtable, backtrace) }
112 }
113
114 #[cold]
115 pub(crate) fn from_adhoc<M>(message: M, backtrace: Option<Backtrace>) -> Self
116 where
117 M: Display + Debug + Send + Sync + 'static,
118 {
119 use crate::wrapper::MessageError;
120 let error: MessageError<M> = MessageError(message);
121 let vtable = &ErrorVTable {
122 object_drop: object_drop::<MessageError<M>>,
123 object_ref: object_ref::<MessageError<M>>,
124 #[cfg(all(feature = "std", anyhow_no_ptr_addr_of))]
125 object_mut: object_mut::<MessageError<M>>,
126 object_boxed: object_boxed::<MessageError<M>>,
127 object_downcast: object_downcast::<M>,
128 #[cfg(anyhow_no_ptr_addr_of)]
129 object_downcast_mut: object_downcast_mut::<M>,
130 object_drop_rest: object_drop_front::<M>,
131 #[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
132 object_backtrace: no_backtrace,
133 };
134
135 unsafe { Error::construct(error, vtable, backtrace) }
138 }
139
140 #[cold]
141 pub(crate) fn from_display<M>(message: M, backtrace: Option<Backtrace>) -> Self
142 where
143 M: Display + Send + Sync + 'static,
144 {
145 use crate::wrapper::DisplayError;
146 let error: DisplayError<M> = DisplayError(message);
147 let vtable = &ErrorVTable {
148 object_drop: object_drop::<DisplayError<M>>,
149 object_ref: object_ref::<DisplayError<M>>,
150 #[cfg(all(feature = "std", anyhow_no_ptr_addr_of))]
151 object_mut: object_mut::<DisplayError<M>>,
152 object_boxed: object_boxed::<DisplayError<M>>,
153 object_downcast: object_downcast::<M>,
154 #[cfg(anyhow_no_ptr_addr_of)]
155 object_downcast_mut: object_downcast_mut::<M>,
156 object_drop_rest: object_drop_front::<M>,
157 #[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
158 object_backtrace: no_backtrace,
159 };
160
161 unsafe { Error::construct(error, vtable, backtrace) }
164 }
165
166 #[cfg(feature = "std")]
167 #[cold]
168 pub(crate) fn from_context<C, E>(context: C, error: E, backtrace: Option<Backtrace>) -> Self
169 where
170 C: Display + Send + Sync + 'static,
171 E: StdError + Send + Sync + 'static,
172 {
173 let error: ContextError<C, E> = ContextError {
174 context,
175 error,
176 };
177
178 let vtable = &ErrorVTable {
179 object_drop: object_drop::<ContextError<C, E>>,
180 object_ref: object_ref::<ContextError<C, E>>,
181 #[cfg(anyhow_no_ptr_addr_of)]
182 object_mut: object_mut::<ContextError<C, E>>,
183 object_boxed: object_boxed::<ContextError<C, E>>,
184 object_downcast: context_downcast::<C, E>,
185 #[cfg(anyhow_no_ptr_addr_of)]
186 object_downcast_mut: context_downcast_mut::<C, E>,
187 object_drop_rest: context_drop_rest::<C, E>,
188 #[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
189 object_backtrace: no_backtrace,
190 };
191
192 unsafe { Error::construct(error, vtable, backtrace) }
194 }
195
196 #[cfg(feature = "std")]
197 #[cold]
198 pub(crate) fn from_boxed(error: Box<dyn StdError + Send + Sync>, backtrace: Option<Backtrace>) -> Self {
199 use crate::wrapper::BoxedError;
200 let error = BoxedError(error);
201 let vtable = &ErrorVTable {
202 object_drop: object_drop::<BoxedError>,
203 object_ref: object_ref::<BoxedError>,
204 #[cfg(anyhow_no_ptr_addr_of)]
205 object_mut: object_mut::<BoxedError>,
206 object_boxed: object_boxed::<BoxedError>,
207 object_downcast: object_downcast::<Box<dyn StdError + Send + Sync>>,
208 #[cfg(anyhow_no_ptr_addr_of)]
209 object_downcast_mut: object_downcast_mut::<Box<dyn StdError + Send + Sync>>,
210 object_drop_rest: object_drop_front::<Box<dyn StdError + Send + Sync>>,
211 #[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
212 object_backtrace: no_backtrace,
213 };
214
215 unsafe { Error::construct(error, vtable, backtrace) }
218 }
219
220 #[cold]
226 unsafe fn construct<E>(error: E, vtable: &'static ErrorVTable, backtrace: Option<Backtrace>) -> Self
227 where
228 E: StdError + Send + Sync + 'static,
229 {
230 let inner: Box<ErrorImpl<E>> = Box::new(ErrorImpl {
231 vtable,
232 backtrace,
233 _object: error,
234 });
235 let inner = Own::new(inner).cast::<ErrorImpl>();
242 Error {
243 inner,
244 }
245 }
246
247 #[cold]
302 #[must_use]
303 pub fn context<C>(self, context: C) -> Self
304 where
305 C: Display + Send + Sync + 'static,
306 {
307 let error: ContextError<C, Error> = ContextError {
308 context,
309 error: self,
310 };
311
312 let vtable = &ErrorVTable {
313 object_drop: object_drop::<ContextError<C, Error>>,
314 object_ref: object_ref::<ContextError<C, Error>>,
315 #[cfg(all(feature = "std", anyhow_no_ptr_addr_of))]
316 object_mut: object_mut::<ContextError<C, Error>>,
317 object_boxed: object_boxed::<ContextError<C, Error>>,
318 object_downcast: context_chain_downcast::<C>,
319 #[cfg(anyhow_no_ptr_addr_of)]
320 object_downcast_mut: context_chain_downcast_mut::<C>,
321 object_drop_rest: context_chain_drop_rest::<C>,
322 #[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
323 object_backtrace: context_backtrace::<C>,
324 };
325
326 let backtrace = None;
328
329 unsafe { Error::construct(error, vtable, backtrace) }
331 }
332
333 #[cfg(any(std_backtrace, feature = "backtrace"))]
361 pub fn backtrace(&self) -> &impl_backtrace!() {
362 unsafe { ErrorImpl::backtrace(self.inner.by_ref()) }
363 }
364
365 #[cfg(feature = "std")]
387 #[cfg_attr(docsrs, doc(cfg(feature = "std")))]
388 #[cold]
389 pub fn chain(&self) -> Chain {
390 unsafe { ErrorImpl::chain(self.inner.by_ref()) }
391 }
392
393 #[cfg(feature = "std")]
399 #[cfg_attr(docsrs, doc(cfg(feature = "std")))]
400 pub fn root_cause(&self) -> &(dyn StdError + 'static) {
401 self.chain().last().unwrap()
402 }
403
404 pub fn is<E>(&self) -> bool
413 where
414 E: Display + Debug + Send + Sync + 'static,
415 {
416 self.downcast_ref::<E>().is_some()
417 }
418
419 pub fn downcast<E>(mut self) -> Result<E, Self>
421 where
422 E: Display + Debug + Send + Sync + 'static,
423 {
424 let target = TypeId::of::<E>();
425 let inner = self.inner.by_mut();
426 unsafe {
427 #[cfg(not(anyhow_no_ptr_addr_of))]
430 let addr = match (vtable(inner.ptr).object_downcast)(inner.by_ref(), target) {
431 Some(addr) => addr.by_mut().extend(),
432 None => return Err(self),
433 };
434 #[cfg(anyhow_no_ptr_addr_of)]
435 let addr = match (vtable(inner.ptr).object_downcast_mut)(inner, target) {
436 Some(addr) => addr.extend(),
437 None => return Err(self),
438 };
439
440 let outer = ManuallyDrop::new(self);
443
444 let error = addr.cast::<E>().read();
446
447 (vtable(outer.inner.ptr).object_drop_rest)(outer.inner, target);
449
450 Ok(error)
451 }
452 }
453
454 pub fn downcast_ref<E>(&self) -> Option<&E>
491 where
492 E: Display + Debug + Send + Sync + 'static,
493 {
494 let target = TypeId::of::<E>();
495 unsafe {
496 let addr = (vtable(self.inner.ptr).object_downcast)(self.inner.by_ref(), target)?;
499 Some(addr.cast::<E>().deref())
500 }
501 }
502
503 pub fn downcast_mut<E>(&mut self) -> Option<&mut E>
505 where
506 E: Display + Debug + Send + Sync + 'static,
507 {
508 let target = TypeId::of::<E>();
509 unsafe {
510 #[cfg(not(anyhow_no_ptr_addr_of))]
514 let addr = (vtable(self.inner.ptr).object_downcast)(self.inner.by_ref(), target)?.by_mut();
515
516 #[cfg(anyhow_no_ptr_addr_of)]
517 let addr = (vtable(self.inner.ptr).object_downcast_mut)(self.inner.by_mut(), target)?;
518
519 Some(addr.cast::<E>().deref_mut())
520 }
521 }
522
523 #[cfg(error_generic_member_access)]
524 pub(crate) fn provide<'a>(&'a self, request: &mut Request<'a>) {
525 unsafe { ErrorImpl::provide(self.inner.by_ref(), request) }
526 }
527
528 #[cfg(error_generic_member_access)]
534 #[doc(hidden)]
535 pub fn thiserror_provide<'a>(&'a self, request: &mut Request<'a>) {
536 Self::provide(self, request);
537 }
538}
539
540#[cfg(feature = "std")]
541#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
542impl<E> From<E> for Error
543where
544 E: StdError + Send + Sync + 'static,
545{
546 #[cold]
547 fn from(error: E) -> Self {
548 let backtrace = backtrace_if_absent!(&error);
549 Error::from_std(error, backtrace)
550 }
551}
552
553#[cfg(feature = "std")]
554#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
555impl Deref for Error {
556 type Target = dyn StdError + Send + Sync + 'static;
557
558 fn deref(&self) -> &Self::Target {
559 unsafe { ErrorImpl::error(self.inner.by_ref()) }
560 }
561}
562
563#[cfg(feature = "std")]
564#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
565impl DerefMut for Error {
566 fn deref_mut(&mut self) -> &mut Self::Target {
567 unsafe { ErrorImpl::error_mut(self.inner.by_mut()) }
568 }
569}
570
571impl Display for Error {
572 fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
573 unsafe { ErrorImpl::display(self.inner.by_ref(), formatter) }
574 }
575}
576
577impl Debug for Error {
578 fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
579 unsafe { ErrorImpl::debug(self.inner.by_ref(), formatter) }
580 }
581}
582
583impl Drop for Error {
584 fn drop(&mut self) {
585 unsafe {
586 (vtable(self.inner.ptr).object_drop)(self.inner);
588 }
589 }
590}
591
592struct ErrorVTable {
593 object_drop: unsafe fn(Own<ErrorImpl>),
594 object_ref: unsafe fn(Ref<ErrorImpl>) -> Ref<dyn StdError + Send + Sync + 'static>,
595 #[cfg(all(feature = "std", anyhow_no_ptr_addr_of))]
596 object_mut: unsafe fn(Mut<ErrorImpl>) -> &mut (dyn StdError + Send + Sync + 'static),
597 object_boxed: unsafe fn(Own<ErrorImpl>) -> Box<dyn StdError + Send + Sync + 'static>,
598 object_downcast: unsafe fn(Ref<ErrorImpl>, TypeId) -> Option<Ref<()>>,
599 #[cfg(anyhow_no_ptr_addr_of)]
600 object_downcast_mut: unsafe fn(Mut<ErrorImpl>, TypeId) -> Option<Mut<()>>,
601 object_drop_rest: unsafe fn(Own<ErrorImpl>, TypeId),
602 #[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
603 object_backtrace: unsafe fn(Ref<ErrorImpl>) -> Option<&Backtrace>,
604}
605
606unsafe fn object_drop<E>(e: Own<ErrorImpl>) {
608 let unerased_own = e.cast::<ErrorImpl<E>>();
611 drop(unsafe { unerased_own.boxed() });
612}
613
614unsafe fn object_drop_front<E>(e: Own<ErrorImpl>, target: TypeId) {
616 let _ = target;
620 let unerased_own = e.cast::<ErrorImpl<ManuallyDrop<E>>>();
621 drop(unsafe { unerased_own.boxed() });
622}
623
624unsafe fn object_ref<E>(e: Ref<ErrorImpl>) -> Ref<dyn StdError + Send + Sync + 'static>
626where
627 E: StdError + Send + Sync + 'static,
628{
629 let unerased_ref = e.cast::<ErrorImpl<E>>();
632
633 #[cfg(not(anyhow_no_ptr_addr_of))]
634 return Ref::from_raw(unsafe { NonNull::new_unchecked(ptr::addr_of!((*unerased_ref.as_ptr())._object) as *mut E) });
635
636 #[cfg(anyhow_no_ptr_addr_of)]
637 return Ref::new(unsafe { &unerased_ref.deref()._object });
638}
639
640#[cfg(all(feature = "std", anyhow_no_ptr_addr_of))]
643unsafe fn object_mut<E>(e: Mut<ErrorImpl>) -> &mut (dyn StdError + Send + Sync + 'static)
644where
645 E: StdError + Send + Sync + 'static,
646{
647 let unerased_mut = e.cast::<ErrorImpl<E>>();
649 unsafe { &mut unerased_mut.deref_mut()._object }
650}
651
652unsafe fn object_boxed<E>(e: Own<ErrorImpl>) -> Box<dyn StdError + Send + Sync + 'static>
654where
655 E: StdError + Send + Sync + 'static,
656{
657 let unerased_own = e.cast::<ErrorImpl<E>>();
659 unsafe { unerased_own.boxed() }
660}
661
662unsafe fn object_downcast<E>(e: Ref<ErrorImpl>, target: TypeId) -> Option<Ref<()>>
664where
665 E: 'static,
666{
667 if TypeId::of::<E>() == target {
668 let unerased_ref = e.cast::<ErrorImpl<E>>();
672
673 #[cfg(not(anyhow_no_ptr_addr_of))]
674 return Some(
675 Ref::from_raw(unsafe { NonNull::new_unchecked(ptr::addr_of!((*unerased_ref.as_ptr())._object) as *mut E) })
676 .cast::<()>(),
677 );
678
679 #[cfg(anyhow_no_ptr_addr_of)]
680 return Some(Ref::new(unsafe { &unerased_ref.deref()._object }).cast::<()>());
681 } else {
682 None
683 }
684}
685
686#[cfg(anyhow_no_ptr_addr_of)]
688unsafe fn object_downcast_mut<E>(e: Mut<ErrorImpl>, target: TypeId) -> Option<Mut<()>>
689where
690 E: 'static,
691{
692 if TypeId::of::<E>() == target {
693 let unerased_mut = e.cast::<ErrorImpl<E>>();
696 let unerased = unsafe { unerased_mut.deref_mut() };
697 Some(Mut::new(&mut unerased._object).cast::<()>())
698 } else {
699 None
700 }
701}
702
703#[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
704fn no_backtrace(e: Ref<ErrorImpl>) -> Option<&Backtrace> {
705 let _ = e;
706 None
707}
708
709#[cfg(feature = "std")]
711unsafe fn context_downcast<C, E>(e: Ref<ErrorImpl>, target: TypeId) -> Option<Ref<()>>
712where
713 C: 'static,
714 E: 'static,
715{
716 if TypeId::of::<C>() == target {
717 let unerased_ref = e.cast::<ErrorImpl<ContextError<C, E>>>();
718 let unerased = unsafe { unerased_ref.deref() };
719 Some(Ref::new(&unerased._object.context).cast::<()>())
720 } else if TypeId::of::<E>() == target {
721 let unerased_ref = e.cast::<ErrorImpl<ContextError<C, E>>>();
722 let unerased = unsafe { unerased_ref.deref() };
723 Some(Ref::new(&unerased._object.error).cast::<()>())
724 } else {
725 None
726 }
727}
728
729#[cfg(all(feature = "std", anyhow_no_ptr_addr_of))]
731unsafe fn context_downcast_mut<C, E>(e: Mut<ErrorImpl>, target: TypeId) -> Option<Mut<()>>
732where
733 C: 'static,
734 E: 'static,
735{
736 if TypeId::of::<C>() == target {
737 let unerased_mut = e.cast::<ErrorImpl<ContextError<C, E>>>();
738 let unerased = unsafe { unerased_mut.deref_mut() };
739 Some(Mut::new(&mut unerased._object.context).cast::<()>())
740 } else if TypeId::of::<E>() == target {
741 let unerased_mut = e.cast::<ErrorImpl<ContextError<C, E>>>();
742 let unerased = unsafe { unerased_mut.deref_mut() };
743 Some(Mut::new(&mut unerased._object.error).cast::<()>())
744 } else {
745 None
746 }
747}
748
749#[cfg(feature = "std")]
751unsafe fn context_drop_rest<C, E>(e: Own<ErrorImpl>, target: TypeId)
752where
753 C: 'static,
754 E: 'static,
755{
756 if TypeId::of::<C>() == target {
759 let unerased_own = e.cast::<ErrorImpl<ContextError<ManuallyDrop<C>, E>>>();
760 drop(unsafe { unerased_own.boxed() });
761 } else {
762 let unerased_own = e.cast::<ErrorImpl<ContextError<C, ManuallyDrop<E>>>>();
763 drop(unsafe { unerased_own.boxed() });
764 }
765}
766
767unsafe fn context_chain_downcast<C>(e: Ref<ErrorImpl>, target: TypeId) -> Option<Ref<()>>
769where
770 C: 'static,
771{
772 let unerased_ref = e.cast::<ErrorImpl<ContextError<C, Error>>>();
773 let unerased = unsafe { unerased_ref.deref() };
774 if TypeId::of::<C>() == target {
775 Some(Ref::new(&unerased._object.context).cast::<()>())
776 } else {
777 let source = &unerased._object.error;
779 unsafe { (vtable(source.inner.ptr).object_downcast)(source.inner.by_ref(), target) }
780 }
781}
782
783#[cfg(anyhow_no_ptr_addr_of)]
785unsafe fn context_chain_downcast_mut<C>(e: Mut<ErrorImpl>, target: TypeId) -> Option<Mut<()>>
786where
787 C: 'static,
788{
789 let unerased_mut = e.cast::<ErrorImpl<ContextError<C, Error>>>();
790 let unerased = unsafe { unerased_mut.deref_mut() };
791 if TypeId::of::<C>() == target {
792 Some(Mut::new(&mut unerased._object.context).cast::<()>())
793 } else {
794 let source = &mut unerased._object.error;
796 unsafe { (vtable(source.inner.ptr).object_downcast_mut)(source.inner.by_mut(), target) }
797 }
798}
799
800unsafe fn context_chain_drop_rest<C>(e: Own<ErrorImpl>, target: TypeId)
802where
803 C: 'static,
804{
805 if TypeId::of::<C>() == target {
808 let unerased_own = e.cast::<ErrorImpl<ContextError<ManuallyDrop<C>, Error>>>();
809 drop(unsafe { unerased_own.boxed() });
811 } else {
812 let unerased_own = e.cast::<ErrorImpl<ContextError<C, ManuallyDrop<Error>>>>();
813 let unerased = unsafe { unerased_own.boxed() };
814 let inner = unerased._object.error.inner;
816 drop(unerased);
817 let vtable = unsafe { vtable(inner.ptr) };
818 unsafe { (vtable.object_drop_rest)(inner, target) };
820 }
821}
822
823#[cfg(all(not(error_generic_member_access), any(std_backtrace, feature = "backtrace")))]
825#[allow(clippy::unnecessary_wraps)]
826unsafe fn context_backtrace<C>(e: Ref<ErrorImpl>) -> Option<&Backtrace>
827where
828 C: 'static,
829{
830 let unerased_ref = e.cast::<ErrorImpl<ContextError<C, Error>>>();
831 let unerased = unsafe { unerased_ref.deref() };
832 let backtrace = unsafe { ErrorImpl::backtrace(unerased._object.error.inner.by_ref()) };
833 Some(backtrace)
834}
835
836#[repr(C)]
840pub(crate) struct ErrorImpl<E = ()> {
841 vtable: &'static ErrorVTable,
842 backtrace: Option<Backtrace>,
843 _object: E,
846}
847
848unsafe fn vtable(p: NonNull<ErrorImpl>) -> &'static ErrorVTable {
851 unsafe { *(p.as_ptr() as *const &'static ErrorVTable) }
853}
854
855#[repr(C)]
858pub(crate) struct ContextError<C, E> {
859 pub context: C,
860 pub error: E,
861}
862
863impl<E> ErrorImpl<E> {
864 fn erase(&self) -> Ref<ErrorImpl> {
865 Ref::new(self).cast::<ErrorImpl>()
869 }
870}
871
872impl ErrorImpl {
873 pub(crate) unsafe fn error(this: Ref<Self>) -> &(dyn StdError + Send + Sync + 'static) {
874 unsafe { (vtable(this.ptr).object_ref)(this).deref() }
877 }
878
879 #[cfg(feature = "std")]
880 pub(crate) unsafe fn error_mut(this: Mut<Self>) -> &mut (dyn StdError + Send + Sync + 'static) {
881 #[cfg(not(anyhow_no_ptr_addr_of))]
885 return unsafe { (vtable(this.ptr).object_ref)(this.by_ref()).by_mut().deref_mut() };
886
887 #[cfg(anyhow_no_ptr_addr_of)]
888 return unsafe { (vtable(this.ptr).object_mut)(this) };
889 }
890
891 #[cfg(any(std_backtrace, feature = "backtrace"))]
892 pub(crate) unsafe fn backtrace(this: Ref<Self>) -> &Backtrace {
893 unsafe { this.deref() }
897 .backtrace
898 .as_ref()
899 .or_else(|| {
900 #[cfg(error_generic_member_access)]
901 return error::request_ref::<Backtrace>(unsafe { Self::error(this) });
902 #[cfg(not(error_generic_member_access))]
903 return unsafe { (vtable(this.ptr).object_backtrace)(this) };
904 })
905 .expect("backtrace capture failed")
906 }
907
908 #[cfg(error_generic_member_access)]
909 unsafe fn provide<'a>(this: Ref<'a, Self>, request: &mut Request<'a>) {
910 if let Some(backtrace) = unsafe { &this.deref().backtrace } {
911 request.provide_ref(backtrace);
912 }
913 unsafe { Self::error(this) }.provide(request);
914 }
915
916 #[cold]
917 pub(crate) unsafe fn chain(this: Ref<Self>) -> Chain {
918 Chain::new(unsafe { Self::error(this) })
919 }
920}
921
922impl<E> StdError for ErrorImpl<E>
923where
924 E: StdError,
925{
926 fn source(&self) -> Option<&(dyn StdError + 'static)> {
927 unsafe { ErrorImpl::error(self.erase()).source() }
928 }
929
930 #[cfg(error_generic_member_access)]
931 fn provide<'a>(&'a self, request: &mut Request<'a>) {
932 unsafe { ErrorImpl::provide(self.erase(), request) }
933 }
934}
935
936impl<E> Debug for ErrorImpl<E>
937where
938 E: Debug,
939{
940 fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
941 unsafe { ErrorImpl::debug(self.erase(), formatter) }
942 }
943}
944
945impl<E> Display for ErrorImpl<E>
946where
947 E: Display,
948{
949 fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
950 unsafe { Display::fmt(ErrorImpl::error(self.erase()), formatter) }
951 }
952}
953
954impl From<Error> for Box<dyn StdError + Send + Sync + 'static> {
955 #[cold]
956 fn from(error: Error) -> Self {
957 let outer = ManuallyDrop::new(error);
958 unsafe {
959 (vtable(outer.inner.ptr).object_boxed)(outer.inner)
962 }
963 }
964}
965
966impl From<Error> for Box<dyn StdError + Send + 'static> {
967 fn from(error: Error) -> Self {
968 Box::<dyn StdError + Send + Sync>::from(error)
969 }
970}
971
972impl From<Error> for Box<dyn StdError + 'static> {
973 fn from(error: Error) -> Self {
974 Box::<dyn StdError + Send + Sync>::from(error)
975 }
976}
977
978#[cfg(feature = "std")]
979impl AsRef<dyn StdError + Send + Sync> for Error {
980 fn as_ref(&self) -> &(dyn StdError + Send + Sync + 'static) {
981 &**self
982 }
983}
984
985#[cfg(feature = "std")]
986impl AsRef<dyn StdError> for Error {
987 fn as_ref(&self) -> &(dyn StdError + 'static) {
988 &**self
989 }
990}