Skip to content
This repository was archived by the owner on Aug 16, 2021. It is now read-only.

Commit 2b09834

Browse files
committed
Add generic parameter to some types (errors can now add trait bounds)
1 parent 225f592 commit 2b09834

File tree

3 files changed

+28
-17
lines changed

3 files changed

+28
-17
lines changed

src/error_chain.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -78,13 +78,13 @@ macro_rules! error_chain_processed {
7878
pub $error_kind_name,
7979
/// Contains the error chain and the backtrace.
8080
#[doc(hidden)]
81-
pub $crate::State,
81+
pub $crate::State<Trait>,
8282
);
8383

84-
impl $crate::ChainedError for $error_name {
84+
impl $crate::ChainedError<Trait> for $error_name {
8585
type ErrorKind = $error_kind_name;
8686

87-
fn new(kind: $error_kind_name, state: $crate::State) -> $error_name {
87+
fn new(kind: $error_kind_name, state: $crate::State<Trait>) -> $error_name {
8888
$error_name(kind, state)
8989
}
9090

src/example_generated.rs

+4-3
Original file line numberDiff line numberDiff line change
@@ -20,10 +20,11 @@
2020
//! arise frequently.
2121
2222
/// Another code generated by the macro.
23+
2324
pub mod inner {
2425
error_chain! {
2526
derive {
26-
PartialEq, Eq
27+
PartialEq
2728
}
2829
}
2930
}
@@ -40,11 +41,11 @@ error_chain! {
4041
Custom
4142
}
4243
derive {
43-
PartialEq, Eq
44+
PartialEq
4445
}
4546
}
4647

47-
fn foo<T: PartialEq + Eq>() {}
48+
fn foo<T: PartialEq>() {}
4849
fn bar() {
4950
foo::<Error>();
5051
}

src/lib.rs

+21-11
Original file line numberDiff line numberDiff line change
@@ -502,6 +502,7 @@ use std::iter::Iterator;
502502
#[cfg(feature = "backtrace")]
503503
use std::sync::Arc;
504504
use std::fmt;
505+
use std::marker::PhantomData;
505506

506507
#[cfg(feature = "backtrace")]
507508
pub use backtrace::Backtrace;
@@ -558,7 +559,7 @@ pub fn make_backtrace() -> Option<Arc<Backtrace>> {
558559

559560
/// This trait is implemented on all the errors generated by the `error_chain`
560561
/// macro.
561-
pub trait ChainedError: error::Error + Send + 'static {
562+
pub trait ChainedError<S: ?Sized>: error::Error + Send + 'static {
562563
/// Associated kind type.
563564
type ErrorKind;
564565

@@ -585,7 +586,7 @@ pub trait ChainedError: error::Error + Send + 'static {
585586
///
586587
/// The full cause chain and backtrace, if present, will be printed.
587588
fn display_chain<'a>(&'a self) -> DisplayChain<'a, Self> {
588-
DisplayChain(self)
589+
DisplayChain(self, PhantomData)
589590
}
590591

591592
/// Extends the error chain with a new entry.
@@ -595,7 +596,7 @@ pub trait ChainedError: error::Error + Send + 'static {
595596

596597
/// Creates an error from its parts.
597598
#[doc(hidden)]
598-
fn new(kind: Self::ErrorKind, state: State) -> Self where Self: Sized;
599+
fn new(kind: Self::ErrorKind, state: State<S>) -> Self where Self: Sized;
599600

600601
/// Returns the first known backtrace, either from its State or from one
601602
/// of the errors from `foreign_links`.
@@ -607,10 +608,17 @@ pub trait ChainedError: error::Error + Send + 'static {
607608

608609
/// A struct which formats an error for output.
609610
#[derive(Debug)]
611+
<<<<<<< HEAD
610612
pub struct DisplayChain<'a, T: 'a + ?Sized>(&'a T);
611613

612614
impl<'a, T> fmt::Display for DisplayChain<'a, T>
613615
where T: ChainedError
616+
=======
617+
pub struct Display<'a, T: 'a + ?Sized, S: ?Sized>(&'a T, PhantomData<S>);
618+
619+
impl<'a, T, S> fmt::Display for Display<'a, T, S>
620+
where T: ChainedError<S>
621+
>>>>>>> Add generic parameter to some types (errors can now add trait bounds)
614622
{
615623
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
616624
// Keep `try!` for 1.10 support
@@ -631,33 +639,35 @@ impl<'a, T> fmt::Display for DisplayChain<'a, T>
631639
/// Common state between errors.
632640
#[derive(Debug)]
633641
#[doc(hidden)]
634-
pub struct State {
642+
pub struct State<T: ?Sized> {
635643
/// Next error in the error chain.
636-
pub next_error: Option<Box<error::Error + Send>>,
644+
pub next_error: Option<Box<T>>,
637645
/// Backtrace for the current error.
638646
#[cfg(feature = "backtrace")]
639647
pub backtrace: Option<Arc<Backtrace>>,
640648
}
641649

642-
impl Default for State {
650+
impl<T> Default for State<T> {
643651
#[cfg(feature = "backtrace")]
644-
fn default() -> State {
652+
fn default() -> Self {
645653
State {
646654
next_error: None,
647655
backtrace: make_backtrace(),
648656
}
649657
}
650658

651659
#[cfg(not(feature = "backtrace"))]
652-
fn default() -> State {
660+
fn default() -> Self {
653661
State { next_error: None }
654662
}
655663
}
656664

657-
impl State {
665+
impl<T> State<T>
666+
where T: error::Error + Send + 'static
667+
{
658668
/// Creates a new State type
659669
#[cfg(feature = "backtrace")]
660-
pub fn new<CE: ChainedError>(e: Box<error::Error + Send>) -> State {
670+
pub fn new<CE: ChainedError<T>>(e: Box<T>) -> Self {
661671
let backtrace = CE::extract_backtrace(&*e).or_else(make_backtrace);
662672
State {
663673
next_error: Some(e),
@@ -667,7 +677,7 @@ impl State {
667677

668678
/// Creates a new State type
669679
#[cfg(not(feature = "backtrace"))]
670-
pub fn new<CE: ChainedError>(e: Box<error::Error + Send>) -> State {
680+
pub fn new<CE: ChainedError>(e: Box<error::Error + Send>) -> Self {
671681
State { next_error: Some(e) }
672682
}
673683

0 commit comments

Comments
 (0)