зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1691505 - Unify CompilationStencil and CompilationStencilSet types. r=arai
Introduce a `StencilDelazificationSet` type to hold the vector of delazification stencils. This is held as an optional UniquePtr that hangs off the `CompilationStencil`. Combine the different variants of prepareForInstantiation, instantiateStencils, etc by making `gcOutputForDelazifcation` optional. If there are delazifications present, we assert there is output. NOTE: This rewrites the `prepareForInstantiation` logic because the existing code seemed to mix up gcOutput and gcOutputForDelazifcation. Differential Revision: https://phabricator.services.mozilla.com/D104460
This commit is contained in:
Родитель
546c109ff0
Коммит
bd660428af
|
@ -46,7 +46,7 @@
|
|||
# include "frontend/TokenStream.h"
|
||||
#endif
|
||||
#include "frontend/BytecodeCompilation.h"
|
||||
#include "frontend/CompilationStencil.h" // frontend::CompilationStencil, frontend::CompilationStencilSet
|
||||
#include "frontend/CompilationStencil.h" // frontend::CompilationStencil
|
||||
#include "gc/Allocator.h"
|
||||
#include "gc/Zone.h"
|
||||
#include "jit/BaselineJIT.h"
|
||||
|
@ -5038,21 +5038,21 @@ static bool EvalStencilXDR(JSContext* cx, uint32_t argc, Value* vp) {
|
|||
const char* filename = "compileStencilXDR-DATA.js";
|
||||
uint32_t lineno = 1;
|
||||
|
||||
/* Prepare the CompilationStencilSet for decoding. */
|
||||
/* Prepare the CompilationStencil for decoding. */
|
||||
CompileOptions options(cx);
|
||||
options.setFileAndLine(filename, lineno);
|
||||
options.setForceFullParse();
|
||||
|
||||
Rooted<frontend::CompilationStencilSet> stencilSet(
|
||||
cx, frontend::CompilationStencilSet(cx, options));
|
||||
if (!stencilSet.get().input.initForGlobal(cx)) {
|
||||
Rooted<frontend::CompilationStencil> stencil(
|
||||
cx, frontend::CompilationStencil(cx, options));
|
||||
if (!stencil.get().input.initForGlobal(cx)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Deserialize the stencil from XDR. */
|
||||
JS::TranscodeRange xdrRange(src->dataPointer(), src->byteLength().get());
|
||||
bool succeeded = false;
|
||||
if (!stencilSet.get().deserializeStencils(cx, xdrRange, &succeeded)) {
|
||||
if (!stencil.get().deserializeStencils(cx, xdrRange, &succeeded)) {
|
||||
return false;
|
||||
}
|
||||
if (!succeeded) {
|
||||
|
@ -5063,8 +5063,8 @@ static bool EvalStencilXDR(JSContext* cx, uint32_t argc, Value* vp) {
|
|||
/* Instantiate the stencil. */
|
||||
Rooted<frontend::CompilationGCOutput> output(cx);
|
||||
Rooted<frontend::CompilationGCOutput> outputForDelazification(cx);
|
||||
if (!stencilSet.get().instantiateStencils(cx, output.get(),
|
||||
outputForDelazification.get())) {
|
||||
if (!frontend::CompilationStencil::instantiateStencils(
|
||||
cx, stencil.get(), output.get(), outputForDelazification.address())) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
|
@ -17,8 +17,8 @@
|
|||
|
||||
#include "jstypes.h" // JS_PUBLIC_API
|
||||
|
||||
#include "frontend/CompilationStencil.h" // CompilationStencil, CompilationStencilSet, CompilationGCOutput
|
||||
#include "frontend/ParseContext.h" // js::frontend::UsedNameTracker
|
||||
#include "frontend/CompilationStencil.h" // CompilationStencil, CompilationGCOutput
|
||||
#include "frontend/ParseContext.h" // js::frontend::UsedNameTracker
|
||||
#include "frontend/SharedContext.h" // js::frontend::Directives, js::frontend::{,Eval,Global}SharedContext
|
||||
#include "js/CompileOptions.h" // JS::ReadOnlyCompileOptions
|
||||
#include "js/RootingAPI.h" // JS::{,Mutable}Handle, JS::Rooted
|
||||
|
@ -72,20 +72,13 @@ extern UniquePtr<CompilationStencil> CompileGlobalScriptToStencil(
|
|||
// Part of InstantiateStencils can be done by calling PrepareForInstantiate.
|
||||
// PrepareForInstantiate is GC-free operation that can be performed
|
||||
// off-main-thread without parse global.
|
||||
extern bool PrepareForInstantiate(JSContext* cx, CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput);
|
||||
extern bool PrepareForInstantiate(
|
||||
JSContext* cx, CompilationStencilSet& stencilSet,
|
||||
CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification);
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification = nullptr);
|
||||
|
||||
extern bool InstantiateStencils(JSContext* cx, CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput);
|
||||
|
||||
extern bool InstantiateStencils(JSContext* cx,
|
||||
CompilationStencilSet& stencilSet,
|
||||
CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification);
|
||||
extern bool InstantiateStencils(
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification = nullptr);
|
||||
|
||||
extern JSScript* CompileGlobalScript(JSContext* cx,
|
||||
const JS::ReadOnlyCompileOptions& options,
|
||||
|
|
|
@ -305,13 +305,15 @@ UniquePtr<CompilationStencil> frontend::CompileGlobalScriptToStencil(
|
|||
return CompileGlobalScriptToStencilImpl(cx, options, srcBuf, scopeKind);
|
||||
}
|
||||
|
||||
bool frontend::InstantiateStencils(JSContext* cx, CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput) {
|
||||
bool frontend::InstantiateStencils(
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification) {
|
||||
{
|
||||
AutoGeckoProfilerEntry pseudoFrame(cx, "stencil instantiate",
|
||||
JS::ProfilingCategoryPair::JS_Parsing);
|
||||
|
||||
if (!CompilationStencil::instantiateStencils(cx, stencil, gcOutput)) {
|
||||
if (!CompilationStencil::instantiateStencils(cx, stencil, gcOutput,
|
||||
gcOutputForDelazification)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@ -330,53 +332,14 @@ bool frontend::InstantiateStencils(JSContext* cx, CompilationStencil& stencil,
|
|||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool frontend::InstantiateStencils(
|
||||
JSContext* cx, CompilationStencilSet& stencilSet,
|
||||
CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification_) {
|
||||
{
|
||||
AutoGeckoProfilerEntry pseudoFrame(cx, "stencil instantiate",
|
||||
JS::ProfilingCategoryPair::JS_Parsing);
|
||||
|
||||
if (!stencilSet.instantiateStencils(cx, gcOutput,
|
||||
gcOutputForDelazification_)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Enqueue an off-thread source compression task after finishing parsing.
|
||||
if (!cx->isHelperThreadContext()) {
|
||||
if (!stencilSet.input.source()->tryCompressOffThread(cx)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
Rooted<JSScript*> script(cx, gcOutput.script);
|
||||
if (!stencilSet.input.options.hideScriptFromDebugger) {
|
||||
DebugAPI::onNewScript(cx, script);
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool frontend::PrepareForInstantiate(JSContext* cx, CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput) {
|
||||
AutoGeckoProfilerEntry pseudoFrame(cx, "stencil instantiate",
|
||||
JS::ProfilingCategoryPair::JS_Parsing);
|
||||
|
||||
return CompilationStencil::prepareForInstantiate(cx, stencil, gcOutput);
|
||||
}
|
||||
|
||||
bool frontend::PrepareForInstantiate(
|
||||
JSContext* cx, CompilationStencilSet& stencilSet,
|
||||
CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification_) {
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification) {
|
||||
AutoGeckoProfilerEntry pseudoFrame(cx, "stencil instantiate",
|
||||
JS::ProfilingCategoryPair::JS_Parsing);
|
||||
|
||||
return stencilSet.prepareForInstantiate(cx, gcOutput,
|
||||
gcOutputForDelazification_);
|
||||
return CompilationStencil::prepareForInstantiate(cx, stencil, gcOutput,
|
||||
gcOutputForDelazification);
|
||||
}
|
||||
|
||||
template <typename Unit>
|
||||
|
|
|
@ -48,6 +48,7 @@ namespace frontend {
|
|||
struct CompilationInput;
|
||||
struct CompilationStencil;
|
||||
struct CompilationGCOutput;
|
||||
struct StencilDelazificationSet;
|
||||
class ScriptStencilIterable;
|
||||
|
||||
// ScopeContext hold information derivied from the scope and environment chains
|
||||
|
@ -177,7 +178,6 @@ struct CompilationAtomCache {
|
|||
bool hasAtomAt(ParserAtomIndex index) const;
|
||||
bool setAtomAt(JSContext* cx, ParserAtomIndex index, JSAtom* atom);
|
||||
bool allocate(JSContext* cx, size_t length);
|
||||
bool extendIfNecessary(JSContext* cx, size_t length);
|
||||
|
||||
void stealBuffer(AtomCacheVector& atoms);
|
||||
void releaseBuffer(AtomCacheVector& atoms);
|
||||
|
@ -560,6 +560,10 @@ struct CompilationStencil : public BaseCompilationStencil {
|
|||
// therefore only generated during initial parse.
|
||||
StencilAsmJSContainer asmJS;
|
||||
|
||||
// A series of delazifications may also be associated with this stencil. They
|
||||
// contain bytecode, scopes, etc generated by delazification.
|
||||
UniquePtr<StencilDelazificationSet> delazificationSet;
|
||||
|
||||
// Set to true once prepareForInstantiate is called.
|
||||
// NOTE: This field isn't XDR-encoded.
|
||||
bool preparationIsPerformed = false;
|
||||
|
@ -570,24 +574,23 @@ struct CompilationStencil : public BaseCompilationStencil {
|
|||
CompilationStencil(JSContext* cx, const JS::ReadOnlyCompileOptions& options)
|
||||
: alloc(LifoAllocChunkSize), input(options) {}
|
||||
|
||||
static MOZ_MUST_USE bool prepareInputAndStencilForInstantiate(
|
||||
JSContext* cx, CompilationInput& input, BaseCompilationStencil& stencil);
|
||||
static MOZ_MUST_USE bool prepareGCOutputForInstantiate(
|
||||
JSContext* cx, BaseCompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput);
|
||||
|
||||
static MOZ_MUST_USE bool prepareForInstantiate(JSContext* cx,
|
||||
CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput);
|
||||
static MOZ_MUST_USE bool instantiateStencils(JSContext* cx,
|
||||
CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput);
|
||||
static MOZ_MUST_USE bool instantiateStencilsAfterPreparation(
|
||||
static MOZ_MUST_USE bool instantiateBaseStencilAfterPreparation(
|
||||
JSContext* cx, CompilationInput& input,
|
||||
const BaseCompilationStencil& stencil, CompilationGCOutput& gcOutput);
|
||||
|
||||
static MOZ_MUST_USE bool prepareForInstantiate(
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification = nullptr);
|
||||
|
||||
static MOZ_MUST_USE bool instantiateStencils(
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification = nullptr);
|
||||
|
||||
MOZ_MUST_USE bool serializeStencils(JSContext* cx, JS::TranscodeBuffer& buf,
|
||||
bool* succeededOut = nullptr);
|
||||
MOZ_MUST_USE bool deserializeStencils(JSContext* cx,
|
||||
const JS::TranscodeRange& range,
|
||||
bool* succeededOut = nullptr);
|
||||
|
||||
// Move constructor is necessary to use Rooted, but must be explicit in
|
||||
// order to steal the LifoAlloc data
|
||||
|
@ -648,44 +651,18 @@ inline const CompilationStencil& BaseCompilationStencil::asCompilationStencil()
|
|||
return *static_cast<const CompilationStencil*>(this);
|
||||
}
|
||||
|
||||
// A set of stencils, for XDR purpose.
|
||||
// This contains the initial compilation, and a vector of delazification.
|
||||
struct CompilationStencilSet : public CompilationStencil {
|
||||
private:
|
||||
// A set of stencils generated by delazifying functions. This should only be
|
||||
// used by a CompilationStencil that owns this. This is primarily used for
|
||||
// bytecode caching with XDR.
|
||||
struct StencilDelazificationSet {
|
||||
using ScriptIndexVector = Vector<ScriptIndex, 0, js::SystemAllocPolicy>;
|
||||
|
||||
MOZ_MUST_USE bool buildDelazificationIndices(JSContext* cx);
|
||||
|
||||
public:
|
||||
Vector<BaseCompilationStencil, 0, js::SystemAllocPolicy> delazifications;
|
||||
ScriptIndexVector delazificationIndices;
|
||||
CompilationAtomCache::AtomCacheVector delazificationAtomCache;
|
||||
|
||||
CompilationStencilSet(JSContext* cx,
|
||||
const JS::ReadOnlyCompileOptions& options)
|
||||
: CompilationStencil(cx, options) {}
|
||||
|
||||
// Move constructor is necessary to use Rooted.
|
||||
CompilationStencilSet(CompilationStencilSet&& other) = default;
|
||||
|
||||
// To avoid any misuses, make sure this is neither copyable or assignable.
|
||||
CompilationStencilSet(const CompilationStencilSet&) = delete;
|
||||
CompilationStencilSet& operator=(const CompilationStencilSet&) = delete;
|
||||
CompilationStencilSet& operator=(CompilationStencilSet&&) = delete;
|
||||
|
||||
MOZ_MUST_USE bool prepareForInstantiate(
|
||||
JSContext* cx, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification);
|
||||
MOZ_MUST_USE bool instantiateStencils(
|
||||
JSContext* cx, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification);
|
||||
MOZ_MUST_USE bool instantiateStencilsAfterPreparation(
|
||||
JSContext* cx, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification);
|
||||
|
||||
MOZ_MUST_USE bool deserializeStencils(JSContext* cx,
|
||||
const JS::TranscodeRange& range,
|
||||
bool* succeededOut);
|
||||
MOZ_MUST_USE bool buildDelazificationIndices(
|
||||
JSContext* cx, const CompilationStencil& stencil);
|
||||
};
|
||||
|
||||
// The output of GC allocation from stencil.
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
#include "frontend/AbstractScopePtr.h" // ScopeIndex
|
||||
#include "frontend/BytecodeCompilation.h" // CanLazilyParse
|
||||
#include "frontend/BytecodeSection.h" // EmitScriptThingsVector
|
||||
#include "frontend/CompilationStencil.h" // CompilationStencil, CompilationStencilSet, CompilationGCOutput
|
||||
#include "frontend/CompilationStencil.h" // CompilationStencil, CompilationGCOutput
|
||||
#include "frontend/SharedContext.h"
|
||||
#include "gc/AllocKind.h" // gc::AllocKind
|
||||
#include "gc/Rooting.h" // RootedAtom
|
||||
|
@ -1243,21 +1243,71 @@ static void FunctionsFromExistingLazy(CompilationInput& input,
|
|||
}
|
||||
|
||||
/* static */
|
||||
bool CompilationStencil::instantiateStencils(JSContext* cx,
|
||||
CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput) {
|
||||
bool CompilationStencil::instantiateStencils(
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification) {
|
||||
if (!stencil.preparationIsPerformed) {
|
||||
if (!prepareForInstantiate(cx, stencil, gcOutput)) {
|
||||
if (!prepareForInstantiate(cx, stencil, gcOutput,
|
||||
gcOutputForDelazification)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return instantiateStencilsAfterPreparation(cx, stencil.input, stencil,
|
||||
gcOutput);
|
||||
if (!instantiateBaseStencilAfterPreparation(cx, stencil.input, stencil,
|
||||
gcOutput)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (stencil.delazificationSet) {
|
||||
MOZ_ASSERT(gcOutputForDelazification);
|
||||
|
||||
CompilationAtomCache::AtomCacheVector reusableAtomCache;
|
||||
stencil.input.atomCache.releaseBuffer(reusableAtomCache);
|
||||
|
||||
size_t numDelazifications =
|
||||
stencil.delazificationSet->delazifications.length();
|
||||
for (size_t i = 0; i < numDelazifications; i++) {
|
||||
auto& delazification = stencil.delazificationSet->delazifications[i];
|
||||
auto index = stencil.delazificationSet->delazificationIndices[i];
|
||||
|
||||
JSFunction* fun = gcOutput.functions[index];
|
||||
MOZ_ASSERT(fun);
|
||||
|
||||
BaseScript* lazy = fun->baseScript();
|
||||
MOZ_ASSERT(!lazy->hasBytecode());
|
||||
|
||||
if (!lazy->isReadyForDelazification()) {
|
||||
MOZ_ASSERT(false, "Delazification target is not ready. Bad XDR?");
|
||||
continue;
|
||||
}
|
||||
|
||||
Rooted<CompilationInput> delazificationInput(
|
||||
cx, CompilationInput(stencil.input.options));
|
||||
delazificationInput.get().initFromLazy(lazy);
|
||||
|
||||
delazificationInput.get().atomCache.stealBuffer(reusableAtomCache);
|
||||
|
||||
if (!instantiateBaseStencilAfterPreparation(cx, delazificationInput.get(),
|
||||
delazification,
|
||||
*gcOutputForDelazification)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Destroy elements, without unreserving.
|
||||
gcOutputForDelazification->functions.clear();
|
||||
gcOutputForDelazification->scopes.clear();
|
||||
|
||||
delazificationInput.get().atomCache.releaseBuffer(reusableAtomCache);
|
||||
}
|
||||
|
||||
stencil.input.atomCache.stealBuffer(reusableAtomCache);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/* static */
|
||||
bool CompilationStencil::instantiateStencilsAfterPreparation(
|
||||
bool CompilationStencil::instantiateBaseStencilAfterPreparation(
|
||||
JSContext* cx, CompilationInput& input,
|
||||
const BaseCompilationStencil& stencil, CompilationGCOutput& gcOutput) {
|
||||
// Distinguish between the initial (possibly lazy) compile and any subsequent
|
||||
|
@ -1345,9 +1395,10 @@ bool CompilationStencil::instantiateStencilsAfterPreparation(
|
|||
return true;
|
||||
}
|
||||
|
||||
bool CompilationStencilSet::buildDelazificationIndices(JSContext* cx) {
|
||||
bool StencilDelazificationSet::buildDelazificationIndices(
|
||||
JSContext* cx, const CompilationStencil& stencil) {
|
||||
// Standalone-functions are not supported by XDR.
|
||||
MOZ_ASSERT(!scriptData[0].isFunction());
|
||||
MOZ_ASSERT(!stencil.scriptData[0].isFunction());
|
||||
|
||||
// If no delazifications, we are done.
|
||||
if (delazifications.empty()) {
|
||||
|
@ -1372,8 +1423,9 @@ bool CompilationStencilSet::buildDelazificationIndices(JSContext* cx) {
|
|||
|
||||
MOZ_ASSERT(keyToIndex.count() == delazifications.length());
|
||||
|
||||
for (size_t i = 1; i < scriptData.size(); i++) {
|
||||
auto key = BaseCompilationStencil::toFunctionKey(scriptExtra[i].extent);
|
||||
for (size_t i = 1; i < stencil.scriptData.size(); i++) {
|
||||
auto key =
|
||||
BaseCompilationStencil::toFunctionKey(stencil.scriptExtra[i].extent);
|
||||
auto ptr = keyToIndex.lookup(key);
|
||||
if (!ptr) {
|
||||
continue;
|
||||
|
@ -1384,85 +1436,17 @@ bool CompilationStencilSet::buildDelazificationIndices(JSContext* cx) {
|
|||
return true;
|
||||
}
|
||||
|
||||
bool CompilationStencilSet::instantiateStencils(
|
||||
JSContext* cx, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification) {
|
||||
if (!prepareForInstantiate(cx, gcOutput, gcOutputForDelazification)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return instantiateStencilsAfterPreparation(cx, gcOutput,
|
||||
gcOutputForDelazification);
|
||||
}
|
||||
|
||||
bool CompilationStencilSet::instantiateStencilsAfterPreparation(
|
||||
JSContext* cx, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification) {
|
||||
if (!CompilationStencil::instantiateStencilsAfterPreparation(cx, input, *this,
|
||||
gcOutput)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
CompilationAtomCache::AtomCacheVector reusableAtomCache;
|
||||
input.atomCache.releaseBuffer(reusableAtomCache);
|
||||
|
||||
for (size_t i = 0; i < delazifications.length(); i++) {
|
||||
auto& delazification = delazifications[i];
|
||||
auto index = delazificationIndices[i];
|
||||
|
||||
JSFunction* fun = gcOutput.functions[index];
|
||||
MOZ_ASSERT(fun);
|
||||
|
||||
BaseScript* lazy = fun->baseScript();
|
||||
MOZ_ASSERT(!lazy->hasBytecode());
|
||||
|
||||
if (!lazy->isReadyForDelazification()) {
|
||||
MOZ_ASSERT(false, "Delazification target is not ready. Bad XDR?");
|
||||
continue;
|
||||
}
|
||||
|
||||
Rooted<CompilationInput> delazificationInput(
|
||||
cx, CompilationInput(input.options));
|
||||
delazificationInput.get().initFromLazy(lazy);
|
||||
|
||||
delazificationInput.get().atomCache.stealBuffer(reusableAtomCache);
|
||||
|
||||
if (!CompilationStencil::prepareGCOutputForInstantiate(
|
||||
cx, delazification, gcOutputForDelazification)) {
|
||||
return false;
|
||||
}
|
||||
if (!CompilationStencil::instantiateStencilsAfterPreparation(
|
||||
cx, delazificationInput.get(), delazification,
|
||||
gcOutputForDelazification)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Destroy elements, without unreserving.
|
||||
gcOutputForDelazification.functions.clear();
|
||||
gcOutputForDelazification.scopes.clear();
|
||||
|
||||
delazificationInput.get().atomCache.releaseBuffer(reusableAtomCache);
|
||||
}
|
||||
|
||||
input.atomCache.stealBuffer(reusableAtomCache);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/* static */
|
||||
bool CompilationStencil::prepareInputAndStencilForInstantiate(
|
||||
JSContext* cx, CompilationInput& input, BaseCompilationStencil& stencil) {
|
||||
if (!input.atomCache.allocate(cx, stencil.parserAtomData.size())) {
|
||||
return false;
|
||||
}
|
||||
bool CompilationStencil::prepareForInstantiate(
|
||||
JSContext* cx, CompilationStencil& stencil, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput* gcOutputForDelazification) {
|
||||
stencil.preparationIsPerformed = true;
|
||||
|
||||
return true;
|
||||
}
|
||||
size_t maxParserAtomDataLength = stencil.parserAtomData.size();
|
||||
size_t maxScriptDataLength = 0;
|
||||
size_t maxScopeDataLength = 0;
|
||||
|
||||
/* static */
|
||||
bool CompilationStencil::prepareGCOutputForInstantiate(
|
||||
JSContext* cx, BaseCompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput) {
|
||||
// Reserve the `gcOutput` vectors.
|
||||
if (!gcOutput.functions.reserve(stencil.scriptData.size())) {
|
||||
ReportOutOfMemory(cx);
|
||||
return false;
|
||||
|
@ -1472,65 +1456,38 @@ bool CompilationStencil::prepareGCOutputForInstantiate(
|
|||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
// Reserve the `gcOutputForDelazification` vectors.
|
||||
if (stencil.delazificationSet) {
|
||||
MOZ_ASSERT(gcOutputForDelazification);
|
||||
|
||||
/* static */
|
||||
bool CompilationStencil::prepareForInstantiate(JSContext* cx,
|
||||
CompilationStencil& stencil,
|
||||
CompilationGCOutput& gcOutput) {
|
||||
auto& input = stencil.input;
|
||||
|
||||
if (!prepareInputAndStencilForInstantiate(cx, input, stencil)) {
|
||||
return false;
|
||||
}
|
||||
if (!prepareGCOutputForInstantiate(cx, stencil, gcOutput)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
stencil.preparationIsPerformed = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CompilationStencilSet::prepareForInstantiate(
|
||||
JSContext* cx, CompilationGCOutput& gcOutput,
|
||||
CompilationGCOutput& gcOutputForDelazification) {
|
||||
if (!CompilationStencil::prepareForInstantiate(cx, *this, gcOutput)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
size_t maxScriptDataLength = 0;
|
||||
size_t maxScopeDataLength = 0;
|
||||
size_t maxParserAtomDataLength = 0;
|
||||
for (auto& delazification : delazifications) {
|
||||
if (maxParserAtomDataLength < delazification.parserAtomData.size()) {
|
||||
maxParserAtomDataLength = delazification.parserAtomData.size();
|
||||
for (auto& delazification : stencil.delazificationSet->delazifications) {
|
||||
if (maxParserAtomDataLength < delazification.parserAtomData.size()) {
|
||||
maxParserAtomDataLength = delazification.parserAtomData.size();
|
||||
}
|
||||
if (maxScriptDataLength < delazification.scriptData.size()) {
|
||||
maxScriptDataLength = delazification.scriptData.size();
|
||||
}
|
||||
if (maxScopeDataLength < delazification.scopeData.size()) {
|
||||
maxScopeDataLength = delazification.scopeData.size();
|
||||
}
|
||||
}
|
||||
if (maxScriptDataLength < delazification.scriptData.size()) {
|
||||
maxScriptDataLength = delazification.scriptData.size();
|
||||
|
||||
if (!gcOutputForDelazification->functions.reserve(maxScriptDataLength)) {
|
||||
ReportOutOfMemory(cx);
|
||||
return false;
|
||||
}
|
||||
if (maxScopeDataLength < delazification.scopeData.size()) {
|
||||
maxScopeDataLength = delazification.scopeData.size();
|
||||
if (!gcOutputForDelazification->scopes.reserve(maxScopeDataLength)) {
|
||||
ReportOutOfMemory(cx);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!stencil.delazificationSet->buildDelazificationIndices(cx, stencil)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
if (!input.atomCache.extendIfNecessary(cx, maxParserAtomDataLength)) {
|
||||
return false;
|
||||
}
|
||||
if (!gcOutput.functions.reserve(maxScriptDataLength)) {
|
||||
ReportOutOfMemory(cx);
|
||||
return false;
|
||||
}
|
||||
if (!gcOutput.scopes.reserve(maxScopeDataLength)) {
|
||||
ReportOutOfMemory(cx);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!buildDelazificationIndices(cx)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
// The `atomCache` is used for the base and delazification stencils.
|
||||
return stencil.input.atomCache.allocate(cx, maxParserAtomDataLength);
|
||||
}
|
||||
|
||||
bool CompilationStencil::serializeStencils(JSContext* cx,
|
||||
|
@ -1566,9 +1523,9 @@ bool CompilationStencil::serializeStencils(JSContext* cx,
|
|||
return true;
|
||||
}
|
||||
|
||||
bool CompilationStencilSet::deserializeStencils(JSContext* cx,
|
||||
const JS::TranscodeRange& range,
|
||||
bool* succeededOut) {
|
||||
bool CompilationStencil::deserializeStencils(JSContext* cx,
|
||||
const JS::TranscodeRange& range,
|
||||
bool* succeededOut) {
|
||||
if (succeededOut) {
|
||||
*succeededOut = false;
|
||||
}
|
||||
|
@ -2812,19 +2769,6 @@ bool CompilationAtomCache::allocate(JSContext* cx, size_t length) {
|
|||
return true;
|
||||
}
|
||||
|
||||
bool CompilationAtomCache::extendIfNecessary(JSContext* cx, size_t length) {
|
||||
if (length <= atoms_.length()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!atoms_.resize(length)) {
|
||||
ReportOutOfMemory(cx);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void CompilationAtomCache::stealBuffer(AtomCacheVector& atoms) {
|
||||
atoms_ = std::move(atoms);
|
||||
// Destroy elements, without unreserving.
|
||||
|
|
|
@ -126,24 +126,24 @@ using ParserBindingIter = AbstractBindingIter<TaggedParserAtomIndex>;
|
|||
// ...
|
||||
// }
|
||||
//
|
||||
// struct StencilDelazificationSet {
|
||||
// Span<BaseCompilationStencil> delazifications;
|
||||
// ...
|
||||
// }
|
||||
//
|
||||
// struct CompilationStencil : BaseCompilationStencil {
|
||||
// LifoAlloc alloc;
|
||||
// CompilationInput input;
|
||||
// Span<ScriptStencilExtra> scriptExtra;
|
||||
// ...
|
||||
// }
|
||||
//
|
||||
// struct CompilationStencilSet : CompilationStencil {
|
||||
// Span<BaseCompilationStencil> delazifications;
|
||||
// StencilDelazifcationSet* delazificationSet;
|
||||
// ...
|
||||
// }
|
||||
//
|
||||
// When we delazify a function that was lazily parsed, we generate a new Stencil
|
||||
// at the point too. These delazifications can be cached as well. When loading
|
||||
// back from a cache we group these together in a `CompilationStencilSet`. Note
|
||||
// that the base class we inherit from provides storage for the initial lazy
|
||||
// parse and the `delazifications` field is the collection of delazified
|
||||
// function data that are available.
|
||||
// back from a cache we group these together in a `StencilDelazificationSet`
|
||||
// structure that hangs off the `CompilationStencil`. This delazification data
|
||||
// is only meaningful if we also have the initial parse stencil.
|
||||
//
|
||||
//
|
||||
// CompilationGCOutput
|
||||
|
|
|
@ -42,7 +42,7 @@
|
|||
#include "builtin/Symbol.h"
|
||||
#include "frontend/BytecodeCompilation.h" // frontend::CompileGlobalScriptToStencil, frontend::InstantiateStencils
|
||||
#include "frontend/BytecodeCompiler.h"
|
||||
#include "frontend/CompilationStencil.h" // frontend::CompilationStencilSet, frontend::CompilationGCOutput
|
||||
#include "frontend/CompilationStencil.h" // frontend::CompilationStencil, frontend::CompilationGCOutput
|
||||
#include "gc/FreeOp.h"
|
||||
#include "gc/Marking.h"
|
||||
#include "gc/Policy.h"
|
||||
|
@ -5747,16 +5747,17 @@ JS_PUBLIC_API JS::TranscodeResult JS::DecodeScript(
|
|||
return JS::TranscodeResult_Ok;
|
||||
}
|
||||
|
||||
static JS::TranscodeResult DecodeStencil(
|
||||
JSContext* cx, JS::TranscodeBuffer& buffer,
|
||||
frontend::CompilationStencilSet& stencilSet, size_t cursorIndex) {
|
||||
XDRStencilDecoder decoder(cx, &stencilSet.input.options, buffer, cursorIndex);
|
||||
static JS::TranscodeResult DecodeStencil(JSContext* cx,
|
||||
JS::TranscodeBuffer& buffer,
|
||||
frontend::CompilationStencil& stencil,
|
||||
size_t cursorIndex) {
|
||||
XDRStencilDecoder decoder(cx, &stencil.input.options, buffer, cursorIndex);
|
||||
|
||||
if (!stencilSet.input.initForGlobal(cx)) {
|
||||
if (!stencil.input.initForGlobal(cx)) {
|
||||
return JS::TranscodeResult_Throw;
|
||||
}
|
||||
|
||||
XDRResult res = decoder.codeStencils(stencilSet);
|
||||
XDRResult res = decoder.codeStencils(stencil);
|
||||
if (res.isErr()) {
|
||||
return res.unwrapErr();
|
||||
}
|
||||
|
@ -5778,19 +5779,19 @@ JS_PUBLIC_API JS::TranscodeResult JS::DecodeScriptMaybeStencil(
|
|||
|
||||
// The buffer contains stencil.
|
||||
|
||||
Rooted<frontend::CompilationStencilSet> stencilSet(
|
||||
cx, frontend::CompilationStencilSet(cx, options));
|
||||
Rooted<frontend::CompilationStencil> stencil(
|
||||
cx, frontend::CompilationStencil(cx, options));
|
||||
|
||||
JS::TranscodeResult res =
|
||||
DecodeStencil(cx, buffer, stencilSet.get(), cursorIndex);
|
||||
DecodeStencil(cx, buffer, stencil.get(), cursorIndex);
|
||||
if (res != JS::TranscodeResult_Ok) {
|
||||
return res;
|
||||
}
|
||||
|
||||
Rooted<frontend::CompilationGCOutput> gcOutput(cx);
|
||||
Rooted<frontend::CompilationGCOutput> gcOutputForDelazification(cx);
|
||||
if (!frontend::InstantiateStencils(cx, stencilSet.get(), gcOutput.get(),
|
||||
gcOutputForDelazification.get())) {
|
||||
if (!frontend::InstantiateStencils(cx, stencil.get(), gcOutput.get(),
|
||||
gcOutputForDelazification.address())) {
|
||||
return JS::TranscodeResult_Throw;
|
||||
}
|
||||
|
||||
|
@ -5823,25 +5824,25 @@ JS_PUBLIC_API JS::TranscodeResult JS::DecodeScriptAndStartIncrementalEncoding(
|
|||
size_t cursorIndex) {
|
||||
MOZ_DIAGNOSTIC_ASSERT(options.useStencilXDR);
|
||||
|
||||
Rooted<frontend::CompilationStencilSet> stencilSet(
|
||||
cx, frontend::CompilationStencilSet(cx, options));
|
||||
Rooted<frontend::CompilationStencil> stencil(
|
||||
cx, frontend::CompilationStencil(cx, options));
|
||||
|
||||
JS::TranscodeResult res =
|
||||
DecodeStencil(cx, buffer, stencilSet.get(), cursorIndex);
|
||||
DecodeStencil(cx, buffer, stencil.get(), cursorIndex);
|
||||
if (res != JS::TranscodeResult_Ok) {
|
||||
return res;
|
||||
}
|
||||
|
||||
UniquePtr<XDRIncrementalStencilEncoder> xdrEncoder;
|
||||
if (!stencilSet.get().input.source()->xdrEncodeStencils(cx, stencilSet.get(),
|
||||
xdrEncoder)) {
|
||||
if (!stencil.get().input.source()->xdrEncodeStencils(cx, stencil.get(),
|
||||
xdrEncoder)) {
|
||||
return JS::TranscodeResult_Throw;
|
||||
}
|
||||
|
||||
Rooted<frontend::CompilationGCOutput> gcOutput(cx);
|
||||
Rooted<frontend::CompilationGCOutput> gcOutputForDelazification(cx);
|
||||
if (!frontend::InstantiateStencils(cx, stencilSet.get(), gcOutput.get(),
|
||||
gcOutputForDelazification.get())) {
|
||||
if (!frontend::InstantiateStencils(cx, stencil.get(), gcOutput.get(),
|
||||
gcOutputForDelazification.address())) {
|
||||
return JS::TranscodeResult_Throw;
|
||||
}
|
||||
|
||||
|
|
|
@ -20,7 +20,7 @@
|
|||
#include "jsapi.h"
|
||||
|
||||
#include "ds/Fifo.h"
|
||||
#include "frontend/CompilationStencil.h" // CompilationStencil, CompilationStencilSet, CompilationGCOutput
|
||||
#include "frontend/CompilationStencil.h" // CompilationStencil, CompilationGCOutput
|
||||
#include "js/CompileOptions.h"
|
||||
#include "js/TypeDecls.h"
|
||||
#include "threading/ConditionVariable.h"
|
||||
|
@ -519,12 +519,10 @@ struct ParseTask : public mozilla::LinkedListElement<ParseTask>,
|
|||
// Holds the ScriptSourceObjects generated for the script compilation.
|
||||
GCVector<ScriptSourceObject*, 1, SystemAllocPolicy> sourceObjects;
|
||||
|
||||
// Holds the CompilationStencil generated for the script compilation.
|
||||
// Holds the CompilationStencil generated for the script compilation or
|
||||
// decoding task.
|
||||
UniquePtr<frontend::CompilationStencil> stencil_;
|
||||
|
||||
// Holds the CompilationStencilSet generated by decoding task.
|
||||
UniquePtr<frontend::CompilationStencilSet> stencilSet_;
|
||||
|
||||
frontend::CompilationGCOutput gcOutput_;
|
||||
|
||||
frontend::CompilationGCOutput gcOutputForDelazification_;
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
#include <algorithm>
|
||||
|
||||
#include "frontend/BytecodeCompilation.h"
|
||||
#include "frontend/CompilationStencil.h" // frontend::CompilationStencilSet, frontend::CompilationGCOutput
|
||||
#include "frontend/CompilationStencil.h" // frontend::CompilationStencil, frontend::CompilationGCOutput
|
||||
#include "frontend/ParserAtom.h" // frontend::ParserAtomsTable
|
||||
#include "gc/GC.h" // gc::MergeRealms
|
||||
#include "jit/IonCompileTask.h"
|
||||
|
@ -585,9 +585,6 @@ void ParseTask::trace(JSTracer* trc) {
|
|||
if (stencil_) {
|
||||
stencil_->trace(trc);
|
||||
}
|
||||
if (stencilSet_) {
|
||||
stencilSet_->trace(trc);
|
||||
}
|
||||
gcOutput_.trace(trc);
|
||||
gcOutputForDelazification_.trace(trc);
|
||||
}
|
||||
|
@ -695,17 +692,12 @@ void ScriptParseTask<Unit>::parse(JSContext* cx) {
|
|||
}
|
||||
|
||||
bool ParseTask::instantiateStencils(JSContext* cx) {
|
||||
if (!stencil_ && !stencilSet_) {
|
||||
if (!stencil_) {
|
||||
return false;
|
||||
}
|
||||
|
||||
bool result;
|
||||
if (stencil_) {
|
||||
result = frontend::InstantiateStencils(cx, *stencil_, gcOutput_);
|
||||
} else {
|
||||
result = frontend::InstantiateStencils(cx, *stencilSet_, gcOutput_,
|
||||
gcOutputForDelazification_);
|
||||
}
|
||||
bool result = frontend::InstantiateStencils(cx, *stencil_, gcOutput_,
|
||||
&gcOutputForDelazification_);
|
||||
|
||||
// Whatever happens to the top-level script compilation (even if it fails),
|
||||
// we must finish initializing the SSO. This is because there may be valid
|
||||
|
@ -778,29 +770,29 @@ void ScriptDecodeTask::parse(JSContext* cx) {
|
|||
|
||||
if (options.useStencilXDR) {
|
||||
// The buffer contains stencil.
|
||||
Rooted<UniquePtr<frontend::CompilationStencilSet>> stencilSet(
|
||||
cx, js_new<frontend::CompilationStencilSet>(cx, options));
|
||||
if (!stencilSet) {
|
||||
Rooted<UniquePtr<frontend::CompilationStencil>> stencil(
|
||||
cx, js_new<frontend::CompilationStencil>(cx, options));
|
||||
if (!stencil) {
|
||||
ReportOutOfMemory(cx);
|
||||
return;
|
||||
}
|
||||
|
||||
XDRStencilDecoder decoder(cx, &stencilSet.get()->input.options, range);
|
||||
if (!stencilSet.get()->input.initForGlobal(cx)) {
|
||||
XDRStencilDecoder decoder(cx, &stencil.get()->input.options, range);
|
||||
if (!stencil.get()->input.initForGlobal(cx)) {
|
||||
return;
|
||||
}
|
||||
|
||||
XDRResult res = decoder.codeStencils(*stencilSet);
|
||||
XDRResult res = decoder.codeStencils(*stencil);
|
||||
if (!res.isOk()) {
|
||||
return;
|
||||
}
|
||||
|
||||
stencilSet_ = std::move(stencilSet.get());
|
||||
stencil_ = std::move(stencil.get());
|
||||
|
||||
if (stencilSet_) {
|
||||
if (!frontend::PrepareForInstantiate(cx, *stencilSet_, gcOutput_,
|
||||
gcOutputForDelazification_)) {
|
||||
stencilSet_ = nullptr;
|
||||
if (stencil_) {
|
||||
if (!frontend::PrepareForInstantiate(cx, *stencil_, gcOutput_,
|
||||
&gcOutputForDelazification_)) {
|
||||
stencil_ = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2078,7 +2070,7 @@ JSScript* GlobalHelperThreadState::finishSingleParseTask(
|
|||
DebugAPI::onNewScript(cx, script);
|
||||
}
|
||||
} else {
|
||||
MOZ_ASSERT(parseTask->stencil_.get() || parseTask->stencilSet_.get());
|
||||
MOZ_ASSERT(parseTask->stencil_.get());
|
||||
|
||||
if (!parseTask->instantiateStencils(cx)) {
|
||||
return nullptr;
|
||||
|
@ -2096,14 +2088,8 @@ JSScript* GlobalHelperThreadState::finishSingleParseTask(
|
|||
|
||||
if (parseTask->stencil_.get()) {
|
||||
auto* stencil = parseTask->stencil_.get();
|
||||
if (!stencil->input.source()->xdrEncodeInitialStencil(cx, *stencil,
|
||||
xdrEncoder)) {
|
||||
return nullptr;
|
||||
}
|
||||
} else {
|
||||
auto* stencilSet = parseTask->stencilSet_.get();
|
||||
if (!stencilSet->input.source()->xdrEncodeStencils(cx, *stencilSet,
|
||||
xdrEncoder)) {
|
||||
if (!stencil->input.source()->xdrEncodeStencils(cx, *stencil,
|
||||
xdrEncoder)) {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2725,15 +2725,17 @@ bool ScriptSource::xdrEncodeInitialStencil(
|
|||
}
|
||||
|
||||
bool ScriptSource::xdrEncodeStencils(
|
||||
JSContext* cx, frontend::CompilationStencilSet& stencilSet,
|
||||
JSContext* cx, frontend::CompilationStencil& stencil,
|
||||
UniquePtr<XDRIncrementalStencilEncoder>& xdrEncoder) {
|
||||
if (!xdrEncodeInitialStencil(cx, stencilSet, xdrEncoder)) {
|
||||
if (!xdrEncodeInitialStencil(cx, stencil, xdrEncoder)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (auto& delazification : stencilSet.delazifications) {
|
||||
if (!xdrEncodeFunctionStencilWith(cx, delazification, xdrEncoder)) {
|
||||
return false;
|
||||
if (stencil.delazificationSet) {
|
||||
for (auto& delazification : stencil.delazificationSet->delazifications) {
|
||||
if (!xdrEncodeFunctionStencilWith(cx, delazification, xdrEncoder)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1033,8 +1033,7 @@ class ScriptSource {
|
|||
// Caller is responsible for calling `setIncrementalEncoder` after
|
||||
// instantiating stencil (so, corresponding canonical ScriptSourceObject
|
||||
// gets created).
|
||||
bool xdrEncodeStencils(JSContext* cx,
|
||||
frontend::CompilationStencilSet& stencilSet,
|
||||
bool xdrEncodeStencils(JSContext* cx, frontend::CompilationStencil& stencil,
|
||||
UniquePtr<XDRIncrementalStencilEncoder>& xdrEncoder);
|
||||
|
||||
void setIncrementalEncoder(XDRIncrementalStencilEncoder* xdrEncoder);
|
||||
|
|
|
@ -645,7 +645,7 @@ struct JSRuntime {
|
|||
|
||||
// Used internally to initialize the self-hosted global using XDR content.
|
||||
bool initSelfHostingFromXDR(JSContext* cx, const JS::CompileOptions& options,
|
||||
js::frontend::CompilationStencilSet& stencilSet,
|
||||
js::frontend::CompilationStencil& stencil,
|
||||
js::MutableHandle<JSScript*> scriptOut);
|
||||
|
||||
public:
|
||||
|
|
|
@ -2771,10 +2771,10 @@ static bool VerifyGlobalNames(JSContext* cx, Handle<GlobalObject*> shg) {
|
|||
return true;
|
||||
}
|
||||
|
||||
bool JSRuntime::initSelfHostingFromXDR(
|
||||
JSContext* cx, const CompileOptions& options,
|
||||
frontend::CompilationStencilSet& stencilSet,
|
||||
MutableHandle<JSScript*> scriptOut) {
|
||||
bool JSRuntime::initSelfHostingFromXDR(JSContext* cx,
|
||||
const CompileOptions& options,
|
||||
frontend::CompilationStencil& stencil,
|
||||
MutableHandle<JSScript*> scriptOut) {
|
||||
MOZ_ASSERT(selfHostingGlobal_);
|
||||
MOZ_ASSERT(selfHostedXDR.length() > 0);
|
||||
scriptOut.set(nullptr);
|
||||
|
@ -2782,7 +2782,7 @@ bool JSRuntime::initSelfHostingFromXDR(
|
|||
// Deserialize the stencil from XDR.
|
||||
JS::TranscodeRange xdrRange(selfHostedXDR);
|
||||
bool decodeOk = false;
|
||||
if (!stencilSet.deserializeStencils(cx, xdrRange, &decodeOk)) {
|
||||
if (!stencil.deserializeStencils(cx, xdrRange, &decodeOk)) {
|
||||
return false;
|
||||
}
|
||||
// If XDR decode failed, it's not a propagated error.
|
||||
|
@ -2793,7 +2793,7 @@ bool JSRuntime::initSelfHostingFromXDR(
|
|||
|
||||
// Instantiate the stencil.
|
||||
Rooted<frontend::CompilationGCOutput> output(cx);
|
||||
if (!frontend::CompilationStencil::instantiateStencils(cx, stencilSet,
|
||||
if (!frontend::CompilationStencil::instantiateStencils(cx, stencil,
|
||||
output.get())) {
|
||||
return false;
|
||||
}
|
||||
|
@ -2836,13 +2836,13 @@ bool JSRuntime::initSelfHosting(JSContext* cx) {
|
|||
// Try initializing from Stencil XDR.
|
||||
if (selfHostedXDR.length() > 0) {
|
||||
// Initialize the compilation info that houses the stencil.
|
||||
Rooted<frontend::CompilationStencilSet> stencilSet(
|
||||
cx, frontend::CompilationStencilSet(cx, options));
|
||||
if (!stencilSet.get().input.initForSelfHostingGlobal(cx)) {
|
||||
Rooted<frontend::CompilationStencil> stencil(
|
||||
cx, frontend::CompilationStencil(cx, options));
|
||||
if (!stencil.get().input.initForSelfHostingGlobal(cx)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!initSelfHostingFromXDR(cx, options, stencilSet.get(), &script)) {
|
||||
if (!initSelfHostingFromXDR(cx, options, stencil.get(), &script)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -19,9 +19,9 @@
|
|||
|
||||
#include "builtin/ModuleObject.h"
|
||||
#include "debugger/DebugAPI.h"
|
||||
#include "frontend/CompilationStencil.h" // frontend::BaseCompilationStencil, frontend::CompilationStencil, frontend::CompilationStencilSet
|
||||
#include "frontend/ParserAtom.h" // frontend::ParserAtom
|
||||
#include "js/BuildId.h" // JS::BuildIdCharVector
|
||||
#include "frontend/CompilationStencil.h" // frontend::BaseCompilationStencil, frontend::CompilationStencil
|
||||
#include "frontend/ParserAtom.h" // frontend::ParserAtom
|
||||
#include "js/BuildId.h" // JS::BuildIdCharVector
|
||||
#include "vm/JSContext.h"
|
||||
#include "vm/JSScript.h"
|
||||
#include "vm/SharedStencil.h" // js::SourceExtent
|
||||
|
@ -478,45 +478,58 @@ XDRResult XDRIncrementalStencilEncoder::linearize(JS::TranscodeBuffer& buffer,
|
|||
void XDRDecoder::trace(JSTracer* trc) { atomTable_.trace(trc); }
|
||||
|
||||
XDRResult XDRStencilDecoder::codeStencils(
|
||||
frontend::CompilationStencilSet& stencilSet) {
|
||||
MOZ_ASSERT(stencilSet.delazifications.length() == 0);
|
||||
frontend::CompilationStencil& stencil) {
|
||||
MOZ_ASSERT(!stencil.delazificationSet);
|
||||
|
||||
frontend::ParserAtomSpanBuilder parserAtomBuilder(cx()->runtime(),
|
||||
stencilSet.parserAtomData);
|
||||
stencil.parserAtomData);
|
||||
parserAtomBuilder_ = &parserAtomBuilder;
|
||||
stencilAlloc_ = &stencilSet.alloc;
|
||||
stencilAlloc_ = &stencil.alloc;
|
||||
|
||||
MOZ_TRY(codeStencil(stencilSet));
|
||||
MOZ_TRY(codeStencil(stencil));
|
||||
|
||||
if (!stencilSet.delazifications.reserve(nchunks_ - 1)) {
|
||||
ReportOutOfMemory(cx());
|
||||
return fail(JS::TranscodeResult_Throw);
|
||||
}
|
||||
// Decode any delazification stencil from XDR.
|
||||
if (nchunks_ > 1) {
|
||||
auto delazificationSet = MakeUnique<frontend::StencilDelazificationSet>();
|
||||
if (!delazificationSet) {
|
||||
ReportOutOfMemory(cx());
|
||||
return fail(JS::TranscodeResult_Throw);
|
||||
}
|
||||
|
||||
for (size_t i = 1; i < nchunks_; i++) {
|
||||
stencilSet.delazifications.infallibleEmplaceBack();
|
||||
auto& delazification = stencilSet.delazifications[i - 1];
|
||||
if (!delazificationSet->delazifications.reserve(nchunks_ - 1)) {
|
||||
ReportOutOfMemory(cx());
|
||||
return fail(JS::TranscodeResult_Throw);
|
||||
}
|
||||
|
||||
hasFinishedAtomTable_ = false;
|
||||
for (size_t i = 1; i < nchunks_; i++) {
|
||||
delazificationSet->delazifications.infallibleEmplaceBack();
|
||||
auto& delazification = delazificationSet->delazifications[i - 1];
|
||||
|
||||
frontend::ParserAtomSpanBuilder parserAtomBuilder(
|
||||
cx()->runtime(), delazification.parserAtomData);
|
||||
parserAtomBuilder_ = &parserAtomBuilder;
|
||||
hasFinishedAtomTable_ = false;
|
||||
|
||||
MOZ_TRY(codeFunctionStencil(delazification));
|
||||
frontend::ParserAtomSpanBuilder parserAtomBuilder(
|
||||
cx()->runtime(), delazification.parserAtomData);
|
||||
parserAtomBuilder_ = &parserAtomBuilder;
|
||||
|
||||
MOZ_TRY(codeFunctionStencil(delazification));
|
||||
}
|
||||
|
||||
stencil.delazificationSet = std::move(delazificationSet);
|
||||
}
|
||||
|
||||
return Ok();
|
||||
}
|
||||
|
||||
XDRResult XDRIncrementalStencilEncoder::codeStencils(
|
||||
frontend::CompilationStencilSet& stencilSet) {
|
||||
frontend::CompilationStencil& stencil) {
|
||||
MOZ_ASSERT(encodedFunctions_.count() == 0);
|
||||
|
||||
MOZ_TRY(codeStencil(stencilSet));
|
||||
MOZ_TRY(codeStencil(stencil));
|
||||
|
||||
for (auto& delazification : stencilSet.delazifications) {
|
||||
MOZ_TRY(codeFunctionStencil(delazification));
|
||||
if (stencil.delazificationSet) {
|
||||
for (auto& delazification : stencil.delazificationSet->delazifications) {
|
||||
MOZ_TRY(codeFunctionStencil(delazification));
|
||||
}
|
||||
}
|
||||
|
||||
return Ok();
|
||||
|
|
|
@ -29,7 +29,6 @@ struct SourceExtent;
|
|||
|
||||
namespace frontend {
|
||||
struct CompilationStencil;
|
||||
struct CompilationStencilSet;
|
||||
struct CompilationInput;
|
||||
struct BaseCompilationStencil;
|
||||
} // namespace frontend
|
||||
|
@ -254,7 +253,7 @@ class XDRState : public XDRCoderBase {
|
|||
virtual void finishAtomTable() { MOZ_CRASH("does not have atomTable"); }
|
||||
|
||||
virtual XDRResult codeDelazificationStencils(
|
||||
frontend::CompilationStencilSet& stencilSet) {
|
||||
frontend::CompilationStencil& stencil) {
|
||||
MOZ_CRASH("cannot code delazification stencils.");
|
||||
}
|
||||
|
||||
|
@ -557,7 +556,7 @@ class XDRStencilDecoder : public XDRDecoderBase {
|
|||
bool hasOptions() const override { return true; }
|
||||
const JS::ReadOnlyCompileOptions& options() override { return *options_; }
|
||||
|
||||
XDRResult codeStencils(frontend::CompilationStencilSet& stencilSet);
|
||||
XDRResult codeStencils(frontend::CompilationStencil& stencil);
|
||||
|
||||
private:
|
||||
const JS::ReadOnlyCompileOptions* options_;
|
||||
|
@ -640,7 +639,7 @@ class XDRIncrementalStencilEncoder : public XDREncoder {
|
|||
|
||||
XDRResult linearize(JS::TranscodeBuffer& buffer, js::ScriptSource* ss);
|
||||
|
||||
XDRResult codeStencils(frontend::CompilationStencilSet& stencilSet);
|
||||
XDRResult codeStencils(frontend::CompilationStencil& stencil);
|
||||
|
||||
private:
|
||||
void switchToBuffer(XDRBuffer<XDR_ENCODE>* target) { buf = target; }
|
||||
|
|
Загрузка…
Ссылка в новой задаче