Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
chore: backport EPROTOTYPE fixes from libuv (#32944)
* chore: backport EPROTOTYPE fixes from libuv This commit backports three commits from libuv's 1.x branch to fix issues with CPU going to 100% on macOS when EPROTOTYPE is returned. See: libuv/libuv@abb109f See: libuv/libuv@3a7b955 See: libuv/libuv@de24da8 * Update .patches Co-authored-by: Fedor Indutny <fedor@indutny.com> Co-authored-by: Shelley Vohr <shelley.vohr@gmail.com>
- Loading branch information
1 parent
7ab8555
commit 7c9b609
Showing
4 changed files
with
137 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
25 changes: 25 additions & 0 deletions
25
patches/node/darwin_bump_minimum_supported_version_to_10_15_3406.patch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 | ||
From: Ben Noordhuis <info@bnoordhuis.nl> | ||
Date: Tue, 8 Feb 2022 14:18:29 +0100 | ||
Subject: darwin: bump minimum supported version to 10.15 (#3406) | ||
|
||
We can't realistically claim to support 10.7 or any version that Apple | ||
no longer supports so let's bump the baseline to something more | ||
realistic. | ||
|
||
Refs: https://github.com/libuv/libuv/pull/482 | ||
Refs: https://github.com/libuv/libuv/pull/3405 | ||
|
||
diff --git a/deps/uv/SUPPORTED_PLATFORMS.md b/deps/uv/SUPPORTED_PLATFORMS.md | ||
index 30e0ea617a6fcaa5b4b7c7c5b117652e61f367d3..dc57dfb12dc7ddf8d29308ac44f46084a933d5ca 100644 | ||
--- a/deps/uv/SUPPORTED_PLATFORMS.md | ||
+++ b/deps/uv/SUPPORTED_PLATFORMS.md | ||
@@ -3,7 +3,7 @@ | ||
| System | Support type | Supported versions | Notes | | ||
|---|---|---|---| | ||
| GNU/Linux | Tier 1 | Linux >= 2.6.32 with glibc >= 2.12 | | | ||
-| macOS | Tier 1 | macOS >= 10.7 | | | ||
+| macOS | Tier 1 | macOS >= 10.15 | Current and previous macOS release | | ||
| Windows | Tier 1 | >= Windows 8 | VS 2015 and later are supported | | ||
| FreeBSD | Tier 1 | >= 10 | | | ||
| AIX | Tier 2 | >= 6 | Maintainers: @libuv/aix | |
65 changes: 65 additions & 0 deletions
65
patches/node/darwin_remove_eprototype_error_workaround_3405.patch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 | ||
From: Ben Noordhuis <info@bnoordhuis.nl> | ||
Date: Sun, 9 Jan 2022 12:20:15 +0100 | ||
Subject: darwin: remove EPROTOTYPE error workaround (#3405) | ||
|
||
It's been reported in the past that OS X 10.10, because of a race | ||
condition in the XNU kernel, sometimes returns a transient EPROTOTYPE | ||
error when trying to write to a socket. Libuv handles that by retrying | ||
the operation until it succeeds or fails with a different error. | ||
|
||
Recently it's been reported that current versions of the operating | ||
system formerly known as OS X fail permanently with EPROTOTYPE under | ||
certain conditions, resulting in an infinite loop. | ||
|
||
Because Apple isn't exactly forthcoming with bug fixes or even details, | ||
I'm opting to simply remove the workaround and have the error bubble up. | ||
|
||
Refs: https://github.com/libuv/libuv/pull/482 | ||
|
||
diff --git a/deps/uv/src/unix/stream.c b/deps/uv/src/unix/stream.c | ||
index bc64fe8f44b26d9f4c0d4d0d282b65cdf11a531b..1af448e7691392c3f7794eed1905d9132394e207 100644 | ||
--- a/deps/uv/src/unix/stream.c | ||
+++ b/deps/uv/src/unix/stream.c | ||
@@ -58,20 +58,6 @@ struct uv__stream_select_s { | ||
fd_set* swrite; | ||
size_t swrite_sz; | ||
}; | ||
- | ||
-/* Due to a possible kernel bug at least in OS X 10.10 "Yosemite", | ||
- * EPROTOTYPE can be returned while trying to write to a socket that is | ||
- * shutting down. If we retry the write, we should get the expected EPIPE | ||
- * instead. | ||
- */ | ||
-# define RETRY_ON_WRITE_ERROR(errno) (errno == EINTR || errno == EPROTOTYPE) | ||
-# define IS_TRANSIENT_WRITE_ERROR(errno, send_handle) \ | ||
- (errno == EAGAIN || errno == EWOULDBLOCK || errno == ENOBUFS || \ | ||
- (errno == EMSGSIZE && send_handle != NULL)) | ||
-#else | ||
-# define RETRY_ON_WRITE_ERROR(errno) (errno == EINTR) | ||
-# define IS_TRANSIENT_WRITE_ERROR(errno, send_handle) \ | ||
- (errno == EAGAIN || errno == EWOULDBLOCK || errno == ENOBUFS) | ||
#endif /* defined(__APPLE__) */ | ||
|
||
static void uv__stream_connect(uv_stream_t*); | ||
@@ -866,17 +852,17 @@ static int uv__try_write(uv_stream_t* stream, | ||
|
||
do | ||
n = sendmsg(uv__stream_fd(stream), &msg, 0); | ||
- while (n == -1 && RETRY_ON_WRITE_ERROR(errno)); | ||
+ while (n == -1 && errno == EINTR); | ||
} else { | ||
do | ||
n = uv__writev(uv__stream_fd(stream), iov, iovcnt); | ||
- while (n == -1 && RETRY_ON_WRITE_ERROR(errno)); | ||
+ while (n == -1 && errno == EINTR); | ||
} | ||
|
||
if (n >= 0) | ||
return n; | ||
|
||
- if (IS_TRANSIENT_WRITE_ERROR(errno, send_handle)) | ||
+ if (errno == EAGAIN || errno == EWOULDBLOCK || errno == ENOBUFS) | ||
return UV_EAGAIN; | ||
|
||
return UV__ERR(errno); |
44 changes: 44 additions & 0 deletions
44
patches/node/darwin_translate_eprototype_to_econnreset_3413.patch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 | ||
From: Ben Noordhuis <info@bnoordhuis.nl> | ||
Date: Wed, 12 Jan 2022 16:11:43 +0100 | ||
Subject: darwin: translate EPROTOTYPE to ECONNRESET (#3413) | ||
|
||
macOS versions 10.10 and 10.15 - and presumbaly 10.11 to 10.14, too - | ||
have a bug where a race condition causes the kernel to return EPROTOTYPE | ||
because the socket isn't fully constructed. | ||
|
||
It's probably the result of the peer closing the connection and that is | ||
why libuv translates it to ECONNRESET. | ||
|
||
Previously, libuv retried until the EPROTOTYPE error went away but some | ||
VPN software causes the same behavior except the error is permanent, not | ||
transient, turning the retry mechanism into an infinite loop. | ||
|
||
Refs: https://github.com/libuv/libuv/pull/482 | ||
Refs: https://github.com/libuv/libuv/pull/3405 | ||
|
||
diff --git a/deps/uv/src/unix/stream.c b/deps/uv/src/unix/stream.c | ||
index 1af448e7691392c3f7794eed1905d9132394e207..9d22debf2bf5bd5912ade152e55a85ad652e3819 100644 | ||
--- a/deps/uv/src/unix/stream.c | ||
+++ b/deps/uv/src/unix/stream.c | ||
@@ -865,6 +865,20 @@ static int uv__try_write(uv_stream_t* stream, | ||
if (errno == EAGAIN || errno == EWOULDBLOCK || errno == ENOBUFS) | ||
return UV_EAGAIN; | ||
|
||
+#ifdef __APPLE__ | ||
+ /* macOS versions 10.10 and 10.15 - and presumbaly 10.11 to 10.14, too - | ||
+ * have a bug where a race condition causes the kernel to return EPROTOTYPE | ||
+ * because the socket isn't fully constructed. It's probably the result of | ||
+ * the peer closing the connection and that is why libuv translates it to | ||
+ * ECONNRESET. Previously, libuv retried until the EPROTOTYPE error went | ||
+ * away but some VPN software causes the same behavior except the error is | ||
+ * permanent, not transient, turning the retry mechanism into an infinite | ||
+ * loop. See https://github.com/libuv/libuv/pull/482. | ||
+ */ | ||
+ if (errno == EPROTOTYPE) | ||
+ return UV_ECONNRESET; | ||
+#endif /* __APPLE__ */ | ||
+ | ||
return UV__ERR(errno); | ||
} | ||
|