From ed60e1d2ed0db432496e020b5682b10b132fa130 Mon Sep 17 00:00:00 2001 From: Andrey Zgarbul Date: Fri, 18 Mar 2022 09:18:28 +0300 Subject: [PATCH 1/2] OFFSET & WIDTH constanst --- CHANGELOG.md | 2 ++ src/generate/register.rs | 49 ++++++++++++++++++++++++++++++++-------- 2 files changed, 42 insertions(+), 9 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 027402f6..03e31b01 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,7 +9,9 @@ and this project adheres to [Semantic Versioning](http://semver.org/). ### Added +- Constant values of field offsets and width - added `dyn` keyword to sanatizer. + ### Changed - Generate Rust arrays for all register & cluster arrays with sequential_addresses. diff --git a/src/generate/register.rs b/src/generate/register.rs index bd673040..27e703b7 100644 --- a/src/generate/register.rs +++ b/src/generate/register.rs @@ -347,8 +347,8 @@ pub fn fields( let mut evs_r = None; let field_dim = match f { - Field::Array(_, de) => { - let (first, index) = if let Some(dim_index) = &de.dim_index { + Field::Array(info, de) => { + let first = if let Some(dim_index) = &de.dim_index { if let Ok(first) = dim_index[0].parse::() { let sequential_indexes = dim_index .iter() @@ -357,24 +357,42 @@ pub fn fields( if !sequential_indexes { return Err(anyhow!("unsupported array indexes in {}", f.name)); } - (first, None) + first } else { - (0, de.dim_index.clone()) + 0 } } else { - (0, None) - }; - let suffixes: Vec<_> = match index { - Some(ix) => ix, - None => (0..de.dim).map(|i| (first + i).to_string()).collect(), + 0 }; + let suffixes: Vec<_> = de.indexes().collect(); let suffixes_str = format!("({}-{})", first, first + de.dim - 1); + for (name, offset) in + crate::svd::array::names(info, de).zip(svd_rs::field::bit_offsets(info, de)) + { + let offset_name = Ident::new( + &(name.clone() + "_OFFSET").to_sanitized_upper_case(), + Span::call_site(), + ); + let doc = format!("`{}` field offset", name); + let offset = &util::unsuffixed(offset as _); + mod_items.extend(quote! { + #[doc = #doc] + pub const #offset_name: u8 = #offset; + }); + } Some((first, de.dim, de.dim_increment, suffixes, suffixes_str)) } Field::Single(_) => { if f.name.contains("%s") { return Err(anyhow!("incorrect field {}", f.name)); } + let doc = format!("`{}` field offset", f.name); + let offset_name = Ident::new(&(name_pc.clone() + "_OFFSET"), span); + let offset = &util::unsuffixed(offset); + mod_items.extend(quote! { + #[doc = #doc] + pub const #offset_name: u8 = #offset; + }); None } }; @@ -558,11 +576,14 @@ pub fn fields( } } + let unwidth = crate::util::unsuffixed(width as _); mod_items.extend(quote! { #[doc = #readerdoc] pub struct #name_pc_r(crate::FieldReader<#fty, #name_pc_a>); impl #name_pc_r { + #[doc = "Field width"] + pub const WIDTH: u8 = #unwidth; #[inline(always)] pub(crate) fn new(bits: #fty) -> Self { #name_pc_r(crate::FieldReader::new(bits)) @@ -581,11 +602,14 @@ pub fn fields( }); } } else { + let unwidth = crate::util::unsuffixed(width as _); mod_items.extend(quote! { #[doc = #readerdoc] pub struct #name_pc_r(crate::FieldReader<#fty, #fty>); impl #name_pc_r { + #[doc = "Field width"] + pub const WIDTH: u8 = #unwidth; #[inline(always)] pub(crate) fn new(bits: #fty) -> Self { #name_pc_r(crate::FieldReader::new(bits)) @@ -610,6 +634,13 @@ pub fn fields( let name_pc_cgw = Ident::new(&(name_pc.clone() + "_CGW"), span); let mut proxy_items = TokenStream::new(); + + let unwidth = crate::util::unsuffixed(width as _); + proxy_items.extend(quote! { + #[doc = "Field width"] + pub const WIDTH: u8 = #unwidth; + }); + let mut unsafety = unsafety(f.write_constraint.as_ref(), width); if let Some((evs, base)) = lookup_filter(&lookup_results, Usage::Write) { From 12a21c7bd0962fed8c4ca56947554f892e36141f Mon Sep 17 00:00:00 2001 From: Andrey Zgarbul Date: Fri, 18 Mar 2022 11:23:52 +0300 Subject: [PATCH 2/2] digit_or_hex --- src/generate/register.rs | 2 +- src/util.rs | 8 ++++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/src/generate/register.rs b/src/generate/register.rs index 27e703b7..e0d31fa2 100644 --- a/src/generate/register.rs +++ b/src/generate/register.rs @@ -318,7 +318,7 @@ pub fn fields( let can_write = can_write && (f.access != Some(Access::ReadOnly)); let mask = u64::MAX >> (64 - width); - let hexmask = &util::hex(mask); + let hexmask = &util::digit_or_hex(mask); let offset = u64::from(offset); let rv = properties.reset_value.map(|rv| (rv >> offset) & mask); let fty = width.to_ty()?; diff --git a/src/util.rs b/src/util.rs index e43a394d..06cffeb0 100644 --- a/src/util.rs +++ b/src/util.rs @@ -260,6 +260,14 @@ pub fn access_of(properties: &RegisterProperties, fields: Option<&[Field]>) -> A }) } +pub fn digit_or_hex(n: u64) -> TokenStream { + if n < 10 { + unsuffixed(n) + } else { + hex(n) + } +} + /// Turns `n` into an unsuffixed separated hex token pub fn hex(n: u64) -> TokenStream { let (h4, h3, h2, h1) = (