☠☠ backed out by 8c598532de9f ☠ ☠ | |
author | Mats Palmgren <matspal@gmail.com> |
Thu, 23 Jun 2011 01:16:00 +0200 | |
changeset 71581 | bc0b2201ca8594d96aec985b9ad33ec98e84f6ba |
parent 71580 | 7bb02cc447e0145c73cf23bc5193d7742d80a7cd |
child 71582 | 5544f74c84b96fde258b9244664c20250599e135 |
push id | 20566 |
push user | mlamouri@mozilla.com |
push date | Thu, 23 Jun 2011 09:20:24 +0000 |
treeherder | mozilla-central@c70b05ca6e88 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | roc |
bugs | 654002 |
milestone | 7.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
|
--- a/layout/generic/nsContainerFrame.cpp +++ b/layout/generic/nsContainerFrame.cpp @@ -214,43 +214,46 @@ nsContainerFrame::RemoveFrame(nsIAtom* // the line the brFrame was on can attempt to pull up any frames // that can fit from lines below it. PRBool generateReflowCommand = PR_TRUE; #ifdef IBMBIDI if (nsGkAtoms::nextBidi == aListName) { generateReflowCommand = PR_FALSE; } #endif - nsContainerFrame* parent = static_cast<nsContainerFrame*>(aOldFrame->GetParent()); while (aOldFrame) { + nsContainerFrame* parent = + static_cast<nsContainerFrame*>(aOldFrame->GetParent()); // When the parent is an inline frame we have a simple task - just // remove the frame from its parents list and generate a reflow // command. nsIFrame* oldFrameNextContinuation = aOldFrame->GetNextContinuation(); //XXXfr probably should use StealFrame here. I'm not sure if we need to // check the overflow lists atm, but we'll need a prescontext lookup // for overflow containers once we can split abspos elements with // inline containing blocks. if (parent == this) { if (!parent->mFrames.DestroyFrameIfPresent(aOldFrame)) { // Try to remove it from our overflow list, if we have one. // The simplest way is to reuse StealFrame. StealFrame(PresContext(), aOldFrame, PR_TRUE); aOldFrame->Destroy(); } } else { - // This recursive call takes care of all continuations after aOldFrame, - // so we don't need to loop anymore. - parent->RemoveFrame(nsnull, aOldFrame); - break; + // We don't want to simply make a recursive call here because with + // thousands of continuations it would exhaust the stack. Instead, + // unhook aOldFrame from the continuation chain, destroy it, and + // continue the loop. + if (oldFrameNextContinuation) { + oldFrameNextContinuation->SetPrevContinuation(nsnull); + aOldFrame->SetNextContinuation(nsnull); + } + parent->RemoveFrame(aListName, aOldFrame); } aOldFrame = oldFrameNextContinuation; - if (aOldFrame) { - parent = static_cast<nsContainerFrame*>(aOldFrame->GetParent()); - } } if (generateReflowCommand) { PresContext()->PresShell()-> FrameNeedsReflow(this, nsIPresShell::eTreeChange, NS_FRAME_HAS_DIRTY_CHILDREN); } }