Merge pull request #341 from lulf/usart-dma-read
Add uart::Read DMA-based implementation
This commit is contained in:
commit
5d31dd328f
@ -80,7 +80,23 @@ impl<'d, T: Instance, TxDma, RxDma> Uart<'d, T, TxDma, RxDma> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn read(&mut self, buffer: &mut [u8]) -> Result<(), Error> {
|
||||
async fn read_dma(&mut self, buffer: &mut [u8]) -> Result<(), Error>
|
||||
where
|
||||
RxDma: crate::usart::RxDma<T>,
|
||||
{
|
||||
let ch = &mut self.rx_dma;
|
||||
unsafe {
|
||||
self.inner.regs().cr3().modify(|reg| {
|
||||
reg.set_dmar(true);
|
||||
});
|
||||
}
|
||||
let r = self.inner.regs();
|
||||
let src = r.dr().ptr() as *mut u8;
|
||||
ch.read(ch.request(), src, buffer).await;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn read_blocking(&mut self, buffer: &mut [u8]) -> Result<(), Error> {
|
||||
unsafe {
|
||||
let r = self.inner.regs();
|
||||
for b in buffer {
|
||||
@ -143,3 +159,15 @@ impl<'d, T: Instance, TxDma, RxDma> embassy_traits::uart::Write for Uart<'d, T,
|
||||
self.write_dma(buf).map_err(|_| embassy_traits::uart::Error::Other)
|
||||
}
|
||||
}
|
||||
|
||||
// rustfmt::skip because intellij removes the 'where' claus on the associated type.
|
||||
#[rustfmt::skip]
|
||||
impl<'d, T: Instance, TxDma, RxDma> embassy_traits::uart::Read for Uart<'d, T, TxDma, RxDma>
|
||||
where RxDma: crate::usart::RxDma<T>
|
||||
{
|
||||
type ReadFuture<'a> where Self: 'a = impl Future<Output = Result<(), embassy_traits::uart::Error>>;
|
||||
|
||||
fn read<'a>(&'a mut self, buf: &'a mut [u8]) -> Self::ReadFuture<'a> {
|
||||
self.read_dma(buf).map_err(|_| embassy_traits::uart::Error::Other)
|
||||
}
|
||||
}
|
||||
|
@ -84,7 +84,23 @@ impl<'d, T: Instance, TxDma, RxDma> Uart<'d, T, TxDma, RxDma> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn read(&mut self, buffer: &mut [u8]) -> Result<(), Error> {
|
||||
async fn read_dma(&mut self, buffer: &mut [u8]) -> Result<(), Error>
|
||||
where
|
||||
RxDma: crate::usart::RxDma<T>,
|
||||
{
|
||||
let ch = &mut self.rx_dma;
|
||||
unsafe {
|
||||
self.inner.regs().cr3().modify(|reg| {
|
||||
reg.set_dmar(true);
|
||||
});
|
||||
}
|
||||
let r = self.inner.regs();
|
||||
let src = r.rdr().ptr() as *mut u8;
|
||||
ch.read(ch.request(), src, buffer).await;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn read_blocking(&mut self, buffer: &mut [u8]) -> Result<(), Error> {
|
||||
unsafe {
|
||||
let r = self.inner.regs();
|
||||
for b in buffer {
|
||||
@ -147,3 +163,15 @@ impl<'d, T: Instance, TxDma, RxDma> embassy_traits::uart::Write for Uart<'d, T,
|
||||
self.write_dma(buf).map_err(|_| embassy_traits::uart::Error::Other)
|
||||
}
|
||||
}
|
||||
|
||||
// rustfmt::skip because intellij removes the 'where' claus on the associated type.
|
||||
#[rustfmt::skip]
|
||||
impl<'d, T: Instance, TxDma, RxDma> embassy_traits::uart::Read for Uart<'d, T, TxDma, RxDma>
|
||||
where RxDma: crate::usart::RxDma<T>
|
||||
{
|
||||
type ReadFuture<'a> where Self: 'a = impl Future<Output = Result<(), embassy_traits::uart::Error>>;
|
||||
|
||||
fn read<'a>(&'a mut self, buf: &'a mut [u8]) -> Self::ReadFuture<'a> {
|
||||
self.read_dma(buf).map_err(|_| embassy_traits::uart::Error::Other)
|
||||
}
|
||||
}
|
||||
|
@ -33,7 +33,7 @@ fn main() -> ! {
|
||||
|
||||
let mut buf = [0u8; 1];
|
||||
loop {
|
||||
usart.read(&mut buf).unwrap();
|
||||
usart.read_blocking(&mut buf).unwrap();
|
||||
usart.bwrite_all(&buf).unwrap();
|
||||
}
|
||||
}
|
||||
|
@ -31,7 +31,7 @@ async fn main_task() {
|
||||
|
||||
let mut buf = [0u8; 1];
|
||||
loop {
|
||||
usart.read(&mut buf).unwrap();
|
||||
usart.read_blocking(&mut buf).unwrap();
|
||||
usart.bwrite_all(&buf).unwrap();
|
||||
}
|
||||
}
|
||||
|
42
examples/stm32l0/src/bin/usart_dma.rs
Normal file
42
examples/stm32l0/src/bin/usart_dma.rs
Normal file
@ -0,0 +1,42 @@
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
#![feature(trait_alias)]
|
||||
#![feature(min_type_alias_impl_trait)]
|
||||
#![feature(impl_trait_in_bindings)]
|
||||
#![feature(type_alias_impl_trait)]
|
||||
#![allow(incomplete_features)]
|
||||
|
||||
#[path = "../example_common.rs"]
|
||||
mod example_common;
|
||||
|
||||
use example_common::*;
|
||||
|
||||
use defmt::panic;
|
||||
use embassy::executor::Spawner;
|
||||
use embassy_stm32::usart::{Config, Uart};
|
||||
use embassy_stm32::{rcc, Peripherals};
|
||||
use embassy_traits::uart::{Read, Write};
|
||||
|
||||
#[embassy::main]
|
||||
async fn main(_spawner: Spawner, mut p: Peripherals) {
|
||||
let mut rcc = rcc::Rcc::new(p.RCC);
|
||||
rcc.enable_debug_wfe(&mut p.DBGMCU, true);
|
||||
|
||||
let mut usart = Uart::new(
|
||||
p.USART1,
|
||||
p.PB7,
|
||||
p.PB6,
|
||||
p.DMA1_CH2,
|
||||
p.DMA1_CH3,
|
||||
Config::default(),
|
||||
);
|
||||
|
||||
usart.write(b"Hello Embassy World!\r\n").await.unwrap();
|
||||
info!("wrote Hello, starting echo");
|
||||
|
||||
let mut buf = [0; 1];
|
||||
loop {
|
||||
usart.read(&mut buf[..]).await.unwrap();
|
||||
usart.write(&buf[..]).await.unwrap();
|
||||
}
|
||||
}
|
@ -33,7 +33,7 @@ fn main() -> ! {
|
||||
|
||||
let mut buf = [0u8; 1];
|
||||
loop {
|
||||
usart.read(&mut buf).unwrap();
|
||||
usart.read_blocking(&mut buf).unwrap();
|
||||
usart.bwrite_all(&buf).unwrap();
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user