aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDario Nieuwenhuis <[email protected]>2023-06-18 10:40:22 +0000
committerGitHub <[email protected]>2023-06-18 10:40:22 +0000
commitadaed307b4d81ed09611e496524b1d96ad04c60d (patch)
tree0253e5113b90cd4ceaff3a0bb889d3e0839b68fa
parentae83e6f5367197feb8361b9a28adbdedbe37e0c5 (diff)
parentb4f96e192cd8c86f437e1d155388a860dcd3e1fd (diff)
Merge pull request #1561 from petegibson/stm32-buffereduart-int-flags-fix
Ensure idle & ove flags are cleared in BufferedUart ISR on STM32
-rw-r--r--embassy-stm32/src/usart/buffered.rs38
1 files changed, 22 insertions, 16 deletions
diff --git a/embassy-stm32/src/usart/buffered.rs b/embassy-stm32/src/usart/buffered.rs
index 613da5674..086196a2c 100644
--- a/embassy-stm32/src/usart/buffered.rs
+++ b/embassy-stm32/src/usart/buffered.rs
@@ -21,27 +21,33 @@ impl<T: BasicInstance> interrupt::typelevel::Handler<T::Interrupt> for Interrupt
21 // RX 21 // RX
22 unsafe { 22 unsafe {
23 let sr = sr(r).read(); 23 let sr = sr(r).read();
24 // On v1 & v2, reading DR clears the rxne, error and idle interrupt
25 // flags. Keep this close to the SR read to reduce the chance of a
26 // flag being set in-between.
27 let dr = if sr.rxne() || cfg!(any(usart_v1, usart_v2)) && (sr.ore() || sr.idle()) {
28 Some(rdr(r).read_volatile())
29 } else {
30 None
31 };
24 clear_interrupt_flags(r, sr); 32 clear_interrupt_flags(r, sr);
25 33
34 if sr.pe() {
35 warn!("Parity error");
36 }
37 if sr.fe() {
38 warn!("Framing error");
39 }
40 if sr.ne() {
41 warn!("Noise error");
42 }
43 if sr.ore() {
44 warn!("Overrun error");
45 }
26 if sr.rxne() { 46 if sr.rxne() {
27 if sr.pe() {
28 warn!("Parity error");
29 }
30 if sr.fe() {
31 warn!("Framing error");
32 }
33 if sr.ne() {
34 warn!("Noise error");
35 }
36 if sr.ore() {
37 warn!("Overrun error");
38 }
39
40 let mut rx_writer = state.rx_buf.writer(); 47 let mut rx_writer = state.rx_buf.writer();
41 let buf = rx_writer.push_slice(); 48 let buf = rx_writer.push_slice();
42 if !buf.is_empty() { 49 if !buf.is_empty() {
43 // This read also clears the error and idle interrupt flags on v1. 50 buf[0] = dr.unwrap();
44 buf[0] = rdr(r).read_volatile();
45 rx_writer.push_done(1); 51 rx_writer.push_done(1);
46 } else { 52 } else {
47 // FIXME: Should we disable any further RX interrupts when the buffer becomes full. 53 // FIXME: Should we disable any further RX interrupts when the buffer becomes full.
@@ -54,7 +60,7 @@ impl<T: BasicInstance> interrupt::typelevel::Handler<T::Interrupt> for Interrupt
54 60
55 if sr.idle() { 61 if sr.idle() {
56 state.rx_waker.wake(); 62 state.rx_waker.wake();
57 }; 63 }
58 } 64 }
59 65
60 // TX 66 // TX