Make SettingsError easier to diagnose;
This commit is contained in:
committed by
Dan Gohman
parent
8b296e4874
commit
de1d82b4ba
@@ -85,7 +85,7 @@ impl Builder {
|
||||
/// Look up a descriptor by name.
|
||||
fn lookup(&self, name: &str) -> SetResult<(usize, detail::Detail)> {
|
||||
match probe(self.template, name, simple_hash(name)) {
|
||||
Err(_) => Err(SetError::BadName),
|
||||
Err(_) => Err(SetError::BadName(name.to_string())),
|
||||
Ok(entry) => {
|
||||
let d = &self.template.descriptors[self.template.hash_table[entry] as usize];
|
||||
Ok((d.offset as usize, d.detail))
|
||||
@@ -98,14 +98,17 @@ fn parse_bool_value(value: &str) -> SetResult<bool> {
|
||||
match value {
|
||||
"true" | "on" | "yes" | "1" => Ok(true),
|
||||
"false" | "off" | "no" | "0" => Ok(false),
|
||||
_ => Err(SetError::BadValue),
|
||||
_ => Err(SetError::BadValue("bool".to_string())),
|
||||
}
|
||||
}
|
||||
|
||||
fn parse_enum_value(value: &str, choices: &[&str]) -> SetResult<u8> {
|
||||
match choices.iter().position(|&tag| tag == value) {
|
||||
Some(idx) => Ok(idx as u8),
|
||||
None => Err(SetError::BadValue),
|
||||
None => Err(SetError::BadValue(format!(
|
||||
"any among {}",
|
||||
choices.join(", ")
|
||||
))),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -134,13 +137,15 @@ impl Configurable for Builder {
|
||||
self.set_bit(offset, bit, parse_bool_value(value)?);
|
||||
}
|
||||
Detail::Num => {
|
||||
self.bytes[offset] = value.parse().map_err(|_| SetError::BadValue)?;
|
||||
self.bytes[offset] = value
|
||||
.parse()
|
||||
.map_err(|_| SetError::BadValue("number".to_string()))?;
|
||||
}
|
||||
Detail::Enum { last, enumerators } => {
|
||||
self.bytes[offset] =
|
||||
parse_enum_value(value, self.template.enums(last, enumerators))?;
|
||||
}
|
||||
Detail::Preset => return Err(SetError::BadName),
|
||||
Detail::Preset => return Err(SetError::BadName(name.to_string())),
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
@@ -150,16 +155,16 @@ impl Configurable for Builder {
|
||||
#[derive(Fail, Debug, PartialEq, Eq)]
|
||||
pub enum SetError {
|
||||
/// No setting by this name exists.
|
||||
#[fail(display = "No existing setting with this name")]
|
||||
BadName,
|
||||
#[fail(display = "No existing setting named '{}'", _0)]
|
||||
BadName(String),
|
||||
|
||||
/// Type mismatch for setting (e.g., setting an enum setting as a bool).
|
||||
#[fail(display = "Trying to set a setting with the wrong type")]
|
||||
BadType,
|
||||
|
||||
/// This is not a valid value for this setting.
|
||||
#[fail(display = "Unexpected value for a setting")]
|
||||
BadValue,
|
||||
#[fail(display = "Unexpected value for a setting, expected {}", _0)]
|
||||
BadValue(String),
|
||||
}
|
||||
|
||||
/// A result returned when changing a setting.
|
||||
@@ -385,7 +390,7 @@ mod tests {
|
||||
#[test]
|
||||
fn modify_bool() {
|
||||
let mut b = builder();
|
||||
assert_eq!(b.enable("not_there"), Err(BadName));
|
||||
assert_eq!(b.enable("not_there"), Err(BadName("not_there".to_string())));
|
||||
assert_eq!(b.enable("enable_simd"), Ok(()));
|
||||
assert_eq!(b.set("enable_simd", "false"), Ok(()));
|
||||
|
||||
@@ -396,10 +401,19 @@ mod tests {
|
||||
#[test]
|
||||
fn modify_string() {
|
||||
let mut b = builder();
|
||||
assert_eq!(b.set("not_there", "true"), Err(BadName));
|
||||
assert_eq!(b.set("enable_simd", ""), Err(BadValue));
|
||||
assert_eq!(b.set("enable_simd", "best"), Err(BadValue));
|
||||
assert_eq!(b.set("opt_level", "true"), Err(BadValue));
|
||||
assert_eq!(
|
||||
b.set("not_there", "true"),
|
||||
Err(BadName("not_there".to_string()))
|
||||
);
|
||||
assert_eq!(b.set("enable_simd", ""), Err(BadValue("bool".to_string())));
|
||||
assert_eq!(
|
||||
b.set("enable_simd", "best"),
|
||||
Err(BadValue("bool".to_string()))
|
||||
);
|
||||
assert_eq!(
|
||||
b.set("opt_level", "true"),
|
||||
Err(BadValue("any among default, best, fastest".to_string()))
|
||||
);
|
||||
assert_eq!(b.set("opt_level", "best"), Ok(()));
|
||||
assert_eq!(b.set("enable_simd", "0"), Ok(()));
|
||||
|
||||
|
||||
Reference in New Issue
Block a user