From fcc6951c707144ba423b81e03bc2f34b6cfa7286 Mon Sep 17 00:00:00 2001 From: Brian Cully Date: Mon, 23 Sep 2019 12:45:09 -0400 Subject: Mark pipe descriptor register memory as volatile. Most of the values in the descriptor memory can be modified by the hardware, so we need to tell Rust that. Also, refactor the common register setup code into `register.rs`. --- src/pipe/register.rs | 95 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 95 insertions(+) create mode 100644 src/pipe/register.rs (limited to 'src/pipe/register.rs') diff --git a/src/pipe/register.rs b/src/pipe/register.rs new file mode 100644 index 0000000..555b70a --- /dev/null +++ b/src/pipe/register.rs @@ -0,0 +1,95 @@ +//! Generic register access. + +use core::marker::PhantomData; +use vcell::VolatileCell; + +pub trait Readable {} +pub trait Writable {} + +pub struct Register { + value: VolatileCell, + _marker: PhantomData, +} + +impl From for Register { + fn from(v: T) -> Self { + Self { + value: VolatileCell::new(v), + _marker: PhantomData, + } + } +} + +impl Register +where + Self: Readable, + T: Copy, +{ + pub fn read(&self) -> R { + R { + bits: self.value.get(), + _marker: PhantomData, + } + } +} + +impl Register +where + Self: Readable + Writable, + T: Copy, +{ + pub fn write(&self, f: F) + where + F: FnOnce(&mut W) -> &mut W, + { + let mut w = W { + bits: self.value.get(), + _marker: PhantomData, + }; + self.value.set(f(&mut w).bits); + } + + pub fn modify(&self, f: F) + where + F: FnOnce(T, &mut W) -> &mut W, + { + let mut w = W { + bits: self.value.get(), + _marker: PhantomData, + }; + self.value.set(f(w.bits, &mut w).bits); + } +} + +pub struct R { + pub bits: T, + _marker: PhantomData, +} + +impl R +where + T: Copy, +{ + pub fn new(bits: T) -> Self { + Self { + bits, + _marker: PhantomData, + } + } + + pub fn bits(&self) -> T { + self.bits + } +} + +pub struct W { + pub bits: T, + _marker: PhantomData, +} + +impl W { + pub unsafe fn bits(&mut self, bits: T) -> &mut Self { + self.bits = bits; + self + } +} -- cgit v1.2.3