No Issue - Make nsCocoaWindow hold a death grip on its native window until its destructor. https://bugzilla.mozilla.org/show_bug.cgi?id=1880582

This commit is contained in:
Brian Smith 2024-11-30 17:53:28 -06:00 • committed by roytam1
commit 1554c778f4
2 changed files with 15 additions and 1 deletions

View file

@ -384,8 +384,13 @@ protected:
nsIWidget* mParent; // if we're a popup, this is our parent [WEAK] nsIWidget* mParent; // if we're a popup, this is our parent [WEAK]
nsIWidget* mAncestorLink; // link to traverse ancestors [WEAK] nsIWidget* mAncestorLink; // link to traverse ancestors [WEAK]
BaseWindow* mWindow; // our cocoa window [STRONG] BaseWindow* mWindow; // our cocoa window [STRONG]
BaseWindow* mClosedRetainedWindow; // a second strong reference to our
// window upon closing it, held through our destructor. This is useful
// to ensure that macOS run loops which reference the window will still
// have something to point to even if they don't use proper retain and
// release patterns.
WindowDelegate* mDelegate; // our delegate for processing window msgs [STRONG] WindowDelegate* mDelegate; // our delegate for processing window msgs [STRONG]
RefPtr<nsMenuBarX> mMenuBar; RefPtr<nsMenuBarX> mMenuBar;
NSWindow* mSheetWindowParent; // if this is a sheet, this is the NSWindow it's attached to NSWindow* mSheetWindowParent; // if this is a sheet, this is the NSWindow it's attached to
nsChildView* mPopupContentView; // if this is a popup, this is its content widget nsChildView* mPopupContentView; // if this is a popup, this is its content widget
// if this is a toplevel window, and there is any ongoing fullscreen // if this is a toplevel window, and there is any ongoing fullscreen

View file

@ -110,6 +110,7 @@ nsCocoaWindow::nsCocoaWindow()
: mParent(nullptr) : mParent(nullptr)
, mAncestorLink(nullptr) , mAncestorLink(nullptr)
, mWindow(nil) , mWindow(nil)
, mClosedRetainedWindow(nil)
, mDelegate(nil) , mDelegate(nil)
, mSheetWindowParent(nil) , mSheetWindowParent(nil)
, mPopupContentView(nil) , mPopupContentView(nil)
@ -148,6 +149,12 @@ void nsCocoaWindow::DestroyNativeWindow()
// We want to unhook the delegate here because we don't want events // We want to unhook the delegate here because we don't want events
// sent to it after this object has been destroyed. // sent to it after this object has been destroyed.
[mWindow setDelegate:nil]; [mWindow setDelegate:nil];
// Closing the window will also release it. Our second reference will
// keep it alive through our destructor. Release any reference we might
// have from an earlier call to DestroyNativeWindow, then create a new
// one.
[mClosedRetainedWindow autorelease];
mClosedRetainedWindow = [mWindow retain];
[mWindow close]; [mWindow close];
mWindow = nil; mWindow = nil;
[mDelegate autorelease]; [mDelegate autorelease];
@ -182,6 +189,8 @@ nsCocoaWindow::~nsCocoaWindow()
DestroyNativeWindow(); DestroyNativeWindow();
} }
[mClosedRetainedWindow release];
NS_IF_RELEASE(mPopupContentView); NS_IF_RELEASE(mPopupContentView);
// Deal with the possiblity that we're being destroyed while running modal. // Deal with the possiblity that we're being destroyed while running modal.