diff --git a/dom/workers/ServiceWorkerManager.cpp b/dom/workers/ServiceWorkerManager.cpp index a2bb7bd8267..d86f01bdf6d 100644 --- a/dom/workers/ServiceWorkerManager.cpp +++ b/dom/workers/ServiceWorkerManager.cpp @@ -25,6 +25,7 @@ #include "jsapi.h" #include "mozilla/BasePrincipal.h" +#include "mozilla/ClearOnShutdown.h" #include "mozilla/ErrorNames.h" #include "mozilla/LoadContext.h" #include "mozilla/dom/BindingUtils.h" @@ -84,6 +85,8 @@ static_assert(nsIHttpChannelInternal::CORS_MODE_CORS == static_cast(Re static_assert(nsIHttpChannelInternal::CORS_MODE_CORS_WITH_FORCED_PREFLIGHT == static_cast(RequestMode::Cors_with_forced_preflight), "RequestMode enumeration value should match Necko CORS mode value."); +static StaticRefPtr gInstance; + struct ServiceWorkerManager::RegistrationDataPerPrincipal { // Ordered list of scopes for glob matching. @@ -343,9 +346,6 @@ NS_INTERFACE_MAP_BEGIN(ServiceWorkerManager) NS_INTERFACE_MAP_ENTRY(nsIServiceWorkerManager) NS_INTERFACE_MAP_ENTRY(nsIIPCBackgroundChildCreateCallback) NS_INTERFACE_MAP_ENTRY(nsIObserver) - if (aIID.Equals(NS_GET_IID(ServiceWorkerManager))) - foundInterface = static_cast(this); - else NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIServiceWorkerManager) NS_INTERFACE_MAP_END @@ -354,7 +354,17 @@ ServiceWorkerManager::ServiceWorkerManager() { // Register this component to PBackground. MOZ_ALWAYS_TRUE(BackgroundChild::GetOrCreateForCurrentThread(this)); +} +ServiceWorkerManager::~ServiceWorkerManager() +{ + // The map will assert if it is not empty when destroyed. + mRegistrationInfos.Clear(); +} + +void +ServiceWorkerManager::Init() +{ if (XRE_GetProcessType() == GeckoProcessType_Default) { nsRefPtr swr = ServiceWorkerRegistrar::Get(); MOZ_ASSERT(swr); @@ -376,12 +386,6 @@ ServiceWorkerManager::ServiceWorkerManager() } } -ServiceWorkerManager::~ServiceWorkerManager() -{ - // The map will assert if it is not empty when destroyed. - mRegistrationInfos.Clear(); -} - class ContinueLifecycleTask : public nsISupports { NS_DECL_ISUPPORTS @@ -2287,9 +2291,19 @@ ServiceWorkerManager::GetOrCreateJobQueue(const nsACString& aKey, already_AddRefed ServiceWorkerManager::GetInstance() { - nsCOMPtr swm = mozilla::services::GetServiceWorkerManager(); - nsRefPtr concrete = do_QueryObject(swm); - return concrete.forget(); + // Note: We don't simply check gInstance for null-ness here, since otherwise + // this can resurrect the ServiceWorkerManager pretty late during shutdown. + static bool firstTime = true; + if (firstTime) { + AssertIsOnMainThread(); + + gInstance = new ServiceWorkerManager(); + gInstance->Init(); + ClearOnShutdown(&gInstance); + firstTime = false; + } + nsRefPtr copy = gInstance.get(); + return copy.forget(); } void diff --git a/dom/workers/ServiceWorkerManager.h b/dom/workers/ServiceWorkerManager.h index cff2beaf089..aa354f2e245 100644 --- a/dom/workers/ServiceWorkerManager.h +++ b/dom/workers/ServiceWorkerManager.h @@ -277,16 +277,6 @@ public: NS_DECL_NSISERVICEWORKERMANAGER NS_DECL_NSIIPCBACKGROUNDCHILDCREATECALLBACK NS_DECL_NSIOBSERVER - NS_DECLARE_STATIC_IID_ACCESSOR(NS_SERVICEWORKERMANAGER_IMPL_IID) - - static ServiceWorkerManager* FactoryCreate() - { - AssertIsOnMainThread(); - - ServiceWorkerManager* res = new ServiceWorkerManager; - NS_ADDREF(res); - return res; - } struct RegistrationDataPerPrincipal; nsClassHashtable mRegistrationInfos; @@ -382,6 +372,9 @@ private: ServiceWorkerManager(); ~ServiceWorkerManager(); + void + Init(); + ServiceWorkerJobQueue* GetOrCreateJobQueue(const nsACString& aOriginSuffix, const nsACString& aScope); @@ -538,9 +531,6 @@ private: nsTArray mPendingOperations; }; -NS_DEFINE_STATIC_IID_ACCESSOR(ServiceWorkerManager, - NS_SERVICEWORKERMANAGER_IMPL_IID); - } // namespace workers } // namespace dom } // namespace mozilla diff --git a/layout/build/nsLayoutModule.cpp b/layout/build/nsLayoutModule.cpp index 6d81b4d9ef2..c2f1216acbe 100644 --- a/layout/build/nsLayoutModule.cpp +++ b/layout/build/nsLayoutModule.cpp @@ -312,7 +312,7 @@ NS_GENERIC_FACTORY_SINGLETON_CONSTRUCTOR(DOMRequestService, NS_GENERIC_FACTORY_SINGLETON_CONSTRUCTOR(QuotaManager, QuotaManager::FactoryCreate) NS_GENERIC_FACTORY_SINGLETON_CONSTRUCTOR(ServiceWorkerManager, - ServiceWorkerManager::FactoryCreate) + ServiceWorkerManager::GetInstance) NS_GENERIC_FACTORY_SINGLETON_CONSTRUCTOR(ServiceWorkerPeriodicUpdater, ServiceWorkerPeriodicUpdater::GetSingleton) NS_GENERIC_FACTORY_CONSTRUCTOR(WorkerDebuggerManager)