From 243668df5424e047dbfe8c4151eef5c7ebc88dc1 Mon Sep 17 00:00:00 2001 From: Emil Fresk Date: Sat, 14 Nov 2020 16:02:36 +0100 Subject: [PATCH 1/4] Multilock support --- Cargo.toml | 3 +- examples/multilock.rs | 77 ++++++++++++++++++++++++++++ macros/src/codegen/hardware_tasks.rs | 1 + macros/src/codegen/idle.rs | 1 + macros/src/codegen/module.rs | 2 + macros/src/codegen/software_tasks.rs | 1 + src/lib.rs | 2 +- 7 files changed, 85 insertions(+), 2 deletions(-) create mode 100644 examples/multilock.rs diff --git a/Cargo.toml b/Cargo.toml index 5818644202..b98bbdc8d3 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -57,7 +57,8 @@ required-features = ["__v7"] [dependencies] cortex-m = "0.6.2" cortex-m-rtic-macros = { path = "macros", version = "0.6.0-alpha.0" } -rtic-core = "0.3.0" +# rtic-core = "0.3.0" +rtic-core = { git = "https://github.com/rtic-rs/rtic-core.git", branch = "multilock", version = "0.3.1" } cortex-m-rt = "0.6.9" heapless = "0.5.0" bare-metal = "1.0.0" diff --git a/examples/multilock.rs b/examples/multilock.rs new file mode 100644 index 0000000000..99d26ad792 --- /dev/null +++ b/examples/multilock.rs @@ -0,0 +1,77 @@ +//! examples/mutlilock.rs +//! +//! The multi-lock feature example. + +#![deny(unsafe_code)] +#![deny(warnings)] +#![no_main] +#![no_std] + +use panic_semihosting as _; + +#[rtic::app(device = lm3s6965, dispatchers = [GPIOA])] +mod app { + use cortex_m_semihosting::{debug, hprintln}; + + #[resources] + struct Resources { + #[init(0)] + shared1: u32, + #[init(0)] + shared2: u32, + #[init(0)] + shared3: u32, + } + + #[init] + fn init(_: init::Context) -> init::LateResources { + locks::spawn().ok(); + + init::LateResources {} + } + + // when omitted priority is assumed to be `1` + #[task(resources = [shared1, shared2, shared3])] + fn locks(c: locks::Context) { + let mut s1 = c.resources.shared1; + let mut s2 = c.resources.shared2; + let mut s3 = c.resources.shared3; + + hprintln!("Multiple single locks").unwrap(); + s1.lock(|s1| { + s2.lock(|s2| { + s3.lock(|s3| { + *s1 += 1; + *s2 += 1; + *s3 += 1; + + hprintln!( + "Multiple single locks, s1: {}, s2: {}, s3: {}", + *s1, + *s2, + *s3 + ) + .unwrap(); + }) + }) + }); + + hprintln!("Multilock!").unwrap(); + + (s1, s2, s3).lock(|s1, s2, s3| { + *s1 += 1; + *s2 += 1; + *s3 += 1; + + hprintln!( + "Multiple single locks, s1: {}, s2: {}, s3: {}", + *s1, + *s2, + *s3 + ) + .unwrap(); + }); + + debug::exit(debug::EXIT_SUCCESS); + } +} diff --git a/macros/src/codegen/hardware_tasks.rs b/macros/src/codegen/hardware_tasks.rs index c9d0297ea1..6930d3e037 100644 --- a/macros/src/codegen/hardware_tasks.rs +++ b/macros/src/codegen/hardware_tasks.rs @@ -105,6 +105,7 @@ pub fn codegen( #[allow(non_snake_case)] fn #name(#(#locals_pat,)* #context: #name::Context) { use rtic::Mutex as _; + use rtic::mutex_prelude::*; #(#stmts)* } diff --git a/macros/src/codegen/idle.rs b/macros/src/codegen/idle.rs index c8c8955df8..b1d2e00b27 100644 --- a/macros/src/codegen/idle.rs +++ b/macros/src/codegen/idle.rs @@ -68,6 +68,7 @@ pub fn codegen( #[allow(non_snake_case)] fn #name(#(#locals_pat,)* #context: #name::Context) -> ! { use rtic::Mutex as _; + use rtic::mutex_prelude::*; #(#stmts)* } diff --git a/macros/src/codegen/module.rs b/macros/src/codegen/module.rs index 838a989f26..2ff4801e43 100644 --- a/macros/src/codegen/module.rs +++ b/macros/src/codegen/module.rs @@ -219,6 +219,7 @@ pub fn codegen( pub fn spawn(#(#args,)*) -> Result<(), #ty> { // #let_instant // do we need it? use rtic::Mutex as _; + use rtic::mutex_prelude::*; let input = #tupled; @@ -258,6 +259,7 @@ pub fn codegen( ) -> Result<(), #ty> { unsafe { use rtic::Mutex as _; + use rtic::mutex_prelude::*; let input = #tupled; if let Some(index) = rtic::export::interrupt::free(|_| #app_path::#fq.dequeue()) { diff --git a/macros/src/codegen/software_tasks.rs b/macros/src/codegen/software_tasks.rs index 833e338dd5..9cb5f7a97d 100644 --- a/macros/src/codegen/software_tasks.rs +++ b/macros/src/codegen/software_tasks.rs @@ -111,6 +111,7 @@ pub fn codegen( #[allow(non_snake_case)] fn #name(#(#locals_pat,)* #context: #name::Context #(,#inputs)*) { use rtic::Mutex as _; + use rtic::mutex_prelude::*; #(#stmts)* } diff --git a/src/lib.rs b/src/lib.rs index a7d399cd45..fc1991c659 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -43,7 +43,7 @@ use cortex_m::{ }; use cortex_m_rt as _; // vector table pub use cortex_m_rtic_macros::app; -pub use rtic_core::{Exclusive, Mutex}; +pub use rtic_core::{Exclusive, Mutex, prelude as mutex_prelude}; #[cfg(armv7m)] pub mod cyccnt; From d079949139b9d4d5280a08143edc1d717d5c5b52 Mon Sep 17 00:00:00 2001 From: Emil Fresk Date: Sat, 14 Nov 2020 16:09:20 +0100 Subject: [PATCH 2/4] Add multilock to the book --- book/en/src/by-example/resources.md | 8 ++++++++ src/lib.rs | 2 +- 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/book/en/src/by-example/resources.md b/book/en/src/by-example/resources.md index 301961d009..3a3e0b7660 100644 --- a/book/en/src/by-example/resources.md +++ b/book/en/src/by-example/resources.md @@ -64,6 +64,14 @@ $ cargo run --example lock {{#include ../../../../ci/expected/lock.run}} ``` +## Multi-lock + +As an extension to `lock`, and to reduce rightward drift, locks can be taken as tuples. The following examples shows this in use: + +``` rust +{{#include ../../../../examples/multilock.rs}} +``` + ## Late resources Late resources are resources that are not given an initial value at compile time using the `#[init]` attribute but instead are initialized at runtime using the `init::LateResources` values returned by the `init` function. diff --git a/src/lib.rs b/src/lib.rs index fc1991c659..9c2b252d45 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -43,7 +43,7 @@ use cortex_m::{ }; use cortex_m_rt as _; // vector table pub use cortex_m_rtic_macros::app; -pub use rtic_core::{Exclusive, Mutex, prelude as mutex_prelude}; +pub use rtic_core::{prelude as mutex_prelude, Exclusive, Mutex}; #[cfg(armv7m)] pub mod cyccnt; From 9cbe639ebfb0947a26fb0b7fe00ef21004fa4d8b Mon Sep 17 00:00:00 2001 From: Emil Fresk Date: Sat, 14 Nov 2020 16:16:45 +0100 Subject: [PATCH 3/4] Updated changelog, use released version of rtic-core --- CHANGELOG.md | 4 ++++ Cargo.toml | 3 +-- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4ccaba816d..a5ff05f0a4 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,10 @@ This project adheres to [Semantic Versioning](http://semver.org/). ## [Unreleased] +### Added + +- Support for multi-locks, see `examples/multilock.rs` for syntax. + ## [v0.6.0-alpha.0] - 2020-11-14 ### Added diff --git a/Cargo.toml b/Cargo.toml index b98bbdc8d3..05c572b1f8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -57,8 +57,7 @@ required-features = ["__v7"] [dependencies] cortex-m = "0.6.2" cortex-m-rtic-macros = { path = "macros", version = "0.6.0-alpha.0" } -# rtic-core = "0.3.0" -rtic-core = { git = "https://github.com/rtic-rs/rtic-core.git", branch = "multilock", version = "0.3.1" } +rtic-core = "0.3.1" cortex-m-rt = "0.6.9" heapless = "0.5.0" bare-metal = "1.0.0" From f111c825ba3ab886a1a6bf63a0689c3d63b0f441 Mon Sep 17 00:00:00 2001 From: Emil Fresk Date: Sat, 14 Nov 2020 16:18:18 +0100 Subject: [PATCH 4/4] Added multilock to CI --- .github/workflows/build.yml | 1 + ci/expected/multilock.run | 4 ++++ examples/multilock.rs | 7 ++++--- 3 files changed, 9 insertions(+), 3 deletions(-) create mode 100644 ci/expected/multilock.run diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 739c7bd9e2..e729db6775 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -243,6 +243,7 @@ jobs: resource lock + multilock late only-shared-access diff --git a/ci/expected/multilock.run b/ci/expected/multilock.run new file mode 100644 index 0000000000..10a377c5cf --- /dev/null +++ b/ci/expected/multilock.run @@ -0,0 +1,4 @@ +Multiple single locks +Multiple single locks, s1: 1, s2: 1, s3: 1 +Multilock! +Multiple single locks, s1: 2, s2: 2, s3: 2 diff --git a/examples/multilock.rs b/examples/multilock.rs index 99d26ad792..a6985dfa0c 100644 --- a/examples/multilock.rs +++ b/examples/multilock.rs @@ -9,9 +9,10 @@ use panic_semihosting as _; -#[rtic::app(device = lm3s6965, dispatchers = [GPIOA])] +#[rtic::app(device = lm3s6965)] mod app { use cortex_m_semihosting::{debug, hprintln}; + use lm3s6965::Interrupt; #[resources] struct Resources { @@ -25,13 +26,13 @@ mod app { #[init] fn init(_: init::Context) -> init::LateResources { - locks::spawn().ok(); + rtic::pend(Interrupt::GPIOA); init::LateResources {} } // when omitted priority is assumed to be `1` - #[task(resources = [shared1, shared2, shared3])] + #[task(binds = GPIOA, resources = [shared1, shared2, shared3])] fn locks(c: locks::Context) { let mut s1 = c.resources.shared1; let mut s2 = c.resources.shared2;