aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDario Nieuwenhuis <[email protected]>2022-07-23 01:29:35 +0200
committerDario Nieuwenhuis <[email protected]>2022-07-23 02:40:13 +0200
commit8a9d2f59af004902d3978a2922843833b98bcce0 (patch)
tree27a435fe0bc81d344472b76a6cd3666edbb83889
parente0521ea249d375097c9d62c602b8f598e6b65292 (diff)
Update embassy-stm32
-rw-r--r--embassy-cortex-m/src/peripheral.rs21
-rw-r--r--embassy-hal-common/src/unborrow.rs10
-rw-r--r--embassy-lora/src/stm32wl/mod.rs46
-rw-r--r--embassy-nrf/src/lib.rs2
-rw-r--r--embassy-rp/src/lib.rs2
-rw-r--r--embassy-stm32/src/can/bxcan.rs48
-rw-r--r--embassy-stm32/src/crc/v1.rs15
-rw-r--r--embassy-stm32/src/crc/v2v3.rs8
-rw-r--r--embassy-stm32/src/dac/v2.rs13
-rw-r--r--embassy-stm32/src/dcmi.rs20
-rw-r--r--embassy-stm32/src/dma/mod.rs11
-rw-r--r--embassy-stm32/src/eth/v1/mod.rs22
-rw-r--r--embassy-stm32/src/eth/v2/mod.rs22
-rw-r--r--embassy-stm32/src/flash/mod.rs16
-rw-r--r--embassy-stm32/src/gpio.rs19
-rw-r--r--embassy-stm32/src/i2c/v2.rs15
-rw-r--r--embassy-stm32/src/lib.rs2
-rw-r--r--embassy-stm32/src/pwm/simple_pwm.rs12
-rw-r--r--embassy-stm32/src/rng.rs11
-rw-r--r--embassy-stm32/src/sdmmc/mod.rs377
-rw-r--r--embassy-stm32/src/spi/mod.rs45
-rw-r--r--embassy-stm32/src/usart/mod.rs12
-rw-r--r--examples/stm32f4/src/bin/sdmmc.rs11
-rw-r--r--examples/stm32f7/src/bin/sdmmc.rs11
-rw-r--r--examples/stm32h7/src/bin/low_level_timer_api.rs12
-rw-r--r--examples/stm32h7/src/bin/sdmmc.rs9
26 files changed, 432 insertions, 360 deletions
diff --git a/embassy-cortex-m/src/peripheral.rs b/embassy-cortex-m/src/peripheral.rs
index 6a03bfb9f..c5fa20e71 100644
--- a/embassy-cortex-m/src/peripheral.rs
+++ b/embassy-cortex-m/src/peripheral.rs
@@ -1,9 +1,9 @@
1//! Peripheral interrupt handling specific to cortex-m devices. 1//! Peripheral interrupt handling specific to cortex-m devices.
2use core::marker::PhantomData;
3use core::mem::MaybeUninit; 2use core::mem::MaybeUninit;
4 3
5use cortex_m::peripheral::scb::VectActive; 4use cortex_m::peripheral::scb::VectActive;
6use cortex_m::peripheral::{NVIC, SCB}; 5use cortex_m::peripheral::{NVIC, SCB};
6use embassy_hal_common::{unborrow, Unborrow, Unborrowed};
7 7
8use crate::interrupt::{Interrupt, InterruptExt, Priority}; 8use crate::interrupt::{Interrupt, InterruptExt, Priority};
9 9
@@ -33,8 +33,7 @@ impl<S> StateStorage<S> {
33/// a safe way. 33/// a safe way.
34pub struct PeripheralMutex<'a, S: PeripheralState> { 34pub struct PeripheralMutex<'a, S: PeripheralState> {
35 state: *mut S, 35 state: *mut S,
36 _phantom: PhantomData<&'a mut S>, 36 irq: Unborrowed<'a, S::Interrupt>,
37 irq: S::Interrupt,
38} 37}
39 38
40/// Whether `irq` can be preempted by the current interrupt. 39/// Whether `irq` can be preempted by the current interrupt.
@@ -62,8 +61,14 @@ impl<'a, S: PeripheralState> PeripheralMutex<'a, S> {
62 /// Create a new `PeripheralMutex` wrapping `irq`, with `init` initializing the initial state. 61 /// Create a new `PeripheralMutex` wrapping `irq`, with `init` initializing the initial state.
63 /// 62 ///
64 /// Registers `on_interrupt` as the `irq`'s handler, and enables it. 63 /// Registers `on_interrupt` as the `irq`'s handler, and enables it.
65 pub fn new(irq: S::Interrupt, storage: &'a mut StateStorage<S>, init: impl FnOnce() -> S) -> Self { 64 pub fn new(
66 if can_be_preempted(&irq) { 65 irq: impl Unborrow<Target = S::Interrupt> + 'a,
66 storage: &'a mut StateStorage<S>,
67 init: impl FnOnce() -> S,
68 ) -> Self {
69 unborrow!(irq);
70
71 if can_be_preempted(&*irq) {
67 panic!( 72 panic!(
68 "`PeripheralMutex` cannot be created in an interrupt with higher priority than the interrupt it wraps" 73 "`PeripheralMutex` cannot be created in an interrupt with higher priority than the interrupt it wraps"
69 ); 74 );
@@ -88,11 +93,7 @@ impl<'a, S: PeripheralState> PeripheralMutex<'a, S> {
88 irq.set_handler_context(state_ptr as *mut ()); 93 irq.set_handler_context(state_ptr as *mut ());
89 irq.enable(); 94 irq.enable();
90 95
91 Self { 96 Self { irq, state: state_ptr }
92 irq,
93 state: state_ptr,
94 _phantom: PhantomData,
95 }
96 } 97 }
97 98
98 /// Access the peripheral state ensuring interrupts are disabled so that the state can be 99 /// Access the peripheral state ensuring interrupts are disabled so that the state can be
diff --git a/embassy-hal-common/src/unborrow.rs b/embassy-hal-common/src/unborrow.rs
index 7ed823c52..06e8d0c82 100644
--- a/embassy-hal-common/src/unborrow.rs
+++ b/embassy-hal-common/src/unborrow.rs
@@ -16,6 +16,16 @@ impl<'a, T> Unborrowed<'a, T> {
16 } 16 }
17 } 17 }
18 18
19 pub fn map_into<U>(self) -> Unborrowed<'a, U>
20 where
21 T: Into<U>,
22 {
23 Unborrowed {
24 inner: self.inner.into(),
25 _lifetime: PhantomData,
26 }
27 }
28
19 pub unsafe fn into_inner(self) -> T { 29 pub unsafe fn into_inner(self) -> T {
20 self.inner 30 self.inner
21 } 31 }
diff --git a/embassy-lora/src/stm32wl/mod.rs b/embassy-lora/src/stm32wl/mod.rs
index d7d399692..49991db13 100644
--- a/embassy-lora/src/stm32wl/mod.rs
+++ b/embassy-lora/src/stm32wl/mod.rs
@@ -3,7 +3,7 @@ use core::future::Future;
3use core::mem::MaybeUninit; 3use core::mem::MaybeUninit;
4 4
5use embassy::channel::signal::Signal; 5use embassy::channel::signal::Signal;
6use embassy_hal_common::unborrow; 6use embassy_hal_common::{unborrow, Unborrowed};
7use embassy_stm32::dma::NoDma; 7use embassy_stm32::dma::NoDma;
8use embassy_stm32::gpio::{AnyPin, Output}; 8use embassy_stm32::gpio::{AnyPin, Output};
9use embassy_stm32::interrupt::{InterruptExt, SUBGHZ_RADIO}; 9use embassy_stm32::interrupt::{InterruptExt, SUBGHZ_RADIO};
@@ -30,35 +30,35 @@ pub struct RadioError;
30 30
31static IRQ: Signal<(Status, u16)> = Signal::new(); 31static IRQ: Signal<(Status, u16)> = Signal::new();
32 32
33struct StateInner<'a> { 33struct StateInner<'d> {
34 radio: SubGhz<'a, NoDma, NoDma>, 34 radio: SubGhz<'d, NoDma, NoDma>,
35 switch: RadioSwitch<'a>, 35 switch: RadioSwitch<'d>,
36} 36}
37 37
38/// External state storage for the radio state 38/// External state storage for the radio state
39pub struct SubGhzState<'a>(MaybeUninit<StateInner<'a>>); 39pub struct SubGhzState<'a>(MaybeUninit<StateInner<'a>>);
40impl<'a> SubGhzState<'a> { 40impl<'d> SubGhzState<'d> {
41 pub const fn new() -> Self { 41 pub const fn new() -> Self {
42 Self(MaybeUninit::uninit()) 42 Self(MaybeUninit::uninit())
43 } 43 }
44} 44}
45 45
46/// The radio peripheral keeping the radio state and owning the radio IRQ. 46/// The radio peripheral keeping the radio state and owning the radio IRQ.
47pub struct SubGhzRadio<'a> { 47pub struct SubGhzRadio<'d> {
48 state: *mut StateInner<'a>, 48 state: *mut StateInner<'d>,
49 _irq: SUBGHZ_RADIO, 49 _irq: Unborrowed<'d, SUBGHZ_RADIO>,
50} 50}
51 51
52impl<'a> SubGhzRadio<'a> { 52impl<'d> SubGhzRadio<'d> {
53 /// Create a new instance of a SubGhz radio for LoRaWAN. 53 /// Create a new instance of a SubGhz radio for LoRaWAN.
54 /// 54 ///
55 /// # Safety 55 /// # Safety
56 /// Do not leak self or futures 56 /// Do not leak self or futures
57 pub unsafe fn new( 57 pub unsafe fn new(
58 state: &'a mut SubGhzState<'a>, 58 state: &'d mut SubGhzState<'d>,
59 radio: SubGhz<'a, NoDma, NoDma>, 59 radio: SubGhz<'d, NoDma, NoDma>,
60 switch: RadioSwitch<'a>, 60 switch: RadioSwitch<'d>,
61 irq: impl Unborrow<Target = SUBGHZ_RADIO>, 61 irq: impl Unborrow<Target = SUBGHZ_RADIO> + 'd,
62 ) -> Self { 62 ) -> Self {
63 unborrow!(irq); 63 unborrow!(irq);
64 64
@@ -73,7 +73,7 @@ impl<'a> SubGhzRadio<'a> {
73 // This is safe because we only get interrupts when configured for, so 73 // This is safe because we only get interrupts when configured for, so
74 // the radio will be awaiting on the signal at this point. If not, the ISR will 74 // the radio will be awaiting on the signal at this point. If not, the ISR will
75 // anyway only adjust the state in the IRQ signal state. 75 // anyway only adjust the state in the IRQ signal state.
76 let state = &mut *(p as *mut StateInner<'a>); 76 let state = &mut *(p as *mut StateInner<'d>);
77 state.on_interrupt(); 77 state.on_interrupt();
78 }); 78 });
79 irq.set_handler_context(state_ptr as *mut ()); 79 irq.set_handler_context(state_ptr as *mut ());
@@ -86,7 +86,7 @@ impl<'a> SubGhzRadio<'a> {
86 } 86 }
87} 87}
88 88
89impl<'a> StateInner<'a> { 89impl<'d> StateInner<'d> {
90 /// Configure radio settings in preparation for TX or RX 90 /// Configure radio settings in preparation for TX or RX
91 pub(crate) fn configure(&mut self) -> Result<(), RadioError> { 91 pub(crate) fn configure(&mut self) -> Result<(), RadioError> {
92 trace!("Configuring STM32WL SUBGHZ radio"); 92 trace!("Configuring STM32WL SUBGHZ radio");
@@ -272,13 +272,13 @@ impl PhyRxTx for SubGhzRadio<'static> {
272 } 272 }
273} 273}
274 274
275impl<'a> From<embassy_stm32::spi::Error> for RadioError { 275impl From<embassy_stm32::spi::Error> for RadioError {
276 fn from(_: embassy_stm32::spi::Error) -> Self { 276 fn from(_: embassy_stm32::spi::Error) -> Self {
277 RadioError 277 RadioError
278 } 278 }
279} 279}
280 280
281impl<'a> Timings for SubGhzRadio<'a> { 281impl<'d> Timings for SubGhzRadio<'d> {
282 fn get_rx_window_offset_ms(&self) -> i32 { 282 fn get_rx_window_offset_ms(&self) -> i32 {
283 -200 283 -200
284 } 284 }
@@ -288,14 +288,14 @@ impl<'a> Timings for SubGhzRadio<'a> {
288} 288}
289 289
290/// Represents the radio switch found on STM32WL based boards, used to control the radio for transmission or reception. 290/// Represents the radio switch found on STM32WL based boards, used to control the radio for transmission or reception.
291pub struct RadioSwitch<'a> { 291pub struct RadioSwitch<'d> {
292 ctrl1: Output<'a, AnyPin>, 292 ctrl1: Output<'d, AnyPin>,
293 ctrl2: Output<'a, AnyPin>, 293 ctrl2: Output<'d, AnyPin>,
294 ctrl3: Output<'a, AnyPin>, 294 ctrl3: Output<'d, AnyPin>,
295} 295}
296 296
297impl<'a> RadioSwitch<'a> { 297impl<'d> RadioSwitch<'d> {
298 pub fn new(ctrl1: Output<'a, AnyPin>, ctrl2: Output<'a, AnyPin>, ctrl3: Output<'a, AnyPin>) -> Self { 298 pub fn new(ctrl1: Output<'d, AnyPin>, ctrl2: Output<'d, AnyPin>, ctrl3: Output<'d, AnyPin>) -> Self {
299 Self { ctrl1, ctrl2, ctrl3 } 299 Self { ctrl1, ctrl2, ctrl3 }
300 } 300 }
301 301
diff --git a/embassy-nrf/src/lib.rs b/embassy-nrf/src/lib.rs
index 3699ad0fa..b6a21caa2 100644
--- a/embassy-nrf/src/lib.rs
+++ b/embassy-nrf/src/lib.rs
@@ -135,7 +135,7 @@ pub use chip::pac;
135pub(crate) use chip::pac; 135pub(crate) use chip::pac;
136pub use chip::{peripherals, Peripherals}; 136pub use chip::{peripherals, Peripherals};
137pub use embassy_cortex_m::executor; 137pub use embassy_cortex_m::executor;
138pub use embassy_hal_common::{unborrow, Unborrow}; 138pub use embassy_hal_common::{unborrow, Unborrow, Unborrowed};
139pub use embassy_macros::cortex_m_interrupt as interrupt; 139pub use embassy_macros::cortex_m_interrupt as interrupt;
140 140
141pub mod config { 141pub mod config {
diff --git a/embassy-rp/src/lib.rs b/embassy-rp/src/lib.rs
index 7da0d30c1..e36761ac9 100644
--- a/embassy-rp/src/lib.rs
+++ b/embassy-rp/src/lib.rs
@@ -17,7 +17,7 @@ mod reset;
17// Reexports 17// Reexports
18 18
19pub use embassy_cortex_m::executor; 19pub use embassy_cortex_m::executor;
20pub use embassy_hal_common::{unborrow, Unborrow}; 20pub use embassy_hal_common::{unborrow, Unborrow, Unborrowed};
21pub use embassy_macros::cortex_m_interrupt as interrupt; 21pub use embassy_macros::cortex_m_interrupt as interrupt;
22#[cfg(feature = "unstable-pac")] 22#[cfg(feature = "unstable-pac")]
23pub use rp2040_pac2 as pac; 23pub use rp2040_pac2 as pac;
diff --git a/embassy-stm32/src/can/bxcan.rs b/embassy-stm32/src/can/bxcan.rs
index b54fd3ff3..6c0de2ded 100644
--- a/embassy-stm32/src/can/bxcan.rs
+++ b/embassy-stm32/src/can/bxcan.rs
@@ -1,19 +1,17 @@
1use core::marker::PhantomData;
2use core::ops::{Deref, DerefMut}; 1use core::ops::{Deref, DerefMut};
3 2
4pub use bxcan; 3pub use bxcan;
5use embassy_hal_common::unborrow; 4use embassy_hal_common::{unborrow, Unborrowed};
6 5
7use crate::gpio::sealed::AFType; 6use crate::gpio::sealed::AFType;
8use crate::rcc::RccPeripheral; 7use crate::rcc::RccPeripheral;
9use crate::{peripherals, Unborrow}; 8use crate::{peripherals, Unborrow};
10 9
11pub struct Can<'d, T: Instance + bxcan::Instance> { 10pub struct Can<'d, T: Instance> {
12 phantom: PhantomData<&'d mut T>, 11 can: bxcan::Can<BxcanInstance<'d, T>>,
13 can: bxcan::Can<T>,
14} 12}
15 13
16impl<'d, T: Instance + bxcan::Instance> Can<'d, T> { 14impl<'d, T: Instance> Can<'d, T> {
17 pub fn new( 15 pub fn new(
18 peri: impl Unborrow<Target = T> + 'd, 16 peri: impl Unborrow<Target = T> + 'd,
19 rx: impl Unborrow<Target = impl RxPin<T>> + 'd, 17 rx: impl Unborrow<Target = impl RxPin<T>> + 'd,
@@ -30,32 +28,29 @@ impl<'d, T: Instance + bxcan::Instance> Can<'d, T> {
30 T::reset(); 28 T::reset();
31 29
32 Self { 30 Self {
33 phantom: PhantomData, 31 can: bxcan::Can::builder(BxcanInstance(peri)).enable(),
34 can: bxcan::Can::builder(peri).enable(),
35 } 32 }
36 } 33 }
37} 34}
38 35
39impl<'d, T: Instance + bxcan::Instance> Drop for Can<'d, T> { 36impl<'d, T: Instance> Drop for Can<'d, T> {
40 fn drop(&mut self) { 37 fn drop(&mut self) {
41 // Cannot call `free()` because it moves the instance. 38 // Cannot call `free()` because it moves the instance.
42 // Manually reset the peripheral. 39 // Manually reset the peripheral.
43 unsafe { 40 unsafe { T::regs().mcr().write(|w| w.set_reset(true)) }
44 T::regs().mcr().write(|w| w.set_reset(true));
45 }
46 T::disable(); 41 T::disable();
47 } 42 }
48} 43}
49 44
50impl<'d, T: Instance + bxcan::Instance> Deref for Can<'d, T> { 45impl<'d, T: Instance> Deref for Can<'d, T> {
51 type Target = bxcan::Can<T>; 46 type Target = bxcan::Can<BxcanInstance<'d, T>>;
52 47
53 fn deref(&self) -> &Self::Target { 48 fn deref(&self) -> &Self::Target {
54 &self.can 49 &self.can
55 } 50 }
56} 51}
57 52
58impl<'d, T: Instance + bxcan::Instance> DerefMut for Can<'d, T> { 53impl<'d, T: Instance> DerefMut for Can<'d, T> {
59 fn deref_mut(&mut self) -> &mut Self::Target { 54 fn deref_mut(&mut self) -> &mut Self::Target {
60 &mut self.can 55 &mut self.can
61 } 56 }
@@ -63,15 +58,25 @@ impl<'d, T: Instance + bxcan::Instance> DerefMut for Can<'d, T> {
63 58
64pub(crate) mod sealed { 59pub(crate) mod sealed {
65 pub trait Instance { 60 pub trait Instance {
61 const REGISTERS: *mut bxcan::RegisterBlock;
62
66 fn regs() -> &'static crate::pac::can::Can; 63 fn regs() -> &'static crate::pac::can::Can;
67 } 64 }
68} 65}
69 66
70pub trait Instance: sealed::Instance + RccPeripheral {} 67pub trait Instance: sealed::Instance + RccPeripheral {}
71 68
69pub struct BxcanInstance<'a, T>(Unborrowed<'a, T>);
70
71unsafe impl<'d, T: Instance> bxcan::Instance for BxcanInstance<'d, T> {
72 const REGISTERS: *mut bxcan::RegisterBlock = T::REGISTERS;
73}
74
72foreach_peripheral!( 75foreach_peripheral!(
73 (can, $inst:ident) => { 76 (can, $inst:ident) => {
74 impl sealed::Instance for peripherals::$inst { 77 impl sealed::Instance for peripherals::$inst {
78 const REGISTERS: *mut bxcan::RegisterBlock = crate::pac::$inst.0 as *mut _;
79
75 fn regs() -> &'static crate::pac::can::Can { 80 fn regs() -> &'static crate::pac::can::Can {
76 &crate::pac::$inst 81 &crate::pac::$inst
77 } 82 }
@@ -79,15 +84,12 @@ foreach_peripheral!(
79 84
80 impl Instance for peripherals::$inst {} 85 impl Instance for peripherals::$inst {}
81 86
82 unsafe impl bxcan::Instance for peripherals::$inst {
83 const REGISTERS: *mut bxcan::RegisterBlock = crate::pac::$inst.0 as *mut _;
84 }
85 }; 87 };
86); 88);
87 89
88foreach_peripheral!( 90foreach_peripheral!(
89 (can, CAN) => { 91 (can, CAN) => {
90 unsafe impl bxcan::FilterOwner for peripherals::CAN { 92 unsafe impl<'d> bxcan::FilterOwner for BxcanInstance<'d, peripherals::CAN> {
91 const NUM_FILTER_BANKS: u8 = 14; 93 const NUM_FILTER_BANKS: u8 = 14;
92 } 94 }
93 }; 95 };
@@ -102,19 +104,19 @@ foreach_peripheral!(
102 ))] { 104 ))] {
103 // Most L4 devices and some F7 devices use the name "CAN1" 105 // Most L4 devices and some F7 devices use the name "CAN1"
104 // even if there is no "CAN2" peripheral. 106 // even if there is no "CAN2" peripheral.
105 unsafe impl bxcan::FilterOwner for peripherals::CAN1 { 107 unsafe impl<'d> bxcan::FilterOwner for BxcanInstance<'d, peripherals::CAN1> {
106 const NUM_FILTER_BANKS: u8 = 14; 108 const NUM_FILTER_BANKS: u8 = 14;
107 } 109 }
108 } else { 110 } else {
109 unsafe impl bxcan::FilterOwner for peripherals::CAN1 { 111 unsafe impl<'d> bxcan::FilterOwner for BxcanInstance<'d, peripherals::CAN1> {
110 const NUM_FILTER_BANKS: u8 = 28; 112 const NUM_FILTER_BANKS: u8 = 28;
111 } 113 }
112 unsafe impl bxcan::MasterInstance for peripherals::CAN1 {} 114 unsafe impl<'d> bxcan::MasterInstance for BxcanInstance<'d, peripherals::CAN1> {}
113 } 115 }
114 } 116 }
115 }; 117 };
116 (can, CAN3) => { 118 (can, CAN3) => {
117 unsafe impl bxcan::FilterOwner for peripherals::CAN3 { 119 unsafe impl<'d> bxcan::FilterOwner for BxcanInstance<'d, peripherals::CAN3> {
118 const NUM_FILTER_BANKS: u8 = 14; 120 const NUM_FILTER_BANKS: u8 = 14;
119 } 121 }
120 }; 122 };
diff --git a/embassy-stm32/src/crc/v1.rs b/embassy-stm32/src/crc/v1.rs
index 87133714c..85abf22d1 100644
--- a/embassy-stm32/src/crc/v1.rs
+++ b/embassy-stm32/src/crc/v1.rs
@@ -1,6 +1,4 @@
1use core::marker::PhantomData; 1use embassy_hal_common::{unborrow, Unborrowed};
2
3use embassy_hal_common::unborrow;
4 2
5use crate::pac::CRC as PAC_CRC; 3use crate::pac::CRC as PAC_CRC;
6use crate::peripherals::CRC; 4use crate::peripherals::CRC;
@@ -8,24 +6,21 @@ use crate::rcc::sealed::RccPeripheral;
8use crate::Unborrow; 6use crate::Unborrow;
9 7
10pub struct Crc<'d> { 8pub struct Crc<'d> {
11 _peripheral: CRC, 9 _peri: Unborrowed<'d, CRC>,
12 _phantom: PhantomData<&'d mut CRC>,
13} 10}
14 11
15impl<'d> Crc<'d> { 12impl<'d> Crc<'d> {
16 /// Instantiates the CRC32 peripheral and initializes it to default values. 13 /// Instantiates the CRC32 peripheral and initializes it to default values.
17 pub fn new(peripheral: impl Unborrow<Target = CRC> + 'd) -> Self { 14 pub fn new(peripheral: impl Unborrow<Target = CRC> + 'd) -> Self {
15 unborrow!(peripheral);
16
18 // Note: enable and reset come from RccPeripheral. 17 // Note: enable and reset come from RccPeripheral.
19 // enable CRC clock in RCC. 18 // enable CRC clock in RCC.
20 CRC::enable(); 19 CRC::enable();
21 // Reset CRC to default values. 20 // Reset CRC to default values.
22 CRC::reset(); 21 CRC::reset();
23 // Unborrow the peripheral 22 // Unborrow the peripheral
24 unborrow!(peripheral); 23 let mut instance = Self { _peri: peripheral };
25 let mut instance = Self {
26 _peripheral: peripheral,
27 _phantom: PhantomData,
28 };
29 instance.reset(); 24 instance.reset();
30 instance 25 instance
31 } 26 }
diff --git a/embassy-stm32/src/crc/v2v3.rs b/embassy-stm32/src/crc/v2v3.rs
index 63f24e4e1..06da29c17 100644
--- a/embassy-stm32/src/crc/v2v3.rs
+++ b/embassy-stm32/src/crc/v2v3.rs
@@ -1,6 +1,4 @@
1use core::marker::PhantomData; 1use embassy_hal_common::{unborrow, Unborrowed};
2
3use embassy_hal_common::unborrow;
4 2
5use crate::pac::crc::vals; 3use crate::pac::crc::vals;
6use crate::pac::CRC as PAC_CRC; 4use crate::pac::CRC as PAC_CRC;
@@ -9,8 +7,7 @@ use crate::rcc::sealed::RccPeripheral;
9use crate::Unborrow; 7use crate::Unborrow;
10 8
11pub struct Crc<'d> { 9pub struct Crc<'d> {
12 _peripheral: CRC, 10 _peripheral: Unborrowed<'d, CRC>,
13 _phantom: PhantomData<&'d mut CRC>,
14 _config: Config, 11 _config: Config,
15} 12}
16 13
@@ -79,7 +76,6 @@ impl<'d> Crc<'d> {
79 unborrow!(peripheral); 76 unborrow!(peripheral);
80 let mut instance = Self { 77 let mut instance = Self {
81 _peripheral: peripheral, 78 _peripheral: peripheral,
82 _phantom: PhantomData,
83 _config: config, 79 _config: config,
84 }; 80 };
85 CRC::reset(); 81 CRC::reset();
diff --git a/embassy-stm32/src/dac/v2.rs b/embassy-stm32/src/dac/v2.rs
index ba7856a5a..798eefbf9 100644
--- a/embassy-stm32/src/dac/v2.rs
+++ b/embassy-stm32/src/dac/v2.rs
@@ -1,6 +1,4 @@
1use core::marker::PhantomData; 1use embassy_hal_common::{unborrow, Unborrowed};
2
3use embassy_hal_common::unborrow;
4 2
5use crate::dac::{DacPin, Instance}; 3use crate::dac::{DacPin, Instance};
6use crate::pac::dac; 4use crate::pac::dac;
@@ -90,7 +88,7 @@ pub enum Value {
90 88
91pub struct Dac<'d, T: Instance> { 89pub struct Dac<'d, T: Instance> {
92 channels: u8, 90 channels: u8,
93 phantom: PhantomData<&'d mut T>, 91 _peri: Unborrowed<'d, T>,
94} 92}
95 93
96macro_rules! enable { 94macro_rules! enable {
@@ -116,7 +114,7 @@ impl<'d, T: Instance> Dac<'d, T> {
116 Self::new_inner(peri, 2) 114 Self::new_inner(peri, 2)
117 } 115 }
118 116
119 fn new_inner(_peri: T, channels: u8) -> Self { 117 fn new_inner(peri: Unborrowed<'d, T>, channels: u8) -> Self {
120 unsafe { 118 unsafe {
121 // Sadly we cannot use `RccPeripheral::enable` since devices are quite inconsistent DAC clock 119 // Sadly we cannot use `RccPeripheral::enable` since devices are quite inconsistent DAC clock
122 // configuration. 120 // configuration.
@@ -144,10 +142,7 @@ impl<'d, T: Instance> Dac<'d, T> {
144 } 142 }
145 } 143 }
146 144
147 Self { 145 Self { channels, _peri: peri }
148 channels,
149 phantom: PhantomData,
150 }
151 } 146 }
152 147
153 /// Check the channel is configured 148 /// Check the channel is configured
diff --git a/embassy-stm32/src/dcmi.rs b/embassy-stm32/src/dcmi.rs
index f4ca93a71..bcf723498 100644
--- a/embassy-stm32/src/dcmi.rs
+++ b/embassy-stm32/src/dcmi.rs
@@ -1,8 +1,7 @@
1use core::marker::PhantomData;
2use core::task::Poll; 1use core::task::Poll;
3 2
4use embassy::waitqueue::AtomicWaker; 3use embassy::waitqueue::AtomicWaker;
5use embassy_hal_common::unborrow; 4use embassy_hal_common::{unborrow, Unborrowed};
6use futures::future::poll_fn; 5use futures::future::poll_fn;
7 6
8use crate::gpio::sealed::AFType; 7use crate::gpio::sealed::AFType;
@@ -82,9 +81,8 @@ macro_rules! config_pins {
82} 81}
83 82
84pub struct Dcmi<'d, T: Instance, Dma: FrameDma<T>> { 83pub struct Dcmi<'d, T: Instance, Dma: FrameDma<T>> {
85 inner: T, 84 inner: Unborrowed<'d, T>,
86 dma: Dma, 85 dma: Unborrowed<'d, Dma>,
87 phantom: PhantomData<&'d mut T>,
88} 86}
89 87
90impl<'d, T, Dma> Dcmi<'d, T, Dma> 88impl<'d, T, Dma> Dcmi<'d, T, Dma>
@@ -301,9 +299,9 @@ where
301 } 299 }
302 300
303 fn new_inner( 301 fn new_inner(
304 peri: T, 302 peri: Unborrowed<'d, T>,
305 dma: Dma, 303 dma: Unborrowed<'d, Dma>,
306 irq: T::Interrupt, 304 irq: Unborrowed<'d, T::Interrupt>,
307 config: Config, 305 config: Config,
308 use_embedded_synchronization: bool, 306 use_embedded_synchronization: bool,
309 edm: u8, 307 edm: u8,
@@ -327,11 +325,7 @@ where
327 irq.unpend(); 325 irq.unpend();
328 irq.enable(); 326 irq.enable();
329 327
330 Self { 328 Self { inner: peri, dma }
331 inner: peri,
332 dma,
333 phantom: PhantomData,
334 }
335 } 329 }
336 330
337 unsafe fn on_interrupt(_: *mut ()) { 331 unsafe fn on_interrupt(_: *mut ()) {
diff --git a/embassy-stm32/src/dma/mod.rs b/embassy-stm32/src/dma/mod.rs
index 02d6ca0f3..fe2bf900e 100644
--- a/embassy-stm32/src/dma/mod.rs
+++ b/embassy-stm32/src/dma/mod.rs
@@ -8,7 +8,6 @@ mod dmamux;
8mod gpdma; 8mod gpdma;
9 9
10use core::future::Future; 10use core::future::Future;
11use core::marker::PhantomData;
12use core::mem; 11use core::mem;
13use core::pin::Pin; 12use core::pin::Pin;
14use core::task::{Context, Poll, Waker}; 13use core::task::{Context, Poll, Waker};
@@ -207,6 +206,8 @@ impl Default for TransferOptions {
207} 206}
208 207
209mod transfers { 208mod transfers {
209 use embassy_hal_common::Unborrowed;
210
210 use super::*; 211 use super::*;
211 212
212 #[allow(unused)] 213 #[allow(unused)]
@@ -255,17 +256,13 @@ mod transfers {
255 } 256 }
256 257
257 pub(crate) struct Transfer<'a, C: Channel> { 258 pub(crate) struct Transfer<'a, C: Channel> {
258 channel: C, 259 channel: Unborrowed<'a, C>,
259 _phantom: PhantomData<&'a mut C>,
260 } 260 }
261 261
262 impl<'a, C: Channel> Transfer<'a, C> { 262 impl<'a, C: Channel> Transfer<'a, C> {
263 pub(crate) fn new(channel: impl Unborrow<Target = C> + 'a) -> Self { 263 pub(crate) fn new(channel: impl Unborrow<Target = C> + 'a) -> Self {
264 unborrow!(channel); 264 unborrow!(channel);
265 Self { 265 Self { channel }
266 channel,
267 _phantom: PhantomData,
268 }
269 } 266 }
270 } 267 }
271 268
diff --git a/embassy-stm32/src/eth/v1/mod.rs b/embassy-stm32/src/eth/v1/mod.rs
index 7985acc5a..f2cdd9098 100644
--- a/embassy-stm32/src/eth/v1/mod.rs
+++ b/embassy-stm32/src/eth/v1/mod.rs
@@ -6,7 +6,7 @@ use core::task::Waker;
6 6
7use embassy::waitqueue::AtomicWaker; 7use embassy::waitqueue::AtomicWaker;
8use embassy_cortex_m::peripheral::{PeripheralMutex, PeripheralState, StateStorage}; 8use embassy_cortex_m::peripheral::{PeripheralMutex, PeripheralState, StateStorage};
9use embassy_hal_common::unborrow; 9use embassy_hal_common::{unborrow, Unborrowed};
10use embassy_net::{Device, DeviceCapabilities, LinkState, PacketBuf, MTU}; 10use embassy_net::{Device, DeviceCapabilities, LinkState, PacketBuf, MTU};
11 11
12use crate::gpio::sealed::{AFType, Pin as __GpioPin}; 12use crate::gpio::sealed::{AFType, Pin as __GpioPin};
@@ -36,7 +36,7 @@ impl<'d, T: Instance, const TX: usize, const RX: usize> State<'d, T, TX, RX> {
36 36
37pub struct Ethernet<'d, T: Instance, P: PHY, const TX: usize, const RX: usize> { 37pub struct Ethernet<'d, T: Instance, P: PHY, const TX: usize, const RX: usize> {
38 state: PeripheralMutex<'d, Inner<'d, T, TX, RX>>, 38 state: PeripheralMutex<'d, Inner<'d, T, TX, RX>>,
39 pins: [AnyPin; 9], 39 pins: [Unborrowed<'d, AnyPin>; 9],
40 _phy: P, 40 _phy: P,
41 clock_range: Cr, 41 clock_range: Cr,
42 phy_addr: u8, 42 phy_addr: u8,
@@ -207,15 +207,15 @@ impl<'d, T: Instance, P: PHY, const TX: usize, const RX: usize> Ethernet<'d, T,
207 }; 207 };
208 208
209 let pins = [ 209 let pins = [
210 ref_clk.degrade(), 210 ref_clk.map_into(),
211 mdio.degrade(), 211 mdio.map_into(),
212 mdc.degrade(), 212 mdc.map_into(),
213 crs.degrade(), 213 crs.map_into(),
214 rx_d0.degrade(), 214 rx_d0.map_into(),
215 rx_d1.degrade(), 215 rx_d1.map_into(),
216 tx_d0.degrade(), 216 tx_d0.map_into(),
217 tx_d1.degrade(), 217 tx_d1.map_into(),
218 tx_en.degrade(), 218 tx_en.map_into(),
219 ]; 219 ];
220 220
221 let mut this = Self { 221 let mut this = Self {
diff --git a/embassy-stm32/src/eth/v2/mod.rs b/embassy-stm32/src/eth/v2/mod.rs
index 2b1caf992..c67a03077 100644
--- a/embassy-stm32/src/eth/v2/mod.rs
+++ b/embassy-stm32/src/eth/v2/mod.rs
@@ -4,7 +4,7 @@ use core::task::Waker;
4 4
5use embassy::waitqueue::AtomicWaker; 5use embassy::waitqueue::AtomicWaker;
6use embassy_cortex_m::peripheral::{PeripheralMutex, PeripheralState, StateStorage}; 6use embassy_cortex_m::peripheral::{PeripheralMutex, PeripheralState, StateStorage};
7use embassy_hal_common::unborrow; 7use embassy_hal_common::{unborrow, Unborrowed};
8use embassy_net::{Device, DeviceCapabilities, LinkState, PacketBuf, MTU}; 8use embassy_net::{Device, DeviceCapabilities, LinkState, PacketBuf, MTU};
9 9
10use crate::gpio::sealed::{AFType, Pin as _}; 10use crate::gpio::sealed::{AFType, Pin as _};
@@ -25,7 +25,7 @@ impl<'d, T: Instance, const TX: usize, const RX: usize> State<'d, T, TX, RX> {
25} 25}
26pub struct Ethernet<'d, T: Instance, P: PHY, const TX: usize, const RX: usize> { 26pub struct Ethernet<'d, T: Instance, P: PHY, const TX: usize, const RX: usize> {
27 state: PeripheralMutex<'d, Inner<'d, T, TX, RX>>, 27 state: PeripheralMutex<'d, Inner<'d, T, TX, RX>>,
28 pins: [AnyPin; 9], 28 pins: [Unborrowed<'d, AnyPin>; 9],
29 _phy: P, 29 _phy: P,
30 clock_range: u8, 30 clock_range: u8,
31 phy_addr: u8, 31 phy_addr: u8,
@@ -143,15 +143,15 @@ impl<'d, T: Instance, P: PHY, const TX: usize, const RX: usize> Ethernet<'d, T,
143 }; 143 };
144 144
145 let pins = [ 145 let pins = [
146 ref_clk.degrade(), 146 ref_clk.map_into(),
147 mdio.degrade(), 147 mdio.map_into(),
148 mdc.degrade(), 148 mdc.map_into(),
149 crs.degrade(), 149 crs.map_into(),
150 rx_d0.degrade(), 150 rx_d0.map_into(),
151 rx_d1.degrade(), 151 rx_d1.map_into(),
152 tx_d0.degrade(), 152 tx_d0.map_into(),
153 tx_d1.degrade(), 153 tx_d1.map_into(),
154 tx_en.degrade(), 154 tx_en.map_into(),
155 ]; 155 ];
156 156
157 let mut this = Self { 157 let mut this = Self {
diff --git a/embassy-stm32/src/flash/mod.rs b/embassy-stm32/src/flash/mod.rs
index 2047f70e1..bd64fdd76 100644
--- a/embassy-stm32/src/flash/mod.rs
+++ b/embassy-stm32/src/flash/mod.rs
@@ -1,6 +1,4 @@
1use core::marker::PhantomData; 1use embassy_hal_common::{unborrow, Unborrowed};
2
3use embassy_hal_common::unborrow;
4use embedded_storage::nor_flash::{ErrorType, NorFlash, NorFlashError, NorFlashErrorKind, ReadNorFlash}; 2use embedded_storage::nor_flash::{ErrorType, NorFlash, NorFlashError, NorFlashErrorKind, ReadNorFlash};
5 3
6pub use crate::pac::{ERASE_SIZE, ERASE_VALUE, FLASH_BASE, FLASH_SIZE, WRITE_SIZE}; 4pub use crate::pac::{ERASE_SIZE, ERASE_VALUE, FLASH_BASE, FLASH_SIZE, WRITE_SIZE};
@@ -16,20 +14,16 @@ const FLASH_END: usize = FLASH_BASE + FLASH_SIZE;
16mod family; 14mod family;
17 15
18pub struct Flash<'d> { 16pub struct Flash<'d> {
19 _inner: FLASH, 17 _inner: Unborrowed<'d, FLASH>,
20 _phantom: PhantomData<&'d mut FLASH>,
21} 18}
22 19
23impl<'d> Flash<'d> { 20impl<'d> Flash<'d> {
24 pub fn new(p: impl Unborrow<Target = FLASH>) -> Self { 21 pub fn new(p: impl Unborrow<Target = FLASH> + 'd) -> Self {
25 unborrow!(p); 22 unborrow!(p);
26 Self { 23 Self { _inner: p }
27 _inner: p,
28 _phantom: PhantomData,
29 }
30 } 24 }
31 25
32 pub fn unlock(p: impl Unborrow<Target = FLASH>) -> Self { 26 pub fn unlock(p: impl Unborrow<Target = FLASH> + 'd) -> Self {
33 let flash = Self::new(p); 27 let flash = Self::new(p);
34 28
35 unsafe { family::unlock() }; 29 unsafe { family::unlock() };
diff --git a/embassy-stm32/src/gpio.rs b/embassy-stm32/src/gpio.rs
index 3bdaccce6..92cd2bb27 100644
--- a/embassy-stm32/src/gpio.rs
+++ b/embassy-stm32/src/gpio.rs
@@ -1,8 +1,7 @@
1#![macro_use] 1#![macro_use]
2use core::convert::Infallible; 2use core::convert::Infallible;
3use core::marker::PhantomData;
4 3
5use embassy_hal_common::{impl_unborrow, unborrow}; 4use embassy_hal_common::{impl_unborrow, unborrow, Unborrowed};
6 5
7use crate::pac::gpio::{self, vals}; 6use crate::pac::gpio::{self, vals};
8use crate::{pac, peripherals, Unborrow}; 7use crate::{pac, peripherals, Unborrow};
@@ -13,8 +12,7 @@ use crate::{pac, peripherals, Unborrow};
13/// set while not in output mode, so the pin's level will be 'remembered' when it is not in output 12/// set while not in output mode, so the pin's level will be 'remembered' when it is not in output
14/// mode. 13/// mode.
15pub struct Flex<'d, T: Pin> { 14pub struct Flex<'d, T: Pin> {
16 pub(crate) pin: T, 15 pub(crate) pin: Unborrowed<'d, T>,
17 phantom: PhantomData<&'d mut T>,
18} 16}
19 17
20impl<'d, T: Pin> Flex<'d, T> { 18impl<'d, T: Pin> Flex<'d, T> {
@@ -27,10 +25,7 @@ impl<'d, T: Pin> Flex<'d, T> {
27 pub fn new(pin: impl Unborrow<Target = T> + 'd) -> Self { 25 pub fn new(pin: impl Unborrow<Target = T> + 'd) -> Self {
28 unborrow!(pin); 26 unborrow!(pin);
29 // Pin will be in disconnected state. 27 // Pin will be in disconnected state.
30 Self { 28 Self { pin }
31 pin,
32 phantom: PhantomData,
33 }
34 } 29 }
35 30
36 /// Put the pin into input mode. 31 /// Put the pin into input mode.
@@ -626,7 +621,7 @@ pub(crate) mod sealed {
626 } 621 }
627} 622}
628 623
629pub trait Pin: sealed::Pin + Sized + 'static { 624pub trait Pin: Into<AnyPin> + sealed::Pin + Sized + 'static {
630 #[cfg(feature = "exti")] 625 #[cfg(feature = "exti")]
631 type ExtiChannel: crate::exti::Channel; 626 type ExtiChannel: crate::exti::Channel;
632 627
@@ -699,6 +694,12 @@ foreach_pin!(
699 $port_num * 16 + $pin_num 694 $port_num * 16 + $pin_num
700 } 695 }
701 } 696 }
697
698 impl From<peripherals::$pin_name> for AnyPin {
699 fn from(x: peripherals::$pin_name) -> Self {
700 x.degrade()
701 }
702 }
702 }; 703 };
703); 704);
704 705
diff --git a/embassy-stm32/src/i2c/v2.rs b/embassy-stm32/src/i2c/v2.rs
index 108ea7e34..ec7fec15e 100644
--- a/embassy-stm32/src/i2c/v2.rs
+++ b/embassy-stm32/src/i2c/v2.rs
@@ -1,12 +1,11 @@
1use core::cmp; 1use core::cmp;
2use core::marker::PhantomData;
3use core::task::Poll; 2use core::task::Poll;
4 3
5use atomic_polyfill::{AtomicUsize, Ordering}; 4use atomic_polyfill::{AtomicUsize, Ordering};
6use embassy::waitqueue::AtomicWaker; 5use embassy::waitqueue::AtomicWaker;
7use embassy_embedded_hal::SetConfig; 6use embassy_embedded_hal::SetConfig;
8use embassy_hal_common::drop::OnDrop; 7use embassy_hal_common::drop::OnDrop;
9use embassy_hal_common::unborrow; 8use embassy_hal_common::{unborrow, Unborrowed};
10use futures::future::poll_fn; 9use futures::future::poll_fn;
11 10
12use crate::dma::NoDma; 11use crate::dma::NoDma;
@@ -32,15 +31,15 @@ impl State {
32} 31}
33 32
34pub struct I2c<'d, T: Instance, TXDMA = NoDma, RXDMA = NoDma> { 33pub struct I2c<'d, T: Instance, TXDMA = NoDma, RXDMA = NoDma> {
35 phantom: PhantomData<&'d mut T>, 34 _peri: Unborrowed<'d, T>,
36 tx_dma: TXDMA, 35 tx_dma: Unborrowed<'d, TXDMA>,
37 #[allow(dead_code)] 36 #[allow(dead_code)]
38 rx_dma: RXDMA, 37 rx_dma: Unborrowed<'d, RXDMA>,
39} 38}
40 39
41impl<'d, T: Instance, TXDMA, RXDMA> I2c<'d, T, TXDMA, RXDMA> { 40impl<'d, T: Instance, TXDMA, RXDMA> I2c<'d, T, TXDMA, RXDMA> {
42 pub fn new( 41 pub fn new(
43 _peri: impl Unborrow<Target = T> + 'd, 42 peri: impl Unborrow<Target = T> + 'd,
44 scl: impl Unborrow<Target = impl SclPin<T>> + 'd, 43 scl: impl Unborrow<Target = impl SclPin<T>> + 'd,
45 sda: impl Unborrow<Target = impl SdaPin<T>> + 'd, 44 sda: impl Unborrow<Target = impl SdaPin<T>> + 'd,
46 irq: impl Unborrow<Target = T::Interrupt> + 'd, 45 irq: impl Unborrow<Target = T::Interrupt> + 'd,
@@ -48,7 +47,7 @@ impl<'d, T: Instance, TXDMA, RXDMA> I2c<'d, T, TXDMA, RXDMA> {
48 rx_dma: impl Unborrow<Target = RXDMA> + 'd, 47 rx_dma: impl Unborrow<Target = RXDMA> + 'd,
49 freq: Hertz, 48 freq: Hertz,
50 ) -> Self { 49 ) -> Self {
51 unborrow!(irq, scl, sda, tx_dma, rx_dma); 50 unborrow!(peri, irq, scl, sda, tx_dma, rx_dma);
52 51
53 T::enable(); 52 T::enable();
54 T::reset(); 53 T::reset();
@@ -88,7 +87,7 @@ impl<'d, T: Instance, TXDMA, RXDMA> I2c<'d, T, TXDMA, RXDMA> {
88 irq.enable(); 87 irq.enable();
89 88
90 Self { 89 Self {
91 phantom: PhantomData, 90 _peri: peri,
92 tx_dma, 91 tx_dma,
93 rx_dma, 92 rx_dma,
94 } 93 }
diff --git a/embassy-stm32/src/lib.rs b/embassy-stm32/src/lib.rs
index 8b8168589..f58ab2f96 100644
--- a/embassy-stm32/src/lib.rs
+++ b/embassy-stm32/src/lib.rs
@@ -75,7 +75,7 @@ pub(crate) mod _generated {
75// Reexports 75// Reexports
76pub use _generated::{peripherals, Peripherals}; 76pub use _generated::{peripherals, Peripherals};
77pub use embassy_cortex_m::executor; 77pub use embassy_cortex_m::executor;
78pub use embassy_hal_common::{unborrow, Unborrow}; 78pub use embassy_hal_common::{unborrow, Unborrow, Unborrowed};
79pub use embassy_macros::cortex_m_interrupt as interrupt; 79pub use embassy_macros::cortex_m_interrupt as interrupt;
80#[cfg(feature = "unstable-pac")] 80#[cfg(feature = "unstable-pac")]
81pub use stm32_metapac as pac; 81pub use stm32_metapac as pac;
diff --git a/embassy-stm32/src/pwm/simple_pwm.rs b/embassy-stm32/src/pwm/simple_pwm.rs
index 60aa110c7..137d3145f 100644
--- a/embassy-stm32/src/pwm/simple_pwm.rs
+++ b/embassy-stm32/src/pwm/simple_pwm.rs
@@ -1,6 +1,4 @@
1use core::marker::PhantomData; 1use embassy_hal_common::{unborrow, Unborrowed};
2
3use embassy_hal_common::unborrow;
4 2
5use super::*; 3use super::*;
6#[allow(unused_imports)] 4#[allow(unused_imports)]
@@ -9,8 +7,7 @@ use crate::time::Hertz;
9use crate::Unborrow; 7use crate::Unborrow;
10 8
11pub struct SimplePwm<'d, T> { 9pub struct SimplePwm<'d, T> {
12 phantom: PhantomData<&'d mut T>, 10 inner: Unborrowed<'d, T>,
13 inner: T,
14} 11}
15 12
16macro_rules! config_pins { 13macro_rules! config_pins {
@@ -83,10 +80,7 @@ impl<'d, T: CaptureCompare16bitInstance> SimplePwm<'d, T> {
83 80
84 configure_pins(); 81 configure_pins();
85 82
86 let mut this = Self { 83 let mut this = Self { inner: tim };
87 inner: tim,
88 phantom: PhantomData,
89 };
90 84
91 this.inner.set_frequency(freq); 85 this.inner.set_frequency(freq);
92 this.inner.start(); 86 this.inner.start();
diff --git a/embassy-stm32/src/rng.rs b/embassy-stm32/src/rng.rs
index 5b3558c92..967fa71fb 100644
--- a/embassy-stm32/src/rng.rs
+++ b/embassy-stm32/src/rng.rs
@@ -1,10 +1,9 @@
1#![macro_use] 1#![macro_use]
2 2
3use core::marker::PhantomData;
4use core::task::Poll; 3use core::task::Poll;
5 4
6use embassy::waitqueue::AtomicWaker; 5use embassy::waitqueue::AtomicWaker;
7use embassy_hal_common::unborrow; 6use embassy_hal_common::{unborrow, Unborrowed};
8use futures::future::poll_fn; 7use futures::future::poll_fn;
9use rand_core::{CryptoRng, RngCore}; 8use rand_core::{CryptoRng, RngCore};
10 9
@@ -19,8 +18,7 @@ pub enum Error {
19} 18}
20 19
21pub struct Rng<'d, T: Instance> { 20pub struct Rng<'d, T: Instance> {
22 _inner: T, 21 _inner: Unborrowed<'d, T>,
23 _phantom: PhantomData<&'d mut T>,
24} 22}
25 23
26impl<'d, T: Instance> Rng<'d, T> { 24impl<'d, T: Instance> Rng<'d, T> {
@@ -28,10 +26,7 @@ impl<'d, T: Instance> Rng<'d, T> {
28 T::enable(); 26 T::enable();
29 T::reset(); 27 T::reset();
30 unborrow!(inner); 28 unborrow!(inner);
31 let mut random = Self { 29 let mut random = Self { _inner: inner };
32 _inner: inner,
33 _phantom: PhantomData,
34 };
35 random.reset(); 30 random.reset();
36 random 31 random
37 } 32 }
diff --git a/embassy-stm32/src/sdmmc/mod.rs b/embassy-stm32/src/sdmmc/mod.rs
index d94509748..fbb48263d 100644
--- a/embassy-stm32/src/sdmmc/mod.rs
+++ b/embassy-stm32/src/sdmmc/mod.rs
@@ -1,18 +1,17 @@
1#![macro_use] 1#![macro_use]
2 2
3use core::default::Default; 3use core::default::Default;
4use core::marker::PhantomData;
5use core::task::Poll; 4use core::task::Poll;
6 5
7use embassy::waitqueue::AtomicWaker; 6use embassy::waitqueue::AtomicWaker;
8use embassy_hal_common::drop::OnDrop; 7use embassy_hal_common::drop::OnDrop;
9use embassy_hal_common::unborrow; 8use embassy_hal_common::{unborrow, Unborrowed};
10use futures::future::poll_fn; 9use futures::future::poll_fn;
11use sdio_host::{BusWidth, CardCapacity, CardStatus, CurrentState, SDStatus, CID, CSD, OCR, SCR}; 10use sdio_host::{BusWidth, CardCapacity, CardStatus, CurrentState, SDStatus, CID, CSD, OCR, SCR};
12 11
13use crate::dma::NoDma; 12use crate::dma::NoDma;
14use crate::gpio::sealed::AFType; 13use crate::gpio::sealed::{AFType, Pin};
15use crate::gpio::{Pull, Speed}; 14use crate::gpio::{AnyPin, Pull, Speed};
16use crate::interrupt::{Interrupt, InterruptExt}; 15use crate::interrupt::{Interrupt, InterruptExt};
17use crate::pac::sdmmc::Sdmmc as RegBlock; 16use crate::pac::sdmmc::Sdmmc as RegBlock;
18use crate::rcc::RccPeripheral; 17use crate::rcc::RccPeripheral;
@@ -176,12 +175,19 @@ impl Default for Config {
176} 175}
177 176
178/// Sdmmc device 177/// Sdmmc device
179pub struct Sdmmc<'d, T: Instance, P: Pins<T>, Dma = NoDma> { 178pub struct Sdmmc<'d, T: Instance, Dma = NoDma> {
180 sdmmc: PhantomData<&'d mut T>, 179 _peri: Unborrowed<'d, T>,
181 pins: P, 180 irq: Unborrowed<'d, T::Interrupt>,
182 irq: T::Interrupt, 181 dma: Unborrowed<'d, Dma>,
182
183 clk: Unborrowed<'d, AnyPin>,
184 cmd: Unborrowed<'d, AnyPin>,
185 d0: Unborrowed<'d, AnyPin>,
186 d1: Option<Unborrowed<'d, AnyPin>>,
187 d2: Option<Unborrowed<'d, AnyPin>>,
188 d3: Option<Unborrowed<'d, AnyPin>>,
189
183 config: Config, 190 config: Config,
184 dma: Dma,
185 /// Current clock to card 191 /// Current clock to card
186 clock: Hertz, 192 clock: Hertz,
187 /// Current signalling scheme to card 193 /// Current signalling scheme to card
@@ -191,16 +197,99 @@ pub struct Sdmmc<'d, T: Instance, P: Pins<T>, Dma = NoDma> {
191} 197}
192 198
193#[cfg(sdmmc_v1)] 199#[cfg(sdmmc_v1)]
194impl<'d, T: Instance, P: Pins<T>, Dma: SdmmcDma<T>> Sdmmc<'d, T, P, Dma> { 200impl<'d, T: Instance, Dma: SdmmcDma<T>> Sdmmc<'d, T, Dma> {
195 pub fn new( 201 pub fn new_1bit(
196 _peripheral: impl Unborrow<Target = T> + 'd, 202 sdmmc: impl Unborrow<Target = T> + 'd,
197 pins: impl Unborrow<Target = P> + 'd, 203 irq: impl Unborrow<Target = T::Interrupt> + 'd,
204 dma: impl Unborrow<Target = Dma> + 'd,
205 clk: impl Unborrow<Target = impl CkPin<T>> + 'd,
206 cmd: impl Unborrow<Target = impl CmdPin<T>> + 'd,
207 d0: impl Unborrow<Target = impl D0Pin<T>> + 'd,
208 config: Config,
209 ) -> Self {
210 unborrow!(clk, cmd, d0);
211
212 critical_section::with(|_| unsafe {
213 clk.set_as_af_pull(clk.af_num(), AFType::OutputPushPull, Pull::None);
214 cmd.set_as_af_pull(cmd.af_num(), AFType::OutputPushPull, Pull::Up);
215 d0.set_as_af_pull(d0.af_num(), AFType::OutputPushPull, Pull::Up);
216
217 clk.set_speed(Speed::VeryHigh);
218 cmd.set_speed(Speed::VeryHigh);
219 d0.set_speed(Speed::VeryHigh);
220 });
221
222 Self::new_inner(
223 sdmmc,
224 irq,
225 dma,
226 clk.map_into(),
227 cmd.map_into(),
228 d0.map_into(),
229 None,
230 None,
231 None,
232 config,
233 )
234 }
235
236 pub fn new_4bit(
237 sdmmc: impl Unborrow<Target = T> + 'd,
198 irq: impl Unborrow<Target = T::Interrupt> + 'd, 238 irq: impl Unborrow<Target = T::Interrupt> + 'd,
239 dma: impl Unborrow<Target = Dma> + 'd,
240 clk: impl Unborrow<Target = impl CkPin<T>> + 'd,
241 cmd: impl Unborrow<Target = impl CmdPin<T>> + 'd,
242 d0: impl Unborrow<Target = impl D0Pin<T>> + 'd,
243 d1: impl Unborrow<Target = impl D1Pin<T>> + 'd,
244 d2: impl Unborrow<Target = impl D2Pin<T>> + 'd,
245 d3: impl Unborrow<Target = impl D3Pin<T>> + 'd,
199 config: Config, 246 config: Config,
247 ) -> Self {
248 unborrow!(clk, cmd, d0, d1, d2, d3);
249
250 critical_section::with(|_| unsafe {
251 clk.set_as_af_pull(clk.af_num(), AFType::OutputPushPull, Pull::None);
252 cmd.set_as_af_pull(cmd.af_num(), AFType::OutputPushPull, Pull::Up);
253 d0.set_as_af_pull(d0.af_num(), AFType::OutputPushPull, Pull::Up);
254 d1.set_as_af_pull(d1.af_num(), AFType::OutputPushPull, Pull::Up);
255 d2.set_as_af_pull(d2.af_num(), AFType::OutputPushPull, Pull::Up);
256 d3.set_as_af_pull(d3.af_num(), AFType::OutputPushPull, Pull::Up);
257
258 clk.set_speed(Speed::VeryHigh);
259 cmd.set_speed(Speed::VeryHigh);
260 d0.set_speed(Speed::VeryHigh);
261 d1.set_speed(Speed::VeryHigh);
262 d2.set_speed(Speed::VeryHigh);
263 d3.set_speed(Speed::VeryHigh);
264 });
265
266 Self::new_inner(
267 sdmmc,
268 irq,
269 dma,
270 clk.map_into(),
271 cmd.map_into(),
272 d0.map_into(),
273 Some(d1.map_into()),
274 Some(d2.map_into()),
275 Some(d3.map_into()),
276 config,
277 )
278 }
279
280 fn new_inner(
281 sdmmc: impl Unborrow<Target = T> + 'd,
282 irq: impl Unborrow<Target = T::Interrupt> + 'd,
200 dma: impl Unborrow<Target = Dma> + 'd, 283 dma: impl Unborrow<Target = Dma> + 'd,
284 clk: Unborrowed<'d, AnyPin>,
285 cmd: Unborrowed<'d, AnyPin>,
286 d0: Unborrowed<'d, AnyPin>,
287 d1: Option<Unborrowed<'d, AnyPin>>,
288 d2: Option<Unborrowed<'d, AnyPin>>,
289 d3: Option<Unborrowed<'d, AnyPin>>,
290 config: Config,
201 ) -> Self { 291 ) -> Self {
202 unborrow!(irq, pins, dma); 292 unborrow!(sdmmc, irq, dma);
203 pins.configure();
204 293
205 T::enable(); 294 T::enable();
206 T::reset(); 295 T::reset();
@@ -213,11 +302,18 @@ impl<'d, T: Instance, P: Pins<T>, Dma: SdmmcDma<T>> Sdmmc<'d, T, P, Dma> {
213 irq.enable(); 302 irq.enable();
214 303
215 Self { 304 Self {
216 sdmmc: PhantomData, 305 _peri: sdmmc,
217 pins,
218 irq, 306 irq,
219 config,
220 dma, 307 dma,
308
309 clk,
310 cmd,
311 d0,
312 d1,
313 d2,
314 d3,
315
316 config,
221 clock, 317 clock,
222 signalling: Default::default(), 318 signalling: Default::default(),
223 card: None, 319 card: None,
@@ -226,15 +322,94 @@ impl<'d, T: Instance, P: Pins<T>, Dma: SdmmcDma<T>> Sdmmc<'d, T, P, Dma> {
226} 322}
227 323
228#[cfg(sdmmc_v2)] 324#[cfg(sdmmc_v2)]
229impl<'d, T: Instance, P: Pins<T>> Sdmmc<'d, T, P, NoDma> { 325impl<'d, T: Instance> Sdmmc<'d, T, NoDma> {
230 pub fn new( 326 pub fn new_1bit(
231 _peripheral: impl Unborrow<Target = T> + 'd, 327 sdmmc: impl Unborrow<Target = T> + 'd,
232 pins: impl Unborrow<Target = P> + 'd, 328 irq: impl Unborrow<Target = T::Interrupt> + 'd,
329 clk: impl Unborrow<Target = impl CkPin<T>> + 'd,
330 cmd: impl Unborrow<Target = impl CmdPin<T>> + 'd,
331 d0: impl Unborrow<Target = impl D0Pin<T>> + 'd,
332 config: Config,
333 ) -> Self {
334 unborrow!(clk, cmd, d0);
335
336 critical_section::with(|_| unsafe {
337 clk.set_as_af_pull(clk.af_num(), AFType::OutputPushPull, Pull::None);
338 cmd.set_as_af_pull(cmd.af_num(), AFType::OutputPushPull, Pull::Up);
339 d0.set_as_af_pull(d0.af_num(), AFType::OutputPushPull, Pull::Up);
340
341 clk.set_speed(Speed::VeryHigh);
342 cmd.set_speed(Speed::VeryHigh);
343 d0.set_speed(Speed::VeryHigh);
344 });
345
346 Self::new_inner(
347 sdmmc,
348 irq,
349 clk.map_into(),
350 cmd.map_into(),
351 d0.map_into(),
352 None,
353 None,
354 None,
355 config,
356 )
357 }
358
359 pub fn new_4bit(
360 sdmmc: impl Unborrow<Target = T> + 'd,
361 irq: impl Unborrow<Target = T::Interrupt> + 'd,
362 clk: impl Unborrow<Target = impl CkPin<T>> + 'd,
363 cmd: impl Unborrow<Target = impl CmdPin<T>> + 'd,
364 d0: impl Unborrow<Target = impl D0Pin<T>> + 'd,
365 d1: impl Unborrow<Target = impl D1Pin<T>> + 'd,
366 d2: impl Unborrow<Target = impl D2Pin<T>> + 'd,
367 d3: impl Unborrow<Target = impl D3Pin<T>> + 'd,
368 config: Config,
369 ) -> Self {
370 unborrow!(clk, cmd, d0, d1, d2, d3);
371
372 critical_section::with(|_| unsafe {
373 clk.set_as_af_pull(clk.af_num(), AFType::OutputPushPull, Pull::None);
374 cmd.set_as_af_pull(cmd.af_num(), AFType::OutputPushPull, Pull::Up);
375 d0.set_as_af_pull(d0.af_num(), AFType::OutputPushPull, Pull::Up);
376 d1.set_as_af_pull(d1.af_num(), AFType::OutputPushPull, Pull::Up);
377 d2.set_as_af_pull(d2.af_num(), AFType::OutputPushPull, Pull::Up);
378 d3.set_as_af_pull(d3.af_num(), AFType::OutputPushPull, Pull::Up);
379
380 clk.set_speed(Speed::VeryHigh);
381 cmd.set_speed(Speed::VeryHigh);
382 d0.set_speed(Speed::VeryHigh);
383 d1.set_speed(Speed::VeryHigh);
384 d2.set_speed(Speed::VeryHigh);
385 d3.set_speed(Speed::VeryHigh);
386 });
387
388 Self::new_inner(
389 sdmmc,
390 irq,
391 clk.map_into(),
392 cmd.map_into(),
393 d0.map_into(),
394 Some(d1.map_into()),
395 Some(d2.map_into()),
396 Some(d3.map_into()),
397 config,
398 )
399 }
400
401 fn new_inner(
402 sdmmc: impl Unborrow<Target = T> + 'd,
233 irq: impl Unborrow<Target = T::Interrupt> + 'd, 403 irq: impl Unborrow<Target = T::Interrupt> + 'd,
404 clk: Unborrowed<'d, AnyPin>,
405 cmd: Unborrowed<'d, AnyPin>,
406 d0: Unborrowed<'d, AnyPin>,
407 d1: Option<Unborrowed<'d, AnyPin>>,
408 d2: Option<Unborrowed<'d, AnyPin>>,
409 d3: Option<Unborrowed<'d, AnyPin>>,
234 config: Config, 410 config: Config,
235 ) -> Self { 411 ) -> Self {
236 unborrow!(irq, pins); 412 unborrow!(sdmmc, irq);
237 pins.configure();
238 413
239 T::enable(); 414 T::enable();
240 T::reset(); 415 T::reset();
@@ -247,11 +422,18 @@ impl<'d, T: Instance, P: Pins<T>> Sdmmc<'d, T, P, NoDma> {
247 irq.enable(); 422 irq.enable();
248 423
249 Self { 424 Self {
250 sdmmc: PhantomData, 425 _peri: sdmmc,
251 pins,
252 irq, 426 irq,
427 dma: NoDma.unborrow(),
428
429 clk,
430 cmd,
431 d0,
432 d1,
433 d2,
434 d3,
435
253 config, 436 config,
254 dma: NoDma,
255 clock, 437 clock,
256 signalling: Default::default(), 438 signalling: Default::default(),
257 card: None, 439 card: None,
@@ -259,23 +441,28 @@ impl<'d, T: Instance, P: Pins<T>> Sdmmc<'d, T, P, NoDma> {
259 } 441 }
260} 442}
261 443
262impl<'d, T: Instance, P: Pins<T>, Dma: SdmmcDma<T>> Sdmmc<'d, T, P, Dma> { 444impl<'d, T: Instance, Dma: SdmmcDma<T>> Sdmmc<'d, T, Dma> {
263 #[inline(always)] 445 #[inline(always)]
264 pub async fn init_card(&mut self, freq: Hertz) -> Result<(), Error> { 446 pub async fn init_card(&mut self, freq: Hertz) -> Result<(), Error> {
265 let inner = T::inner(); 447 let inner = T::inner();
266 let freq = freq.into(); 448 let freq = freq.into();
267 449
450 let bus_width = match self.d3.is_some() {
451 true => BusWidth::Four,
452 false => BusWidth::One,
453 };
454
268 inner 455 inner
269 .init_card( 456 .init_card(
270 freq, 457 freq,
271 P::BUSWIDTH, 458 bus_width,
272 &mut self.card, 459 &mut self.card,
273 &mut self.signalling, 460 &mut self.signalling,
274 T::frequency(), 461 T::frequency(),
275 &mut self.clock, 462 &mut self.clock,
276 T::state(), 463 T::state(),
277 self.config.data_transfer_timeout, 464 self.config.data_transfer_timeout,
278 &mut self.dma, 465 &mut *self.dma,
279 ) 466 )
280 .await 467 .await
281 } 468 }
@@ -295,7 +482,7 @@ impl<'d, T: Instance, P: Pins<T>, Dma: SdmmcDma<T>> Sdmmc<'d, T, P, Dma> {
295 card_capacity, 482 card_capacity,
296 state, 483 state,
297 self.config.data_transfer_timeout, 484 self.config.data_transfer_timeout,
298 &mut self.dma, 485 &mut *self.dma,
299 ) 486 )
300 .await 487 .await
301 } 488 }
@@ -314,7 +501,7 @@ impl<'d, T: Instance, P: Pins<T>, Dma: SdmmcDma<T>> Sdmmc<'d, T, P, Dma> {
314 card, 501 card,
315 state, 502 state,
316 self.config.data_transfer_timeout, 503 self.config.data_transfer_timeout,
317 &mut self.dma, 504 &mut *self.dma,
318 ) 505 )
319 .await 506 .await
320 } 507 }
@@ -345,12 +532,26 @@ impl<'d, T: Instance, P: Pins<T>, Dma: SdmmcDma<T>> Sdmmc<'d, T, P, Dma> {
345 } 532 }
346} 533}
347 534
348impl<'d, T: Instance, P: Pins<T>, Dma> Drop for Sdmmc<'d, T, P, Dma> { 535impl<'d, T: Instance, Dma> Drop for Sdmmc<'d, T, Dma> {
349 fn drop(&mut self) { 536 fn drop(&mut self) {
350 self.irq.disable(); 537 self.irq.disable();
351 let inner = T::inner(); 538 let inner = T::inner();
352 unsafe { inner.on_drop() }; 539 unsafe { inner.on_drop() };
353 self.pins.deconfigure(); 540
541 critical_section::with(|_| unsafe {
542 self.clk.set_as_disconnected();
543 self.cmd.set_as_disconnected();
544 self.d0.set_as_disconnected();
545 if let Some(x) = &mut self.d1 {
546 x.set_as_disconnected();
547 }
548 if let Some(x) = &mut self.d2 {
549 x.set_as_disconnected();
550 }
551 if let Some(x) = &mut self.d3 {
552 x.set_as_disconnected();
553 }
554 });
354 } 555 }
355} 556}
356 557
@@ -1296,114 +1497,6 @@ cfg_if::cfg_if! {
1296 } 1497 }
1297} 1498}
1298 1499
1299pub trait Pins<T: Instance>: sealed::Pins<T> + 'static {
1300 const BUSWIDTH: BusWidth;
1301
1302 fn configure(&mut self);
1303 fn deconfigure(&mut self);
1304}
1305
1306impl<T, CLK, CMD, D0, D1, D2, D3> sealed::Pins<T> for (CLK, CMD, D0, D1, D2, D3)
1307where
1308 T: Instance,
1309 CLK: CkPin<T>,
1310 CMD: CmdPin<T>,
1311 D0: D0Pin<T>,
1312 D1: D1Pin<T>,
1313 D2: D2Pin<T>,
1314 D3: D3Pin<T>,
1315{
1316}
1317
1318impl<T, CLK, CMD, D0> sealed::Pins<T> for (CLK, CMD, D0)
1319where
1320 T: Instance,
1321 CLK: CkPin<T>,
1322 CMD: CmdPin<T>,
1323 D0: D0Pin<T>,
1324{
1325}
1326
1327impl<T, CLK, CMD, D0, D1, D2, D3> Pins<T> for (CLK, CMD, D0, D1, D2, D3)
1328where
1329 T: Instance,
1330 CLK: CkPin<T>,
1331 CMD: CmdPin<T>,
1332 D0: D0Pin<T>,
1333 D1: D1Pin<T>,
1334 D2: D2Pin<T>,
1335 D3: D3Pin<T>,
1336{
1337 const BUSWIDTH: BusWidth = BusWidth::Four;
1338
1339 fn configure(&mut self) {
1340 let (clk_pin, cmd_pin, d0_pin, d1_pin, d2_pin, d3_pin) = self;
1341
1342 critical_section::with(|_| unsafe {
1343 clk_pin.set_as_af_pull(clk_pin.af_num(), AFType::OutputPushPull, Pull::None);
1344 cmd_pin.set_as_af_pull(cmd_pin.af_num(), AFType::OutputPushPull, Pull::Up);
1345 d0_pin.set_as_af_pull(d0_pin.af_num(), AFType::OutputPushPull, Pull::Up);
1346 d1_pin.set_as_af_pull(d1_pin.af_num(), AFType::OutputPushPull, Pull::Up);
1347 d2_pin.set_as_af_pull(d2_pin.af_num(), AFType::OutputPushPull, Pull::Up);
1348 d3_pin.set_as_af_pull(d3_pin.af_num(), AFType::OutputPushPull, Pull::Up);
1349
1350 clk_pin.set_speed(Speed::VeryHigh);
1351 cmd_pin.set_speed(Speed::VeryHigh);
1352 d0_pin.set_speed(Speed::VeryHigh);
1353 d1_pin.set_speed(Speed::VeryHigh);
1354 d2_pin.set_speed(Speed::VeryHigh);
1355 d3_pin.set_speed(Speed::VeryHigh);
1356 });
1357 }
1358
1359 fn deconfigure(&mut self) {
1360 let (clk_pin, cmd_pin, d0_pin, d1_pin, d2_pin, d3_pin) = self;
1361
1362 critical_section::with(|_| unsafe {
1363 clk_pin.set_as_disconnected();
1364 cmd_pin.set_as_disconnected();
1365 d0_pin.set_as_disconnected();
1366 d1_pin.set_as_disconnected();
1367 d2_pin.set_as_disconnected();
1368 d3_pin.set_as_disconnected();
1369 });
1370 }
1371}
1372
1373impl<T, CLK, CMD, D0> Pins<T> for (CLK, CMD, D0)
1374where
1375 T: Instance,
1376 CLK: CkPin<T>,
1377 CMD: CmdPin<T>,
1378 D0: D0Pin<T>,
1379{
1380 const BUSWIDTH: BusWidth = BusWidth::One;
1381
1382 fn configure(&mut self) {
1383 let (clk_pin, cmd_pin, d0_pin) = self;
1384
1385 critical_section::with(|_| unsafe {
1386 clk_pin.set_as_af_pull(clk_pin.af_num(), AFType::OutputPushPull, Pull::None);
1387 cmd_pin.set_as_af_pull(cmd_pin.af_num(), AFType::OutputPushPull, Pull::Up);
1388 d0_pin.set_as_af_pull(d0_pin.af_num(), AFType::OutputPushPull, Pull::Up);
1389
1390 clk_pin.set_speed(Speed::VeryHigh);
1391 cmd_pin.set_speed(Speed::VeryHigh);
1392 d0_pin.set_speed(Speed::VeryHigh);
1393 });
1394 }
1395
1396 fn deconfigure(&mut self) {
1397 let (clk_pin, cmd_pin, d0_pin) = self;
1398
1399 critical_section::with(|_| unsafe {
1400 clk_pin.set_as_disconnected();
1401 cmd_pin.set_as_disconnected();
1402 d0_pin.set_as_disconnected();
1403 });
1404 }
1405}
1406
1407foreach_peripheral!( 1500foreach_peripheral!(
1408 (sdmmc, $inst:ident) => { 1501 (sdmmc, $inst:ident) => {
1409 impl sealed::Instance for peripherals::$inst { 1502 impl sealed::Instance for peripherals::$inst {
diff --git a/embassy-stm32/src/spi/mod.rs b/embassy-stm32/src/spi/mod.rs
index a02f4492f..595957b2e 100644
--- a/embassy-stm32/src/spi/mod.rs
+++ b/embassy-stm32/src/spi/mod.rs
@@ -1,10 +1,9 @@
1#![macro_use] 1#![macro_use]
2 2
3use core::marker::PhantomData;
4use core::ptr; 3use core::ptr;
5 4
6use embassy_embedded_hal::SetConfig; 5use embassy_embedded_hal::SetConfig;
7use embassy_hal_common::unborrow; 6use embassy_hal_common::{unborrow, Unborrowed};
8pub use embedded_hal_02::spi::{Mode, Phase, Polarity, MODE_0, MODE_1, MODE_2, MODE_3}; 7pub use embedded_hal_02::spi::{Mode, Phase, Polarity, MODE_0, MODE_1, MODE_2, MODE_3};
9use futures::future::join; 8use futures::future::join;
10 9
@@ -73,13 +72,13 @@ impl Config {
73} 72}
74 73
75pub struct Spi<'d, T: Instance, Tx, Rx> { 74pub struct Spi<'d, T: Instance, Tx, Rx> {
76 sck: Option<AnyPin>, 75 _peri: Unborrowed<'d, T>,
77 mosi: Option<AnyPin>, 76 sck: Option<Unborrowed<'d, AnyPin>>,
78 miso: Option<AnyPin>, 77 mosi: Option<Unborrowed<'d, AnyPin>>,
79 txdma: Tx, 78 miso: Option<Unborrowed<'d, AnyPin>>,
80 rxdma: Rx, 79 txdma: Unborrowed<'d, Tx>,
80 rxdma: Unborrowed<'d, Rx>,
81 current_word_size: WordSize, 81 current_word_size: WordSize,
82 phantom: PhantomData<&'d mut T>,
83} 82}
84 83
85impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> { 84impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> {
@@ -93,7 +92,7 @@ impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> {
93 freq: Hertz, 92 freq: Hertz,
94 config: Config, 93 config: Config,
95 ) -> Self { 94 ) -> Self {
96 unborrow!(sck, mosi, miso); 95 unborrow!(peri, sck, mosi, miso);
97 unsafe { 96 unsafe {
98 sck.set_as_af(sck.af_num(), AFType::OutputPushPull); 97 sck.set_as_af(sck.af_num(), AFType::OutputPushPull);
99 #[cfg(any(spi_v2, spi_v3, spi_v4))] 98 #[cfg(any(spi_v2, spi_v3, spi_v4))]
@@ -108,9 +107,9 @@ impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> {
108 107
109 Self::new_inner( 108 Self::new_inner(
110 peri, 109 peri,
111 Some(sck.degrade()), 110 Some(sck.map_into()),
112 Some(mosi.degrade()), 111 Some(mosi.map_into()),
113 Some(miso.degrade()), 112 Some(miso.map_into()),
114 txdma, 113 txdma,
115 rxdma, 114 rxdma,
116 freq, 115 freq,
@@ -139,9 +138,9 @@ impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> {
139 138
140 Self::new_inner( 139 Self::new_inner(
141 peri, 140 peri,
142 Some(sck.degrade()), 141 Some(sck.map_into()),
143 None, 142 None,
144 Some(miso.degrade()), 143 Some(miso.map_into()),
145 txdma, 144 txdma,
146 rxdma, 145 rxdma,
147 freq, 146 freq,
@@ -170,8 +169,8 @@ impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> {
170 169
171 Self::new_inner( 170 Self::new_inner(
172 peri, 171 peri,
173 Some(sck.degrade()), 172 Some(sck.map_into()),
174 Some(mosi.degrade()), 173 Some(mosi.map_into()),
175 None, 174 None,
176 txdma, 175 txdma,
177 rxdma, 176 rxdma,
@@ -181,16 +180,16 @@ impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> {
181 } 180 }
182 181
183 fn new_inner( 182 fn new_inner(
184 _peri: impl Unborrow<Target = T> + 'd, 183 peri: impl Unborrow<Target = T> + 'd,
185 sck: Option<AnyPin>, 184 sck: Option<Unborrowed<'d, AnyPin>>,
186 mosi: Option<AnyPin>, 185 mosi: Option<Unborrowed<'d, AnyPin>>,
187 miso: Option<AnyPin>, 186 miso: Option<Unborrowed<'d, AnyPin>>,
188 txdma: impl Unborrow<Target = Tx> + 'd, 187 txdma: impl Unborrow<Target = Tx> + 'd,
189 rxdma: impl Unborrow<Target = Rx> + 'd, 188 rxdma: impl Unborrow<Target = Rx> + 'd,
190 freq: Hertz, 189 freq: Hertz,
191 config: Config, 190 config: Config,
192 ) -> Self { 191 ) -> Self {
193 unborrow!(txdma, rxdma); 192 unborrow!(peri, txdma, rxdma);
194 193
195 let pclk = T::frequency(); 194 let pclk = T::frequency();
196 let br = compute_baud_rate(pclk, freq.into()); 195 let br = compute_baud_rate(pclk, freq.into());
@@ -280,13 +279,13 @@ impl<'d, T: Instance, Tx, Rx> Spi<'d, T, Tx, Rx> {
280 } 279 }
281 280
282 Self { 281 Self {
282 _peri: peri,
283 sck, 283 sck,
284 mosi, 284 mosi,
285 miso, 285 miso,
286 txdma, 286 txdma,
287 rxdma, 287 rxdma,
288 current_word_size: WordSize::EightBit, 288 current_word_size: WordSize::EightBit,
289 phantom: PhantomData,
290 } 289 }
291 } 290 }
292 291
@@ -995,7 +994,7 @@ pub trait Word: Copy + 'static + sealed::Word + Default + crate::dma::Word {}
995impl Word for u8 {} 994impl Word for u8 {}
996impl Word for u16 {} 995impl Word for u16 {}
997 996
998pub trait Instance: sealed::Instance + RccPeripheral {} 997pub trait Instance: Unborrow<Target = Self> + sealed::Instance + RccPeripheral {}
999pin_trait!(SckPin, Instance); 998pin_trait!(SckPin, Instance);
1000pin_trait!(MosiPin, Instance); 999pin_trait!(MosiPin, Instance);
1001pin_trait!(MisoPin, Instance); 1000pin_trait!(MisoPin, Instance);
diff --git a/embassy-stm32/src/usart/mod.rs b/embassy-stm32/src/usart/mod.rs
index a893e4b80..6b12378da 100644
--- a/embassy-stm32/src/usart/mod.rs
+++ b/embassy-stm32/src/usart/mod.rs
@@ -2,7 +2,7 @@
2 2
3use core::marker::PhantomData; 3use core::marker::PhantomData;
4 4
5use embassy_hal_common::unborrow; 5use embassy_hal_common::{unborrow, Unborrowed};
6 6
7use crate::dma::NoDma; 7use crate::dma::NoDma;
8use crate::gpio::sealed::AFType; 8use crate::gpio::sealed::AFType;
@@ -72,23 +72,22 @@ pub enum Error {
72} 72}
73 73
74pub struct Uart<'d, T: Instance, TxDma = NoDma, RxDma = NoDma> { 74pub struct Uart<'d, T: Instance, TxDma = NoDma, RxDma = NoDma> {
75 phantom: PhantomData<&'d mut T>,
76 tx: UartTx<'d, T, TxDma>, 75 tx: UartTx<'d, T, TxDma>,
77 rx: UartRx<'d, T, RxDma>, 76 rx: UartRx<'d, T, RxDma>,
78} 77}
79 78
80pub struct UartTx<'d, T: Instance, TxDma = NoDma> { 79pub struct UartTx<'d, T: Instance, TxDma = NoDma> {
81 phantom: PhantomData<&'d mut T>, 80 phantom: PhantomData<&'d mut T>,
82 tx_dma: TxDma, 81 tx_dma: Unborrowed<'d, TxDma>,
83} 82}
84 83
85pub struct UartRx<'d, T: Instance, RxDma = NoDma> { 84pub struct UartRx<'d, T: Instance, RxDma = NoDma> {
86 phantom: PhantomData<&'d mut T>, 85 phantom: PhantomData<&'d mut T>,
87 rx_dma: RxDma, 86 rx_dma: Unborrowed<'d, RxDma>,
88} 87}
89 88
90impl<'d, T: Instance, TxDma> UartTx<'d, T, TxDma> { 89impl<'d, T: Instance, TxDma> UartTx<'d, T, TxDma> {
91 fn new(tx_dma: TxDma) -> Self { 90 fn new(tx_dma: Unborrowed<'d, TxDma>) -> Self {
92 Self { 91 Self {
93 tx_dma, 92 tx_dma,
94 phantom: PhantomData, 93 phantom: PhantomData,
@@ -134,7 +133,7 @@ impl<'d, T: Instance, TxDma> UartTx<'d, T, TxDma> {
134} 133}
135 134
136impl<'d, T: Instance, RxDma> UartRx<'d, T, RxDma> { 135impl<'d, T: Instance, RxDma> UartRx<'d, T, RxDma> {
137 fn new(rx_dma: RxDma) -> Self { 136 fn new(rx_dma: Unborrowed<'d, RxDma>) -> Self {
138 Self { 137 Self {
139 rx_dma, 138 rx_dma,
140 phantom: PhantomData, 139 phantom: PhantomData,
@@ -234,7 +233,6 @@ impl<'d, T: Instance, TxDma, RxDma> Uart<'d, T, TxDma, RxDma> {
234 } 233 }
235 234
236 Self { 235 Self {
237 phantom: PhantomData,
238 tx: UartTx::new(tx_dma), 236 tx: UartTx::new(tx_dma),
239 rx: UartRx::new(rx_dma), 237 rx: UartRx::new(rx_dma),
240 } 238 }
diff --git a/examples/stm32f4/src/bin/sdmmc.rs b/examples/stm32f4/src/bin/sdmmc.rs
index 665670261..752ad57bf 100644
--- a/examples/stm32f4/src/bin/sdmmc.rs
+++ b/examples/stm32f4/src/bin/sdmmc.rs
@@ -21,12 +21,17 @@ async fn main(_spawner: Spawner, p: Peripherals) -> ! {
21 21
22 let irq = interrupt::take!(SDIO); 22 let irq = interrupt::take!(SDIO);
23 23
24 let mut sdmmc = Sdmmc::new( 24 let mut sdmmc = Sdmmc::new_4bit(
25 p.SDIO, 25 p.SDIO,
26 (p.PC12, p.PD2, p.PC8, p.PC9, p.PC10, p.PC11),
27 irq, 26 irq,
28 Default::default(),
29 p.DMA2_CH3, 27 p.DMA2_CH3,
28 p.PC12,
29 p.PD2,
30 p.PC8,
31 p.PC9,
32 p.PC10,
33 p.PC11,
34 Default::default(),
30 ); 35 );
31 36
32 // Should print 400kHz for initialization 37 // Should print 400kHz for initialization
diff --git a/examples/stm32f7/src/bin/sdmmc.rs b/examples/stm32f7/src/bin/sdmmc.rs
index 011e1fd95..be1c2b152 100644
--- a/examples/stm32f7/src/bin/sdmmc.rs
+++ b/examples/stm32f7/src/bin/sdmmc.rs
@@ -21,12 +21,17 @@ async fn main(_spawner: Spawner, p: Peripherals) -> ! {
21 21
22 let irq = interrupt::take!(SDMMC1); 22 let irq = interrupt::take!(SDMMC1);
23 23
24 let mut sdmmc = Sdmmc::new( 24 let mut sdmmc = Sdmmc::new_4bit(
25 p.SDMMC1, 25 p.SDMMC1,
26 (p.PC12, p.PD2, p.PC8, p.PC9, p.PC10, p.PC11),
27 irq, 26 irq,
28 Default::default(),
29 p.DMA2_CH3, 27 p.DMA2_CH3,
28 p.PC12,
29 p.PD2,
30 p.PC8,
31 p.PC9,
32 p.PC10,
33 p.PC11,
34 Default::default(),
30 ); 35 );
31 36
32 // Should print 400kHz for initialization 37 // Should print 400kHz for initialization
diff --git a/examples/stm32h7/src/bin/low_level_timer_api.rs b/examples/stm32h7/src/bin/low_level_timer_api.rs
index fc19d84e4..e54f1bb67 100644
--- a/examples/stm32h7/src/bin/low_level_timer_api.rs
+++ b/examples/stm32h7/src/bin/low_level_timer_api.rs
@@ -2,8 +2,6 @@
2#![no_main] 2#![no_main]
3#![feature(type_alias_impl_trait)] 3#![feature(type_alias_impl_trait)]
4 4
5use core::marker::PhantomData;
6
7use defmt::*; 5use defmt::*;
8use embassy::executor::Spawner; 6use embassy::executor::Spawner;
9use embassy::time::{Duration, Timer}; 7use embassy::time::{Duration, Timer};
@@ -11,7 +9,7 @@ use embassy_stm32::gpio::low_level::AFType;
11use embassy_stm32::gpio::Speed; 9use embassy_stm32::gpio::Speed;
12use embassy_stm32::pwm::*; 10use embassy_stm32::pwm::*;
13use embassy_stm32::time::{khz, mhz, Hertz}; 11use embassy_stm32::time::{khz, mhz, Hertz};
14use embassy_stm32::{unborrow, Config, Peripherals, Unborrow}; 12use embassy_stm32::{unborrow, Config, Peripherals, Unborrow, Unborrowed};
15use {defmt_rtt as _, panic_probe as _}; 13use {defmt_rtt as _, panic_probe as _};
16 14
17pub fn config() -> Config { 15pub fn config() -> Config {
@@ -49,8 +47,7 @@ async fn main(_spawner: Spawner, p: Peripherals) {
49 } 47 }
50} 48}
51pub struct SimplePwm32<'d, T: CaptureCompare32bitInstance> { 49pub struct SimplePwm32<'d, T: CaptureCompare32bitInstance> {
52 phantom: PhantomData<&'d mut T>, 50 inner: Unborrowed<'d, T>,
53 inner: T,
54} 51}
55 52
56impl<'d, T: CaptureCompare32bitInstance> SimplePwm32<'d, T> { 53impl<'d, T: CaptureCompare32bitInstance> SimplePwm32<'d, T> {
@@ -78,10 +75,7 @@ impl<'d, T: CaptureCompare32bitInstance> SimplePwm32<'d, T> {
78 ch4.set_as_af(ch1.af_num(), AFType::OutputPushPull); 75 ch4.set_as_af(ch1.af_num(), AFType::OutputPushPull);
79 } 76 }
80 77
81 let mut this = Self { 78 let mut this = Self { inner: tim };
82 inner: tim,
83 phantom: PhantomData,
84 };
85 79
86 this.set_freq(freq); 80 this.set_freq(freq);
87 this.inner.start(); 81 this.inner.start();
diff --git a/examples/stm32h7/src/bin/sdmmc.rs b/examples/stm32h7/src/bin/sdmmc.rs
index 787f700ae..163807d86 100644
--- a/examples/stm32h7/src/bin/sdmmc.rs
+++ b/examples/stm32h7/src/bin/sdmmc.rs
@@ -21,10 +21,15 @@ async fn main(_spawner: Spawner, p: Peripherals) -> ! {
21 21
22 let irq = interrupt::take!(SDMMC1); 22 let irq = interrupt::take!(SDMMC1);
23 23
24 let mut sdmmc = Sdmmc::new( 24 let mut sdmmc = Sdmmc::new_4bit(
25 p.SDMMC1, 25 p.SDMMC1,
26 (p.PC12, p.PD2, p.PC8, p.PC9, p.PC10, p.PC11),
27 irq, 26 irq,
27 p.PC12,
28 p.PD2,
29 p.PC8,
30 p.PC9,
31 p.PC10,
32 p.PC11,
28 Default::default(), 33 Default::default(),
29 ); 34 );
30 35