mirror of
https://github.com/rtic-rs/rtic.git
synced 2025-12-16 21:05:35 +01:00
RFC #207
This commit is contained in:
parent
b150ab29e2
commit
4e51bb68b9
33 changed files with 143 additions and 142 deletions
|
|
@ -3,7 +3,7 @@ use std::collections::HashSet;
|
|||
use proc_macro2::Span;
|
||||
use rtfm_syntax::{
|
||||
analyze::Analysis,
|
||||
ast::{App, CustomArg, HardwareTaskKind},
|
||||
ast::{App, CustomArg},
|
||||
};
|
||||
use syn::{parse, Path};
|
||||
|
||||
|
|
@ -44,18 +44,9 @@ pub fn app<'a>(app: &'a App, analysis: &Analysis) -> parse::Result<Extra<'a>> {
|
|||
|
||||
// check that all exceptions are valid; only exceptions with configurable priorities are
|
||||
// accepted
|
||||
for (name, task) in app
|
||||
.hardware_tasks
|
||||
.iter()
|
||||
.filter(|(_, task)| task.kind == HardwareTaskKind::Exception)
|
||||
{
|
||||
let name_s = task.args.binds(name).to_string();
|
||||
for (name, task) in &app.hardware_tasks {
|
||||
let name_s = task.args.binds.to_string();
|
||||
match &*name_s {
|
||||
// NOTE that some of these don't exist on ARMv6-M but we don't check that here -- the
|
||||
// code we generate will check that the exception actually exists on ARMv6-M
|
||||
"MemoryManagement" | "BusFault" | "UsageFault" | "SecureFault" | "SVCall"
|
||||
| "DebugMonitor" | "PendSV" => {} // OK
|
||||
|
||||
"SysTick" => {
|
||||
if analysis.timer_queues.get(&task.args.core).is_some() {
|
||||
return Err(parse::Error::new(
|
||||
|
|
@ -67,12 +58,14 @@ pub fn app<'a>(app: &'a App, analysis: &Analysis) -> parse::Result<Extra<'a>> {
|
|||
}
|
||||
}
|
||||
|
||||
_ => {
|
||||
"NonMaskableInt" | "HardFault" => {
|
||||
return Err(parse::Error::new(
|
||||
name.span(),
|
||||
"only exceptions with configurable priority can be used as hardware tasks",
|
||||
));
|
||||
}
|
||||
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -50,9 +50,9 @@ pub fn codegen(
|
|||
};
|
||||
|
||||
let symbol = if cfg!(feature = "homogeneous") {
|
||||
util::suffixed(&task.args.binds(name).to_string(), core)
|
||||
util::suffixed(&task.args.binds.to_string(), core)
|
||||
} else {
|
||||
task.args.binds(name).clone()
|
||||
task.args.binds.clone()
|
||||
};
|
||||
let priority = task.args.priority;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
use proc_macro2::TokenStream as TokenStream2;
|
||||
use quote::quote;
|
||||
use rtfm_syntax::ast::{App, HardwareTaskKind};
|
||||
use rtfm_syntax::ast::App;
|
||||
|
||||
use crate::{analyze::Analysis, check::Extra, codegen::util};
|
||||
|
||||
|
|
@ -52,9 +52,9 @@ pub fn codegen(
|
|||
.get(&core)
|
||||
.iter()
|
||||
.flat_map(|interrupts| *interrupts)
|
||||
.chain(app.hardware_tasks.iter().flat_map(|(name, task)| {
|
||||
if task.kind == HardwareTaskKind::Interrupt {
|
||||
Some((&task.args.priority, task.args.binds(name)))
|
||||
.chain(app.hardware_tasks.values().flat_map(|task| {
|
||||
if !util::is_exception(&task.args.binds) {
|
||||
Some((&task.args.priority, &task.args.binds))
|
||||
} else {
|
||||
// we do exceptions in another pass
|
||||
None
|
||||
|
|
@ -102,9 +102,9 @@ pub fn codegen(
|
|||
}
|
||||
|
||||
// set exception priorities
|
||||
for (name, priority) in app.hardware_tasks.iter().filter_map(|(name, task)| {
|
||||
if task.kind == HardwareTaskKind::Exception {
|
||||
Some((task.args.binds(name), task.args.priority))
|
||||
for (name, priority) in app.hardware_tasks.values().filter_map(|task| {
|
||||
if util::is_exception(&task.args.binds) {
|
||||
Some((&task.args.binds, task.args.priority))
|
||||
} else {
|
||||
None
|
||||
}
|
||||
|
|
|
|||
|
|
@ -113,6 +113,18 @@ pub fn interrupt_ident(core: Core, cores: u8) -> Ident {
|
|||
}
|
||||
}
|
||||
|
||||
/// Whether `name` is an exception with configurable priority
|
||||
pub fn is_exception(name: &Ident) -> bool {
|
||||
let s = name.to_string();
|
||||
|
||||
match &*s {
|
||||
"MemoryManagement" | "BusFault" | "UsageFault" | "SecureFault" | "SVCall"
|
||||
| "DebugMonitor" | "PendSV" | "SysTick" => true,
|
||||
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
|
||||
/// Generates a pre-reexport identifier for the "late resources" struct
|
||||
pub fn late_resources_ident(init: &Ident) -> Ident {
|
||||
Ident::new(
|
||||
|
|
|
|||
|
|
@ -16,19 +16,14 @@ mod tests;
|
|||
|
||||
#[proc_macro_attribute]
|
||||
pub fn app(args: TokenStream, input: TokenStream) -> TokenStream {
|
||||
let (app, analysis) = match rtfm_syntax::parse(
|
||||
args,
|
||||
input,
|
||||
Settings {
|
||||
parse_cores: cfg!(feature = "heterogeneous") || cfg!(feature = "homogeneous"),
|
||||
parse_exception: true,
|
||||
parse_extern_interrupt: true,
|
||||
parse_interrupt: true,
|
||||
parse_schedule: true,
|
||||
optimize_priorities: true,
|
||||
..Settings::default()
|
||||
},
|
||||
) {
|
||||
let mut settings = Settings::default();
|
||||
settings.optimize_priorities = true;
|
||||
settings.parse_binds = true;
|
||||
settings.parse_cores = cfg!(feature = "heterogeneous") || cfg!(feature = "homogeneous");
|
||||
settings.parse_extern_interrupt = true;
|
||||
settings.parse_schedule = true;
|
||||
|
||||
let (app, analysis) = match rtfm_syntax::parse(args, input, settings) {
|
||||
Err(e) => return e.to_compile_error().into(),
|
||||
Ok(x) => x,
|
||||
};
|
||||
|
|
|
|||
|
|
@ -3,6 +3,10 @@ use rtfm_syntax::Settings;
|
|||
|
||||
#[test]
|
||||
fn analyze() {
|
||||
let mut settings = Settings::default();
|
||||
settings.parse_cores = true;
|
||||
settings.parse_extern_interrupt = true;
|
||||
|
||||
let (app, analysis) = rtfm_syntax::parse2(
|
||||
quote!(device = pac, cores = 2),
|
||||
quote!(
|
||||
|
|
@ -35,13 +39,9 @@ fn analyze() {
|
|||
}
|
||||
};
|
||||
),
|
||||
Settings {
|
||||
parse_cores: true,
|
||||
parse_extern_interrupt: true,
|
||||
..Settings::default()
|
||||
},
|
||||
settings,
|
||||
)
|
||||
.unwrap();
|
||||
.unwrap();
|
||||
|
||||
let analysis = crate::analyze::app(analysis, &app);
|
||||
|
||||
|
|
|
|||
|
|
@ -3,6 +3,8 @@ use rtfm_syntax::Settings;
|
|||
|
||||
#[test]
|
||||
fn analyze() {
|
||||
let mut settings = Settings::default();
|
||||
settings.parse_extern_interrupt = true;
|
||||
let (app, analysis) = rtfm_syntax::parse2(
|
||||
quote!(device = pac),
|
||||
quote!(
|
||||
|
|
@ -20,10 +22,7 @@ fn analyze() {
|
|||
}
|
||||
};
|
||||
),
|
||||
Settings {
|
||||
parse_extern_interrupt: true,
|
||||
..Settings::default()
|
||||
},
|
||||
settings,
|
||||
)
|
||||
.unwrap();
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue