Browse Source

fix: intermittent 100% CPU usage on macOS (#24414)

Co-authored-by: Shelley Vohr <[email protected]>
trop[bot] 4 years ago
parent
commit
93a9512ce1

+ 1 - 0
patches/node/.patches

@@ -50,3 +50,4 @@ tools_update_certdata_txt_to_nss_3_47.patch
 crypto_update_root_certificates_to_nss_3_47.patch
 tools_update_certdata_txt_to_nss_3_53.patch
 crypto_update_root_certificates_to_nss_3_53.patch
+darwin_work_around_clock_jumping_back_in_time.patch

+ 64 - 0
patches/node/darwin_work_around_clock_jumping_back_in_time.patch

@@ -0,0 +1,64 @@
+From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
+From: Ben Noordhuis <[email protected]>
+Date: Wed, 1 Jul 2020 10:32:57 +0200
+Subject: darwin: work around clock jumping back in time
+
+It was reported that mach_absolute_time() can jump backward in time when
+the machine is suspended. Use mach_continuous_time() when available to
+work around that (macOS 10.12 and up.)
+
+Fixes: https://github.com/libuv/libuv/issues/2891
+PR-URL: https://github.com/libuv/libuv/pull/2894
+Reviewed-By: Phil Willoughby <[email protected]>
+Reviewed-By: Santiago Gimeno <[email protected]>
+
+diff --git a/deps/uv/src/unix/darwin.c b/deps/uv/src/unix/darwin.c
+index 5cf03aea0b405402b88494f3840bcfe606551b53..030ed1adb23966f89877135dd0bd20629248f007 100644
+--- a/deps/uv/src/unix/darwin.c
++++ b/deps/uv/src/unix/darwin.c
+@@ -25,6 +25,7 @@
+ #include <stdint.h>
+ #include <errno.h>
+ 
++#include <dlfcn.h>
+ #include <mach/mach.h>
+ #include <mach/mach_time.h>
+ #include <mach-o/dyld.h> /* _NSGetExecutablePath */
+@@ -32,6 +33,10 @@
+ #include <sys/sysctl.h>
+ #include <unistd.h>  /* 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;
+ }
+ 
+