summaryrefslogtreecommitdiff
path: root/embassy-nrf
diff options
context:
space:
mode:
authorHenrik Alsér <henrik.alser@me.com>2022-05-07 09:47:29 +0200
committerGitHub <noreply@github.com>2022-05-07 09:47:29 +0200
commit1ca5475010a1cae6ebc55a27948ca4320decd5cd (patch)
tree2484384d601823b4dfe96c2bc4bf2d260b34c5f1 /embassy-nrf
parent108a98136096f8b530266aa6687bdbbed4a6a382 (diff)
parenta4bf190f2f0ce28a298626de6de1c8059269cedc (diff)
downloadembassy-1ca5475010a1cae6ebc55a27948ca4320decd5cd.zip
Merge branch 'embassy-rs:master' into qdec
Diffstat (limited to 'embassy-nrf')
-rw-r--r--embassy-nrf/Cargo.toml5
-rw-r--r--embassy-nrf/src/buffered_uarte.rs144
-rw-r--r--embassy-nrf/src/lib.rs1
3 files changed, 84 insertions, 66 deletions
diff --git a/embassy-nrf/Cargo.toml b/embassy-nrf/Cargo.toml
index b7c09286..cf61abcc 100644
--- a/embassy-nrf/Cargo.toml
+++ b/embassy-nrf/Cargo.toml
@@ -19,10 +19,10 @@ flavors = [
time = ["embassy/time"]
-defmt = ["dep:defmt", "embassy/defmt", "embassy-usb?/defmt"]
+defmt = ["dep:defmt", "embassy/defmt", "embassy-usb?/defmt", "embedded-io?/defmt"]
# Enable nightly-only features
-nightly = ["embassy/nightly", "embedded-hal-1", "embedded-hal-async", "embassy-usb", "embedded-storage-async"]
+nightly = ["embassy/nightly", "embedded-hal-1", "embedded-hal-async", "embassy-usb", "embedded-storage-async", "dep:embedded-io"]
# Reexport the PAC for the currently enabled chip at `embassy_nrf::pac`.
# This is unstable because semver-minor (non-breaking) releases of embassy-nrf may major-bump (breaking) the PAC version.
@@ -73,6 +73,7 @@ embassy-usb = {version = "0.1.0", path = "../embassy-usb", optional=true }
embedded-hal-02 = { package = "embedded-hal", version = "0.2.6", features = ["unproven"] }
embedded-hal-1 = { package = "embedded-hal", version = "1.0.0-alpha.8", optional = true}
embedded-hal-async = { version = "0.1.0-alpha.0", optional = true}
+embedded-io = { version = "0.2.0", features = ["async"], optional = true }
defmt = { version = "0.3", optional = true }
log = { version = "0.4.14", optional = true }
diff --git a/embassy-nrf/src/buffered_uarte.rs b/embassy-nrf/src/buffered_uarte.rs
index b49c1278..fc4e9c8d 100644
--- a/embassy-nrf/src/buffered_uarte.rs
+++ b/embassy-nrf/src/buffered_uarte.rs
@@ -14,18 +14,17 @@
//! Please also see [crate::uarte] to understand when [BufferedUarte] should be used.
use core::cmp::min;
+use core::future::Future;
use core::marker::PhantomData;
-use core::mem;
-use core::pin::Pin;
use core::sync::atomic::{compiler_fence, Ordering};
-use core::task::{Context, Poll};
+use core::task::Poll;
use embassy::interrupt::InterruptExt;
-use embassy::io::{AsyncBufRead, AsyncWrite};
use embassy::util::Unborrow;
use embassy::waitqueue::WakerRegistration;
use embassy_hal_common::peripheral::{PeripheralMutex, PeripheralState, StateStorage};
use embassy_hal_common::ring_buffer::RingBuffer;
use embassy_hal_common::{low_power_wait_until, unborrow};
+use futures::future::poll_fn;
use crate::gpio::Pin as GpioPin;
use crate::pac;
@@ -197,82 +196,99 @@ impl<'d, U: UarteInstance, T: TimerInstance> BufferedUarte<'d, U, T> {
}
}
-impl<'d, U: UarteInstance, T: TimerInstance> AsyncBufRead for BufferedUarte<'d, U, T> {
- fn poll_fill_buf(
- mut self: Pin<&mut Self>,
- cx: &mut Context<'_>,
- ) -> Poll<embassy::io::Result<&[u8]>> {
- self.inner.with(|state| {
- compiler_fence(Ordering::SeqCst);
- trace!("poll_read");
-
- // We have data ready in buffer? Return it.
- let buf = state.rx.pop_buf();
- if !buf.is_empty() {
- trace!(" got {:?} {:?}", buf.as_ptr() as u32, buf.len());
- let buf: &[u8] = buf;
- let buf: &[u8] = unsafe { mem::transmute(buf) };
- return Poll::Ready(Ok(buf));
+impl<'d, U: UarteInstance, T: TimerInstance> embedded_io::Io for BufferedUarte<'d, U, T> {
+ type Error = core::convert::Infallible;
+}
+
+impl<'d, U: UarteInstance, T: TimerInstance> embedded_io::asynch::Read for BufferedUarte<'d, U, T> {
+ type ReadFuture<'a> = impl Future<Output = Result<usize, Self::Error>>
+ where
+ Self: 'a;
+
+ fn read<'a>(&'a mut self, buf: &'a mut [u8]) -> Self::ReadFuture<'a> {
+ poll_fn(move |cx| {
+ let mut do_pend = false;
+ let res = self.inner.with(|state| {
+ compiler_fence(Ordering::SeqCst);
+ trace!("poll_read");
+
+ // We have data ready in buffer? Return it.
+ let data = state.rx.pop_buf();
+ if !data.is_empty() {
+ trace!(" got {:?} {:?}", data.as_ptr() as u32, data.len());
+ let len = data.len().min(data.len());
+ buf[..len].copy_from_slice(&data[..len]);
+ state.rx.pop(len);
+ do_pend = true;
+ return Poll::Ready(Ok(len));
+ }
+
+ trace!(" empty");
+ state.rx_waker.register(cx.waker());
+ Poll::Pending
+ });
+ if do_pend {
+ self.inner.pend();
}
- trace!(" empty");
- state.rx_waker.register(cx.waker());
- Poll::<embassy::io::Result<&[u8]>>::Pending
+ res
})
}
-
- fn consume(mut self: Pin<&mut Self>, amt: usize) {
- self.inner.with(|state| {
- trace!("consume {:?}", amt);
- state.rx.pop(amt);
- });
- self.inner.pend();
- }
}
-impl<'d, U: UarteInstance, T: TimerInstance> AsyncWrite for BufferedUarte<'d, U, T> {
- fn poll_write(
- mut self: Pin<&mut Self>,
- cx: &mut Context<'_>,
- buf: &[u8],
- ) -> Poll<embassy::io::Result<usize>> {
- let poll = self.inner.with(|state| {
- trace!("poll_write: {:?}", buf.len());
-
- let tx_buf = state.tx.push_buf();
- if tx_buf.is_empty() {
- trace!("poll_write: pending");
- state.tx_waker.register(cx.waker());
- return Poll::Pending;
- }
+impl<'d, U: UarteInstance, T: TimerInstance> embedded_io::asynch::Write
+ for BufferedUarte<'d, U, T>
+{
+ type WriteFuture<'a> = impl Future<Output = Result<usize, Self::Error>>
+ where
+ Self: 'a;
+
+ fn write<'a>(&'a mut self, buf: &'a [u8]) -> Self::WriteFuture<'a> {
+ poll_fn(move |cx| {
+ let res = self.inner.with(|state| {
+ trace!("poll_write: {:?}", buf.len());
+
+ let tx_buf = state.tx.push_buf();
+ if tx_buf.is_empty() {
+ trace!("poll_write: pending");
+ state.tx_waker.register(cx.waker());
+ return Poll::Pending;
+ }
- let n = min(tx_buf.len(), buf.len());
- tx_buf[..n].copy_from_slice(&buf[..n]);
- state.tx.push(n);
+ let n = min(tx_buf.len(), buf.len());
+ tx_buf[..n].copy_from_slice(&buf[..n]);
+ state.tx.push(n);
- trace!("poll_write: queued {:?}", n);
+ trace!("poll_write: queued {:?}", n);
- compiler_fence(Ordering::SeqCst);
+ compiler_fence(Ordering::SeqCst);
- Poll::Ready(Ok(n))
- });
+ Poll::Ready(Ok(n))
+ });
- self.inner.pend();
+ self.inner.pend();
- poll
+ res
+ })
}
- fn poll_flush(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<embassy::io::Result<()>> {
- self.inner.with(|state| {
- trace!("poll_flush");
+ type FlushFuture<'a> = impl Future<Output = Result<(), Self::Error>>
+ where
+ Self: 'a;
- if !state.tx.is_empty() {
- trace!("poll_flush: pending");
- state.tx_waker.register(cx.waker());
- return Poll::Pending;
- }
+ fn flush<'a>(&'a mut self) -> Self::FlushFuture<'a> {
+ poll_fn(move |cx| {
+ self.inner.with(|state| {
+ trace!("poll_flush");
+
+ if !state.tx.is_empty() {
+ trace!("poll_flush: pending");
+ state.tx_waker.register(cx.waker());
+ return Poll::Pending;
+ }
- Poll::Ready(Ok(()))
+ Poll::Ready(Ok(()))
+ })
})
}
}
diff --git a/embassy-nrf/src/lib.rs b/embassy-nrf/src/lib.rs
index 46234b4b..9c298a8b 100644
--- a/embassy-nrf/src/lib.rs
+++ b/embassy-nrf/src/lib.rs
@@ -64,6 +64,7 @@ pub(crate) mod util;
#[cfg(feature = "_time-driver")]
mod time_driver;
+#[cfg(feature = "nightly")]
pub mod buffered_uarte;
pub mod gpio;
#[cfg(feature = "gpiote")]