mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-12-02 01:48:05 +00:00
Bug 1058043 - ServiceWorkerRegistration should not keep a reference to the window, r=nsm
This commit is contained in:
parent
51c5e60fe1
commit
77c2d8452a
@ -13,7 +13,6 @@
|
||||
#include "nsServiceManagerUtils.h"
|
||||
#include "ServiceWorker.h"
|
||||
|
||||
#include "nsIObserverService.h"
|
||||
#include "nsIServiceWorkerManager.h"
|
||||
#include "nsISupportsPrimitives.h"
|
||||
#include "nsPIDOMWindow.h"
|
||||
@ -24,7 +23,6 @@ namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(ServiceWorkerRegistration)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIObserver)
|
||||
NS_INTERFACE_MAP_END_INHERITING(DOMEventTargetHelper)
|
||||
|
||||
NS_IMPL_ADDREF_INHERITED(ServiceWorkerRegistration, DOMEventTargetHelper)
|
||||
@ -32,35 +30,30 @@ NS_IMPL_RELEASE_INHERITED(ServiceWorkerRegistration, DOMEventTargetHelper)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_INHERITED(ServiceWorkerRegistration,
|
||||
DOMEventTargetHelper,
|
||||
mWindow,
|
||||
mInstallingWorker,
|
||||
mWaitingWorker,
|
||||
mActiveWorker)
|
||||
|
||||
ServiceWorkerRegistration::ServiceWorkerRegistration(nsPIDOMWindow* aWindow,
|
||||
const nsAString& aScope)
|
||||
: mWindow(aWindow)
|
||||
: DOMEventTargetHelper(aWindow)
|
||||
, mScope(aScope)
|
||||
, mInnerID(0)
|
||||
, mIsListeningForEvents(false)
|
||||
{
|
||||
MOZ_ASSERT(aWindow);
|
||||
MOZ_ASSERT(aWindow->IsInnerWindow());
|
||||
|
||||
SetIsDOMBinding();
|
||||
StartListeningForEvents();
|
||||
|
||||
mInnerID = aWindow->WindowID();
|
||||
|
||||
nsCOMPtr<nsIObserverService> obs = services::GetObserverService();
|
||||
if (obs) {
|
||||
obs->AddObserver(this, "inner-window-destroyed", false);
|
||||
}
|
||||
}
|
||||
|
||||
ServiceWorkerRegistration::~ServiceWorkerRegistration()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
ServiceWorkerRegistration::DisconnectFromOwner()
|
||||
{
|
||||
StopListeningForEvents();
|
||||
DOMEventTargetHelper::DisconnectFromOwner();
|
||||
}
|
||||
|
||||
JSObject*
|
||||
@ -138,13 +131,13 @@ ServiceWorkerRegistration::GetWorkerReference(WhichServiceWorker aWhichOne)
|
||||
nsCOMPtr<nsISupports> serviceWorker;
|
||||
switch(aWhichOne) {
|
||||
case WhichServiceWorker::INSTALLING_WORKER:
|
||||
rv = swm->GetInstalling(mWindow, getter_AddRefs(serviceWorker));
|
||||
rv = swm->GetInstalling(GetOwner(), getter_AddRefs(serviceWorker));
|
||||
break;
|
||||
case WhichServiceWorker::WAITING_WORKER:
|
||||
rv = swm->GetWaiting(mWindow, getter_AddRefs(serviceWorker));
|
||||
rv = swm->GetWaiting(GetOwner(), getter_AddRefs(serviceWorker));
|
||||
break;
|
||||
case WhichServiceWorker::ACTIVE_WORKER:
|
||||
rv = swm->GetActive(mWindow, getter_AddRefs(serviceWorker));
|
||||
rv = swm->GetActive(GetOwner(), getter_AddRefs(serviceWorker));
|
||||
break;
|
||||
default:
|
||||
MOZ_CRASH("Invalid enum value");
|
||||
@ -180,74 +173,27 @@ ServiceWorkerRegistration::InvalidateWorkerReference(WhichServiceWorker aWhichOn
|
||||
void
|
||||
ServiceWorkerRegistration::StartListeningForEvents()
|
||||
{
|
||||
MOZ_ASSERT(!mIsListeningForEvents);
|
||||
|
||||
nsCOMPtr<nsIServiceWorkerManager> swm = do_GetService(SERVICEWORKERMANAGER_CONTRACTID);
|
||||
MOZ_ASSERT(mWindow);
|
||||
|
||||
if (swm) {
|
||||
swm->AddRegistrationEventListener(GetDocumentURI(), this);
|
||||
}
|
||||
|
||||
mIsListeningForEvents = true;
|
||||
}
|
||||
|
||||
void
|
||||
ServiceWorkerRegistration::StopListeningForEvents()
|
||||
{
|
||||
if (!mIsListeningForEvents) {
|
||||
return;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIServiceWorkerManager> swm = do_GetService(SERVICEWORKERMANAGER_CONTRACTID);
|
||||
|
||||
// StopListeningForEvents is called in the dtor, and it can happen that
|
||||
// SnowWhite had already set to null mWindow.
|
||||
if (swm && mWindow) {
|
||||
if (swm) {
|
||||
swm->RemoveRegistrationEventListener(GetDocumentURI(), this);
|
||||
}
|
||||
|
||||
mIsListeningForEvents = false;
|
||||
}
|
||||
|
||||
nsIURI*
|
||||
ServiceWorkerRegistration::GetDocumentURI() const
|
||||
{
|
||||
MOZ_ASSERT(mWindow);
|
||||
return mWindow->GetDocumentURI();
|
||||
MOZ_ASSERT(GetOwner());
|
||||
return GetOwner()->GetDocumentURI();
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
ServiceWorkerRegistration::Observe(nsISupports* aSubject, const char* aTopic,
|
||||
const char16_t* aData)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
if (strcmp(aTopic, "inner-window-destroyed")) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (!mIsListeningForEvents) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsISupportsPRUint64> wrapper = do_QueryInterface(aSubject);
|
||||
NS_ENSURE_TRUE(wrapper, NS_ERROR_FAILURE);
|
||||
|
||||
uint64_t innerID;
|
||||
nsresult rv = wrapper->GetData(&innerID);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
if (innerID == mInnerID) {
|
||||
nsCOMPtr<nsIObserverService> obs = services::GetObserverService();
|
||||
if (obs) {
|
||||
obs->RemoveObserver(this, "inner-window-destroyed");
|
||||
}
|
||||
|
||||
StopListeningForEvents();
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
} // dom namespace
|
||||
} // mozilla namespace
|
||||
|
@ -22,11 +22,9 @@ class ServiceWorker;
|
||||
}
|
||||
|
||||
class ServiceWorkerRegistration MOZ_FINAL : public DOMEventTargetHelper
|
||||
, public nsIObserver
|
||||
{
|
||||
public:
|
||||
NS_DECL_ISUPPORTS_INHERITED
|
||||
NS_DECL_NSIOBSERVER
|
||||
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(ServiceWorkerRegistration,
|
||||
DOMEventTargetHelper)
|
||||
|
||||
@ -35,12 +33,6 @@ public:
|
||||
ServiceWorkerRegistration(nsPIDOMWindow* aWindow,
|
||||
const nsAString& aScope);
|
||||
|
||||
nsPIDOMWindow*
|
||||
GetParentObject() const
|
||||
{
|
||||
return mWindow;
|
||||
}
|
||||
|
||||
JSObject*
|
||||
WrapObject(JSContext* aCx);
|
||||
|
||||
@ -70,6 +62,9 @@ public:
|
||||
void
|
||||
InvalidateWorkerReference(WhichServiceWorker aWhichOnes);
|
||||
|
||||
// DOMEventTargethelper
|
||||
virtual void DisconnectFromOwner() MOZ_OVERRIDE;
|
||||
|
||||
private:
|
||||
~ServiceWorkerRegistration();
|
||||
|
||||
@ -82,8 +77,6 @@ private:
|
||||
void
|
||||
StopListeningForEvents();
|
||||
|
||||
nsCOMPtr<nsPIDOMWindow> mWindow;
|
||||
|
||||
// The following properties are cached here to ensure JS equality is satisfied
|
||||
// instead of acquiring a new worker instance from the ServiceWorkerManager
|
||||
// for every access. A null value is considered a cache miss.
|
||||
@ -93,9 +86,6 @@ private:
|
||||
nsRefPtr<workers::ServiceWorker> mActiveWorker;
|
||||
|
||||
const nsString mScope;
|
||||
|
||||
uint64_t mInnerID;
|
||||
bool mIsListeningForEvents;
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
|
Loading…
Reference in New Issue
Block a user