Skip to content

esp: RTOS optimizations#898

Open
tact1m4n3 wants to merge 14 commits intomainfrom
esp_rtos_upgrade
Open

esp: RTOS optimizations#898
tact1m4n3 wants to merge 14 commits intomainfrom
esp_rtos_upgrade

Conversation

@tact1m4n3
Copy link
Collaborator

@tact1m4n3 tact1m4n3 commented Feb 8, 2026

Some numbers with 200 concurrent tasks:

  • Plain cooperative rescheduling of a task until the switch to a different task: 140-150 cycles
  • If the task suspends itself (eg: waiting on a mutex without timeout): 126-137 cycles (this only measures the yielding time, not the overhead induced by the mutex)
  • If the task sleeps: 268-1700 cycles (1700 is for the 200th task that must be inserted at the end of the sleep_queue since it wakes up last). This is O(n). Also there is an overhead in the tick interrupt when all these tasks are woken up: the max tick interrupt time is close to 4000cycles (O(n) with the number of tasks waking up on the same tick) (otherwise being ~250cycles if no tasks wake).

I also added support for time slicing (switch between tasks of the same priority on the tick interval). This is by default off.

Tasks can now be awaited and the memory freed. I used this to implement cleanup for radio/timer.zig, but for the tasks spawned by the wifi driver it is more complicated so I will leave this for a later PR.

Unit tests for the esp port now run on CI.

pub const highest: @This() = @enumFromInt(std.math.maxInt(@typeInfo(@This()).@"enum".tag_type));

pub fn next_higher(prio: Priority) Priority {
return @enumFromInt(@intFromEnum(prio) +| 1);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is this supposed to wrap around? that is the +| for?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+| is saturating add which means the addition will "saturate" at the max int value before the overflow. This function isn't used anymore so I'll just remove it.

\\mret
:
: [schedule_in_isr] "i" (&schedule_in_isr),
: [tick_handler] "i" (&tick_handler),
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we not need all the clobbers? Is this because it's an interrupt handler?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since it is a naked function, I don't think clobbers would make any difference since the compiler has nowhere to save/restore those registers.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants