diff --git a/CHANGELOG.md b/CHANGELOG.md index 75eab9a1..9c935cd6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/). - removed register writer & reader wrappers, generic `REG` in field writers (#731) - Updated syn to version 2 (#732) - Let readable field fetch doc from svd description (#734) +- Add `steal()` for each peripheral ## [v0.29.0] - 2023-06-05 diff --git a/src/generate/peripheral.rs b/src/generate/peripheral.rs index 5dbfdeb8..b27051bb 100644 --- a/src/generate/peripheral.rs +++ b/src/generate/peripheral.rs @@ -53,6 +53,25 @@ pub fn render(p_original: &Peripheral, index: &Index, config: &Config) -> Result feature_attribute.extend(quote! { #[cfg(feature = #feature_name)] }); }; + let steal_fn = quote! { + /// Steal an instance of this peripheral + /// + /// # Safety + /// + /// Ensure that the new instance of the peripheral cannot be used in a way + /// that may race with any existing instances, for example by only + /// accessing read-only or write-only registers, or by consuming the + /// original peripheral and using critical sections to coordinate + /// access between multiple new instances. + /// + /// Additionally, other software such as HALs may rely on only one + /// peripheral instance existing to ensure memory safety; ensure + /// no stolen instances are passed to such software. + pub unsafe fn steal() -> Self { + Self { _marker: PhantomData } + } + }; + match &p { Peripheral::Array(p, dim) => { let names: Vec> = names(p, dim).map(|n| n.into()).collect(); @@ -91,6 +110,8 @@ pub fn render(p_original: &Peripheral, index: &Index, config: &Config) -> Result pub const fn ptr() -> *const #base::RegisterBlock { Self::PTR } + + #steal_fn } #feature_attribute_n @@ -150,6 +171,8 @@ pub fn render(p_original: &Peripheral, index: &Index, config: &Config) -> Result pub const fn ptr() -> *const #base::RegisterBlock { Self::PTR } + + #steal_fn } #feature_attribute diff --git a/src/lib.rs b/src/lib.rs index 08d90bf6..2fae4718 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -186,9 +186,9 @@ //! use the implementation provided by the target crate like `cortex-m`, `riscv` and `*-hal` crates. //! See more details in the [`critical-section`](https://crates.io/crates/critical-section) crate documentation. //! -//! The singleton property can be *unsafely* bypassed using the `ptr` static method which is -//! available on all the peripheral types. This method is useful for implementing safe higher -//! level abstractions. +//! The singleton property can be *unsafely* bypassed using the `ptr` or `steal` static methods +//! which are available on all the peripheral types. This method is useful for implementing safe +//! higher level abstractions. //! //! ```ignore //! struct PA0 { _0: () }