summaryrefslogtreecommitdiff
path: root/evutil_time.c
diff options
context:
space:
mode:
Diffstat (limited to 'evutil_time.c')
-rw-r--r--evutil_time.c58
1 files changed, 50 insertions, 8 deletions
diff --git a/evutil_time.c b/evutil_time.c
index c3a23589..c3272182 100644
--- a/evutil_time.c
+++ b/evutil_time.c
@@ -65,6 +65,9 @@
#ifndef EVENT__HAVE_GETTIMEOFDAY
/* No gettimeofday; this must be windows. */
+
+typedef void (WINAPI *GetSystemTimePreciseAsFileTime_fn_t) (LPFILETIME);
+
int
evutil_gettimeofday(struct timeval *tv, struct timezone *tz)
{
@@ -90,7 +93,22 @@ evutil_gettimeofday(struct timeval *tv, struct timezone *tz)
if (tv == NULL)
return -1;
- GetSystemTimeAsFileTime(&ft.ft_ft);
+ static GetSystemTimePreciseAsFileTime_fn_t GetSystemTimePreciseAsFileTime_fn = NULL;
+ static int check_precise = 1;
+
+ if (EVUTIL_UNLIKELY(check_precise)) {
+ HMODULE h = evutil_load_windows_system_library_(TEXT("kernel32.dll"));
+ if (h != NULL)
+ GetSystemTimePreciseAsFileTime_fn =
+ (GetSystemTimePreciseAsFileTime_fn_t)
+ GetProcAddress(h, "GetSystemTimePreciseAsFileTime");
+ check_precise = 0;
+ }
+
+ if (GetSystemTimePreciseAsFileTime_fn != NULL)
+ GetSystemTimePreciseAsFileTime_fn(&ft.ft_ft);
+ else
+ GetSystemTimeAsFileTime(&ft.ft_ft);
if (EVUTIL_UNLIKELY(ft.ft_64 < EPOCH_BIAS)) {
/* Time before the unix epoch. */
@@ -126,8 +144,22 @@ evutil_usleep_(const struct timeval *tv)
return;
#if defined(_WIN32)
{
- long msec = evutil_tv_to_msec_(tv);
- Sleep((DWORD)msec);
+ __int64 usec;
+ LARGE_INTEGER li;
+ HANDLE timer;
+
+ usec = tv->tv_sec * 1000000LL + tv->tv_usec;
+ if (!usec)
+ return;
+
+ li.QuadPart = -10LL * usec;
+ timer = CreateWaitableTimer(NULL, TRUE, NULL);
+ if (!timer)
+ return;
+
+ SetWaitableTimer(timer, &li, 0, NULL, NULL, 0);
+ WaitForSingleObject(timer, INFINITE);
+ CloseHandle(timer);
}
#elif defined(EVENT__HAVE_NANOSLEEP)
{
@@ -158,18 +190,28 @@ evutil_date_rfc1123(char *date, const size_t datelen, const struct tm *tm)
time_t t = time(NULL);
-#ifndef _WIN32
+#if defined(EVENT__HAVE__GMTIME64_S) || !defined(_WIN32)
struct tm sys;
#endif
/* If `tm` is null, set system's current time. */
if (tm == NULL) {
-#ifdef _WIN32
- /** TODO: detect _gmtime64()/_gmtime64_s() */
- tm = gmtime(&t);
-#else
+#if !defined(_WIN32)
gmtime_r(&t, &sys);
tm = &sys;
+ /** detect _gmtime64()/_gmtime64_s() */
+#elif defined(EVENT__HAVE__GMTIME64_S)
+ errno_t err;
+ err = _gmtime64_s(&sys, &t);
+ if (err) {
+ event_errx(1, "Invalid argument to _gmtime64_s");
+ } else {
+ tm = &sys;
+ }
+#elif defined(EVENT__HAVE__GMTIME64)
+ tm = _gmtime64(&t);
+#else
+ tm = gmtime(&t);
#endif
}