Bug 811394. Prevent recursion into nsXULWindow::Destroy. r=smaug
authorBoris Zbarsky <bzbarsky@mit.edu>
Thu, 15 Nov 2012 08:28:40 -0800
changeset 113387 6e9e10baf0ddfd0cd73fd45e2066a72da7d8c6e1
parent 113386 77972f22952a1e3c3ba57b5881491da6a350ddab
child 113388 84c7ef253748a99222f1bb071600b8cd059f4cf8
push id23870
push userryanvm@gmail.com
push dateFri, 16 Nov 2012 01:21:36 +0000
treeherdermozilla-central@58ebb638a7ea [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerssmaug
bugs811394
milestone19.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 811394. Prevent recursion into nsXULWindow::Destroy. r=smaug
xpfe/appshell/src/nsXULWindow.cpp
xpfe/appshell/src/nsXULWindow.h
--- a/xpfe/appshell/src/nsXULWindow.cpp
+++ b/xpfe/appshell/src/nsXULWindow.cpp
@@ -90,16 +90,17 @@ nsXULWindow::nsXULWindow(uint32_t aChrom
     mIntrinsicallySized(false),
     mCenterAfterLoad(false),
     mIsHiddenWindow(false),
     mLockedUntilChromeLoad(false),
     mIgnoreXULSize(false),
     mIgnoreXULPosition(false),
     mChromeFlagsFrozen(false),
     mIgnoreXULSizeMode(false),
+    mDestroying(false),
     mContextFlags(0),
     mPersistentAttributesDirty(0),
     mPersistentAttributesMask(0),
     mChromeFlags(aChromeFlags)
 {
 }
 
 nsXULWindow::~nsXULWindow()
@@ -404,16 +405,23 @@ NS_IMETHODIMP nsXULWindow::Create()
   return NS_OK;
 }
 
 NS_IMETHODIMP nsXULWindow::Destroy()
 {
   if (!mWindow)
      return NS_OK;
 
+  // Ensure we don't reenter this code
+  if (mDestroying)
+    return NS_OK;
+
+  mozilla::AutoRestore<bool> guard(mDestroying);
+  mDestroying = true;
+
   nsCOMPtr<nsIAppShellService> appShell(do_GetService(NS_APPSHELLSERVICE_CONTRACTID));
   NS_ASSERTION(appShell, "Couldn't get appShell... xpcom shutdown?");
   if (appShell)
     appShell->UnregisterTopLevelWindow(static_cast<nsIXULWindow*>(this));
 
   nsCOMPtr<nsIXULWindow> parentWindow(do_QueryReferent(mParentWindow));
   if (parentWindow)
     parentWindow->RemoveChildWindow(this);
--- a/xpfe/appshell/src/nsXULWindow.h
+++ b/xpfe/appshell/src/nsXULWindow.h
@@ -133,16 +133,19 @@ protected:
    bool                    mIntrinsicallySized; 
    bool                    mCenterAfterLoad;
    bool                    mIsHiddenWindow;
    bool                    mLockedUntilChromeLoad;
    bool                    mIgnoreXULSize;
    bool                    mIgnoreXULPosition;
    bool                    mChromeFlagsFrozen;
    bool                    mIgnoreXULSizeMode;
+   // mDestroying is used to prevent reentry into into Destroy(), which can
+   // otherwise happen due to script running as we tear down various things.
+   bool                    mDestroying;
    uint32_t                mContextFlags;
    uint32_t                mPersistentAttributesDirty; // persistentAttributes
    uint32_t                mPersistentAttributesMask;
    uint32_t                mChromeFlags;
    nsString                mTitle;
    nsIntRect               mOpenerScreenRect; // the screen rect of the opener
 
    nsCOMArray<nsIWeakReference> mTargetableShells; // targetable shells only