Skip to content

Commit 92dbac8

Browse files
bors[bot]burrbull
andauthored
Merge #98
98: use `anyhow` as Error type instead of `failure` r=Emilgardis a=burrbull https://crates.io/crates/anyhow + https://crates.io/crates/thiserror Co-authored-by: Andrey Zgarbul <zgarbul.andrey@gmail.com>
2 parents 3a36265 + 349cce5 commit 92dbac8

29 files changed

+220
-323
lines changed

Cargo.toml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,8 @@ unproven = []
2020
[dependencies]
2121
either = "1.5"
2222
xmltree = "0.8"
23-
failure = "0.1"
23+
anyhow = "1.0.19"
24+
thiserror = "1.0.5"
2425

2526
[dependencies.serde]
2627
version = "1.0"

src/elementext.rs

Lines changed: 17 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -4,25 +4,24 @@
44
use xmltree::Element;
55

66
use crate::types::{BoolParse, Parse};
7-
use failure::ResultExt;
87

98
use crate::error::*;
109

1110
/// Defines extensions for implementation over xmltree::Element
1211
pub trait ElementExt {
13-
fn get_child_text_opt<K>(&self, k: K) -> Result<Option<String>, SVDError>
12+
fn get_child_text_opt<K>(&self, k: K) -> Result<Option<String>>
1413
where
1514
String: PartialEq<K>;
16-
fn get_child_text<K>(&self, k: K) -> Result<String, SVDError>
15+
fn get_child_text<K>(&self, k: K) -> Result<String>
1716
where
1817
String: PartialEq<K>,
1918
K: core::fmt::Display + Clone;
2019

21-
fn get_text(&self) -> Result<String, SVDError>;
20+
fn get_text(&self) -> Result<String>;
2221

23-
fn get_child_elem<'a>(&'a self, n: &str) -> Result<&'a Element, SVDError>;
24-
fn get_child_u32(&self, n: &str) -> Result<u32, SVDError>;
25-
fn get_child_bool(&self, n: &str) -> Result<bool, SVDError>;
22+
fn get_child_elem<'a>(&'a self, n: &str) -> Result<&'a Element>;
23+
fn get_child_u32(&self, n: &str) -> Result<u32>;
24+
fn get_child_bool(&self, n: &str) -> Result<bool>;
2625

2726
fn merge(&self, n: &Self) -> Self;
2827

@@ -31,7 +30,7 @@ pub trait ElementExt {
3130

3231
/// Implements extensions for xmltree::Element
3332
impl ElementExt for Element {
34-
fn get_child_text_opt<K>(&self, k: K) -> Result<Option<String>, SVDError>
33+
fn get_child_text_opt<K>(&self, k: K) -> Result<Option<String>>
3534
where
3635
String: PartialEq<K>,
3736
{
@@ -41,44 +40,42 @@ impl ElementExt for Element {
4140
Ok(None)
4241
}
4342
}
44-
fn get_child_text<K>(&self, k: K) -> Result<String, SVDError>
43+
fn get_child_text<K>(&self, k: K) -> Result<String>
4544
where
4645
String: PartialEq<K>,
4746
K: core::fmt::Display + Clone,
4847
{
4948
self.get_child_text_opt(k.clone())?
50-
.ok_or_else(|| SVDErrorKind::MissingTag(self.clone(), format!("{}", k)).into())
49+
.ok_or_else(|| SVDError::MissingTag(self.clone(), format!("{}", k)).into())
5150
}
5251

5352
/// Get text contained by an XML Element
54-
fn get_text(&self) -> Result<String, SVDError> {
53+
fn get_text(&self) -> Result<String> {
5554
match self.text.as_ref() {
5655
Some(s) => Ok(s.clone()),
57-
// FIXME: Doesn't look good because SVDErrorKind doesn't format by itself. We already
56+
// FIXME: Doesn't look good because SVDError doesn't format by itself. We already
5857
// capture the element and this information can be used for getting the name
5958
// This would fix ParseError
60-
None => Err(SVDErrorKind::EmptyTag(self.clone(), self.name.clone()).into()),
59+
None => Err(SVDError::EmptyTag(self.clone(), self.name.clone()).into()),
6160
}
6261
}
6362

6463
/// Get a named child element from an XML Element
65-
fn get_child_elem<'a>(&'a self, n: &str) -> Result<&'a Element, SVDError> {
64+
fn get_child_elem<'a>(&'a self, n: &str) -> Result<&'a Element> {
6665
match self.get_child(n) {
6766
Some(s) => Ok(s),
68-
None => Err(SVDErrorKind::MissingTag(self.clone(), n.to_string()).into()),
67+
None => Err(SVDError::MissingTag(self.clone(), n.to_string()).into()),
6968
}
7069
}
7170

