Skip to content

Commit

Permalink
deps: V8: cherry-pick 1a782f6543ae
Browse files Browse the repository at this point in the history
Original commit message:

    [base] add build flag to use MADV_DONTFORK

    Embedders like Node.js and Electron expose fork(2)/execve(2) to their
    users. Unfortunately when the V8 heap is very large, these APIs become
    rather slow on Linux, due to the kernel needing to do all the
    bookkeeping for the forked process (in clone's dup_mmap and execve's
    exec_mmap). Of course, this is useless because the forked child thread
    will never actually need to access the V8 heap.

    Add a new build flag v8_enable_private_mapping_fork_optimization which
    marks all pages allocated by OS::Allocate as MADV_DONTFORK. This
    improves the performance of Node.js's fork/execve combination by 10x on
    a 600 MB heap.

    Fixed: v8:7381
    Change-Id: Ib649f774d4a932b41886313ce89acc369923699d
    Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/4602858
    Commit-Queue: Michael Lippautz <mlippautz@chromium.org>
    Reviewed-by: Michael Lippautz <mlippautz@chromium.org>
    Cr-Commit-Position: refs/heads/main@{#88447}

Refs: v8/v8@1a782f6
PR-URL: #48523
Backport-PR-URL: #50098
Fixes: #25382
Fixes: #14917
Refs: nodejs/performance#93
Refs: nodejs/performance#89
Reviewed-By: Yagiz Nizipli <yagiz@nizipli.com>
Reviewed-By: Juan José Arboleda <soyjuanarbol@gmail.com>
Reviewed-By: Debadree Chatterjee <debadree333@gmail.com>
  • Loading branch information
kvakil authored and targos committed Nov 26, 2023
1 parent a98addb commit 747fbb4
Show file tree
Hide file tree
Showing 2 changed files with 20 additions and 0 deletions.
14 changes: 14 additions & 0 deletions deps/v8/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,17 @@ declare_args() {
# Sets -dENABLE_HUGEPAGE
v8_enable_hugepage = false

# Sets -dV8_ENABLE_PRIVATE_MAPPING_FORK_OPTIMIZATION.
#
# This flag speeds up the performance of fork/execve on Linux systems for
# embedders which use it (like Node.js). It works by marking the pages that
# V8 allocates as MADV_DONTFORK. Without MADV_DONTFORK, the Linux kernel
# spends a long time manipulating page mappings on fork and exec which the
# child process doesn't generally need to access.
#
# See v8:7381 for more details.
v8_enable_private_mapping_fork_optimization = false

# Sets -dENABLE_HANDLE_ZAPPING.
v8_enable_handle_zapping = !is_on_release_branch || is_debug

Expand Down Expand Up @@ -862,6 +873,9 @@ config("features") {
if (v8_enable_hugepage) {
defines += [ "ENABLE_HUGEPAGE" ]
}
if (v8_enable_private_mapping_fork_optimization) {
defines += [ "V8_ENABLE_PRIVATE_MAPPING_FORK_OPTIMIZATION" ]
}
if (v8_enable_object_print) {
defines += [ "OBJECT_PRINT" ]
}
Expand Down
6 changes: 6 additions & 0 deletions deps/v8/src/base/platform/platform-posix.cc
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,12 @@ void* Allocate(void* hint, size_t size, OS::MemoryPermission access,
int flags = GetFlagsForMemoryPermission(access, page_type);
void* result = mmap(hint, size, prot, flags, kMmapFd, kMmapFdOffset);
if (result == MAP_FAILED) return nullptr;

#if V8_ENABLE_PRIVATE_MAPPING_FORK_OPTIMIZATION
// This is advisory, so we ignore errors.
madvise(result, size, MADV_DONTFORK);
#endif

#if ENABLE_HUGEPAGE
if (result != nullptr && size >= kHugePageSize) {
const uintptr_t huge_start =
Expand Down

0 comments on commit 747fbb4

Please sign in to comment.