From 5bc85dd21ce89cb79d998b9b664588a27d4137bd Mon Sep 17 00:00:00 2001 From: Toby Gray Date: Thu, 7 Jun 2012 15:51:24 +0100 Subject: [PATCH] lib: Fixing ThreadTimeout implementation for Windows to correctly calculate seconds since theUunix epoc. --- src/time.cc | 27 ++++++++++++++++++--------- 1 file changed, 18 insertions(+), 9 deletions(-) diff --git a/src/time.cc b/src/time.cc index 53990698..dd977bb6 100644 --- a/src/time.cc +++ b/src/time.cc @@ -242,20 +242,29 @@ time_t Message2Time(uint16_t r_date, uint16_t r_time) /// struct timespec* ThreadTimeout(int timeout_ms, struct timespec *spec) { -#ifndef WIN32 struct timeval now; +#ifndef WIN32 gettimeofday(&now, NULL); - - spec->tv_sec = now.tv_sec + timeout_ms / 1000; - spec->tv_nsec = (now.tv_usec + timeout_ms % 1000 * 1000) * 1000; #else - SYSTEMTIME now; - GetSystemTime(&now); - - spec->tv_sec = now.wSecond + timeout_ms / 1000; - spec->tv_nsec = (now.wMilliseconds + timeout_ms) * 1000; + SYSTEMTIME st; + FILETIME ft; + LONGLONG ll; + + GetSystemTime(&st); + SystemTimeToFileTime(&st, &ft); + /* Now convert the file time to a timespec */ + ll = (static_cast(ft.dwHighDateTime) << 32) | ft.dwLowDateTime; + // Adjust the offset to 100ns periods from UNIX epoc + ll -= 116444736000000000; + // Adjust the offset to micro-seconds since the UNIX epoc + ll /= 10; + + now.tv_sec = static_cast(ll / 1000000); + now.tv_usec = static_cast(ll % 1000000); #endif + spec->tv_sec = now.tv_sec + timeout_ms / 1000; + spec->tv_nsec = (now.tv_usec + timeout_ms % 1000 * 1000) * 1000; return spec; } -- 2.11.4.GIT