Menu

#973 sys_now() returns incorrent time

21.11.4
closed
None
lwIP
Medium
18.2.1
False
2024-08-29
2018-08-24
rushmash
No

Hi, seems I have found a bug in sys_now() at os/various/lwip_bindings/sys_arch.c. Current time is calculated incorrectly there.

LwIP uses this function to get difference in time, so for the case when TIMx->CNT is overflowed (when it has changed value from 4294967295 to 0) and OSAL_ST_FREQUENCY != 1000 or CH_CFG_ST_RESOLUTION != 32 - the difference in time in ms is significantly larger than 1 as these values are stored in u32_t.

I propose the following fix, which takes into consideration OSAL_ST_FREQUENCY and CH_CFG_ST_RESOLUTION. It looks a bit bulky, but I think it should work.

u32_t sys_now( void ) {
    static u32_t timeMs = 0;
    static systime_t lastSysTime = 0;
    systime_t dt = osalOsGetSystemTimeX() - lastSysTime;
    u32_t dtMs;

#if OSAL_ST_FREQUENCY == 1000
    dtMs = dt;
#elif ( OSAL_ST_FREQUENCY / 1000 ) >= 1 && ( OSAL_ST_FREQUENCY % 1000 ) == 0
    dtMs = dt / ( OSAL_ST_FREQUENCY / 1000 );
    dt = dtMs * ( OSAL_ST_FREQUENCY / 1000 );
#elif ( 1000 / OSAL_ST_FREQUENCY ) >= 1 && ( 1000 % OSAL_ST_FREQUENCY ) == 0
    dtMs = dt * ( 1000 / OSAL_ST_FREQUENCY );
    dt = dtMs / ( 1000 / OSAL_ST_FREQUENCY );
#else
    dtMs = ( ( u64_t )dt * 1000 ) / OSAL_ST_FREQUENCY;
    dt = ( ( u64_t )dtMs * OSAL_ST_FREQUENCY ) / 1000;
#endif
    timeMs += dtMs;
    lastSysTime += dt;
    return timeMs;
}

Discussion

  • Giovanni Di Sirio

    Fixed using a different method, closing.

     
  • Giovanni Di Sirio

    • status: open --> closed
    • assigned_to: Giovanni Di Sirio
    • Milestone: 18.2.2 --> 21.11.4
     
  • rushmash

    rushmash - 2024-08-29

    Many thanks!

     

Log in to post a comment.