Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 8 additions & 9 deletions fpga_arch_parser/src/arch.rs
Original file line number Diff line number Diff line change
Expand Up @@ -71,22 +71,21 @@ pub struct TileSite {
pub pin_mapping: TileSitePinMapping,
}

pub struct SubTileFracFC {
pub val: f32,
}

pub struct SubTileAbsFC {
pub val: i32,
pub enum SubTileIOFC {
Frac(f32),
Abs(i32),
}

pub enum SubTileIOFC {
Frac(SubTileFracFC),
Abs(SubTileAbsFC),
pub struct SubTileFCOverride {
pub fc: SubTileIOFC,
pub port_name: Option<String>,
pub segment_name: Option<String>,
}

pub struct SubTileFC {
pub in_fc: SubTileIOFC,
pub out_fc: SubTileIOFC,
pub fc_overrides: Vec<SubTileFCOverride>,
}

pub enum PinSide {
Expand Down
2 changes: 1 addition & 1 deletion fpga_arch_parser/src/parse_switch_list.rs
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@ fn parse_switch(name: &OwnedName,
let mut t_del_tags: Vec<SwitchTDel> = Vec::new();
loop {
match parser.next() {
Ok(XmlEvent::StartElement { name, .. }) => {
Ok(XmlEvent::StartElement { name, attributes, .. }) => {
match name.to_string().as_str() {
"Tdel" => {
t_del_tags.push(parse_switch_t_del(&name, &attributes, parser)?);
Expand Down
100 changes: 90 additions & 10 deletions fpga_arch_parser/src/parse_tiles.rs
Original file line number Diff line number Diff line change
Expand Up @@ -118,25 +118,105 @@ fn create_sub_tile_io_fc(ty: &str,
parser: &EventReader<BufReader<File>>) -> Result<SubTileIOFC, FPGAArchParseError> {
match ty {
"frac" => {
Ok(SubTileIOFC::Frac(SubTileFracFC {
val: match val.parse() {
Ok(SubTileIOFC::Frac(
match val.parse() {
Ok(v) => v,
Err(e) => return Err(FPGAArchParseError::AttributeParseError(format!("{val}: {e}"), parser.position())),
},
}))
))
},
"abs" => {
Ok(SubTileIOFC::Abs(SubTileAbsFC {
val: match val.parse() {
Ok(SubTileIOFC::Abs(
match val.parse() {
Ok(v) => v,
Err(e) => return Err(FPGAArchParseError::AttributeParseError(format!("{val}: {e}"), parser.position())),
},
}))
))
},
_ => Err(FPGAArchParseError::AttributeParseError(format!("Unknown fc_type: {}", ty), parser.position())),
}
}

fn parse_sub_tile_fc_override(name: &OwnedName,
attributes: &[OwnedAttribute],
parser: &mut EventReader<BufReader<File>>) -> Result<SubTileFCOverride, FPGAArchParseError> {
assert!(name.to_string() == "fc_override");

let mut fc_type: Option<String> = None;
let mut fc_val: Option<String> = None;
let mut port_name: Option<String> = None;
let mut segment_name: Option<String> = None;

for a in attributes {
match a.name.to_string().as_str() {
"fc_type" => {
fc_type = match fc_type {
None => Some(a.value.clone()),
Some(_) => return Err(FPGAArchParseError::DuplicateAttribute(a.to_string(), parser.position())),
}
},
"fc_val" => {
fc_val = match fc_val {
None => Some(a.value.clone()),
Some(_) => return Err(FPGAArchParseError::DuplicateAttribute(a.to_string(), parser.position())),
}
},
"port_name" => {
port_name = match port_name {
None => Some(a.value.clone()),
Some(_) => return Err(FPGAArchParseError::DuplicateAttribute(a.to_string(), parser.position())),
}
},
"segment_name" => {
segment_name = match segment_name {
None => Some(a.value.clone()),
Some(_) => return Err(FPGAArchParseError::DuplicateAttribute(a.to_string(), parser.position())),
}
},
_ => return Err(FPGAArchParseError::UnknownAttribute(a.to_string(), parser.position())),
};
}
let fc_type = match fc_type {
Some(n) => n,
None => return Err(FPGAArchParseError::MissingRequiredAttribute("fc_type".to_string(), parser.position())),
};
let fc_val = match fc_val {
Some(n) => n,
None => return Err(FPGAArchParseError::MissingRequiredAttribute("fc_val".to_string(), parser.position())),
};
let fc = create_sub_tile_io_fc(&fc_type, &fc_val, parser)?;
if port_name.is_none() && segment_name.is_none() {
return Err(FPGAArchParseError::MissingRequiredAttribute("At least one of port_name or segment_name must be specified.".to_string(), parser.position()));
}

loop {
match parser.next() {
Ok(XmlEvent::StartElement { name, .. }) => {
return Err(FPGAArchParseError::InvalidTag(name.to_string(), parser.position()));
},
Ok(XmlEvent::EndElement { name }) => {
match name.to_string().as_str() {
"fc_override" => break,
_ => return Err(FPGAArchParseError::UnexpectedEndTag(name.to_string(), parser.position())),
}
},
Ok(XmlEvent::EndDocument) => {
return Err(FPGAArchParseError::UnexpectedEndOfDocument(name.to_string()));
},
Err(e) => {
return Err(FPGAArchParseError::XMLParseError(format!("{e:?}"), parser.position()));
},
_ => {},
};
}

Ok(SubTileFCOverride{
fc,
port_name,
segment_name,
})
}

fn parse_sub_tile_fc(name: &OwnedName,
attributes: &[OwnedAttribute],
parser: &mut EventReader<BufReader<File>>) -> Result<SubTileFC, FPGAArchParseError> {
Expand Down Expand Up @@ -196,14 +276,13 @@ fn parse_sub_tile_fc(name: &OwnedName,
let in_fc = create_sub_tile_io_fc(&in_type, &in_val, parser)?;
let out_fc = create_sub_tile_io_fc(&out_type, &out_val, parser)?;

let mut fc_overrides: Vec<SubTileFCOverride> = Vec::new();
loop {
match parser.next() {
Ok(XmlEvent::StartElement { name, .. }) => {
Ok(XmlEvent::StartElement { name, attributes, .. }) => {
match name.to_string().as_str() {
"fc_override" => {
// TODO: Implement.
// FIXME: Check that this is documented in VTR.
let _ = parser.skip();
fc_overrides.push(parse_sub_tile_fc_override(&name, &attributes, parser)?);
},
_ => return Err(FPGAArchParseError::InvalidTag(name.to_string(), parser.position())),
};
Expand All @@ -227,6 +306,7 @@ fn parse_sub_tile_fc(name: &OwnedName,
Ok(SubTileFC {
in_fc,
out_fc,
fc_overrides,
})
}

Expand Down