Use critical_section
crate
This commit is contained in:
@ -39,6 +39,7 @@ embassy-macros = { version = "0.1.0", path = "../embassy-macros", features = ["s
|
||||
embassy-extras = {version = "0.1.0", path = "../embassy-extras" }
|
||||
|
||||
atomic-polyfill = "0.1.1"
|
||||
critical-section = "0.2.0"
|
||||
defmt = { version = "0.2.0", optional = true }
|
||||
log = { version = "0.4.11", optional = true }
|
||||
cortex-m-rt = "0.6.13"
|
||||
|
@ -44,7 +44,7 @@ pub struct ExtiPin<T: Instance> {
|
||||
|
||||
impl<T: Instance> ExtiPin<T> {
|
||||
pub fn new(mut pin: T, interrupt: T::Interrupt, syscfg: &mut SysCfg) -> Self {
|
||||
cortex_m::interrupt::free(|_| {
|
||||
critical_section::with(|_| {
|
||||
pin.make_source(syscfg);
|
||||
});
|
||||
|
||||
@ -99,7 +99,7 @@ impl<T: Instance + digital::InputPin + 'static> ExtiPin<T> {
|
||||
async move {
|
||||
let fut = InterruptFuture::new(&mut self.interrupt);
|
||||
let pin = &mut self.pin;
|
||||
cortex_m::interrupt::free(|_| {
|
||||
critical_section::with(|_| {
|
||||
pin.trigger_edge(if state {
|
||||
EdgeOption::Rising
|
||||
} else {
|
||||
@ -126,7 +126,7 @@ impl<T: Instance + 'static> ExtiPin<T> {
|
||||
async move {
|
||||
let fut = InterruptFuture::new(&mut self.interrupt);
|
||||
let pin = &mut self.pin;
|
||||
cortex_m::interrupt::free(|_| {
|
||||
critical_section::with(|_| {
|
||||
pin.trigger_edge(state);
|
||||
});
|
||||
|
||||
|
@ -3,12 +3,13 @@ use crate::hal::rcc::Clocks;
|
||||
use core::cell::Cell;
|
||||
use core::convert::TryInto;
|
||||
use core::sync::atomic::{compiler_fence, AtomicU32, Ordering};
|
||||
|
||||
use critical_section::CriticalSection;
|
||||
use embassy::interrupt::InterruptExt;
|
||||
use embassy::time::{Clock, TICKS_PER_SECOND};
|
||||
use embassy::util::CriticalSectionMutex as Mutex;
|
||||
|
||||
use crate::interrupt;
|
||||
use crate::interrupt::{CriticalSection, Interrupt, Mutex};
|
||||
use crate::interrupt::Interrupt;
|
||||
|
||||
// RTC timekeeping works with something we call "periods", which are time intervals
|
||||
// of 2^15 ticks. The RTC counter value is 16 bits, so one "overflow cycle" is 2 periods.
|
||||
@ -119,13 +120,13 @@ impl<T: Instance> RTC<T> {
|
||||
for n in 1..=ALARM_COUNT {
|
||||
if self.rtc.compare_interrupt_status(n) {
|
||||
self.rtc.compare_clear_flag(n);
|
||||
interrupt::free(|cs| self.trigger_alarm(n, cs));
|
||||
critical_section::with(|cs| self.trigger_alarm(n, cs));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn next_period(&self) {
|
||||
interrupt::free(|cs| {
|
||||
critical_section::with(|cs| {
|
||||
let period = self.period.fetch_add(1, Ordering::Relaxed) + 1;
|
||||
let t = (period as u64) << 15;
|
||||
|
||||
@ -142,7 +143,7 @@ impl<T: Instance> RTC<T> {
|
||||
})
|
||||
}
|
||||
|
||||
fn trigger_alarm(&self, n: usize, cs: &CriticalSection) {
|
||||
fn trigger_alarm(&self, n: usize, cs: CriticalSection) {
|
||||
self.rtc.set_compare_interrupt(n, false);
|
||||
|
||||
let alarm = &self.alarms.borrow(cs)[n - 1];
|
||||
@ -155,14 +156,14 @@ impl<T: Instance> RTC<T> {
|
||||
}
|
||||
|
||||
fn set_alarm_callback(&self, n: usize, callback: fn(*mut ()), ctx: *mut ()) {
|
||||
interrupt::free(|cs| {
|
||||
critical_section::with(|cs| {
|
||||
let alarm = &self.alarms.borrow(cs)[n - 1];
|
||||
alarm.callback.set(Some((callback, ctx)));
|
||||
})
|
||||
}
|
||||
|
||||
fn set_alarm(&self, n: usize, timestamp: u64) {
|
||||
interrupt::free(|cs| {
|
||||
critical_section::with(|cs| {
|
||||
let alarm = &self.alarms.borrow(cs)[n - 1];
|
||||
alarm.timestamp.set(timestamp);
|
||||
|
||||
|
@ -8,7 +8,6 @@ use core::sync::atomic::{compiler_fence, Ordering};
|
||||
use crate::pac::NVIC_PRIO_BITS;
|
||||
|
||||
// Re-exports
|
||||
pub use cortex_m::interrupt::{CriticalSection, Mutex};
|
||||
pub use embassy::interrupt::{declare, take, Interrupt};
|
||||
|
||||
#[derive(Debug, Copy, Clone, Eq, PartialEq, Ord, PartialOrd)]
|
||||
@ -63,35 +62,6 @@ impl From<Priority> for u8 {
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn free<F, R>(f: F) -> R
|
||||
where
|
||||
F: FnOnce(&CriticalSection) -> R,
|
||||
{
|
||||
unsafe {
|
||||
// TODO: assert that we're in privileged level
|
||||
// Needed because disabling irqs in non-privileged level is a noop, which would break safety.
|
||||
|
||||
let primask: u32;
|
||||
asm!("mrs {}, PRIMASK", out(reg) primask);
|
||||
|
||||
asm!("cpsid i");
|
||||
|
||||
// Prevent compiler from reordering operations inside/outside the critical section.
|
||||
compiler_fence(Ordering::SeqCst);
|
||||
|
||||
let r = f(&CriticalSection::new());
|
||||
|
||||
compiler_fence(Ordering::SeqCst);
|
||||
|
||||
if primask & 1 == 0 {
|
||||
asm!("cpsie i");
|
||||
}
|
||||
|
||||
r
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "stm32f401")]
|
||||
mod irqs {
|
||||
use super::*;
|
||||
|
@ -2,12 +2,13 @@ use crate::hal::rcc::Clocks;
|
||||
use atomic_polyfill::{compiler_fence, AtomicU32, Ordering};
|
||||
use core::cell::Cell;
|
||||
use core::convert::TryInto;
|
||||
|
||||
use critical_section::CriticalSection;
|
||||
use embassy::interrupt::InterruptExt;
|
||||
use embassy::time::{Clock, TICKS_PER_SECOND};
|
||||
use embassy::util::CriticalSectionMutex as Mutex;
|
||||
|
||||
use crate::interrupt;
|
||||
use crate::interrupt::{CriticalSection, Interrupt, Mutex};
|
||||
use crate::interrupt::Interrupt;
|
||||
|
||||
// RTC timekeeping works with something we call "periods", which are time intervals
|
||||
// of 2^15 ticks. The RTC counter value is 16 bits, so one "overflow cycle" is 2 periods.
|
||||
@ -117,13 +118,13 @@ impl<T: Instance> RTC<T> {
|
||||
for n in 1..=ALARM_COUNT {
|
||||
if self.rtc.compare_interrupt_status(n) {
|
||||
self.rtc.compare_clear_flag(n);
|
||||
interrupt::free(|cs| self.trigger_alarm(n, cs));
|
||||
critical_section::with(|cs| self.trigger_alarm(n, cs));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn next_period(&self) {
|
||||
interrupt::free(|cs| {
|
||||
critical_section::with(|cs| {
|
||||
let period = self.period.fetch_add(1, Ordering::Relaxed) + 1;
|
||||
let t = (period as u64) << 15;
|
||||
|
||||
@ -140,7 +141,7 @@ impl<T: Instance> RTC<T> {
|
||||
})
|
||||
}
|
||||
|
||||
fn trigger_alarm(&self, n: usize, cs: &CriticalSection) {
|
||||
fn trigger_alarm(&self, n: usize, cs: CriticalSection) {
|
||||
self.rtc.set_compare_interrupt(n, false);
|
||||
|
||||
let alarm = &self.alarms.borrow(cs)[n - 1];
|
||||
@ -153,14 +154,14 @@ impl<T: Instance> RTC<T> {
|
||||
}
|
||||
|
||||
fn set_alarm_callback(&self, n: usize, callback: fn(*mut ()), ctx: *mut ()) {
|
||||
interrupt::free(|cs| {
|
||||
critical_section::with(|cs| {
|
||||
let alarm = &self.alarms.borrow(cs)[n - 1];
|
||||
alarm.callback.set(Some((callback, ctx)));
|
||||
})
|
||||
}
|
||||
|
||||
fn set_alarm(&self, n: usize, timestamp: u64) {
|
||||
interrupt::free(|cs| {
|
||||
critical_section::with(|cs| {
|
||||
let alarm = &self.alarms.borrow(cs)[n - 1];
|
||||
alarm.timestamp.set(timestamp);
|
||||
|
||||
|
Reference in New Issue
Block a user