aboutsummaryrefslogtreecommitdiff
path: root/embassy-executor
diff options
context:
space:
mode:
Diffstat (limited to 'embassy-executor')
-rw-r--r--embassy-executor/Cargo.toml6
-rw-r--r--embassy-executor/src/raw/mod.rs52
-rw-r--r--embassy-executor/src/raw/trace.rs90
3 files changed, 107 insertions, 41 deletions
diff --git a/embassy-executor/Cargo.toml b/embassy-executor/Cargo.toml
index 7c930b658..0a5360e5d 100644
--- a/embassy-executor/Cargo.toml
+++ b/embassy-executor/Cargo.toml
@@ -31,7 +31,7 @@ features = ["defmt", "arch-cortex-m", "executor-thread", "executor-interrupt"]
31[dependencies] 31[dependencies]
32defmt = { version = "0.3", optional = true } 32defmt = { version = "0.3", optional = true }
33log = { version = "0.4.14", optional = true } 33log = { version = "0.4.14", optional = true }
34rtos-trace = { version = "0.1.2", optional = true } 34rtos-trace = { version = "0.1.3", optional = true }
35 35
36embassy-executor-macros = { version = "0.6.2", path = "../embassy-executor-macros" } 36embassy-executor-macros = { version = "0.6.2", path = "../embassy-executor-macros" }
37embassy-time-driver = { version = "0.1.0", path = "../embassy-time-driver", optional = true } 37embassy-time-driver = { version = "0.1.0", path = "../embassy-time-driver", optional = true }
@@ -91,6 +91,10 @@ arch-spin = ["_arch"]
91executor-thread = [] 91executor-thread = []
92## Enable the interrupt-mode executor (available in Cortex-M only) 92## Enable the interrupt-mode executor (available in Cortex-M only)
93executor-interrupt = [] 93executor-interrupt = []
94## Enable tracing support (adds some overhead)
95trace = []
96## Enable support for rtos-trace framework
97rtos-trace = ["dep:rtos-trace", "trace"]
94 98
95#! ### Task Arena Size 99#! ### Task Arena Size
96#! Sets the [task arena](#task-arena) size. Necessary if you’re not using `nightly`. 100#! Sets the [task arena](#task-arena) size. Necessary if you’re not using `nightly`.
diff --git a/embassy-executor/src/raw/mod.rs b/embassy-executor/src/raw/mod.rs
index ebabee1ba..3f93eae6f 100644
--- a/embassy-executor/src/raw/mod.rs
+++ b/embassy-executor/src/raw/mod.rs
@@ -18,6 +18,8 @@ mod state;
18 18
19#[cfg(feature = "integrated-timers")] 19#[cfg(feature = "integrated-timers")]
20mod timer_queue; 20mod timer_queue;
21#[cfg(feature = "trace")]
22mod trace;
21pub(crate) mod util; 23pub(crate) mod util;
22#[cfg_attr(feature = "turbowakers", path = "waker_turbo.rs")] 24#[cfg_attr(feature = "turbowakers", path = "waker_turbo.rs")]
23mod waker; 25mod waker;
@@ -31,8 +33,6 @@ use core::task::{Context, Poll};
31 33
32#[cfg(feature = "integrated-timers")] 34#[cfg(feature = "integrated-timers")]
33use embassy_time_driver::AlarmHandle; 35use embassy_time_driver::AlarmHandle;
34#[cfg(feature = "rtos-trace")]
35use rtos_trace::trace;
36 36
37use self::run_queue::{RunQueue, RunQueueItem}; 37use self::run_queue::{RunQueue, RunQueueItem};
38use self::state::State; 38use self::state::State;
@@ -352,8 +352,8 @@ impl SyncExecutor {
352 /// - `task` must NOT be already enqueued (in this executor or another one). 352 /// - `task` must NOT be already enqueued (in this executor or another one).
353 #[inline(always)] 353 #[inline(always)]
354 unsafe fn enqueue(&self, task: TaskRef) { 354 unsafe fn enqueue(&self, task: TaskRef) {
355 #[cfg(feature = "rtos-trace")] 355 #[cfg(feature = "trace")]
356 trace::task_ready_begin(task.as_ptr() as u32); 356 trace::task_ready_begin(self, &task);
357 357
358 if self.run_queue.enqueue(task) { 358 if self.run_queue.enqueue(task) {
359 self.pender.pend(); 359 self.pender.pend();
@@ -369,8 +369,8 @@ impl SyncExecutor {
369 pub(super) unsafe fn spawn(&'static self, task: TaskRef) { 369 pub(super) unsafe fn spawn(&'static self, task: TaskRef) {
370 task.header().executor.set(Some(self)); 370 task.header().executor.set(Some(self));
371 371
372 #[cfg(feature = "rtos-trace")] 372 #[cfg(feature = "trace")]
373 trace::task_new(task.as_ptr() as u32); 373 trace::task_new(self, &task);
374 374
375 self.enqueue(task); 375 self.enqueue(task);
376 } 376 }
@@ -400,14 +400,14 @@ impl SyncExecutor {
400 return; 400 return;
401 } 401 }
402 402
403 #[cfg(feature = "rtos-trace")] 403 #[cfg(feature = "trace")]
404 trace::task_exec_begin(p.as_ptr() as u32); 404 trace::task_exec_begin(self, &p);
405 405
406 // Run the task 406 // Run the task
407 task.poll_fn.get().unwrap_unchecked()(p); 407 task.poll_fn.get().unwrap_unchecked()(p);
408 408
409 #[cfg(feature = "rtos-trace")] 409 #[cfg(feature = "trace")]
410 trace::task_exec_end(); 410 trace::task_exec_end(self, &p);
411 411
412 // Enqueue or update into timer_queue 412 // Enqueue or update into timer_queue
413 #[cfg(feature = "integrated-timers")] 413 #[cfg(feature = "integrated-timers")]
@@ -430,8 +430,8 @@ impl SyncExecutor {
430 } 430 }
431 } 431 }
432 432
433 #[cfg(feature = "rtos-trace")] 433 #[cfg(feature = "trace")]
434 trace::system_idle(); 434 trace::executor_idle(self)
435 } 435 }
436} 436}
437 437
@@ -593,31 +593,3 @@ impl embassy_time_queue_driver::TimerQueue for TimerQueue {
593 593
594#[cfg(feature = "integrated-timers")] 594#[cfg(feature = "integrated-timers")]
595embassy_time_queue_driver::timer_queue_impl!(static TIMER_QUEUE: TimerQueue = TimerQueue); 595embassy_time_queue_driver::timer_queue_impl!(static TIMER_QUEUE: TimerQueue = TimerQueue);
596
597#[cfg(all(feature = "rtos-trace", feature = "integrated-timers"))]
598const fn gcd(a: u64, b: u64) -> u64 {
599 if b == 0 {
600 a
601 } else {
602 gcd(b, a % b)
603 }
604}
605
606#[cfg(feature = "rtos-trace")]
607impl rtos_trace::RtosTraceOSCallbacks for Executor {
608 fn task_list() {
609 // We don't know what tasks exist, so we can't send them.
610 }
611 #[cfg(feature = "integrated-timers")]
612 fn time() -> u64 {
613 const GCD_1M: u64 = gcd(embassy_time_driver::TICK_HZ, 1_000_000);
614 embassy_time_driver::now() * (1_000_000 / GCD_1M) / (embassy_time_driver::TICK_HZ / GCD_1M)
615 }
616 #[cfg(not(feature = "integrated-timers"))]
617 fn time() -> u64 {
618 0
619 }
620}
621
622#[cfg(feature = "rtos-trace")]
623rtos_trace::global_os_callbacks! {Executor}
diff --git a/embassy-executor/src/raw/trace.rs b/embassy-executor/src/raw/trace.rs
new file mode 100644
index 000000000..c7bcf9c11
--- /dev/null
+++ b/embassy-executor/src/raw/trace.rs
@@ -0,0 +1,90 @@
1#![allow(unused)]
2use crate::raw::{SyncExecutor, TaskRef};
3
4#[cfg(not(feature = "rtos-trace"))]
5extern "Rust" {
6 fn _embassy_trace_task_new(executor_id: u32, task_id: u32);
7 fn _embassy_trace_task_exec_begin(executor_id: u32, task_id: u32);
8 fn _embassy_trace_task_exec_end(excutor_id: u32, task_id: u32);
9 fn _embassy_trace_task_ready_begin(executor_id: u32, task_id: u32);
10 fn _embassy_trace_executor_idle(executor_id: u32);
11}
12
13#[inline]
14pub(crate) fn task_new(executor: &SyncExecutor, task: &TaskRef) {
15 #[cfg(not(feature = "rtos-trace"))]
16 unsafe {
17 _embassy_trace_task_new(executor as *const _ as u32, task.as_ptr() as u32)
18 }
19
20 #[cfg(feature = "rtos-trace")]
21 rtos_trace::trace::task_new(task.as_ptr() as u32);
22}
23
24#[inline]
25pub(crate) fn task_ready_begin(executor: &SyncExecutor, task: &TaskRef) {
26 #[cfg(not(feature = "rtos-trace"))]
27 unsafe {
28 _embassy_trace_task_ready_begin(executor as *const _ as u32, task.as_ptr() as u32)
29 }
30 #[cfg(feature = "rtos-trace")]
31 rtos_trace::trace::task_ready_begin(task.as_ptr() as u32);
32}
33
34#[inline]
35pub(crate) fn task_exec_begin(executor: &SyncExecutor, task: &TaskRef) {
36 #[cfg(not(feature = "rtos-trace"))]
37 unsafe {
38 _embassy_trace_task_exec_begin(executor as *const _ as u32, task.as_ptr() as u32)
39 }
40 #[cfg(feature = "rtos-trace")]
41 rtos_trace::trace::task_exec_begin(task.as_ptr() as u32);
42}
43
44#[inline]
45pub(crate) fn task_exec_end(executor: &SyncExecutor, task: &TaskRef) {
46 #[cfg(not(feature = "rtos-trace"))]
47 unsafe {
48 _embassy_trace_task_exec_end(executor as *const _ as u32, task.as_ptr() as u32)
49 }
50 #[cfg(feature = "rtos-trace")]
51 rtos_trace::trace::task_exec_end();
52}
53
54#[inline]
55pub(crate) fn executor_idle(executor: &SyncExecutor) {
56 #[cfg(not(feature = "rtos-trace"))]
57 unsafe {
58 _embassy_trace_executor_idle(executor as *const _ as u32)
59 }
60 #[cfg(feature = "rtos-trace")]
61 rtos_trace::trace::system_idle();
62}
63
64#[cfg(all(feature = "rtos-trace", feature = "integrated-timers"))]
65const fn gcd(a: u64, b: u64) -> u64 {
66 if b == 0 {
67 a
68 } else {
69 gcd(b, a % b)
70 }
71}
72
73#[cfg(feature = "rtos-trace")]
74impl rtos_trace::RtosTraceOSCallbacks for crate::raw::SyncExecutor {
75 fn task_list() {
76 // We don't know what tasks exist, so we can't send them.
77 }
78 #[cfg(feature = "integrated-timers")]
79 fn time() -> u64 {
80 const GCD_1M: u64 = gcd(embassy_time_driver::TICK_HZ, 1_000_000);
81 embassy_time_driver::now() * (1_000_000 / GCD_1M) / (embassy_time_driver::TICK_HZ / GCD_1M)
82 }
83 #[cfg(not(feature = "integrated-timers"))]
84 fn time() -> u64 {
85 0
86 }
87}
88
89#[cfg(feature = "rtos-trace")]
90rtos_trace::global_os_callbacks! {SyncExecutor}