From b411d345d064d5c2812234266b7ac156ea5d8b4e Mon Sep 17 00:00:00 2001 From: Geoffrey McRae Date: Wed, 12 Aug 2026 12:13:26 +1000 Subject: [PATCH] [common] event: fix long Linux timeouts Normalize absolute event deadlines with division and remainder, and widen millisecond conversion before multiplying. This prevents multi-second waits from producing EINVAL or wrapping to shorter delays. --- common/src/platform/linux/event.c | 27 ++++++++++++++------------- 1 file changed, 14 insertions(+), 13 deletions(-) diff --git a/common/src/platform/linux/event.c b/common/src/platform/linux/event.c index 5a424310..ccf0603b 100644 --- a/common/src/platform/linux/event.c +++ b/common/src/platform/linux/event.c @@ -143,23 +143,24 @@ bool lgWaitEventAbs(LGEvent * handle, struct timespec * ts) return ret; } +static bool waitEventNS(LGEvent * handle, uint64_t timeout) +{ + struct timespec ts; + clock_gettime(CLOCK_MONOTONIC, &ts); + + const uint64_t nsec = (uint64_t)ts.tv_nsec + timeout; + ts.tv_sec += nsec / 1000000000ULL; + ts.tv_nsec = nsec % 1000000000ULL; + + return lgWaitEventAbs(handle, &ts); +} + bool lgWaitEventNS(LGEvent * handle, unsigned int timeout) { if (timeout == TIMEOUT_INFINITE) return lgWaitEventAbs(handle, NULL); - struct timespec ts; - clock_gettime(CLOCK_MONOTONIC, &ts); - uint64_t nsec = ts.tv_nsec + timeout; - if(nsec > 1000000000UL) - { - ts.tv_nsec = nsec - 1000000000UL; - ++ts.tv_sec; - } - else - ts.tv_nsec = nsec; - - return lgWaitEventAbs(handle, &ts); + return waitEventNS(handle, timeout); } bool lgWaitEvent(LGEvent * handle, unsigned int timeout) @@ -167,7 +168,7 @@ bool lgWaitEvent(LGEvent * handle, unsigned int timeout) if (timeout == TIMEOUT_INFINITE) return lgWaitEventAbs(handle, NULL); - return lgWaitEventNS(handle, timeout * 1000000U); + return waitEventNS(handle, (uint64_t)timeout * 1000000ULL); } bool lgSignalEvent(LGEvent * handle)