diff options
Diffstat (limited to 'js/loader')
-rw-r--r-- | js/loader/ModuleLoadRequest.cpp | 18 | ||||
-rw-r--r-- | js/loader/ModuleLoaderBase.cpp | 15 | ||||
-rw-r--r-- | js/loader/ModuleLoaderBase.h | 2 | ||||
-rw-r--r-- | js/loader/ScriptLoadRequest.h | 2 |
4 files changed, 34 insertions, 3 deletions
diff --git a/js/loader/ModuleLoadRequest.cpp b/js/loader/ModuleLoadRequest.cpp index 7313563df9..1a02ba6dbb 100644 --- a/js/loader/ModuleLoadRequest.cpp +++ b/js/loader/ModuleLoadRequest.cpp @@ -108,8 +108,6 @@ void ModuleLoadRequest::SetReady() { // dependencies have had their source loaded, parsed as a module and the // modules instantiated. - AssertAllImportsFinished(); - ScriptLoadRequest::SetReady(); if (mWaitingParentRequest) { @@ -162,7 +160,7 @@ void ModuleLoadRequest::ModuleErrored() { LOG(("ScriptLoadRequest (%p): Module errored", this)); - if (IsCanceled()) { + if (IsCanceled() || IsCancelingImports()) { return; } @@ -195,6 +193,7 @@ void ModuleLoadRequest::DependenciesLoaded() { MOZ_ASSERT(!IsErrored()); CheckModuleDependenciesLoaded(); + AssertAllImportsFinished(); SetReady(); LoadFinished(); } @@ -223,9 +222,22 @@ void ModuleLoadRequest::CheckModuleDependenciesLoaded() { } void ModuleLoadRequest::CancelImports() { + State origState = mState; + + // To prevent reentering ModuleErrored() for this request via mImports[i]'s + // ChildLoadComplete(). + mState = State::CancelingImports; + for (size_t i = 0; i < mImports.Length(); i++) { + if (mLoader->IsFetchingAndHasWaitingRequest(mImports[i])) { + LOG(("CancelImports import %p is fetching and has waiting\n", + mImports[i].get())); + continue; + } mImports[i]->Cancel(); } + + mState = origState; } void ModuleLoadRequest::LoadFinished() { diff --git a/js/loader/ModuleLoaderBase.cpp b/js/loader/ModuleLoaderBase.cpp index 020542754d..506ad22edd 100644 --- a/js/loader/ModuleLoaderBase.cpp +++ b/js/loader/ModuleLoaderBase.cpp @@ -623,11 +623,13 @@ nsresult ModuleLoaderBase::OnFetchComplete(ModuleLoadRequest* aRequest, if (NS_SUCCEEDED(rv)) { rv = CreateModuleScript(aRequest); +#if defined(MOZ_DIAGNOSTIC_ASSERT_ENABLED) // If a module script was created, it should either have a module record // object or a parse error. if (ModuleScript* ms = aRequest->mModuleScript) { MOZ_DIAGNOSTIC_ASSERT(bool(ms->ModuleRecord()) != ms->HasParseError()); } +#endif aRequest->ClearScriptSource(); @@ -1445,9 +1447,11 @@ void ModuleLoaderBase::RegisterImportMap(UniquePtr<ImportMap> aImportMap) { "Non-preload module loads should block import maps"); MOZ_DIAGNOSTIC_ASSERT(!script->HadImportMap(), "Only one import map can be registered"); +#if defined(MOZ_DIAGNOSTIC_ASSERT_ENABLED) if (JSObject* module = script->ModuleRecord()) { MOZ_DIAGNOSTIC_ASSERT(!JS::ModuleIsLinked(module)); } +#endif script->Shutdown(); } } @@ -1490,6 +1494,17 @@ void ModuleLoaderBase::MoveModulesTo(ModuleLoaderBase* aDest) { mFetchedModules.Clear(); } +bool ModuleLoaderBase::IsFetchingAndHasWaitingRequest( + ModuleLoadRequest* aRequest) { + auto entry = mFetchingModules.Lookup(aRequest->mURI); + if (!entry) { + return false; + } + + RefPtr<LoadingRequest> loadingRequest = entry.Data(); + return !loadingRequest->mWaiting.IsEmpty(); +} + #undef LOG #undef LOG_ENABLED diff --git a/js/loader/ModuleLoaderBase.h b/js/loader/ModuleLoaderBase.h index 89d23e12bc..f902db18a4 100644 --- a/js/loader/ModuleLoaderBase.h +++ b/js/loader/ModuleLoaderBase.h @@ -480,6 +480,8 @@ class ModuleLoaderBase : public nsISupports { nsresult CreateModuleScript(ModuleLoadRequest* aRequest); + bool IsFetchingAndHasWaitingRequest(ModuleLoadRequest* aRequest); + // The slot stored in ImportMetaResolve function. enum { ModulePrivateSlot = 0, SlotCount }; diff --git a/js/loader/ScriptLoadRequest.h b/js/loader/ScriptLoadRequest.h index 442a456b15..f255b65228 100644 --- a/js/loader/ScriptLoadRequest.h +++ b/js/loader/ScriptLoadRequest.h @@ -124,6 +124,7 @@ class ScriptLoadRequest : public nsISupports, Fetching, Compiling, LoadingImports, + CancelingImports, Ready, Canceled }; @@ -139,6 +140,7 @@ class ScriptLoadRequest : public nsISupports, bool IsFetching() const { return mState == State::Fetching; } bool IsCompiling() const { return mState == State::Compiling; } bool IsLoadingImports() const { return mState == State::LoadingImports; } + bool IsCancelingImports() const { return mState == State::CancelingImports; } bool IsCanceled() const { return mState == State::Canceled; } bool IsPendingFetchingError() const { |