Bug 534433. Destroy all nsImageLoaders when the prescontext is torn down. r=mats

This commit is contained in:
Robert O'Callahan 2010-01-14 15:30:05 +13:00
parent 4e9435de20
commit cd2f7f16fc
3 changed files with 14 additions and 12 deletions

View File

@ -253,9 +253,6 @@ nsPresContext::nsPresContext(nsIDocument* aDocument, nsPresContextType aType)
nsPresContext::~nsPresContext() nsPresContext::~nsPresContext()
{ {
for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i)
mImageLoaders[i].Enumerate(destroy_loads, nsnull);
NS_PRECONDITION(!mShell, "Presshell forgot to clear our mShell pointer"); NS_PRECONDITION(!mShell, "Presshell forgot to clear our mShell pointer");
SetShell(nsnull); SetShell(nsnull);
@ -374,11 +371,6 @@ NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(nsPresContext)
// NS_RELEASE(tmp->mLookAndFeel); // a service // NS_RELEASE(tmp->mLookAndFeel); // a service
// NS_RELEASE(tmp->mLangGroup); // an atom // NS_RELEASE(tmp->mLangGroup); // an atom
for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i) {
tmp->mImageLoaders[i].Enumerate(destroy_loads, nsnull);
tmp->mImageLoaders[i].Clear();
}
// NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mTheme); // a service // NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mTheme); // a service
// NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mLangService); // a service // NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mLangService); // a service
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mPrintSettings); NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mPrintSettings);
@ -992,6 +984,15 @@ nsPresContext::SetShell(nsIPresShell* aShell)
UpdateCharSet(doc->GetDocumentCharacterSet()); UpdateCharSet(doc->GetDocumentCharacterSet());
} }
} }
} else {
// Destroy image loaders now that the presshell is going away.
// This is important since imageloaders can have pointers to frames and
// we don't want those pointers to outlive the destruction of the frame
// arena.
for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i) {
mImageLoaders[i].Enumerate(destroy_loads, nsnull);
mImageLoaders[i].Clear();
}
} }
} }
@ -1278,6 +1279,9 @@ nsPresContext::SetImageLoaders(nsIFrame* aTargetFrame,
ImageLoadType aType, ImageLoadType aType,
nsImageLoader* aImageLoaders) nsImageLoader* aImageLoaders)
{ {
NS_ASSERTION(mShell || !aImageLoaders,
"Shouldn't add new image loader after the shell is gone");
nsRefPtr<nsImageLoader> oldLoaders; nsRefPtr<nsImageLoader> oldLoaders;
mImageLoaders[aType].Get(aTargetFrame, getter_AddRefs(oldLoaders)); mImageLoaders[aType].Get(aTargetFrame, getter_AddRefs(oldLoaders));

View File

@ -2748,6 +2748,8 @@ NS_IMETHODIMP
PresShell::NotifyDestroyingFrame(nsIFrame* aFrame) PresShell::NotifyDestroyingFrame(nsIFrame* aFrame)
{ {
if (!mIgnoreFrameDestruction) { if (!mIgnoreFrameDestruction) {
mPresContext->StopImagesFor(aFrame);
mFrameConstructor->NotifyDestroyingFrame(aFrame); mFrameConstructor->NotifyDestroyingFrame(aFrame);
for (PRInt32 idx = mDirtyRoots.Length(); idx; ) { for (PRInt32 idx = mDirtyRoots.Length(); idx; ) {

View File

@ -451,10 +451,6 @@ nsFrame::DestroyFrom(nsIFrame* aDestructRoot)
shell->ClearFrameRefs(this); shell->ClearFrameRefs(this);
} }
//XXX Why is this done in nsFrame instead of some frame class
// that actually loads images?
presContext->StopImagesFor(this);
if (view) { if (view) {
// Break association between view and frame // Break association between view and frame
view->SetClientData(nsnull); view->SetClientData(nsnull);