7271
/// Get a u32 value from a named child element
73-
fn get_child_u32(&self, n: &str) -> Result<u32, SVDError> {
72+
fn get_child_u32(&self, n: &str) -> Result<u32> {
7473
let s = self.get_child_elem(n)?;
75-
u32::parse(&s)
76-
.context(SVDErrorKind::ParseError(self.clone()))
77-
.map_err(|e| e.into())
74+
u32::parse(&s).context(SVDError::ParseError(self.clone()))
7875
}
7976

8077
/// Get a bool value from a named child element
81-
fn get_child_bool(&self, n: &str) -> Result<bool, SVDError> {
78+
fn get_child_bool(&self, n: &str) -> Result<bool> {
8279
let s = self.get_child_elem(n)?;
8380
BoolParse::parse(s)
8481
}

src/error.rs

Lines changed: 20 additions & 81 deletions
Original file line numberDiff line numberDiff line change
@@ -1,63 +1,46 @@
11
//! SVD Errors.
22
//! This module defines error types and messages for SVD parsing and encoding
33
4-
use core::fmt::{self, Display};
5-
use failure::{Backtrace, Context, Fail};
6-
use xmltree::{Element, ParseError};
4+
pub use anyhow::{Context, Result};
5+
use xmltree::Element;
76

8-
#[derive(Debug)]
9-
pub struct SVDError {
10-
inner: Context<SVDErrorKind>,
11-
}
12-
13-
// TODO: Expand and make more complex output possible.
14-
// We can use the `Element` to output name (if available) and etc.
157
#[allow(clippy::large_enum_variant)]
16-
#[derive(Clone, Debug, PartialEq, Eq, Fail)]
17-
pub enum SVDErrorKind {
18-
#[fail(display = "Unknown endianness `{}`", _0)]
8+
#[derive(Clone, Debug, PartialEq, Eq, thiserror::Error)]
9+
pub enum SVDError {
10+
#[error("Unknown endianness `{0}`")]
1911
UnknownEndian(String),
2012
// TODO: Needs context
2113
// TODO: Better name
22-
#[fail(display = "Expected a <{}> tag, found none", _1)]
14+
#[error("Expected a <{1}> tag, found none")]
2315
MissingTag(Element, String),
24-
#[fail(display = "Expected content in <{}> tag, found none", _1)]
16+
#[error("Expected content in <{1}> tag, found none")]
2517
EmptyTag(Element, String),
26-
#[fail(display = "ParseError")]
18+
#[error("ParseError")]
2719
ParseError(Element),
28-
#[fail(display = "NameMismatch")]
20+
#[error("NameMismatch")]
2921
NameMismatch(Element),
30-
#[fail(display = "unknown access variant '{}' found", _1)]
22+
#[error("unknown access variant '{1}' found")]
3123
UnknownAccessType(Element, String),
32-
#[fail(display = "Bit range invalid, {:?}", _1)]
24+
#[error("Bit range invalid, {1:?}")]
3325
InvalidBitRange(Element, InvalidBitRange),
34-
#[fail(display = "Unknown write constraint")]
26+
#[error("Unknown write constraint")]
3527
UnknownWriteConstraint(Element),
36-
#[fail(display = "Multiple wc found")]
28+
#[error("Multiple wc found")]
3729
MoreThanOneWriteConstraint(Element),
38-
#[fail(display = "Unknown usage variant")]
30+
#[error("Unknown usage variant")]
3931
UnknownUsageVariant(Element),
40-
#[fail(display = "Expected a <{}>, found ...", _1)]
32+
#[error("Expected a <{1}>, found ...")]
4133
NotExpectedTag(Element, String),
42-
#[fail(
43-
display = "Invalid RegisterCluster (expected register or cluster), found {}",
44-
_1
45-
)]
34+
#[error("Invalid RegisterCluster (expected register or cluster), found {1}")]
4635
InvalidRegisterCluster(Element, String),
47-
#[fail(display = "Invalid modifiedWriteValues variant, found {}", _1)]
36+
#[error("Invalid modifiedWriteValues variant, found {1}")]
4837
InvalidModifiedWriteValues(Element, String),
49-
#[fail(
50-
display = "The content of the element could not be parsed to a boolean value {}: {}",
51-
_1, _2
52-
)]
38+
#[error("The content of the element could not be parsed to a boolean value {1}: {2}")]
5339
InvalidBooleanValue(Element, String, core::str::ParseBoolError),
54-
#[fail(display = "encoding method not implemented for svd object {}", _0)]
40+
#[error("encoding method not implemented for svd object {0}")]
5541
EncodeNotImplemented(String),
56-
#[fail(display = "Error parsing SVD XML")]
42+
#[error("Error parsing SVD XML")]
5743
FileParseError,
58-
// FIXME: Should not be used, only for prototyping
59-
#[fail(display = "{}", _0)]
60-
Other(String),
6144
}
6245

