aboutsummaryrefslogtreecommitdiff
path: root/embassy-nrf
diff options
context:
space:
mode:
authorUlf Lilleengen <[email protected]>2025-10-29 10:49:39 +0100
committerGitHub <[email protected]>2025-10-29 10:49:39 +0100
commit2120c6e616d88ca3122e92f95a54b92135add51b (patch)
treec1d2aa5b2343d03fbc7dbb9a81ad3e87c25857bc /embassy-nrf
parent2b3c94f26452c8aa1c6f53b9657b3e636673820c (diff)
parent07602b31f0d7dc8ae06b32197162990bb575a7a8 (diff)
Merge branch 'main' into sleep-in-anomaly-fix
Diffstat (limited to 'embassy-nrf')
-rw-r--r--embassy-nrf/CHANGELOG.md1
-rw-r--r--embassy-nrf/src/buffered_uarte/v1.rs49
2 files changed, 32 insertions, 18 deletions
diff --git a/embassy-nrf/CHANGELOG.md b/embassy-nrf/CHANGELOG.md
index 361e5ce57..a0668c495 100644
--- a/embassy-nrf/CHANGELOG.md
+++ b/embassy-nrf/CHANGELOG.md
@@ -21,6 +21,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
21- added: support for nrf54l peripherals: uart, gpiote, twim, twis, spim, spis, dppi, pwm, saadc 21- added: support for nrf54l peripherals: uart, gpiote, twim, twis, spim, spis, dppi, pwm, saadc
22- bugfix: Do not write to UICR from non-secure code on nrf53 22- bugfix: Do not write to UICR from non-secure code on nrf53
23- bugfix: Add delay to uart init anomaly fix 23- bugfix: Add delay to uart init anomaly fix
24- changed: `BufferedUarte::read_ready` now uses the same definition for 'empty' so following read calls will not block when true is returned
24 25
25## 0.8.0 - 2025-09-30 26## 0.8.0 - 2025-09-30
26 27
diff --git a/embassy-nrf/src/buffered_uarte/v1.rs b/embassy-nrf/src/buffered_uarte/v1.rs
index 07de22717..ec360f7d0 100644
--- a/embassy-nrf/src/buffered_uarte/v1.rs
+++ b/embassy-nrf/src/buffered_uarte/v1.rs
@@ -748,6 +748,30 @@ impl<'d> BufferedUarteRx<'d> {
748 } 748 }
749 } 749 }
750 750
751 fn get_rxdrdy_counter(&self) -> usize {
752 let s = self.buffered_state;
753 let timer = &self.timer;
754
755 // Read the RXDRDY counter.
756 timer.cc(0).capture();
757 let mut rxdrdy = timer.cc(0).read() as usize;
758 //trace!(" rxdrdy count = {:?}", rxdrdy);
759
760 // We've set a compare channel that resets the counter to 0 when it reaches `len*2`.
761 // However, it's unclear if that's instant, or there's a small window where you can
762 // still read `len()*2`.
763 // This could happen if in one clock cycle the counter is updated, and in the next the
764 // clear takes effect. The docs are very sparse, they just say "Task delays: After TIMER
765 // is started, the CLEAR, COUNT, and STOP tasks are guaranteed to take effect within one
766 // clock cycle of the PCLK16M." :shrug:
767 // So, we wrap the counter ourselves, just in case.
768 if rxdrdy > s.rx_buf.len() * 2 {
769 rxdrdy = 0;
770 }
771
772 rxdrdy
773 }
774
751 /// Pull some bytes from this source into the specified buffer, returning how many bytes were read. 775 /// Pull some bytes from this source into the specified buffer, returning how many bytes were read.
752 pub async fn read(&mut self, buf: &mut [u8]) -> Result<usize, Error> { 776 pub async fn read(&mut self, buf: &mut [u8]) -> Result<usize, Error> {
753 let data = self.fill_buf().await?; 777 let data = self.fill_buf().await?;
@@ -762,7 +786,7 @@ impl<'d> BufferedUarteRx<'d> {
762 let r = self.r; 786 let r = self.r;
763 let s = self.buffered_state; 787 let s = self.buffered_state;
764 let ss = self.state; 788 let ss = self.state;
765 let timer = &self.timer; 789
766 poll_fn(move |cx| { 790 poll_fn(move |cx| {
767 compiler_fence(Ordering::SeqCst); 791 compiler_fence(Ordering::SeqCst);
768 //trace!("poll_read"); 792 //trace!("poll_read");
@@ -771,22 +795,7 @@ impl<'d> BufferedUarteRx<'d> {
771 return Poll::Ready(Err(Error::Overrun)); 795 return Poll::Ready(Err(Error::Overrun));
772 } 796 }
773 797
774 // Read the RXDRDY counter. 798 let mut end = self.get_rxdrdy_counter();
775 timer.cc(0).capture();
776 let mut end = timer.cc(0).read() as usize;
777 //trace!(" rxdrdy count = {:?}", end);
778
779 // We've set a compare channel that resets the counter to 0 when it reaches `len*2`.
780 // However, it's unclear if that's instant, or there's a small window where you can
781 // still read `len()*2`.
782 // This could happen if in one clock cycle the counter is updated, and in the next the
783 // clear takes effect. The docs are very sparse, they just say "Task delays: After TIMER
784 // is started, the CLEAR, COUNT, and STOP tasks are guaranteed to take effect within one
785 // clock cycle of the PCLK16M." :shrug:
786 // So, we wrap the counter ourselves, just in case.
787 if end > s.rx_buf.len() * 2 {
788 end = 0
789 }
790 799
791 // This logic mirrors `atomic_ring_buffer::Reader::pop_buf()` 800 // This logic mirrors `atomic_ring_buffer::Reader::pop_buf()`
792 let mut start = s.rx_buf.start.load(Ordering::Relaxed); 801 let mut start = s.rx_buf.start.load(Ordering::Relaxed);
@@ -832,7 +841,11 @@ impl<'d> BufferedUarteRx<'d> {
832 if state.rx_overrun.swap(false, Ordering::Acquire) { 841 if state.rx_overrun.swap(false, Ordering::Acquire) {
833 return Err(Error::Overrun); 842 return Err(Error::Overrun);
834 } 843 }
835 Ok(!state.rx_buf.is_empty()) 844
845 let start = state.rx_buf.start.load(Ordering::Relaxed);
846 let end = self.get_rxdrdy_counter();
847
848 Ok(start != end)
836 } 849 }
837} 850}
838 851