tock_registers/
lib.rs

1// Licensed under the Apache License, Version 2.0 or the MIT License.
2// SPDX-License-Identifier: Apache-2.0 OR MIT
3// Copyright Tock Contributors 2022.
4
5//! Tock Register Interface
6//!
7//! Provides efficient mechanisms to express and use type-checked memory mapped
8//! registers and bitfields.
9//!
10//! ```rust
11//! # fn main() {}
12//!
13//! use tock_registers::registers::{ReadOnly, ReadWrite};
14//! use tock_registers::register_bitfields;
15//!
16//! // Register maps are specified like this:
17//! #[repr(C)]
18//! struct Registers {
19//!     // Control register: read-write
20//!     cr: ReadWrite<u32, Control::Register>,
21//!     // Status register: read-only
22//!     s: ReadOnly<u32, Status::Register>,
23//! }
24//!
25//! // Register fields and definitions look like this:
26//! register_bitfields![u32,
27//!     // Simpler bitfields are expressed concisely:
28//!     Control [
29//!         /// Stop the Current Transfer
30//!         STOP 8,
31//!         /// Software Reset
32//!         SWRST 7,
33//!         /// Master Disable
34//!         MDIS 1,
35//!         /// Master Enable
36//!         MEN 0
37//!     ],
38//!
39//!     // More complex registers can express subtypes:
40//!     Status [
41//!         TXCOMPLETE  OFFSET(0) NUMBITS(1) [],
42//!         TXINTERRUPT OFFSET(1) NUMBITS(1) [],
43//!         RXCOMPLETE  OFFSET(2) NUMBITS(1) [],
44//!         RXINTERRUPT OFFSET(3) NUMBITS(1) [],
45//!         MODE        OFFSET(4) NUMBITS(3) [
46//!             FullDuplex = 0,
47//!             HalfDuplex = 1,
48//!             Loopback = 2,
49//!             Disabled = 3
50//!         ],
51//!         ERRORCOUNT OFFSET(6) NUMBITS(3) []
52//!     ]
53//! ];
54//! ```
55//!
56//! Author
57//! ------
58//! - Shane Leonard <shanel@stanford.edu>
59
60#![no_std]
61// If we don't build any actual register types, we don't need unsafe code in
62// this crate
63#![cfg_attr(not(feature = "register_types"), forbid(unsafe_code))]
64
65pub mod fields;
66pub mod interfaces;
67pub mod macros;
68
69#[cfg(feature = "register_types")]
70pub mod registers;
71
72pub mod debug;
73
74mod local_register;
75pub use local_register::LocalRegisterCopy;
76
77use core::fmt::Debug;
78use core::ops::{BitAnd, BitOr, BitOrAssign, Not, Shl, Shr};
79
80/// Trait representing the base type of registers.
81///
82/// UIntLike defines basic properties of types required to read/write/modify a
83/// register through its methods and supertrait requirements.
84///
85/// It features a range of default implementations for common unsigned integer
86/// types, such as [`u8`], [`u16`], [`u32`], [`u64`], [`u128`], and [`usize`].
87pub trait UIntLike:
88    BitAnd<Output = Self>
89    + BitOr<Output = Self>
90    + BitOrAssign
91    + Not<Output = Self>
92    + Eq
93    + Shr<usize, Output = Self>
94    + Shl<usize, Output = Self>
95    + Copy
96    + Clone
97    + Debug
98{
99    /// Return the representation of the value `0` in the implementing type.
100    ///
101    /// This can be used to acquire values of the [`UIntLike`] type, even in
102    /// generic implementations. For instance, to get the value `1`, one can use
103    /// `<T as UIntLike>::zero() + 1`. To get the largest representable value,
104    /// use a bitwise negation: `~(<T as UIntLike>::zero())`.
105    fn zero() -> Self;
106}
107
108// Helper macro for implementing the UIntLike trait on different types.
109macro_rules! UIntLike_impl_for {
110    ($type:ty) => {
111        impl UIntLike for $type {
112            fn zero() -> Self {
113                0
114            }
115        }
116    };
117}
118
119UIntLike_impl_for!(u8);
120UIntLike_impl_for!(u16);
121UIntLike_impl_for!(u32);
122UIntLike_impl_for!(u64);
123UIntLike_impl_for!(u128);
124UIntLike_impl_for!(usize);
125
126/// Descriptive name for each register.
127pub trait RegisterLongName {}
128
129// Useful implementation for when no RegisterLongName is required (e.g. no
130// fields need to be accessed, just the raw register values)
131impl RegisterLongName for () {}