mirror of
https://gitlab.com/bauen1/dn42-roagen
synced 2024-05-11 05:55:36 +00:00
fix parsing of burbles new route object
This commit is contained in:
75
src/main.rs
75
src/main.rs
@ -36,42 +36,69 @@ impl fmt::Display for ROA {
|
|||||||
|
|
||||||
impl TryFrom<File> for ROA {
|
impl TryFrom<File> for ROA {
|
||||||
type Error = &'static str;
|
type Error = &'static str;
|
||||||
|
|
||||||
fn try_from(file: File) -> Result<Self, Self::Error> {
|
fn try_from(file: File) -> Result<Self, Self::Error> {
|
||||||
|
let mut attributes: Vec<(String, String)> = vec![];
|
||||||
|
|
||||||
|
for wrapped_line in std::io::BufReader::new(file).lines() {
|
||||||
|
let line = wrapped_line.unwrap();
|
||||||
|
|
||||||
|
/* is this a continuation of the previous attribute ? */
|
||||||
|
if line.starts_with(' ') {
|
||||||
|
if attributes.is_empty() {
|
||||||
|
return Err("Invalid route object starting with whitespace");
|
||||||
|
}
|
||||||
|
|
||||||
|
let (_, ref mut v) = attributes.last_mut().unwrap();
|
||||||
|
v.push_str(line.trim_start());
|
||||||
|
}
|
||||||
|
|
||||||
|
/* newline continuation */
|
||||||
|
if line.starts_with('+') {
|
||||||
|
if attributes.is_empty() {
|
||||||
|
return Err("Invalid route object starting with a newline continuation");
|
||||||
|
}
|
||||||
|
|
||||||
|
let (_, ref mut v) = attributes.last_mut().unwrap();
|
||||||
|
v.push('\n');
|
||||||
|
}
|
||||||
|
|
||||||
|
let fields: Vec<&str> = line.splitn(2, ' ').collect();
|
||||||
|
if fields.is_empty() {
|
||||||
|
return Err("Invalid route object");
|
||||||
|
}
|
||||||
|
|
||||||
|
attributes.push((
|
||||||
|
(*fields.get(0).unwrap()).to_string(),
|
||||||
|
fields.get(1).unwrap_or(&"").trim_start().to_string()
|
||||||
|
));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
let mut route: Option<IpCidr> = None;
|
let mut route: Option<IpCidr> = None;
|
||||||
let mut origins: Vec<u32> = Vec::new();
|
let mut origins: Vec<u32> = Vec::new();
|
||||||
let mut maxlen: Option<u8> = None;
|
let mut maxlen: Option<u8> = None;
|
||||||
|
|
||||||
for line in std::io::BufReader::new(file).lines() {
|
for (key, value) in attributes {
|
||||||
let real_line = line.unwrap();
|
match key.as_ref() {
|
||||||
let fields: Vec<&str> = real_line.split_whitespace().collect();
|
|
||||||
|
|
||||||
match fields[0] {
|
|
||||||
"route:" | "route6:" => {
|
"route:" | "route6:" => {
|
||||||
route = Some(fields[1].parse().map_err(|_| "invalid route attribute")?);
|
let v: IpCidr = value.parse::<IpCidr>().map_err(|_| "invalid route attribute")?;
|
||||||
}
|
route = Some(v);
|
||||||
|
},
|
||||||
"origin:" => {
|
"origin:" => {
|
||||||
origins.push(
|
let origin: u32 = value.trim_start_matches("AS").parse().map_err(|_| "invalid origin attribute")?;
|
||||||
fields[1]
|
origins.push(origin);
|
||||||
.trim_start_matches("AS")
|
},
|
||||||
.parse()
|
|
||||||
.map_err(|_| "invalid origin attribute")?,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
"max-length:" => {
|
"max-length:" => {
|
||||||
maxlen = Some(
|
maxlen = Some(value.parse().map_err(|_| "invalid max-length attribute")?);
|
||||||
fields[1]
|
},
|
||||||
.parse()
|
|
||||||
.map_err(|_| "invalid max-length attribute")?,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
_ => {}
|
_ => {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
assert!(!origins.is_empty(), "missing origin attribute");
|
if origins.is_empty() {
|
||||||
|
return Err("missing origin attributes");
|
||||||
|
}
|
||||||
|
|
||||||
Ok(Self {
|
Ok(Self {
|
||||||
route: route.expect("missing route attribute"),
|
route: route.expect("missing route attribute"),
|
||||||
|
Reference in New Issue
Block a user