From c95409a11a931b0340267a0af36f76a5c0569cd9 Mon Sep 17 00:00:00 2001 From: Ted Campbell Date: Tue, 3 Aug 2021 21:50:33 +0000 Subject: [PATCH] Bug 1723601 - Fix OOM during self-hosting delazification. r=arai The `CompilationStencil::delazifySelfHostedFunction` code erroneously delazified the outer script before its full set of inner functions. This can result in a nullptr deref under some conditions. Instead, instantaiate inner functions first which is also consistent with the normal Stencil instantiation flow. Differential Revision: https://phabricator.services.mozilla.com/D121637 --- js/src/frontend/Stencil.cpp | 15 +++++++++++++-- .../jit-test/tests/self-hosting/oom-delazify.js | 5 +++++ 2 files changed, 18 insertions(+), 2 deletions(-) create mode 100644 js/src/jit-test/tests/self-hosting/oom-delazify.js diff --git a/js/src/frontend/Stencil.cpp b/js/src/frontend/Stencil.cpp index 886c9b1ee040..13bd1f464841 100644 --- a/js/src/frontend/Stencil.cpp +++ b/js/src/frontend/Stencil.cpp @@ -1744,14 +1744,25 @@ bool CompilationStencil::delazifySelfHostedFunction( gcOutput.get().scopes.infallibleAppend(scope); } - // Phase 4, 5: Instantiate BaseScripts. - for (size_t i = range.start; i < range.limit; i++) { + // Phase 4: Instantiate (inner) BaseScripts. + ScriptIndex innerStart(range.start + 1); + for (size_t i = innerStart; i < range.limit; i++) { if (!JSScript::fromStencil(cx, atomCache, *this, gcOutput.get(), ScriptIndex(i))) { return false; } } + // Phase 5: Finish top-level handling + // NOTE: We do not have a `CompilationInput` handy here, so avoid using the + // `InstantiateTopLevel` helper and directly create the JSScript. Our + // caller also handles the `AllowRelazify` flag for us since self-hosted + // delazification is a special case. + if (!JSScript::fromStencil(cx, atomCache, *this, gcOutput.get(), + range.start)) { + return false; + } + // Phase 6: Update lazy scripts. // NOTE: Self-hosting is always fully parsed so there is nothing to do here. diff --git a/js/src/jit-test/tests/self-hosting/oom-delazify.js b/js/src/jit-test/tests/self-hosting/oom-delazify.js new file mode 100644 index 000000000000..2c9bfc71e9b9 --- /dev/null +++ b/js/src/jit-test/tests/self-hosting/oom-delazify.js @@ -0,0 +1,5 @@ +// |jit-test| --no-blinterp; skip-if: !('oomTest' in this) + +// Disable the JITs to make oomTest more reliable + +oomTest(() => Object.bind())