6346
// TODO: Consider making into an Error
@@ -67,47 +50,3 @@ pub enum InvalidBitRange {
6750
ParseError,
6851
MsbLsb,
6952
}
70-
71-
impl Fail for SVDError {
72-
fn cause(&self) -> Option<&dyn Fail> {
73-
self.inner.cause()
74-
}
75-
76-
fn backtrace(&self) -> Option<&Backtrace> {
77-
self.inner.backtrace()
78-
}
79-
}
80-
81-
impl Display for SVDError {
82-
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
83-
Display::fmt(&self.inner, f)
84-
}
85-
}
86-
87-
impl SVDError {
88-
pub fn kind(&self) -> SVDErrorKind {
89-
self.inner.get_context().clone()
90-
}
91-
}
92-
93-
impl From<SVDErrorKind> for SVDError {
94-
fn from(kind: SVDErrorKind) -> SVDError {
95-
SVDError {
96-
inner: Context::new(kind),
97-
}
98-
}
99-
}
100-
101-
impl From<Context<SVDErrorKind>> for SVDError {
102-
fn from(inner: Context<SVDErrorKind>) -> SVDError {
103-
SVDError { inner }
104-
}
105-
}
106-
107-
impl From<ParseError> for SVDError {
108-
fn from(e: ParseError) -> SVDError {
109-
SVDError {
110-
inner: e.context(SVDErrorKind::FileParseError),
111-
}
112-
}
113-
}

src/lib.rs

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ pub mod svd;
3636
pub use svd::*;
3737
// Error defines SVD error types
3838
pub mod error;
39-
use error::SVDError;
39+
use anyhow::Result;
4040
// Parse defines parsing interfaces
4141
pub mod parse;
4242
use parse::Parse;
@@ -54,15 +54,15 @@ pub mod derive_from;
5454
pub use derive_from::DeriveFrom;
5555

