esp32s3/rt_timer: Adjust spinlock position to avoid deadlock

This commit is contained in:
chenwen@espressif.com
2023-12-27 17:26:19 +08:00
committed by Masayuki Ishikawa
parent f4485a58e3
commit a774587088
+16 -14
View File
@@ -369,11 +369,8 @@ static void start_rt_timer(struct rt_timer_s *timer,
uint64_t timeout, uint64_t timeout,
bool repeat) bool repeat)
{ {
irqstate_t flags;
struct esp32s3_rt_priv_s *priv = &g_rt_priv; struct esp32s3_rt_priv_s *priv = &g_rt_priv;
flags = spin_lock_irqsave(&priv->lock);
/* Only idle timer can be started */ /* Only idle timer can be started */
if (timer->state == RT_TIMER_IDLE) if (timer->state == RT_TIMER_IDLE)
@@ -437,8 +434,6 @@ static void start_rt_timer(struct rt_timer_s *timer,
{ {
tmrwarn("Timer not in idle mode. Only idle timer can be started!\n"); tmrwarn("Timer not in idle mode. Only idle timer can be started!\n");
} }
spin_unlock_irqrestore(&priv->lock, flags);
} }
/**************************************************************************** /****************************************************************************
@@ -458,11 +453,8 @@ static void start_rt_timer(struct rt_timer_s *timer,
static void stop_rt_timer(struct rt_timer_s *timer) static void stop_rt_timer(struct rt_timer_s *timer)
{ {
irqstate_t flags;
struct esp32s3_rt_priv_s *priv = &g_rt_priv; struct esp32s3_rt_priv_s *priv = &g_rt_priv;
flags = spin_lock_irqsave(&priv->lock);
/* "start" function can set the timer's repeat flag, and "stop" function /* "start" function can set the timer's repeat flag, and "stop" function
* should remove this flag. * should remove this flag.
*/ */
@@ -507,8 +499,6 @@ static void stop_rt_timer(struct rt_timer_s *timer)
} }
} }
} }
spin_unlock_irqrestore(&priv->lock, flags);
} }
/**************************************************************************** /****************************************************************************
@@ -572,6 +562,10 @@ static int rt_timer_thread(int argc, char *argv[])
kmm_free(timer); kmm_free(timer);
} }
/* Enter critical section for next scanning list */
flags = spin_lock_irqsave(&priv->lock);
if (raw_state == RT_TIMER_TIMEOUT) if (raw_state == RT_TIMER_TIMEOUT)
{ {
/* Check if the timer is in "repeat" mode */ /* Check if the timer is in "repeat" mode */
@@ -581,10 +575,6 @@ static int rt_timer_thread(int argc, char *argv[])
start_rt_timer(timer, timer->timeout, true); start_rt_timer(timer, timer->timeout, true);
} }
} }
/* Enter critical section for next scanning list */
flags = spin_lock_irqsave(&priv->lock);
} }
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
@@ -754,9 +744,16 @@ void esp32s3_rt_timer_start(struct rt_timer_s *timer,
uint64_t timeout, uint64_t timeout,
bool repeat) bool repeat)
{ {
irqstate_t flags;
struct esp32s3_rt_priv_s *priv = &g_rt_priv;
flags = spin_lock_irqsave(&priv->lock);
stop_rt_timer(timer); stop_rt_timer(timer);
start_rt_timer(timer, timeout, repeat); start_rt_timer(timer, timeout, repeat);
spin_unlock_irqrestore(&priv->lock, flags);
} }
/**************************************************************************** /****************************************************************************
@@ -775,7 +772,12 @@ void esp32s3_rt_timer_start(struct rt_timer_s *timer,
void esp32s3_rt_timer_stop(struct rt_timer_s *timer) void esp32s3_rt_timer_stop(struct rt_timer_s *timer)
{ {
irqstate_t flags;
struct esp32s3_rt_priv_s *priv = &g_rt_priv;
flags = spin_lock_irqsave(&priv->lock);
stop_rt_timer(timer); stop_rt_timer(timer);
spin_unlock_irqrestore(&priv->lock, flags);
} }
/**************************************************************************** /****************************************************************************