diff --git a/src/unix/darwin.c b/src/unix/darwin.c index 654aba26b..4f53ad1fc 100644 --- a/src/unix/darwin.c +++ b/src/unix/darwin.c @@ -25,6 +25,7 @@ #include #include +#include #include #include #include /* _NSGetExecutablePath */ @@ -32,6 +33,10 @@ #include #include /* sysconf */ +static uv_once_t once = UV_ONCE_INIT; +static uint64_t (*time_func)(void); +static mach_timebase_info_data_t timebase; + int uv__platform_loop_init(uv_loop_t* loop) { loop->cf_state = NULL; @@ -48,15 +53,19 @@ void uv__platform_loop_delete(uv_loop_t* loop) { } -uint64_t uv__hrtime(uv_clocktype_t type) { - static mach_timebase_info_data_t info; - - if ((ACCESS_ONCE(uint32_t, info.numer) == 0 || - ACCESS_ONCE(uint32_t, info.denom) == 0) && - mach_timebase_info(&info) != KERN_SUCCESS) +static void uv__hrtime_init_once(void) { + if (KERN_SUCCESS != mach_timebase_info(&timebase)) abort(); - return mach_absolute_time() * info.numer / info.denom; + time_func = (uint64_t (*)(void)) dlsym(RTLD_DEFAULT, "mach_continuous_time"); + if (time_func == NULL) + time_func = mach_absolute_time; +} + + +uint64_t uv__hrtime(uv_clocktype_t type) { + uv_once(&once, uv__hrtime_init_once); + return time_func() * timebase.numer / timebase.denom; }