From 49bab5c835261af3ef2b84489fac54b2135bea28 Mon Sep 17 00:00:00 2001 From: Ben Harris Date: Wed, 27 Aug 2014 20:26:28 +0800 Subject: [PATCH 1/2] Fix getters for register with only wo fields --- ioreg/builder/accessors.rs | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/ioreg/builder/accessors.rs b/ioreg/builder/accessors.rs index 6e0aa1f2..83f0f9da 100644 --- a/ioreg/builder/accessors.rs +++ b/ioreg/builder/accessors.rs @@ -34,8 +34,10 @@ pub struct BuildAccessors<'a, 'b, 'c> { impl<'a, 'b, 'c> node::RegVisitor for BuildAccessors<'a, 'b, 'c> { fn visit_prim_reg(&mut self, path: &Vec, reg: &node::Reg, _width: node::RegWidth, fields: &Vec) { - let item = build_get_fn(self.cx, path, reg); - self.builder.push_item(item); + if fields.iter().any(|f| f.access != node::WriteOnly) { + let item = build_get_fn(self.cx, path, reg); + self.builder.push_item(item); + } for field in fields.iter() { match build_field_accessors(self.cx, path, reg, field) { From 296d34a6ddc30230318412137c451b8f38524be3 Mon Sep 17 00:00:00 2001 From: Ben Gamari Date: Wed, 27 Aug 2014 20:44:25 -0400 Subject: [PATCH 2/2] ioreg: No need to read from write-only registers --- ioreg/builder/setter.rs | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/ioreg/builder/setter.rs b/ioreg/builder/setter.rs index 9068b8a7..c8b371be 100644 --- a/ioreg/builder/setter.rs +++ b/ioreg/builder/setter.rs @@ -122,6 +122,15 @@ fn build_drop<'a>(cx: &'a ExtCtxt, path: &Vec, } } + // no need to read write-only registers + let wo_reg: bool = fields.iter().all(|f| f.access == node::WriteOnly); + let initial_value = + if wo_reg { + quote_expr!(cx, 0) + } else { + quote_expr!(cx, self.reg.value.get()) + }; + let item = quote_item!(cx, #[unsafe_destructor] #[doc = "This performs the register update"] @@ -129,7 +138,7 @@ fn build_drop<'a>(cx: &'a ExtCtxt, path: &Vec, fn drop(&mut self) { let clear_mask: $unpacked_ty = $clear as $unpacked_ty; if self.mask != 0 { - let v: $unpacked_ty = self.reg.value.get() & ! clear_mask & ! self.mask; + let v: $unpacked_ty = $initial_value & ! clear_mask & ! self.mask; self.reg.value.set(self.value | v); } }