diff options
| author | Bob McWhirter <[email protected]> | 2021-07-20 11:38:16 -0400 |
|---|---|---|
| committer | Bob McWhirter <[email protected]> | 2021-07-20 11:38:16 -0400 |
| commit | 2d3137afc7c20dd68e4a187cafd7016f5a0f4d34 (patch) | |
| tree | 40d091d6a8cd0ce049fdea76c636bb8e3300b8b8 | |
| parent | 25b870d811d9ac3955a69996ddf7a68a2af252f5 (diff) | |
The `async move` portion of @thalesfragoso's i2c PR.
| -rw-r--r-- | embassy-stm32/src/dma/bdma.rs | 29 | ||||
| -rw-r--r-- | embassy-stm32/src/dma/dma.rs | 33 |
2 files changed, 34 insertions, 28 deletions
diff --git a/embassy-stm32/src/dma/bdma.rs b/embassy-stm32/src/dma/bdma.rs index 5063ec2e7..e2da2a8ea 100644 --- a/embassy-stm32/src/dma/bdma.rs +++ b/embassy-stm32/src/dma/bdma.rs | |||
| @@ -38,7 +38,7 @@ impl State { | |||
| 38 | static STATE: State = State::new(); | 38 | static STATE: State = State::new(); |
| 39 | 39 | ||
| 40 | #[allow(unused)] | 40 | #[allow(unused)] |
| 41 | pub(crate) async unsafe fn do_transfer( | 41 | pub(crate) unsafe fn do_transfer( |
| 42 | dma: pac::bdma::Dma, | 42 | dma: pac::bdma::Dma, |
| 43 | channel_number: u8, | 43 | channel_number: u8, |
| 44 | state_number: u8, | 44 | state_number: u8, |
| @@ -49,7 +49,7 @@ pub(crate) async unsafe fn do_transfer( | |||
| 49 | mem_len: usize, | 49 | mem_len: usize, |
| 50 | #[cfg(dmamux)] dmamux_regs: pac::dmamux::Dmamux, | 50 | #[cfg(dmamux)] dmamux_regs: pac::dmamux::Dmamux, |
| 51 | #[cfg(dmamux)] dmamux_ch_num: u8, | 51 | #[cfg(dmamux)] dmamux_ch_num: u8, |
| 52 | ) { | 52 | ) -> impl Future<Output = ()> { |
| 53 | // ndtr is max 16 bits. | 53 | // ndtr is max 16 bits. |
| 54 | assert!(mem_len <= 0xFFFF); | 54 | assert!(mem_len <= 0xFFFF); |
| 55 | 55 | ||
| @@ -59,7 +59,7 @@ pub(crate) async unsafe fn do_transfer( | |||
| 59 | // Generate a DMB here to flush the store buffer (M7) before enabling the DMA | 59 | // Generate a DMB here to flush the store buffer (M7) before enabling the DMA |
| 60 | STATE.ch_status[state_number as usize].store(CH_STATUS_NONE, Ordering::Release); | 60 | STATE.ch_status[state_number as usize].store(CH_STATUS_NONE, Ordering::Release); |
| 61 | 61 | ||
| 62 | let on_drop = OnDrop::new(|| unsafe { | 62 | let on_drop = OnDrop::new(move || unsafe { |
| 63 | ch.cr().modify(|w| { | 63 | ch.cr().modify(|w| { |
| 64 | w.set_tcie(false); | 64 | w.set_tcie(false); |
| 65 | w.set_teie(false); | 65 | w.set_teie(false); |
| @@ -95,17 +95,20 @@ pub(crate) async unsafe fn do_transfer( | |||
| 95 | w.set_en(true); | 95 | w.set_en(true); |
| 96 | }); | 96 | }); |
| 97 | 97 | ||
| 98 | let res = poll_fn(|cx| { | 98 | async move { |
| 99 | STATE.ch_wakers[state_number as usize].register(cx.waker()); | 99 | let res = poll_fn(|cx| { |
| 100 | match STATE.ch_status[state_number as usize].load(Ordering::Acquire) { | 100 | STATE.ch_wakers[state_number as usize].register(cx.waker()); |
| 101 | CH_STATUS_NONE => Poll::Pending, | 101 | match STATE.ch_status[state_number as usize].load(Ordering::Acquire) { |
| 102 | x => Poll::Ready(x), | 102 | CH_STATUS_NONE => Poll::Pending, |
| 103 | } | 103 | x => Poll::Ready(x), |
| 104 | }) | 104 | } |
| 105 | .await; | 105 | }) |
| 106 | .await; | ||
| 106 | 107 | ||
| 107 | // TODO handle error | 108 | // TODO handle error |
| 108 | assert!(res == CH_STATUS_COMPLETED); | 109 | assert!(res == CH_STATUS_COMPLETED); |
| 110 | drop(on_drop) | ||
| 111 | } | ||
| 109 | } | 112 | } |
| 110 | 113 | ||
| 111 | macro_rules! dma_num { | 114 | macro_rules! dma_num { |
diff --git a/embassy-stm32/src/dma/dma.rs b/embassy-stm32/src/dma/dma.rs index 8634de205..cf0889a3e 100644 --- a/embassy-stm32/src/dma/dma.rs +++ b/embassy-stm32/src/dma/dma.rs | |||
| @@ -1,7 +1,7 @@ | |||
| 1 | use core::future::Future; | ||
| 1 | use core::task::Poll; | 2 | use core::task::Poll; |
| 2 | 3 | ||
| 3 | use atomic_polyfill::{AtomicU8, Ordering}; | 4 | use atomic_polyfill::{AtomicU8, Ordering}; |
| 4 | use core::future::Future; | ||
| 5 | use embassy::interrupt::{Interrupt, InterruptExt}; | 5 | use embassy::interrupt::{Interrupt, InterruptExt}; |
| 6 | use embassy::util::{AtomicWaker, OnDrop}; | 6 | use embassy::util::{AtomicWaker, OnDrop}; |
| 7 | use futures::future::poll_fn; | 7 | use futures::future::poll_fn; |
| @@ -39,7 +39,7 @@ static STATE: State = State::new(); | |||
| 39 | //async unsafe fn do_transfer(ch: &mut impl Channel, ch_func: u8, src: *const u8, dst: &mut [u8]) { | 39 | //async unsafe fn do_transfer(ch: &mut impl Channel, ch_func: u8, src: *const u8, dst: &mut [u8]) { |
| 40 | 40 | ||
| 41 | #[allow(unused)] | 41 | #[allow(unused)] |
| 42 | pub(crate) async unsafe fn do_transfer( | 42 | pub(crate) unsafe fn do_transfer( |
| 43 | dma: pac::dma::Dma, | 43 | dma: pac::dma::Dma, |
| 44 | channel_number: u8, | 44 | channel_number: u8, |
| 45 | state_number: u8, | 45 | state_number: u8, |
| @@ -50,7 +50,7 @@ pub(crate) async unsafe fn do_transfer( | |||
| 50 | mem_len: usize, | 50 | mem_len: usize, |
| 51 | #[cfg(dmamux)] dmamux_regs: pac::dmamux::Dmamux, | 51 | #[cfg(dmamux)] dmamux_regs: pac::dmamux::Dmamux, |
| 52 | #[cfg(dmamux)] dmamux_ch_num: u8, | 52 | #[cfg(dmamux)] dmamux_ch_num: u8, |
| 53 | ) { | 53 | ) -> impl Future<Output = ()> { |
| 54 | // ndtr is max 16 bits. | 54 | // ndtr is max 16 bits. |
| 55 | assert!(mem_len <= 0xFFFF); | 55 | assert!(mem_len <= 0xFFFF); |
| 56 | 56 | ||
| @@ -60,7 +60,7 @@ pub(crate) async unsafe fn do_transfer( | |||
| 60 | 60 | ||
| 61 | let ch = dma.st(channel_number as _); | 61 | let ch = dma.st(channel_number as _); |
| 62 | 62 | ||
| 63 | let on_drop = OnDrop::new(|| unsafe { | 63 | let on_drop = OnDrop::new(move || unsafe { |
| 64 | ch.cr().modify(|w| { | 64 | ch.cr().modify(|w| { |
| 65 | w.set_tcie(false); | 65 | w.set_tcie(false); |
| 66 | w.set_teie(false); | 66 | w.set_teie(false); |
| @@ -100,18 +100,21 @@ pub(crate) async unsafe fn do_transfer( | |||
| 100 | }); | 100 | }); |
| 101 | } | 101 | } |
| 102 | 102 | ||
| 103 | let res = poll_fn(|cx| { | 103 | async move { |
| 104 | let n = channel_number as usize; | 104 | let res = poll_fn(|cx| { |
| 105 | STATE.ch_wakers[n].register(cx.waker()); | 105 | let n = channel_number as usize; |
| 106 | match STATE.ch_status[n].load(Ordering::Acquire) { | 106 | STATE.ch_wakers[n].register(cx.waker()); |
| 107 | CH_STATUS_NONE => Poll::Pending, | 107 | match STATE.ch_status[n].load(Ordering::Acquire) { |
| 108 | x => Poll::Ready(x), | 108 | CH_STATUS_NONE => Poll::Pending, |
| 109 | } | 109 | x => Poll::Ready(x), |
| 110 | }) | 110 | } |
| 111 | .await; | 111 | }) |
| 112 | .await; | ||
| 112 | 113 | ||
| 113 | // TODO handle error | 114 | // TODO handle error |
| 114 | assert!(res == CH_STATUS_COMPLETED); | 115 | assert!(res == CH_STATUS_COMPLETED); |
| 116 | drop(on_drop) | ||
| 117 | } | ||
| 115 | } | 118 | } |
| 116 | 119 | ||
| 117 | macro_rules! dma_num { | 120 | macro_rules! dma_num { |
