Executor API V2.
- It's no longer possible to call run() reentrantly from within a task (soundness issue) - it's now possible to spawn Send tasks across threads (SendSpawner, #37)
This commit is contained in:
@ -83,11 +83,8 @@ static EXECUTOR: Forever<Executor> = Forever::new();
|
||||
fn main() -> ! {
|
||||
info!("Hello World!");
|
||||
|
||||
let executor = EXECUTOR.put(Executor::new(cortex_m::asm::sev));
|
||||
unwrap!(executor.spawn(run()));
|
||||
|
||||
loop {
|
||||
executor.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
let executor = EXECUTOR.put(Executor::new());
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run()));
|
||||
});
|
||||
}
|
||||
|
@ -61,14 +61,11 @@ fn main() -> ! {
|
||||
unsafe { embassy::time::set_clock(rtc) };
|
||||
|
||||
let alarm = ALARM.put(rtc.alarm0());
|
||||
let executor = EXECUTOR.put(Executor::new_with_alarm(alarm, cortex_m::asm::sev));
|
||||
|
||||
unwrap!(executor.spawn(run1()));
|
||||
unwrap!(executor.spawn(run2()));
|
||||
unwrap!(executor.spawn(run3()));
|
||||
|
||||
loop {
|
||||
executor.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
let executor = EXECUTOR.put(Executor::new());
|
||||
executor.set_alarm(alarm);
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run1()));
|
||||
unwrap!(spawner.spawn(run2()));
|
||||
unwrap!(spawner.spawn(run3()));
|
||||
});
|
||||
}
|
||||
|
@ -73,11 +73,8 @@ static EXECUTOR: Forever<Executor> = Forever::new();
|
||||
fn main() -> ! {
|
||||
info!("Hello World!");
|
||||
|
||||
let executor = EXECUTOR.put(Executor::new(cortex_m::asm::sev));
|
||||
unwrap!(executor.spawn(run()));
|
||||
|
||||
loop {
|
||||
executor.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
let executor = EXECUTOR.put(Executor::new());
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run()));
|
||||
});
|
||||
}
|
||||
|
@ -52,11 +52,8 @@ static EXECUTOR: Forever<Executor> = Forever::new();
|
||||
fn main() -> ! {
|
||||
info!("Hello World!");
|
||||
|
||||
let executor = EXECUTOR.put(Executor::new(cortex_m::asm::sev));
|
||||
unwrap!(executor.spawn(run()));
|
||||
|
||||
loop {
|
||||
executor.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
let executor = EXECUTOR.put(Executor::new());
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run()));
|
||||
});
|
||||
}
|
||||
|
@ -66,9 +66,10 @@ use cortex_m_rt::entry;
|
||||
use defmt::panic;
|
||||
use nrf52840_hal::clocks;
|
||||
|
||||
use embassy::executor::{task, Executor};
|
||||
use embassy::executor::{task, Executor, IrqExecutor};
|
||||
use embassy::time::{Duration, Instant, Timer};
|
||||
use embassy::util::Forever;
|
||||
use embassy_nrf::interrupt::OwnedInterrupt;
|
||||
use embassy_nrf::{interrupt, pac, rtc};
|
||||
|
||||
#[task]
|
||||
@ -114,12 +115,12 @@ async fn run_low() {
|
||||
}
|
||||
|
||||
static RTC: Forever<rtc::RTC<pac::RTC1>> = Forever::new();
|
||||
static ALARM_HIGH: Forever<rtc::Alarm<pac::RTC1>> = Forever::new();
|
||||
static EXECUTOR_HIGH: Forever<IrqExecutor<interrupt::SWI1_EGU1Interrupt>> = Forever::new();
|
||||
static ALARM_MED: Forever<rtc::Alarm<pac::RTC1>> = Forever::new();
|
||||
static EXECUTOR_MED: Forever<IrqExecutor<interrupt::SWI0_EGU0Interrupt>> = Forever::new();
|
||||
static ALARM_LOW: Forever<rtc::Alarm<pac::RTC1>> = Forever::new();
|
||||
static EXECUTOR_LOW: Forever<Executor> = Forever::new();
|
||||
static ALARM_MED: Forever<rtc::Alarm<pac::RTC1>> = Forever::new();
|
||||
static EXECUTOR_MED: Forever<Executor> = Forever::new();
|
||||
static ALARM_HIGH: Forever<rtc::Alarm<pac::RTC1>> = Forever::new();
|
||||
static EXECUTOR_HIGH: Forever<Executor> = Forever::new();
|
||||
|
||||
#[entry]
|
||||
fn main() -> ! {
|
||||
@ -136,41 +137,31 @@ fn main() -> ! {
|
||||
rtc.start();
|
||||
unsafe { embassy::time::set_clock(rtc) };
|
||||
|
||||
let alarm_low = ALARM_LOW.put(rtc.alarm0());
|
||||
let executor_low = EXECUTOR_LOW.put(Executor::new_with_alarm(alarm_low, cortex_m::asm::sev));
|
||||
let alarm_med = ALARM_MED.put(rtc.alarm1());
|
||||
let executor_med = EXECUTOR_MED.put(Executor::new_with_alarm(alarm_med, || {
|
||||
NVIC::pend(interrupt::SWI0_EGU0)
|
||||
}));
|
||||
let alarm_high = ALARM_HIGH.put(rtc.alarm2());
|
||||
let executor_high = EXECUTOR_HIGH.put(Executor::new_with_alarm(alarm_high, || {
|
||||
NVIC::pend(interrupt::SWI1_EGU1)
|
||||
}));
|
||||
// High-priority executor: SWI1_EGU1, priority level 6
|
||||
let irq = interrupt::take!(SWI1_EGU1);
|
||||
irq.set_priority(interrupt::Priority::Level6);
|
||||
let alarm = ALARM_HIGH.put(rtc.alarm2());
|
||||
let executor = EXECUTOR_HIGH.put(IrqExecutor::new(irq));
|
||||
executor.set_alarm(alarm);
|
||||
executor.start(|spawner| {
|
||||
unwrap!(spawner.spawn(run_high()));
|
||||
});
|
||||
|
||||
unsafe {
|
||||
let mut nvic: NVIC = core::mem::transmute(());
|
||||
nvic.set_priority(interrupt::SWI0_EGU0, 7 << 5);
|
||||
nvic.set_priority(interrupt::SWI1_EGU1, 6 << 5);
|
||||
NVIC::unmask(interrupt::SWI0_EGU0);
|
||||
NVIC::unmask(interrupt::SWI1_EGU1);
|
||||
}
|
||||
// Medium-priority executor: SWI0_EGU0, priority level 7
|
||||
let irq = interrupt::take!(SWI0_EGU0);
|
||||
irq.set_priority(interrupt::Priority::Level7);
|
||||
let alarm = ALARM_MED.put(rtc.alarm1());
|
||||
let executor = EXECUTOR_MED.put(IrqExecutor::new(irq));
|
||||
executor.set_alarm(alarm);
|
||||
executor.start(|spawner| {
|
||||
unwrap!(spawner.spawn(run_med()));
|
||||
});
|
||||
|
||||
unwrap!(executor_low.spawn(run_low()));
|
||||
unwrap!(executor_med.spawn(run_med()));
|
||||
unwrap!(executor_high.spawn(run_high()));
|
||||
|
||||
loop {
|
||||
executor_low.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
}
|
||||
|
||||
#[interrupt]
|
||||
unsafe fn SWI0_EGU0() {
|
||||
EXECUTOR_MED.steal().run()
|
||||
}
|
||||
|
||||
#[interrupt]
|
||||
unsafe fn SWI1_EGU1() {
|
||||
EXECUTOR_HIGH.steal().run()
|
||||
// Low priority executor: runs in thread mode, using WFE/SEV
|
||||
let alarm = ALARM_LOW.put(rtc.alarm0());
|
||||
let executor = EXECUTOR_LOW.put(Executor::new());
|
||||
executor.set_alarm(alarm);
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run_low()));
|
||||
});
|
||||
}
|
||||
|
@ -124,11 +124,8 @@ static EXECUTOR: Forever<Executor> = Forever::new();
|
||||
fn main() -> ! {
|
||||
info!("Hello World!");
|
||||
|
||||
let executor = EXECUTOR.put(Executor::new(cortex_m::asm::sev));
|
||||
unwrap!(executor.spawn(run()));
|
||||
|
||||
loop {
|
||||
executor.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
let executor = EXECUTOR.put(Executor::new());
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run()));
|
||||
});
|
||||
}
|
||||
|
@ -53,13 +53,10 @@ fn main() -> ! {
|
||||
unsafe { embassy::time::set_clock(rtc) };
|
||||
|
||||
let alarm = ALARM.put(rtc.alarm0());
|
||||
let executor = EXECUTOR.put(Executor::new_with_alarm(alarm, cortex_m::asm::sev));
|
||||
|
||||
unwrap!(executor.spawn(run1()));
|
||||
unwrap!(executor.spawn(run2()));
|
||||
|
||||
loop {
|
||||
executor.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
let executor = EXECUTOR.put(Executor::new());
|
||||
executor.set_alarm(alarm);
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run1()));
|
||||
unwrap!(spawner.spawn(run2()));
|
||||
});
|
||||
}
|
||||
|
@ -38,7 +38,7 @@ fn main() -> ! {
|
||||
|
||||
rtc.start();
|
||||
|
||||
alarm.set_callback(|| info!("ALARM TRIGGERED"));
|
||||
alarm.set_callback(|_| info!("ALARM TRIGGERED"), core::ptr::null_mut());
|
||||
alarm.set(53719);
|
||||
|
||||
info!("initialized!");
|
||||
|
@ -18,7 +18,31 @@ use nrf52840_hal::clocks;
|
||||
use nrf52840_hal::gpio;
|
||||
|
||||
#[task]
|
||||
async fn run(mut uart: uarte::Uarte<pac::UARTE0>) {
|
||||
async fn run(uart: pac::UARTE0, port: pac::P0) {
|
||||
// Init UART
|
||||
let port0 = gpio::p0::Parts::new(port);
|
||||
|
||||
let pins = uarte::Pins {
|
||||
rxd: port0.p0_08.into_floating_input().degrade(),
|
||||
txd: port0
|
||||
.p0_06
|
||||
.into_push_pull_output(gpio::Level::Low)
|
||||
.degrade(),
|
||||
cts: None,
|
||||
rts: None,
|
||||
};
|
||||
|
||||
// NOTE(unsafe): Safe becasue we do not use `mem::forget` anywhere.
|
||||
let mut uart = unsafe {
|
||||
uarte::Uarte::new(
|
||||
uart,
|
||||
interrupt::take!(UARTE0_UART0),
|
||||
pins,
|
||||
uarte::Parity::EXCLUDED,
|
||||
uarte::Baudrate::BAUD115200,
|
||||
)
|
||||
};
|
||||
|
||||
info!("uarte initialized!");
|
||||
|
||||
// Message must be in SRAM
|
||||
@ -81,36 +105,12 @@ fn main() -> ! {
|
||||
unsafe { embassy::time::set_clock(rtc) };
|
||||
|
||||
let alarm = ALARM.put(rtc.alarm0());
|
||||
let executor = EXECUTOR.put(Executor::new_with_alarm(alarm, cortex_m::asm::sev));
|
||||
let executor = EXECUTOR.put(Executor::new());
|
||||
executor.set_alarm(alarm);
|
||||
|
||||
// Init UART
|
||||
let port0 = gpio::p0::Parts::new(p.P0);
|
||||
|
||||
let pins = uarte::Pins {
|
||||
rxd: port0.p0_08.into_floating_input().degrade(),
|
||||
txd: port0
|
||||
.p0_06
|
||||
.into_push_pull_output(gpio::Level::Low)
|
||||
.degrade(),
|
||||
cts: None,
|
||||
rts: None,
|
||||
};
|
||||
|
||||
// NOTE(unsafe): Safe becasue we do not use `mem::forget` anywhere.
|
||||
let uart = unsafe {
|
||||
uarte::Uarte::new(
|
||||
p.UARTE0,
|
||||
interrupt::take!(UARTE0_UART0),
|
||||
pins,
|
||||
uarte::Parity::EXCLUDED,
|
||||
uarte::Baudrate::BAUD115200,
|
||||
)
|
||||
};
|
||||
|
||||
unwrap!(executor.spawn(run(uart)));
|
||||
|
||||
loop {
|
||||
executor.run();
|
||||
cortex_m::asm::wfe();
|
||||
}
|
||||
let uarte0 = p.UARTE0;
|
||||
let p0 = p.P0;
|
||||
executor.run(|spawner| {
|
||||
unwrap!(spawner.spawn(run(uarte0, p0)));
|
||||
});
|
||||
}
|
||||
|
Reference in New Issue
Block a user