5656
/// Parses the contents of an SVD (XML) string
57-
pub fn parse(xml: &str) -> Result<Device, SVDError> {
57+
pub fn parse(xml: &str) -> Result<Device> {
5858
let xml = trim_utf8_bom(xml);
5959
let tree = Element::parse(xml.as_bytes())?;
6060
Device::parse(&tree)
6161
}
6262

6363
/// Encodes a device object to an SVD (XML) string
6464
#[cfg(feature = "unproven")]
65-
pub fn encode(d: &Device) -> Result<String, SVDError> {
65+
pub fn encode(d: &Device) -> Result<String> {
6666
let root = d.encode()?;
6767
let mut wr = Vec::new();
6868
root.write(&mut wr).unwrap();
@@ -98,7 +98,10 @@ pub(crate) fn new_element(name: &str, text: Option<String>) -> Element {
9898
#[cfg(test)]
9999
#[cfg(feature = "unproven")]
100100
pub fn run_test<
101-
T: Parse<Error = SVDError, Object = T> + Encode<Error = SVDError> + core::fmt::Debug + PartialEq,
101+
T: Parse<Error = anyhow::Error, Object = T>
102+
+ Encode<Error = anyhow::Error>
103+
+ core::fmt::Debug
104+
+ PartialEq,
102105
>(
103106
tests: &[(T, &str)],
104107
) {

src/parse.rs

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,6 @@
33
44
use xmltree::Element;
55

6-
use crate::error::*;
7-
86
/// Parse trait allows SVD objects to be parsed from XML elements.
97
pub trait Parse {
108
/// Object returned by parse method
@@ -18,9 +16,9 @@ pub trait Parse {
1816
/// Parses an optional child element with the provided name and Parse function
1917
/// Returns an none if the child doesn't exist, Ok(Some(e)) if parsing succeeds,
2018
/// and Err() if parsing fails.
21-
pub fn optional<'a, T>(n: &str, e: &'a Element) -> Result<Option<T::Object>, SVDError>
19+
pub fn optional<'a, T>(n: &str, e: &'a Element) -> anyhow::Result<Option<T::Object>>
2220
where
23-
T: Parse<Error = SVDError>,
21+
T: Parse<Error = anyhow::Error>,
2422
{
2523
let child = match e.get_child(n) {
2624
Some(c) => c,

src/svd/access.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -20,9 +20,9 @@ pub enum Access {
2020

2121
impl Parse for Access {
2222
type Object = Access;
23-
type Error = SVDError;
23+
type Error = anyhow::Error;
2424

25-
fn parse(tree: &Element) -> Result<Access, SVDError> {
25+
fn parse(tree: &Element) -> Result<Access> {
2626
let text = tree.get_text()?;
2727

2828
match &text[..] {
@@ -31,16 +31,16 @@ impl Parse for Access {
3131
"read-writeOnce" => Ok(Access::ReadWriteOnce),
3232
"write-only" => Ok(Access::WriteOnly),
3333
"writeOnce" => Ok(Access::WriteOnce),
34-
_ => Err(SVDErrorKind::UnknownAccessType(tree.clone(), text).into()),
34+
_ => Err(SVDError::UnknownAccessType(tree.clone(), text).into()),
3535
}
3636
}
3737
}
3838

3939
#[cfg(feature = "unproven")]
4040
impl Encode for Access {
41-
type Error = SVDError;
41+
type Error = anyhow::Error;
4242

43-
fn encode(&self) -> Result<Element, SVDError> {
43+
fn encode(&self) -> Result<Element> {
4444
let text = match *self {
4545
Access::ReadOnly => String::from("read-only"),
4646
Access::ReadWrite => String::from("read-write"),

src/svd/addressblock.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ use crate::types::Parse;
88

99
#[cfg(feature = "unproven")]
1010
use crate::encode::Encode;
11-
use crate::error::SVDError;
11+
use crate::error::*;
1212
#[cfg(feature = "unproven")]
1313
use crate::new_element;
1414

@@ -22,9 +22,9 @@ pub struct AddressBlock {
2222

2323
impl Parse for AddressBlock {
2424
type Object = AddressBlock;
25-
type Error = SVDError;
25+
type Error = anyhow::Error;
2626

27-
fn parse(tree: &Element) -> Result<AddressBlock, SVDError> {
27+
fn parse(tree: &Element) -> Result<AddressBlock> {
2828
Ok(AddressBlock {
2929
offset: tree.get_child_u32("offset")?,
3030
size: tree.get_child_u32("size")?,
@@ -35,9 +35,9 @@ impl Parse for AddressBlock {
3535

3636
#[cfg(feature = "unproven")]
3737
impl Encode for AddressBlock {
38-
type Error = SVDError;
38+
type Error = anyhow::Error;
3939

40-
fn encode(&self) -> Result<Element, SVDError> {
40+
fn encode(&self) -> Result<Element> {
4141
Ok(Element {
4242
prefix: None,
4343
namespace: None,

0 commit comments

Comments
 (0)