Skip to content

Commit c67b2e0

Browse files
committed
fix timer overflow
1 parent 8525e08 commit c67b2e0

File tree

4 files changed

+30
-29
lines changed

4 files changed

+30
-29
lines changed

src/ipc.c

Lines changed: 18 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,8 @@
4646
* 2022-10-16 Bernard add prioceiling feature in mutex
4747
* 2023-04-16 Xin-zheqi redesigen queue recv and send function return real message size
4848
* 2023-09-15 xqyjlj perf rt_hw_interrupt_disable/enable
49+
* 2025-06-01 htl5241 fix timer overflow
50+
*
4951
*/
5052

5153
#include <rtthread.h>
@@ -2567,7 +2569,7 @@ static rt_err_t _rt_mb_send_wait(rt_mailbox_t mb,
25672569
{
25682570
struct rt_thread *thread;
25692571
rt_base_t level;
2570-
rt_uint32_t tick_delta;
2572+
rt_uint32_t tick_stamp;
25712573
rt_err_t ret;
25722574

25732575
/* parameter check */
@@ -2578,7 +2580,7 @@ static rt_err_t _rt_mb_send_wait(rt_mailbox_t mb,
25782580
RT_DEBUG_SCHEDULER_AVAILABLE(timeout != 0);
25792581

25802582
/* initialize delta tick */
2581-
tick_delta = 0;
2583+
tick_stamp = 0;
25822584
/* get current thread */
25832585
thread = rt_thread_self();
25842586

@@ -2622,7 +2624,7 @@ static rt_err_t _rt_mb_send_wait(rt_mailbox_t mb,
26222624
if (timeout > 0)
26232625
{
26242626
/* get the start tick of timer */
2625-
tick_delta = rt_tick_get();
2627+
tick_stamp = rt_tick_get();
26262628

26272629
LOG_D("mb_send_wait: start timer of thread:%s",
26282630
thread->parent.name);
@@ -2650,8 +2652,7 @@ static rt_err_t _rt_mb_send_wait(rt_mailbox_t mb,
26502652
/* if it's not waiting forever and then re-calculate timeout tick */
26512653
if (timeout > 0)
26522654
{
2653-
tick_delta = rt_tick_get() - tick_delta;
2654-
timeout -= tick_delta;
2655+
timeout -= rt_tick_get_delta(tick_stamp);
26552656
if (timeout < 0)
26562657
timeout = 0;
26572658
}
@@ -2846,7 +2847,7 @@ static rt_err_t _rt_mb_recv(rt_mailbox_t mb, rt_ubase_t *value, rt_int32_t timeo
28462847
{
28472848
struct rt_thread *thread;
28482849
rt_base_t level;
2849-
rt_uint32_t tick_delta;
2850+
rt_uint32_t tick_stamp;
28502851
rt_err_t ret;
28512852

28522853
/* parameter check */
@@ -2857,7 +2858,7 @@ static rt_err_t _rt_mb_recv(rt_mailbox_t mb, rt_ubase_t *value, rt_int32_t timeo
28572858
RT_DEBUG_SCHEDULER_AVAILABLE(timeout != 0);
28582859

28592860
/* initialize delta tick */
2860-
tick_delta = 0;
2861+
tick_stamp = 0;
28612862
/* get current thread */
28622863
thread = rt_thread_self();
28632864

@@ -2902,7 +2903,7 @@ static rt_err_t _rt_mb_recv(rt_mailbox_t mb, rt_ubase_t *value, rt_int32_t timeo
29022903
if (timeout > 0)
29032904
{
29042905
/* get the start tick of timer */
2905-
tick_delta = rt_tick_get();
2906+
tick_stamp = rt_tick_get();
29062907

29072908
LOG_D("mb_recv: start timer of thread:%s",
29082909
thread->parent.name);
@@ -2930,8 +2931,7 @@ static rt_err_t _rt_mb_recv(rt_mailbox_t mb, rt_ubase_t *value, rt_int32_t timeo
29302931
/* if it's not waiting forever and then re-calculate timeout tick */
29312932
if (timeout > 0)
29322933
{
2933-
tick_delta = rt_tick_get() - tick_delta;
2934-
timeout -= tick_delta;
2934+
timeout -= rt_tick_get_delta(tick_stamp);
29352935
if (timeout < 0)
29362936
timeout = 0;
29372937
}
@@ -3382,7 +3382,7 @@ static rt_err_t _rt_mq_send_wait(rt_mq_t mq,
33823382
{
33833383
rt_base_t level;
33843384
struct rt_mq_message *msg;
3385-
rt_uint32_t tick_delta;
3385+
rt_uint32_t tick_stamp;
33863386
struct rt_thread *thread;
33873387
rt_err_t ret;
33883388

@@ -3402,7 +3402,7 @@ static rt_err_t _rt_mq_send_wait(rt_mq_t mq,
34023402
return -RT_ERROR;
34033403

34043404
/* initialize delta tick */
3405-
tick_delta = 0;
3405+
tick_stamp = 0;
34063406
/* get current thread */
34073407
thread = rt_thread_self();
34083408

@@ -3447,7 +3447,7 @@ static rt_err_t _rt_mq_send_wait(rt_mq_t mq,
34473447
if (timeout > 0)
34483448
{
34493449
/* get the start tick of timer */
3450-
tick_delta = rt_tick_get();
3450+
tick_stamp = rt_tick_get();
34513451

34523452
LOG_D("mq_send_wait: start timer of thread:%s",
34533453
thread->parent.name);
@@ -3475,8 +3475,7 @@ static rt_err_t _rt_mq_send_wait(rt_mq_t mq,
34753475
/* if it's not waiting forever and then re-calculate timeout tick */
34763476
if (timeout > 0)
34773477
{
3478-
tick_delta = rt_tick_get() - tick_delta;
3479-
timeout -= tick_delta;
3478+
timeout -= rt_tick_get_delta(tick_stamp);
34803479
if (timeout < 0)
34813480
timeout = 0;
34823481
}
@@ -3765,7 +3764,7 @@ static rt_ssize_t _rt_mq_recv(rt_mq_t mq,
37653764
struct rt_thread *thread;
37663765
rt_base_t level;
37673766
struct rt_mq_message *msg;
3768-
rt_uint32_t tick_delta;
3767+
rt_uint32_t tick_stamp;
37693768
rt_err_t ret;
37703769
rt_size_t len;
37713770

@@ -3781,7 +3780,7 @@ static rt_ssize_t _rt_mq_recv(rt_mq_t mq,
37813780
RT_DEBUG_SCHEDULER_AVAILABLE(timeout != 0);
37823781

37833782
/* initialize delta tick */
3784-
tick_delta = 0;
3783+
tick_stamp = 0;
37853784
/* get current thread */
37863785
thread = rt_thread_self();
37873786
RT_OBJECT_HOOK_CALL(rt_object_trytake_hook, (&(mq->parent.parent)));
@@ -3826,7 +3825,7 @@ static rt_ssize_t _rt_mq_recv(rt_mq_t mq,
38263825
if (timeout > 0)
38273826
{
38283827
/* get the start tick of timer */
3829-
tick_delta = rt_tick_get();
3828+
tick_stamp = rt_tick_get();
38303829

38313830
LOG_D("set thread:%s to timer list",
38323831
thread->parent.name);
@@ -3855,8 +3854,7 @@ static rt_ssize_t _rt_mq_recv(rt_mq_t mq,
38553854
/* if it's not waiting forever and then re-calculate timeout tick */
38563855
if (timeout > 0)
38573856
{
3858-
tick_delta = rt_tick_get() - tick_delta;
3859-
timeout -= tick_delta;
3857+
timeout -= rt_tick_get_delta(tick_stamp);
38603858
if (timeout < 0)
38613859
timeout = 0;
38623860
}

src/mempool.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
* 2022-01-07 Gabriel Moving __on_rt_xxxxx_hook to mempool.c
1818
* 2023-09-15 xqyjlj perf rt_hw_interrupt_disable/enable
1919
* 2023-12-10 xqyjlj fix spinlock assert
20+
* 2025-06-01 htl5241 fix timer overflow
2021
*/
2122

2223
#include <rthw.h>
@@ -335,7 +336,7 @@ void *rt_mp_alloc(rt_mp_t mp, rt_int32_t time)
335336

336337
if (time > 0)
337338
{
338-
time -= rt_tick_get() - before_sleep;
339+
time -= rt_tick_get_delta(before_sleep);
339340
if (time < 0)
340341
time = 0;
341342
}

src/thread.c

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,8 @@
3535
* 2023-09-15 xqyjlj perf rt_hw_interrupt_disable/enable
3636
* 2023-12-10 xqyjlj fix thread_exit/detach/delete
3737
* fix rt_thread_delay
38+
* 2025-06-01 htl5241 fix timer overflow
39+
*
3840
*/
3941

4042
#include <rthw.h>
@@ -692,7 +694,6 @@ RTM_EXPORT(rt_thread_delay);
692694
rt_err_t rt_thread_delay_until(rt_tick_t *tick, rt_tick_t inc_tick)
693695
{
694696
struct rt_thread *thread;
695-
rt_tick_t cur_tick;
696697
rt_base_t critical_level;
697698

698699
RT_ASSERT(tick != RT_NULL);
@@ -708,13 +709,14 @@ rt_err_t rt_thread_delay_until(rt_tick_t *tick, rt_tick_t inc_tick)
708709
/* disable interrupt */
709710
critical_level = rt_enter_critical();
710711

711-
cur_tick = rt_tick_get();
712-
if (cur_tick - *tick < inc_tick)
712+
if (rt_tick_get_delta(*tick) < inc_tick)
713713
{
714714
rt_tick_t left_tick;
715715

716716
*tick += inc_tick;
717-
left_tick = *tick - cur_tick;
717+
left_tick = *tick - rt_tick_get();
718+
if (left_tick > *tick)
719+
left_tick = RT_TICK_MAX - left_tick + 1;
718720

719721
/* suspend thread */
720722
rt_thread_suspend_with_flag(thread, RT_UNINTERRUPTIBLE);
@@ -735,7 +737,7 @@ rt_err_t rt_thread_delay_until(rt_tick_t *tick, rt_tick_t inc_tick)
735737
}
736738
else
737739
{
738-
*tick = cur_tick;
740+
*tick = rt_tick_get();
739741
rt_exit_critical_safe(critical_level);
740742
}
741743

src/timer.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@
2222
* 2023-09-15 xqyjlj perf rt_hw_interrupt_disable/enable
2323
* 2024-01-25 Shell add RT_TIMER_FLAG_THREAD_TIMER for timer to sync with sched
2424
* 2024-05-01 wdfk-prog The rt_timer_check and _soft_timer_check functions are merged
25+
* 2025-06-01 htl5241 remove redundancy
26+
* fix timer overflow
2527
*/
2628

2729
#include <rtthread.h>
@@ -494,8 +496,6 @@ static void _timer_check(rt_list_t *timer_list, struct rt_spinlock *lock)
494496

495497
level = rt_spin_lock_irqsave(lock);
496498

497-
current_tick = rt_tick_get();
498-
499499
rt_list_init(&list);
500500

501501
while (!rt_list_isempty(&timer_list[RT_TIMER_SKIP_LIST_LEVEL - 1]))
@@ -762,7 +762,7 @@ void rt_timer_check(void)
762762
rt_tick_t next_timeout;
763763

764764
ret = _timer_list_next_timeout(_soft_timer_list, &next_timeout);
765-
if ((ret == RT_EOK) && (next_timeout <= rt_tick_get()))
765+
if ((ret == RT_EOK) && ((rt_tick_get() - next_timeout) < RT_TICK_MAX / 2))
766766
{
767767
rt_sem_release(&_soft_timer_sem);
768768
}

0 commit comments

Comments
 (0)