Skip to content

Commit

Permalink
kernel: timer: Fix race condition in k_timer_start
Browse files Browse the repository at this point in the history
The documentation suggests that k_timer_start can be invoked from ISR
and preemptive contexts, however, an assertion failure occurs if one
k_timer_start call preempts another for the same timer instance. This
commit mitigates the issue by implementing a spinlock throughout the
k_timer_start function, ensuring thread-safety.

Fixes: #62908

Signed-off-by: Pedro Sousa <[email protected]>
(cherry picked from commit 4207f4a)
  • Loading branch information
sousapedro596 authored and github-actions[bot] committed Oct 23, 2023
1 parent a6eef0b commit c16d824
Showing 1 changed file with 10 additions and 0 deletions.
10 changes: 10 additions & 0 deletions kernel/timer.c
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,15 @@ void z_impl_k_timer_start(struct k_timer *timer, k_timeout_t duration,
{
SYS_PORT_TRACING_OBJ_FUNC(k_timer, start, timer, duration, period);

/* Acquire spinlock to ensure safety during concurrent calls to
* k_timer_start for scheduling or rescheduling. This is necessary
* since k_timer_start can be preempted, especially for the same
* timer instance.
*/
k_spinlock_key_t key = k_spin_lock(&lock);

if (K_TIMEOUT_EQ(duration, K_FOREVER)) {
k_spin_unlock(&lock, key);
return;
}

Expand All @@ -168,6 +176,8 @@ void z_impl_k_timer_start(struct k_timer *timer, k_timeout_t duration,

z_add_timeout(&timer->timeout, z_timer_expiration_handler,
duration);

k_spin_unlock(&lock, key);
}

#ifdef CONFIG_USERSPACE
Expand Down

0 comments on commit c16d824

Please sign in to comment.