Invert the direction of the Register<T> type parameter

This commit is contained in:
Dylan McKay 2017-12-14 02:13:24 +13:00
parent 0157a8553c
commit cb6e0d3b69
7 changed files with 115 additions and 118 deletions

View File

@ -102,7 +102,7 @@ mod gen {
writeln!(w, "impl {} {{", register.name)?;
for bitfield in register.bitfields.iter() {
// Create a mask for the whole bitset.
writeln!(w, " pub const {}: Bitset<{}, Self> = Bitset::new(0x{:x});", bitfield.name, ty, bitfield.mask)?;
writeln!(w, " pub const {}: Bitset<Self> = Bitset::new(0x{:x});", bitfield.name, bitfield.mask)?;
// We create masks for the individual bits in the field if there
// is more than one bit in the field.
@ -110,8 +110,8 @@ mod gen {
let mut current_mask_bit_num = 0;
for current_register_bit_num in 0..15 {
if (current_mask & 0b1) == 0b1 {
writeln!(w, " pub const {}{}: Mask<{}, Self> = Mask::new(1<<{});",
bitfield.name, current_mask_bit_num, ty, current_register_bit_num)?;
writeln!(w, " pub const {}{}: Mask<Self> = Mask::new(1<<{});",
bitfield.name, current_mask_bit_num, current_register_bit_num)?;
current_mask_bit_num += 1;
}
@ -122,7 +122,8 @@ mod gen {
writeln!(w, "}}")?;
writeln!(w)?;
writeln!(w, "impl Register<{}> for {} {{", ty, register.name)?;
writeln!(w, "impl Register for {} {{", register.name)?;
writeln!(w, " type T = {};", ty)?;
writeln!(w, " const ADDR: *mut {} = 0x{:x} as *mut {};", ty, register.offset, ty)?;
writeln!(w, "}}")?;
}
@ -266,13 +267,13 @@ mod gen {
writeln!(w, " type ControlB = {};", find_reg_suffix("TCCR", "B").name)?;
writeln!(w, " type InterruptMask = {};", find_reg("TIMSK").name)?;
writeln!(w, " type InterruptFlag = {};", find_reg("TIFR").name)?;
writeln!(w, " const CS0: Mask<u8, Self::ControlB> = Self::ControlB::CS00;")?;
writeln!(w, " const CS1: Mask<u8, Self::ControlB> = Self::ControlB::CS01;")?;
writeln!(w, " const CS2: Mask<u8, Self::ControlB> = Self::ControlB::CS02;")?;
writeln!(w, " const WGM0: Mask<u8, Self::ControlA> = Self::ControlA::WGM00;")?;
writeln!(w, " const WGM1: Mask<u8, Self::ControlA> = Self::ControlA::WGM01;")?;
writeln!(w, " const WGM2: Mask<u8, Self::ControlB> = Self::ControlB::WGM020;")?;
writeln!(w, " const OCIEA: Bitset<u8, Self::InterruptMask> = Self::InterruptMask::OCIE0A;")?;
writeln!(w, " const CS0: Mask<Self::ControlB> = Self::ControlB::CS00;")?;
writeln!(w, " const CS1: Mask<Self::ControlB> = Self::ControlB::CS01;")?;
writeln!(w, " const CS2: Mask<Self::ControlB> = Self::ControlB::CS02;")?;
writeln!(w, " const WGM0: Mask<Self::ControlA> = Self::ControlA::WGM00;")?;
writeln!(w, " const WGM1: Mask<Self::ControlA> = Self::ControlA::WGM01;")?;
writeln!(w, " const WGM2: Mask<Self::ControlB> = Self::ControlB::WGM020;")?;
writeln!(w, " const OCIEA: Bitset<Self::InterruptMask> = Self::InterruptMask::OCIE0A;")?;
writeln!(w, "}}")?;
}
@ -300,14 +301,14 @@ mod gen {
writeln!(w, " type ControlC = {};", find_reg_suffix("TCCR", "C").name)?;
writeln!(w, " type InterruptMask = {};", find_reg("TIMSK").name)?;
writeln!(w, " type InterruptFlag = {};", find_reg("TIFR").name)?;
writeln!(w, " const CS0: Mask<u8, Self::ControlB> = Self::ControlB::CS10;")?;
writeln!(w, " const CS1: Mask<u8, Self::ControlB> = Self::ControlB::CS11;")?;
writeln!(w, " const CS2: Mask<u8, Self::ControlB> = Self::ControlB::CS12;")?;
writeln!(w, " const WGM0: Mask<u8, Self::ControlA> = Self::ControlA::WGM10;")?;
writeln!(w, " const WGM1: Mask<u8, Self::ControlA> = Self::ControlA::WGM11;")?;
writeln!(w, " const WGM2: Mask<u8, Self::ControlB> = Self::ControlB::WGM10;")?;
writeln!(w, " const WGM3: Mask<u8, Self::ControlB> = Self::ControlB::WGM11;")?;
writeln!(w, " const OCIEA: Bitset<u8, Self::InterruptMask> = Self::InterruptMask::OCIE1A;")?;
writeln!(w, " const CS0: Mask<Self::ControlB> = Self::ControlB::CS10;")?;
writeln!(w, " const CS1: Mask<Self::ControlB> = Self::ControlB::CS11;")?;
writeln!(w, " const CS2: Mask<Self::ControlB> = Self::ControlB::CS12;")?;
writeln!(w, " const WGM0: Mask<Self::ControlA> = Self::ControlA::WGM10;")?;
writeln!(w, " const WGM1: Mask<Self::ControlA> = Self::ControlA::WGM11;")?;
writeln!(w, " const WGM2: Mask<Self::ControlB> = Self::ControlB::WGM10;")?;
writeln!(w, " const WGM3: Mask<Self::ControlB> = Self::ControlB::WGM11;")?;
writeln!(w, " const OCIEA: Bitset<Self::InterruptMask> = Self::InterruptMask::OCIE1A;")?;
writeln!(w, "}}")?;
}

View File

@ -14,11 +14,11 @@ pub trait HardwareSpi {
type SlaveSelect: Pin;
/// The SPI control register.
type ControlRegister: Register<u8>;
type ControlRegister: Register<T=u8>;
/// The SPI status register.
type StatusRegister: Register<u8>;
type StatusRegister: Register<T=u8>;
/// The SPI data register.
type DataRegister: Register<u8>;
type DataRegister: Register<T=u8>;
/// Sets up the SPI as a master.
fn setup_master(clock: u32) {

View File

@ -2,57 +2,57 @@ use {Bitset, Mask, Register};
use core::marker;
/// A 16-bit timer.
pub trait Timer16 {
pub trait Timer16 : Sized {
/// The first compare register.
/// For example, OCR0A.
type CompareA: Register<u16>;
type CompareA: Register<T=u16>;
/// The second compare register.
/// For example, OCR0B.
type CompareB: Register<u16>;
type CompareB: Register<T=u16>;
/// The counter register.
///
/// For example, TCNT0.
type Counter: Register<u16>;
type Counter: Register<T=u16>;
/// The first control register.
///
/// For example, TCCR0A.
type ControlA: Register<u8>;
type ControlA: Register<T=u8>;
/// The second control register.
///
/// For example, TCCR0B.
type ControlB: Register<u8>;
type ControlB: Register<T=u8>;
/// The third control register.
///
/// For example, TCCR0C.
type ControlC: Register<u8>;
type ControlC: Register<T=u8>;
/// The interrupt mask register.
///
/// For example, TIMSK0.
type InterruptMask: Register<u8>;
type InterruptMask: Register<T=u8>;
/// The interrupt flag register.
///
/// For example, TIFR0.
type InterruptFlag: Register<u8>;
type InterruptFlag: Register<T=u8>;
const CS0: Mask<u8, Self::ControlB>;
const CS1: Mask<u8, Self::ControlB>;
const CS2: Mask<u8, Self::ControlB>;
const CS0: Mask<Self::ControlB>;
const CS1: Mask<Self::ControlB>;
const CS2: Mask<Self::ControlB>;
const WGM0: Mask<u8, Self::ControlA>;
const WGM1: Mask<u8, Self::ControlA>;
const WGM2: Mask<u8, Self::ControlB>;
const WGM3: Mask<u8, Self::ControlB>;
const WGM0: Mask<Self::ControlA>;
const WGM1: Mask<Self::ControlA>;
const WGM2: Mask<Self::ControlB>;
const WGM3: Mask<Self::ControlB>;
const OCIEA: Bitset<u8, Self::InterruptMask>;
const OCIEA: Bitset<Self::InterruptMask>;
fn setup() -> Timer16Setup<T> { Timer16Setup::new() }
fn setup() -> Timer16Setup<Self> { Timer16Setup::new() }
}
pub enum ClockSource {
@ -67,7 +67,7 @@ pub enum ClockSource {
}
impl ClockSource {
fn bits<T: Timer16>(&self) -> Mask<u8, T::ControlB> {
fn bits<T: Timer16>(&self) -> Mask<T::ControlB> {
use self::ClockSource::*;
match *self {
@ -83,7 +83,7 @@ impl ClockSource {
}
#[inline]
fn mask<T: Timer16>() -> Mask<u8, T::ControlB> {
fn mask<T: Timer16>() -> Mask<T::ControlB> {
!(T::CS2 | T::CS1 | T::CS0)
}
}
@ -109,7 +109,7 @@ pub enum WaveformGenerationMode {
impl WaveformGenerationMode {
/// Returns bits for TCCR1A, TCCR1B
#[inline]
fn bits<T: Timer16>(&self) -> (Mask<u8, T::ControlA>, Mask<u8, T::ControlB>) {
fn bits<T: Timer16>(&self) -> (Mask<T::ControlA>, Mask<T::ControlB>) {
use self::WaveformGenerationMode::*;
// It makes more sense to return bytes (A,B), but the manual
@ -139,15 +139,15 @@ impl WaveformGenerationMode {
}
#[inline]
fn mask<T: Timer16>() -> (Mask<u8, T::ControlA>, Mask<u8, T::ControlB>) {
fn mask<T: Timer16>() -> (Mask<T::ControlA>, Mask<T::ControlB>) {
(!(T::WGM0 | T::WGM1), !(T::WGM2 | T::WGM3))
}
}
pub struct Timer16Setup<T: Timer16> {
a: Mask<u8, T::ControlA>,
b: Mask<u8, T::ControlB>,
c: Mask<u8, T::ControlC>,
a: Mask<T::ControlA>,
b: Mask<T::ControlB>,
c: Mask<T::ControlC>,
output_compare_1: Option<u16>,
_phantom: marker::PhantomData<T>,
}

View File

@ -2,49 +2,49 @@ use {Bitset, Mask, Register};
use core::marker;
/// A 8-bit timer.
pub trait Timer8 {
pub trait Timer8 : Sized {
/// The first compare register.
/// For example, OCR0A.
type CompareA: Register<u8>;
type CompareA: Register<T=u8>;
/// The second compare register.
/// For example, OCR0B.
type CompareB: Register<u8>;
type CompareB: Register<T=u8>;
/// The counter register.
///
/// For example, TCNT0.
type Counter: Register<u8>;
type Counter: Register<T=u8>;
/// The first control register.
///
/// For example, TCCR0A.
type ControlA: Register<u8>;
type ControlA: Register<T=u8>;
/// The second control register.
///
/// For example, TCCR0B.
type ControlB: Register<u8>;
type ControlB: Register<T=u8>;
/// The interrupt mask register.
///
/// For example, TIMSK0.
type InterruptMask: Register<u8>;
type InterruptMask: Register<T=u8>;
/// The interrupt flag register.
///
/// For example, TIFR0.
type InterruptFlag: Register<u8>;
type InterruptFlag: Register<T=u8>;
const CS0: Mask<u8, Self::ControlB>;
const CS1: Mask<u8, Self::ControlB>;
const CS2: Mask<u8, Self::ControlB>;
const CS0: Mask<Self::ControlB>;
const CS1: Mask<Self::ControlB>;
const CS2: Mask<Self::ControlB>;
const WGM0: Mask<u8, Self::ControlA>;
const WGM1: Mask<u8, Self::ControlA>;
const WGM2: Mask<u8, Self::ControlB>;
const WGM0: Mask<Self::ControlA>;
const WGM1: Mask<Self::ControlA>;
const WGM2: Mask<Self::ControlB>;
const OCIEA: Bitset<u8, Self::InterruptMask>;
const OCIEA: Bitset<Self::InterruptMask>;
}
pub enum ClockSource {
@ -59,7 +59,7 @@ pub enum ClockSource {
}
impl ClockSource {
fn bits<T: Timer8>(&self) -> Mask<u8, T::ControlB> {
fn bits<T: Timer8>(&self) -> Mask<T::ControlB> {
use self::ClockSource::*;
match *self {
@ -75,7 +75,7 @@ impl ClockSource {
}
#[inline]
fn mask<T: Timer8>() -> Mask<u8, T::ControlB> {
fn mask<T: Timer8>() -> Mask<T::ControlB> {
!(T::CS2 | T::CS1 | T::CS0)
}
}
@ -92,7 +92,7 @@ pub enum WaveformGenerationMode {
impl WaveformGenerationMode {
/// Returns bits for TCCR0A, TCCR0B
#[inline]
fn bits<T: Timer8>(&self) -> (Mask<u8, T::ControlA>, Mask<u8, T::ControlB>) {
fn bits<T: Timer8>(&self) -> (Mask<T::ControlA>, Mask<T::ControlB>) {
use self::WaveformGenerationMode::*;
// It makes more sense to return bytes (A,B), but the manual
@ -114,14 +114,14 @@ impl WaveformGenerationMode {
}
#[inline]
fn mask<T: Timer8>() -> (Mask<u8, T::ControlA>, Mask<u8, T::ControlB>) {
fn mask<T: Timer8>() -> (Mask<T::ControlA>, Mask<T::ControlB>) {
(!(T::WGM0 | T::WGM1), !(T::WGM2))
}
}
pub struct Timer8Setup<T: Timer8> {
a: Mask<u8, T::ControlA>,
b: Mask<u8, T::ControlB>,
a: Mask<T::ControlA>,
b: Mask<T::ControlB>,
output_compare_1: Option<u8>,
_phantom: marker::PhantomData<T>,
}

View File

@ -2,13 +2,13 @@ use Register;
pub trait HardwareUsart {
/// The USART data register.
type DataRegister: Register<u8>;
type DataRegister: Register<T=u8>;
/// USART control and status register A.
type ControlRegisterA: Register<u8>;
type ControlRegisterA: Register<T=u8>;
/// USART control and status register B.
type ControlRegisterB: Register<u8>;
type ControlRegisterB: Register<T=u8>;
/// USART control and status register C.
type ControlRegisterC: Register<u8>;
type ControlRegisterC: Register<T=u8>;
/// USART baud rate register.
type BaudRateRegister: Register<u16>;
type BaudRateRegister: Register<T=u16>;
}

View File

@ -3,14 +3,14 @@ use {DataDirection, Register};
/// An IO pin.
pub trait Pin {
/// The associated data direction register.
type DDR: Register<u8>;
type DDR: Register<T=u8>;
/// The associated port register.
type PORT: Register<u8>;
type PORT: Register<T=u8>;
/// The associated pin register.
///
/// Reads from the register will read input bits.
/// Writes to the register will toggle bits.
type PIN: Register<u8>;
type PIN: Register<T=u8>;
/// The mask of the pin used for accessing registers.
const MASK: u8;

View File

@ -14,15 +14,16 @@ pub trait RegisterValue : Copy + Clone +
}
/// A register.
pub trait Register<T: RegisterValue> : Sized {
type Mask = Mask<T, Self>;
pub trait Register : Sized {
type T: RegisterValue;
type Mask = Mask<Self>;
/// The address of the register.
const ADDR: *mut T;
const ADDR: *mut Self::T;
/// Writes a value to the register.
#[inline(always)]
fn write<V>(value: V) where V: Into<T> {
fn write<V>(value: V) where V: Into<Self::T> {
unsafe {
*Self::ADDR = value.into();
}
@ -30,11 +31,11 @@ pub trait Register<T: RegisterValue> : Sized {
/// Reads the value of the register.
#[inline(always)]
fn read() -> T {
fn read() -> Self::T {
unsafe { *Self::ADDR }
}
fn set(mask: Mask<T, Self>) {
fn set(mask: Mask<Self>) {
Self::set_raw(mask.mask);
}
@ -42,13 +43,13 @@ pub trait Register<T: RegisterValue> : Sized {
///
/// This is equivalent to `r |= mask`.
#[inline(always)]
fn set_raw(mask: T) {
fn set_raw(mask: Self::T) {
unsafe {
*Self::ADDR |= mask;
}
}
fn unset(mask: Mask<T, Self>) {
fn unset(mask: Mask<Self>) {
Self::unset_raw(mask.mask);
}
@ -56,13 +57,13 @@ pub trait Register<T: RegisterValue> : Sized {
///
/// This is equivalent to `r &= !mask`.
#[inline(always)]
fn unset_raw(mask: T) {
fn unset_raw(mask: Self::T) {
unsafe {
*Self::ADDR &= !mask;
}
}
fn toggle(mask: Mask<T, Self>) {
fn toggle(mask: Mask<Self>) {
Self::toggle_raw(mask.mask);
}
@ -70,13 +71,13 @@ pub trait Register<T: RegisterValue> : Sized {
///
/// This is equivalent to `r ^= mask`.
#[inline(always)]
fn toggle_raw(mask: T) {
fn toggle_raw(mask: Self::T) {
unsafe {
*Self::ADDR ^= mask;
}
}
fn is_set(mask: Mask<T, Self>) -> bool {
fn is_set(mask: Mask<Self>) -> bool {
Self::is_set_raw(mask.mask)
}
@ -84,13 +85,13 @@ pub trait Register<T: RegisterValue> : Sized {
///
/// This is equivalent to `(r & mask) == mask`.
#[inline(always)]
fn is_set_raw(mask: T) -> bool {
fn is_set_raw(mask: Self::T) -> bool {
unsafe {
(*Self::ADDR & mask) == mask
}
}
fn is_clear(mask: Mask<T, Self>) -> bool {
fn is_clear(mask: Mask<Self>) -> bool {
Self::is_clear_raw(mask.mask)
}
@ -98,9 +99,9 @@ pub trait Register<T: RegisterValue> : Sized {
///
/// This is equivalent to `(r & mask) == 0`.
#[inline(always)]
fn is_clear_raw(mask: T) -> bool {
fn is_clear_raw(mask: Self::T) -> bool {
unsafe {
(*Self::ADDR & mask) == T::from(0)
(*Self::ADDR & mask) == Self::T::from(0)
}
}
@ -115,35 +116,34 @@ pub trait Register<T: RegisterValue> : Sized {
}
}
fn wait_until_set(mask: Mask<T, Self>) {
fn wait_until_set(mask: Mask<Self>) {
Self::wait_until_set_raw(mask.mask);
}
/// Waits until a mask is set.
#[inline(always)]
fn wait_until_set_raw(mask: T) {
fn wait_until_set_raw(mask: Self::T) {
Self::wait_until(|| Self::is_set_raw(mask))
}
}
/// A register bitmask.
#[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct Bitset<T: RegisterValue, R: Register<T>> {
mask: T,
pub struct Bitset<R: Register> {
mask: R::T,
_phantom: marker::PhantomData<R>,
}
/// A register bitmask.
#[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct Mask<T: RegisterValue, R: Register<T>> {
mask: T,
pub struct Mask<R: Register> {
mask: R::T,
_phantom: marker::PhantomData<R>,
}
impl<T,R> Bitset<T,R>
where T: RegisterValue, R: Register<T> {
impl<R> Bitset<R> where R: Register {
/// Creates a new register mask.
pub const fn new(mask: T) -> Self {
pub const fn new(mask: R::T) -> Self {
Bitset { mask, _phantom: marker::PhantomData }
}
@ -176,10 +176,9 @@ impl<T,R> Bitset<T,R>
}
}
impl<T,R> Mask<T,R>
where T: RegisterValue, R: Register<T> {
impl<R> Mask<R> where R: Register {
/// Creates a new register mask.
pub const fn new(mask: T) -> Self {
pub const fn new(mask: R::T) -> Self {
Mask { mask, _phantom: marker::PhantomData }
}
@ -188,8 +187,7 @@ impl<T,R> Mask<T,R>
}
}
impl<T,R> ops::BitOr for Mask<T,R>
where T: RegisterValue, R: Register<T>
impl<R> ops::BitOr for Mask<R> where R: Register
{
type Output = Self;
@ -198,15 +196,13 @@ impl<T,R> ops::BitOr for Mask<T,R>
}
}
impl<T,R> ops::BitOrAssign for Mask<T,R>
where T: RegisterValue, R: Register<T> {
impl<R> ops::BitOrAssign for Mask<R> where R: Register {
fn bitor_assign(&mut self, rhs: Self) {
self.mask |= rhs.mask;
}
}
impl<T,R> ops::BitAnd for Mask<T,R>
where T: RegisterValue, R: Register<T>
impl<R> ops::BitAnd for Mask<R> where R: Register
{
type Output = Self;
@ -215,15 +211,13 @@ impl<T,R> ops::BitAnd for Mask<T,R>
}
}
impl<T,R> ops::BitAndAssign for Mask<T,R>
where T: RegisterValue, R: Register<T> {
impl<R> ops::BitAndAssign for Mask<R> where R: Register {
fn bitand_assign(&mut self, rhs: Self) {
self.mask &= rhs.mask;
}
}
impl<T,R> ops::Not for Mask<T,R>
where T: RegisterValue, R: Register<T> {
impl<R> ops::Not for Mask<R> where R: Register {
type Output = Self;
fn not(self) -> Self {
@ -231,10 +225,12 @@ impl<T,R> ops::Not for Mask<T,R>
}
}
impl<R> Into<u8> for Mask<u8,R> where R: Register<u8> {
fn into(self) -> u8 {
self.mask
}
impl<R> Into<u8> for Mask<R> where R: Register<T=u8> {
fn into(self) -> u8 { self.mask }
}
impl<R> Into<u16> for Mask<R> where R: Register<T=u16> {
fn into(self) -> u16 { self.mask }
}
impl RegisterValue for u8 { }