<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[198943] trunk</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/198943">198943</a></dd>
<dt>Author</dt> <dd>antti@apple.com</dd>
<dt>Date</dt> <dd>2016-04-01 02:54:12 -0700 (Fri, 01 Apr 2016)</dd>
</dl>

<h3>Log Message</h3>
<pre>Separate render tree updating from style resolve
https://bugs.webkit.org/show_bug.cgi?id=155298

Reviewed by Andreas Kling.

Source/WebCore:

This patch splits computing document style and applying the results into two distinct steps:

Style::TreeResolver::resolve()
        |
        | Style::Update
        V
RenderTreeUpdater::commit()

Style::TreeResolver::resolve() returns a Style::Update object that contains all the changes to be made
for the whole composed tree. RenderTreeUpdater then applies the changes updating, building or tearing
down portions of the render tree as needed.

Style::Update consists of a map that contains new style for each newly resolved element along with some
metadata. A separate map contains text nodes that require reconstruction. It also tracks change roots so
RenderTreeUpdater needs to traverse the changed subtrees only.

The patch eliminates the recursive render tree build code path replacing it with iterative functions.

This will enable future optimizations. For example we won't need to commit to immediate rendering
changes simply because some script or internal function requires up-to-date style.

* CMakeLists.txt:
* WebCore.xcodeproj/project.pbxproj:
* css/StyleResolver.cpp:
(WebCore::StyleResolver::State::State):
(WebCore::StyleResolver::styleForElement):
* css/StyleResolver.h:
(WebCore::StyleResolver::setOverrideDocumentElementStyle):
(WebCore::StyleResolver::State::State):

    Root element style is needed for resolving other elements. Add a way to provide it without looking
    into active document style.

* dom/Document.cpp:
(WebCore::Document::recalcStyle):

    Resolve the document style and commit it immediately (for now).

(WebCore::Document::styleForElementIgnoringPendingStylesheets):
* dom/Document.h:
(WebCore::Document::setNeedsNotifyRemoveAllPendingStylesheet):
(WebCore::Document::inStyleRecalc):
(WebCore::Document::inRenderTreeUpdate):
* dom/Element.cpp:
(WebCore::Element::setChildIndex):

    Setting the unique bit is now done by style relations update code.

* dom/Node.cpp:
(WebCore::Node::setNeedsStyleRecalc):

    Prevent spurious style invalidation during render tree updating.

* rendering/RenderBox.cpp:
(WebCore::RenderBox::styleDidChange):

    Capturing body element color for color:-webkit-text is now done by TreeResolver.

* rendering/RenderElement.h:
(WebCore::RenderElement::setAnimatableStyle): Deleted.

    No longer used.

* style/RenderTreePosition.cpp:
(WebCore::RenderTreePosition::nextSiblingRenderer):

    Skip over non-rendered slot elements.

* style/RenderTreeUpdater.cpp: Added.
(WebCore::RenderTreeUpdater::Parent::Parent):
(WebCore::RenderTreeUpdater::RenderTreeUpdater):
(WebCore::hasDisplayContents):
(WebCore::findRenderingRoot):
(WebCore::RenderTreeUpdater::commit):

    Call updateRenderTree for each change root.

(WebCore::shouldCreateRenderer):
(WebCore::RenderTreeUpdater::updateRenderTree):

    Iteratively traverse the composed tree starting for a change root.
    Apply the changes calling updateElementRenderer and updateTextRenderer as needed.
    Enter subtrees that haves changes to apply.

(WebCore::RenderTreeUpdater::renderTreePosition):

    We may not create renderers for all elements (&lt;slot&gt; or more generally display:contents) that
    have rendered descendants. Search the parent stack to find the valid position.

(WebCore::RenderTreeUpdater::pushParent):
(WebCore::RenderTreeUpdater::popParent):
(WebCore::RenderTreeUpdater::popParentsToDepth):

    Maintain parent stack.

(WebCore::pseudoStyleCacheIsInvalid):
(WebCore::RenderTreeUpdater::updateElementRenderer):

    Create, delete or update the renderer.

(WebCore::moveToFlowThreadIfNeeded):
(WebCore::RenderTreeUpdater::createRenderer):
(WebCore::textRendererIsNeeded):
(WebCore::createTextRenderer):
(WebCore::RenderTreeUpdater::updateTextRenderer):
(WebCore::RenderTreeUpdater::invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded):

    This is moved from TreeResolver.

(WebCore::needsPseudoElement):
(WebCore::RenderTreeUpdater::updateBeforeOrAfterPseudoElement):

    Pseudo elements are handled entirely during render tree construction. Compute their style and
    create or delete them as needed.

* style/RenderTreeUpdater.h: Added.
(WebCore::RenderTreeUpdater::parent):
* style/StyleRelations.cpp:
(WebCore::Style::commitRelationsToRenderStyle):
(WebCore::Style::commitRelations):

    Commit to Style::Update instead of the document if needed.

(WebCore::Style::commitRelationsToDocument): Deleted.
* style/StyleRelations.h:
* style/StyleSharingResolver.cpp:
(WebCore::Style::elementHasDirectionAuto):
(WebCore::Style::SharingResolver::resolve):

    Fetch the shareable style from Style::Update instead of the active document style.

(WebCore::Style::SharingResolver::findSibling):
(WebCore::Style::SharingResolver::canShareStyleWithElement):
* style/StyleSharingResolver.h:
* style/StyleTreeResolver.cpp:
(WebCore::Style::TreeResolver::Parent::Parent):

    No need for render tree position anymore.

(WebCore::Style::TreeResolver::popScope):
(WebCore::Style::TreeResolver::styleForElement):
(WebCore::Style::invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded):
(WebCore::Style::createTextRendererIfNeeded):
(WebCore::Style::updateTextRendererAfterContentChange):
(WebCore::Style::resetStyleForNonRenderedDescendants):
(WebCore::Style::detachChildren):
(WebCore::Style::detachSlotAssignees):
(WebCore::Style::detachRenderTree):
(WebCore::Style::TreeResolver::resolveElement):

    Just resolve the style and return it, no more applying or entering render tree construction code paths.

(WebCore::Style::resolveTextNode):
(WebCore::Style::elementImplicitVisibility):
(WebCore::Style::TreeResolver::pushParent):
(WebCore::Style::TreeResolver::popParent):
(WebCore::Style::TreeResolver::popParentsToDepth):
(WebCore::Style::shouldResolvePseudoElement):
(WebCore::Style::TreeResolver::resolveComposedTree):

    Add style changes to Style::Update.

(WebCore::Style::TreeResolver::resolve):

    Return Style::Update object if non-empty.

(WebCore::Style::postResolutionCallbackQueue):
(WebCore::Style::shouldCreateRenderer): Deleted.
(WebCore::Style::moveToFlowThreadIfNeeded): Deleted.
(WebCore::Style::TreeResolver::createRenderer): Deleted.
(WebCore::Style::TreeResolver::createRenderTreeForChildren): Deleted.
(WebCore::Style::TreeResolver::createRenderTreeForShadowRoot): Deleted.
(WebCore::Style::beforeOrAfterPseudoElement): Deleted.
(WebCore::Style::setBeforeOrAfterPseudoElement): Deleted.
(WebCore::Style::clearBeforeOrAfterPseudoElement): Deleted.
(WebCore::Style::needsPseudoElement): Deleted.
(WebCore::Style::TreeResolver::createRenderTreeForBeforeOrAfterPseudoElement): Deleted.
(WebCore::Style::TreeResolver::createRenderTreeForSlotAssignees): Deleted.
(WebCore::Style::TreeResolver::createRenderTreeRecursively): Deleted.
(WebCore::Style::pseudoStyleCacheIsInvalid): Deleted.
(WebCore::Style::TreeResolver::resolveBeforeOrAfterPseudoElement): Deleted.

    Remove the recursive render tree building code path.

* style/StyleTreeResolver.h:
(WebCore::Style::TreeResolver::scope):
* style/StyleUpdate.cpp: Added.
(WebCore::Style::Update::Update):
(WebCore::Style::Update::elementUpdate):
(WebCore::Style::Update::textUpdate):
(WebCore::Style::Update::elementStyle):
(WebCore::Style::Update::addElement):
(WebCore::Style::Update::addText):
(WebCore::Style::Update::addPossibleRoot):
* style/StyleUpdate.h: Added.
(WebCore::Style::Update::roots):
(WebCore::Style::Update::document):
* svg/SVGElement.h:
(WebCore::SVGElement::updateRelativeLengthsInformation):
* svg/SVGUseElement.cpp:
(WebCore::SVGUseElement::svgAttributeChanged):
(WebCore::SVGUseElement::willRecalcStyle):
(WebCore::SVGUseElement::willAttachRenderers): Deleted.

    Switvh willAttachRenderers to willRecalcStyle as the former is now called too late.

* svg/SVGUseElement.h:

LayoutTests:

* TestExpectations:

    Skip mathml/presentation/menclose-notation-attribute-change-value.html. It will be fixed by upcoming MathML refactoring.

* css3/blending/repaint/blend-mode-isolate-stacking-context-expected.txt:
* css3/viewport-percentage-lengths/viewport-percentage-lengths-resize-expected.txt:

    This is a progression.

* editing/mac/spelling/autocorrection-contraction-expected.txt:
* editing/mac/spelling/autocorrection-removing-underline-after-paste-expected.txt:
* editing/mac/spelling/autocorrection-removing-underline-expected.txt:
* editing/mac/spelling/autocorrection-simple-expected.txt:
* editing/style/remove-underline-from-stylesheet-expected.txt:
* editing/style/typing-style-003-expected.txt:

    Non-rendered whitespace related changes.

* platform/ios-simulator/TestExpectations:

    Skip fast/regions/position-writing-modes-in-variable-width-regions.html on iOS. Similar tests are mostly already skipped.

* platform/ios-simulator/editing/style/typing-style-003-expected.txt: Added.
* platform/mac-wk2/editing/mac/spelling/autocorrection-contraction-expected.txt:
* platform/mac/editing/inserting/editable-html-element-expected.txt:
* platform/mac/editing/inserting/editing-empty-divs-expected.txt:
* platform/mac/editing/inserting/insert-at-end-02-expected.txt:
* platform/mac/editing/pasteboard/4989774-expected.txt:
* platform/mac/editing/selection/4983858-expected.txt:

    Non-rendered whitespace related changes.</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkLayoutTestsChangeLog">trunk/LayoutTests/ChangeLog</a></li>
<li><a href="#trunkLayoutTestsTestExpectations">trunk/LayoutTests/TestExpectations</a></li>
<li><a href="#trunkLayoutTestscss3blendingrepaintblendmodeisolatestackingcontextexpectedtxt">trunk/LayoutTests/css3/blending/repaint/blend-mode-isolate-stacking-context-expected.txt</a></li>
<li><a href="#trunkLayoutTestscss3viewportpercentagelengthsviewportpercentagelengthsresizeexpectedtxt">trunk/LayoutTests/css3/viewport-percentage-lengths/viewport-percentage-lengths-resize-expected.txt</a></li>
<li><a href="#trunkLayoutTestseditingmacspellingautocorrectioncontractionexpectedtxt">trunk/LayoutTests/editing/mac/spelling/autocorrection-contraction-expected.txt</a></li>
<li><a href="#trunkLayoutTestseditingmacspellingautocorrectionremovingunderlineafterpasteexpectedtxt">trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-after-paste-expected.txt</a></li>
<li><a href="#trunkLayoutTestseditingmacspellingautocorrectionremovingunderlineexpectedtxt">trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-expected.txt</a></li>
<li><a href="#trunkLayoutTestseditingmacspellingautocorrectionsimpleexpectedtxt">trunk/LayoutTests/editing/mac/spelling/autocorrection-simple-expected.txt</a></li>
<li><a href="#trunkLayoutTestseditingstyleremoveunderlinefromstylesheetexpectedtxt">trunk/LayoutTests/editing/style/remove-underline-from-stylesheet-expected.txt</a></li>
<li><a href="#trunkLayoutTestseditingstyletypingstyle003expectedtxt">trunk/LayoutTests/editing/style/typing-style-003-expected.txt</a></li>
<li><a href="#trunkLayoutTestsfastdombeforeloadremovebadobjectinbeforeloadlistenerexpectedtxt">trunk/LayoutTests/fast/dom/beforeload/remove-bad-object-in-beforeload-listener-expected.txt</a></li>
<li><a href="#trunkLayoutTestsfastdombeforeloadremoveflashinbeforeloadlistenerexpectedtxt">trunk/LayoutTests/fast/dom/beforeload/remove-flash-in-beforeload-listener-expected.txt</a></li>
<li><a href="#trunkLayoutTestsplatformiossimulatorTestExpectations">trunk/LayoutTests/platform/ios-simulator/TestExpectations</a></li>
<li><a href="#trunkLayoutTestsplatformmaceditinginsertingeditablehtmlelementexpectedtxt">trunk/LayoutTests/platform/mac/editing/inserting/editable-html-element-expected.txt</a></li>
<li><a href="#trunkLayoutTestsplatformmaceditinginsertingeditingemptydivsexpectedtxt">trunk/LayoutTests/platform/mac/editing/inserting/editing-empty-divs-expected.txt</a></li>
<li><a href="#trunkLayoutTestsplatformmaceditinginsertinginsertatend02expectedtxt">trunk/LayoutTests/platform/mac/editing/inserting/insert-at-end-02-expected.txt</a></li>
<li><a href="#trunkLayoutTestsplatformmaceditingpasteboard4989774expectedtxt">trunk/LayoutTests/platform/mac/editing/pasteboard/4989774-expected.txt</a></li>
<li><a href="#trunkLayoutTestsplatformmaceditingselection4983858expectedtxt">trunk/LayoutTests/platform/mac/editing/selection/4983858-expected.txt</a></li>
<li><a href="#trunkLayoutTestsplatformmacwk2editingmacspellingautocorrectioncontractionexpectedtxt">trunk/LayoutTests/platform/mac-wk2/editing/mac/spelling/autocorrection-contraction-expected.txt</a></li>
<li><a href="#trunkLayoutTestspluginsfocusexpectedtxt">trunk/LayoutTests/plugins/focus-expected.txt</a></li>
<li><a href="#trunkSourceWebCoreCMakeListstxt">trunk/Source/WebCore/CMakeLists.txt</a></li>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreWebCorexcodeprojprojectpbxproj">trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceWebCorecssStyleResolvercpp">trunk/Source/WebCore/css/StyleResolver.cpp</a></li>
<li><a href="#trunkSourceWebCorecssStyleResolverh">trunk/Source/WebCore/css/StyleResolver.h</a></li>
<li><a href="#trunkSourceWebCoredomDocumentcpp">trunk/Source/WebCore/dom/Document.cpp</a></li>
<li><a href="#trunkSourceWebCoredomDocumenth">trunk/Source/WebCore/dom/Document.h</a></li>
<li><a href="#trunkSourceWebCoredomElementcpp">trunk/Source/WebCore/dom/Element.cpp</a></li>
<li><a href="#trunkSourceWebCoredomNodecpp">trunk/Source/WebCore/dom/Node.cpp</a></li>
<li><a href="#trunkSourceWebCorerenderingRenderBoxcpp">trunk/Source/WebCore/rendering/RenderBox.cpp</a></li>
<li><a href="#trunkSourceWebCorerenderingRenderElementh">trunk/Source/WebCore/rendering/RenderElement.h</a></li>
<li><a href="#trunkSourceWebCorestyleRenderTreePositioncpp">trunk/Source/WebCore/style/RenderTreePosition.cpp</a></li>
<li><a href="#trunkSourceWebCorestyleStyleRelationscpp">trunk/Source/WebCore/style/StyleRelations.cpp</a></li>
<li><a href="#trunkSourceWebCorestyleStyleRelationsh">trunk/Source/WebCore/style/StyleRelations.h</a></li>
<li><a href="#trunkSourceWebCorestyleStyleSharingResolvercpp">trunk/Source/WebCore/style/StyleSharingResolver.cpp</a></li>
<li><a href="#trunkSourceWebCorestyleStyleSharingResolverh">trunk/Source/WebCore/style/StyleSharingResolver.h</a></li>
<li><a href="#trunkSourceWebCorestyleStyleTreeResolvercpp">trunk/Source/WebCore/style/StyleTreeResolver.cpp</a></li>
<li><a href="#trunkSourceWebCorestyleStyleTreeResolverh">trunk/Source/WebCore/style/StyleTreeResolver.h</a></li>
<li><a href="#trunkSourceWebCoresvgSVGElementh">trunk/Source/WebCore/svg/SVGElement.h</a></li>
<li><a href="#trunkSourceWebCoresvgSVGUseElementcpp">trunk/Source/WebCore/svg/SVGUseElement.cpp</a></li>
<li><a href="#trunkSourceWebCoresvgSVGUseElementh">trunk/Source/WebCore/svg/SVGUseElement.h</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkLayoutTestsplatformiossimulatoreditingstyletypingstyle003expectedtxt">trunk/LayoutTests/platform/ios-simulator/editing/style/typing-style-003-expected.txt</a></li>
<li><a href="#trunkSourceWebCorestyleRenderTreeUpdatercpp">trunk/Source/WebCore/style/RenderTreeUpdater.cpp</a></li>
<li><a href="#trunkSourceWebCorestyleRenderTreeUpdaterh">trunk/Source/WebCore/style/RenderTreeUpdater.h</a></li>
<li><a href="#trunkSourceWebCorestyleStyleUpdatecpp">trunk/Source/WebCore/style/StyleUpdate.cpp</a></li>
<li><a href="#trunkSourceWebCorestyleStyleUpdateh">trunk/Source/WebCore/style/StyleUpdate.h</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkLayoutTestsChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/ChangeLog (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/ChangeLog        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/ChangeLog        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -1,3 +1,42 @@
</span><ins>+2016-03-31  Antti Koivisto  &lt;antti@apple.com&gt;
+
+        Separate render tree updating from style resolve
+        https://bugs.webkit.org/show_bug.cgi?id=155298
+
+        Reviewed by Andreas Kling.
+
+        * TestExpectations:
+
+            Skip mathml/presentation/menclose-notation-attribute-change-value.html. It will be fixed by upcoming MathML refactoring.
+
+        * css3/blending/repaint/blend-mode-isolate-stacking-context-expected.txt:
+        * css3/viewport-percentage-lengths/viewport-percentage-lengths-resize-expected.txt:
+
+            This is a progression.
+
+        * editing/mac/spelling/autocorrection-contraction-expected.txt:
+        * editing/mac/spelling/autocorrection-removing-underline-after-paste-expected.txt:
+        * editing/mac/spelling/autocorrection-removing-underline-expected.txt:
+        * editing/mac/spelling/autocorrection-simple-expected.txt:
+        * editing/style/remove-underline-from-stylesheet-expected.txt:
+        * editing/style/typing-style-003-expected.txt:
+
+            Non-rendered whitespace related changes.
+
+        * platform/ios-simulator/TestExpectations:
+
+            Skip fast/regions/position-writing-modes-in-variable-width-regions.html on iOS. Similar tests are mostly already skipped.
+
+        * platform/ios-simulator/editing/style/typing-style-003-expected.txt: Added.
+        * platform/mac-wk2/editing/mac/spelling/autocorrection-contraction-expected.txt:
+        * platform/mac/editing/inserting/editable-html-element-expected.txt:
+        * platform/mac/editing/inserting/editing-empty-divs-expected.txt:
+        * platform/mac/editing/inserting/insert-at-end-02-expected.txt:
+        * platform/mac/editing/pasteboard/4989774-expected.txt:
+        * platform/mac/editing/selection/4983858-expected.txt:
+
+            Non-rendered whitespace related changes.
+
</ins><span class="cx"> 2016-03-31  Chris Fleizach  &lt;cfleizach@apple.com&gt;
</span><span class="cx"> 
</span><span class="cx">         AX: &lt;attachment&gt; element not accessible
</span></span></pre></div>
<a id="trunkLayoutTestsTestExpectations"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/TestExpectations (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/TestExpectations        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/TestExpectations        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -990,6 +990,9 @@
</span><span class="cx"> storage/indexeddb/modern/exceed-open-file-limit.html [ Skip ]
</span><span class="cx"> webkit.org/b/155028 storage/indexeddb/modern/256-open-databases.html [ Skip ]
</span><span class="cx"> 
</span><ins>+# Fixed by upcoming MathML refactoring
+webkit.org/b/155019 mathml/presentation/menclose-notation-attribute-change-value.html [ Skip ]
+
</ins><span class="cx"> ### END OF IndexedDB failures
</span><span class="cx"> ########################################
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkLayoutTestscss3blendingrepaintblendmodeisolatestackingcontextexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/css3/blending/repaint/blend-mode-isolate-stacking-context-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/css3/blending/repaint/blend-mode-isolate-stacking-context-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/css3/blending/repaint/blend-mode-isolate-stacking-context-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -21,10 +21,10 @@
</span><span class="cx">   (rect 48 290 60 60)
</span><span class="cx">   (rect 28 290 60 60)
</span><span class="cx">   (rect 48 290 60 60)
</span><ins>+  (rect 28 526 60 60)
+  (rect 48 526 60 60)
</ins><span class="cx">   (rect 48 408 60 60)
</span><span class="cx">   (rect 48 408 60 60)
</span><del>-  (rect 28 526 60 60)
-  (rect 48 526 60 60)
</del><span class="cx">   (rect 48 644 60 60)
</span><span class="cx">   (rect 68 644 60 60)
</span><span class="cx">   (rect 48 644 60 60)
</span></span></pre></div>
<a id="trunkLayoutTestscss3viewportpercentagelengthsviewportpercentagelengthsresizeexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/css3/viewport-percentage-lengths/viewport-percentage-lengths-resize-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/css3/viewport-percentage-lengths/viewport-percentage-lengths-resize-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/css3/viewport-percentage-lengths/viewport-percentage-lengths-resize-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -17,19 +17,19 @@
</span><span class="cx"> PASS getComputedStyle(test).fontSize is &quot;30px&quot;
</span><span class="cx"> PASS getComputedStyle(test).width is &quot;450px&quot;
</span><span class="cx"> PASS getComputedStyle(testpseudo, ':after').marginLeft is &quot;120px&quot;
</span><del>-FAIL getComputedStyle(testpseudo, ':after').paddingRight should be 225px. Was 200px.
</del><ins>+PASS getComputedStyle(testpseudo, ':after').paddingRight is &quot;225px&quot;
</ins><span class="cx"> PASS innerWidth is 900
</span><span class="cx"> PASS innerHeight is 640
</span><span class="cx"> PASS getComputedStyle(test).fontSize is &quot;32px&quot;
</span><span class="cx"> PASS getComputedStyle(test).width is &quot;450px&quot;
</span><del>-FAIL getComputedStyle(testpseudo, ':after').marginLeft should be 128px. Was 120px.
-FAIL getComputedStyle(testpseudo, ':after').paddingRight should be 225px. Was 200px.
</del><ins>+PASS getComputedStyle(testpseudo, ':after').marginLeft is &quot;128px&quot;
+PASS getComputedStyle(testpseudo, ':after').paddingRight is &quot;225px&quot;
</ins><span class="cx"> PASS innerWidth is 500
</span><span class="cx"> PASS innerHeight is 640
</span><span class="cx"> PASS getComputedStyle(test).fontSize is &quot;32px&quot;
</span><span class="cx"> PASS getComputedStyle(test).width is &quot;250px&quot;
</span><del>-FAIL getComputedStyle(testpseudo, ':after').marginLeft should be 100px. Was 120px.
-FAIL getComputedStyle(testpseudo, ':after').paddingRight should be 160px. Was 200px.
</del><ins>+PASS getComputedStyle(testpseudo, ':after').marginLeft is &quot;100px&quot;
+PASS getComputedStyle(testpseudo, ':after').paddingRight is &quot;160px&quot;
</ins><span class="cx"> PASS innerWidth is 800
</span><span class="cx"> PASS innerHeight is 600
</span><span class="cx"> PASS getComputedStyle(test).fontSize is &quot;30px&quot;
</span></span></pre></div>
<a id="trunkLayoutTestseditingmacspellingautocorrectioncontractionexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/editing/mac/spelling/autocorrection-contraction-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/editing/mac/spelling/autocorrection-contraction-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/editing/mac/spelling/autocorrection-contraction-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -279,4 +279,4 @@
</span><span class="cx">           RenderText {#text} at (0,0) size 160x28
</span><span class="cx">             text run at (0,0) width 154: &quot;would' wouldn't&quot;
</span><span class="cx">             text run at (153,0) width 7: &quot; &quot;
</span><del>-caret: position 16 of child 0 {#text} of child 5 {DIV} of child 3 {DIV} of body
</del><ins>+caret: position 16 of child 0 {#text} of child 6 {DIV} of child 3 {DIV} of body
</ins></span></pre></div>
<a id="trunkLayoutTestseditingmacspellingautocorrectionremovingunderlineafterpasteexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-after-paste-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-after-paste-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-after-paste-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -82,4 +82,4 @@
</span><span class="cx">             text run at (0,28) width 34: &quot;baz&quot;
</span><span class="cx">         RenderBlock {DIV} at (14,70) size 756x28
</span><span class="cx">           RenderBR {BR} at (0,0) size 0x28
</span><del>-caret: position 0 of child 0 {BR} of child 4 {DIV} of child 5 {DIV} of body
</del><ins>+caret: position 0 of child 0 {BR} of child 5 {DIV} of child 5 {DIV} of body
</ins></span></pre></div>
<a id="trunkLayoutTestseditingmacspellingautocorrectionremovingunderlineexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/editing/mac/spelling/autocorrection-removing-underline-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -78,4 +78,4 @@
</span><span class="cx">           RenderInline {SPAN} at (0,0) size 1x28
</span><span class="cx">         RenderBlock {DIV} at (14,42) size 756x28
</span><span class="cx">           RenderBR {BR} at (0,0) size 0x28
</span><del>-caret: position 0 of child 0 {BR} of child 2 {DIV} of child 5 {DIV} of body
</del><ins>+caret: position 0 of child 0 {BR} of child 3 {DIV} of child 5 {DIV} of body
</ins></span></pre></div>
<a id="trunkLayoutTestseditingmacspellingautocorrectionsimpleexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/editing/mac/spelling/autocorrection-simple-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/editing/mac/spelling/autocorrection-simple-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/editing/mac/spelling/autocorrection-simple-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -137,4 +137,4 @@
</span><span class="cx">         RenderBlock {DIV} at (14,42) size 756x28
</span><span class="cx">           RenderText {#text} at (0,0) size 138x28
</span><span class="cx">             text run at (0,0) width 138: &quot;the notational,&quot;
</span><del>-caret: position 15 of child 0 {#text} of child 2 {DIV} of child 7 {DIV} of body
</del><ins>+caret: position 15 of child 0 {#text} of child 3 {DIV} of child 7 {DIV} of body
</ins></span></pre></div>
<a id="trunkLayoutTestseditingstyleremoveunderlinefromstylesheetexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/editing/style/remove-underline-from-stylesheet-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/editing/style/remove-underline-from-stylesheet-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/editing/style/remove-underline-from-stylesheet-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -76,5 +76,7 @@
</span><span class="cx"> | &quot;xxxxxx &quot;
</span><span class="cx"> | &quot;&lt;#selection-anchor&gt;xxxxxx&lt;#selection-focus&gt;&quot;
</span><span class="cx"> | &quot; xxxxxx&quot;
</span><ins>+| &quot;
+&quot;
</ins><span class="cx"> | &lt;span&gt;
</span><span class="cx"> |   id=&quot;test&quot;
</span></span></pre></div>
<a id="trunkLayoutTestseditingstyletypingstyle003expectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/editing/style/typing-style-003-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/editing/style/typing-style-003-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/editing/style/typing-style-003-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -52,10 +52,10 @@
</span><span class="cx"> EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
</span><span class="cx"> xxxxxxxxxxxxxxx
</span><span class="cx"> execTypeCharacterCommand: x &lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
</span><del>-execTypeCharacterCommand: xx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
-execTypeCharacterCommand: xxx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
-execBoldCommand: xxx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
-execTypeCharacterCommand: xxx&lt;b&gt;x&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
</del><ins>+execTypeCharacterCommand: xx &lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx &lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execBoldCommand: xxx &lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;x&lt;/b&gt; &lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
</ins><span class="cx"> execTypeCharacterCommand: xxx&lt;b&gt;xx&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
</span><span class="cx"> execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
</span><span class="cx"> execItalicCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
</span></span></pre></div>
<a id="trunkLayoutTestsfastdombeforeloadremovebadobjectinbeforeloadlistenerexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/fast/dom/beforeload/remove-bad-object-in-beforeload-listener-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/fast/dom/beforeload/remove-bad-object-in-beforeload-listener-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/fast/dom/beforeload/remove-bad-object-in-beforeload-listener-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -1,3 +1,4 @@
</span><span class="cx"> This page tests that you can correctly remove an object element with an invalid data URL in its beforeload listener without causing a crash.
</span><span class="cx"> 
</span><span class="cx"> PASS
</span><ins>+
</ins></span></pre></div>
<a id="trunkLayoutTestsfastdombeforeloadremoveflashinbeforeloadlistenerexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/fast/dom/beforeload/remove-flash-in-beforeload-listener-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/fast/dom/beforeload/remove-flash-in-beforeload-listener-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/fast/dom/beforeload/remove-flash-in-beforeload-listener-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -1,3 +1,4 @@
</span><span class="cx"> This page tests that you can correctly remove a flash object in a beforeload listener without causing a crash.
</span><span class="cx"> 
</span><span class="cx"> PASS
</span><ins>+
</ins></span></pre></div>
<a id="trunkLayoutTestsplatformiossimulatorTestExpectations"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/platform/ios-simulator/TestExpectations (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/ios-simulator/TestExpectations        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/platform/ios-simulator/TestExpectations        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -2053,6 +2053,7 @@
</span><span class="cx"> fast/regions/percentage-margins-mixed-rtl-dominant-regions.html [ ImageOnlyFailure ]
</span><span class="cx"> fast/regions/percentage-margins-rtl-variable-width-regions.html [ ImageOnlyFailure ]
</span><span class="cx"> fast/regions/percentage-margins-variable-width-regions.html [ ImageOnlyFailure ]
</span><ins>+fast/regions/position-writing-modes-in-variable-width-regions.html [ ImageOnlyFailure ]
</ins><span class="cx"> fast/regions/positioning/fixed-in-named-flow-position-changed.html [ ImageOnlyFailure ]
</span><span class="cx"> fast/regions/positioning/fixed-inside-fixed-in-named-flow.html [ ImageOnlyFailure ]
</span><span class="cx"> fast/regions/positioning/fixed-inside-named-flow-zIndex.html [ ImageOnlyFailure ]
</span></span></pre></div>
<a id="trunkLayoutTestsplatformiossimulatoreditingstyletypingstyle003expectedtxt"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/platform/ios-simulator/editing/style/typing-style-003-expected.txt (0 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/ios-simulator/editing/style/typing-style-003-expected.txt                                (rev 0)
+++ trunk/LayoutTests/platform/ios-simulator/editing/style/typing-style-003-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -0,0 +1,72 @@
</span><ins>+EDITING DELEGATE: shouldBeginEditingInDOMRange:range from 0 of DIV &gt; BODY &gt; HTML &gt; #document to 3 of DIV &gt; BODY &gt; HTML &gt; #document
+EDITING DELEGATE: webViewDidBeginEditing:WebViewDidBeginEditingNotification
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 0 of DIV &gt; BODY &gt; HTML &gt; #document to 0 of DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 3 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 3 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 1 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 2 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 2 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 3 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 3 of #text &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 1 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 2 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 2 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 3 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document to 3 of #text &gt; I &gt; B &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 1 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 2 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 2 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 3 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document to 3 of #text &gt; I &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 1 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+EDITING DELEGATE: shouldChangeSelectedDOMRange:range from 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 2 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document toDOMRange:range from 3 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document to 3 of #text &gt; DIV &gt; BODY &gt; HTML &gt; #document affinity:NSSelectionAffinityDownstream stillSelecting:FALSE
+EDITING DELEGATE: webViewDidChangeSelection:WebViewDidChangeSelectionNotification
+EDITING DELEGATE: webViewDidChange:WebViewDidChangeNotification
+xxxxxxxxxxxxxxx
+execTypeCharacterCommand: x &lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execBoldCommand: xxx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;x&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xx&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execItalicCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;i&gt;x&lt;/i&gt;&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;i&gt;xx&lt;/i&gt;&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;i&gt;xxx&lt;/i&gt;&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execBoldCommand: xxx&lt;b&gt;xxx&lt;i&gt;xxx&lt;/i&gt;&lt;/b&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;i&gt;&lt;b&gt;xxx&lt;/b&gt;x&lt;/i&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;i&gt;&lt;b&gt;xxx&lt;/b&gt;xx&lt;/i&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;i&gt;&lt;b&gt;xxx&lt;/b&gt;xxx&lt;/i&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execItalicCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;i&gt;&lt;b&gt;xxx&lt;/b&gt;xxx&lt;/i&gt;&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;i&gt;&lt;b&gt;xxx&lt;/b&gt;xxx&lt;/i&gt;x&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;i&gt;&lt;b&gt;xxx&lt;/b&gt;xxx&lt;/i&gt;xx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
+execTypeCharacterCommand: xxx&lt;b&gt;xxx&lt;/b&gt;&lt;i&gt;&lt;b&gt;xxx&lt;/b&gt;xxx&lt;/i&gt;xxx&lt;span id=&quot;test&quot;&gt;&lt;/span&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestsplatformmaceditinginsertingeditablehtmlelementexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/platform/mac/editing/inserting/editable-html-element-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/mac/editing/inserting/editable-html-element-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/platform/mac/editing/inserting/editable-html-element-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -22,7 +22,6 @@
</span><span class="cx">           text run at (0,18) width 767: &quot;inserting a paragraph separator doesn't split the body (inserting a paragraph separator usually splits/clones the enclosing&quot;
</span><span class="cx">           text run at (766,18) width 5: &quot; &quot;
</span><span class="cx">           text run at (0,36) width 132: &quot;block flow element).&quot;
</span><del>-        RenderText {#text} at (0,0) size 0x0
</del><span class="cx">       RenderBlock {DIV} at (0,54) size 784x18
</span><span class="cx">         RenderBR {BR} at (0,0) size 0x18
</span><span class="cx"> caret: position 0 of child 0 {BR} of child 2 {DIV} of body
</span></span></pre></div>
<a id="trunkLayoutTestsplatformmaceditinginsertingeditingemptydivsexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/platform/mac/editing/inserting/editing-empty-divs-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/mac/editing/inserting/editing-empty-divs-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/platform/mac/editing/inserting/editing-empty-divs-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -65,7 +65,6 @@
</span><span class="cx">       RenderBlock {DIV} at (0,230) size 708x22 [border: (1px dotted #0000FF)]
</span><span class="cx">         RenderText {#text} at (1,1) size 8x18
</span><span class="cx">           text run at (1,1) width 8: &quot;c&quot;
</span><del>-        RenderText {#text} at (0,0) size 0x0
</del><span class="cx">       RenderBlock {P} at (0,268) size 784x18
</span><span class="cx">         RenderText {#text} at (0,0) size 240x18
</span><span class="cx">           text run at (0,0) width 240: &quot;This div contains a self-closing p tag.&quot;
</span><span class="lines">@@ -81,6 +80,5 @@
</span><span class="cx">         RenderBlock (anonymous) at (1,1) size 706x18
</span><span class="cx">           RenderText {#text} at (0,0) size 8x18
</span><span class="cx">             text run at (0,0) width 8: &quot;c&quot;
</span><del>-          RenderText {#text} at (0,0) size 0x0
</del><span class="cx">         RenderBlock {P} at (1,35) size 706x0
</span><span class="cx"> caret: position 1 of child 0 {#text} of child 21 {DIV} of body
</span></span></pre></div>
<a id="trunkLayoutTestsplatformmaceditinginsertinginsertatend02expectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/platform/mac/editing/inserting/insert-at-end-02-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/mac/editing/inserting/insert-at-end-02-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/platform/mac/editing/inserting/insert-at-end-02-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -29,5 +29,4 @@
</span><span class="cx">         RenderBlock (anonymous) at (2,46) size 780x18
</span><span class="cx">           RenderText {#text} at (0,0) size 8x18
</span><span class="cx">             text run at (0,0) width 8: &quot;x&quot;
</span><del>-          RenderText {#text} at (0,0) size 0x0
</del><span class="cx"> caret: position 1 of child 5 {#text} of child 5 {DIV} of body
</span></span></pre></div>
<a id="trunkLayoutTestsplatformmaceditingpasteboard4989774expectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/platform/mac/editing/pasteboard/4989774-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/mac/editing/pasteboard/4989774-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/platform/mac/editing/pasteboard/4989774-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -12,6 +12,4 @@
</span><span class="cx">         text run at (634,103) width 102: &quot;You should see&quot;
</span><span class="cx">         text run at (735,103) width 5: &quot; &quot;
</span><span class="cx">         text run at (0,121) width 364: &quot;several pictures above all in the same line/paragraph.&quot;
</span><del>-      RenderText {#text} at (0,0) size 0x0
-      RenderText {#text} at (0,0) size 0x0
</del><span class="cx"> caret: position 164 of child 4 {#text} of body
</span></span></pre></div>
<a id="trunkLayoutTestsplatformmaceditingselection4983858expectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/platform/mac/editing/selection/4983858-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/mac/editing/selection/4983858-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/platform/mac/editing/selection/4983858-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -10,7 +10,6 @@
</span><span class="cx">           text run at (716,0) width 65: &quot;paragraph&quot;
</span><span class="cx">           text run at (780,0) width 4: &quot; &quot;
</span><span class="cx">           text run at (0,18) width 165: &quot;below should be selected:&quot;
</span><del>-        RenderText {#text} at (0,0) size 0x0
</del><span class="cx">       RenderBlock {DIV} at (0,36) size 784x18
</span><span class="cx">         RenderText {#text} at (0,0) size 22x18
</span><span class="cx">           text run at (0,0) width 22: &quot;foo&quot;
</span></span></pre></div>
<a id="trunkLayoutTestsplatformmacwk2editingmacspellingautocorrectioncontractionexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/platform/mac-wk2/editing/mac/spelling/autocorrection-contraction-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/platform/mac-wk2/editing/mac/spelling/autocorrection-contraction-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/platform/mac-wk2/editing/mac/spelling/autocorrection-contraction-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -259,4 +259,4 @@
</span><span class="cx">           RenderText {#text} at (0,0) size 172x28
</span><span class="cx">             text run at (0,0) width 166: &quot;wouldn' wouldn't&quot;
</span><span class="cx">             text run at (165,0) width 7: &quot; &quot;
</span><del>-caret: position 17 of child 0 {#text} of child 5 {DIV} of child 3 {DIV} of body
</del><ins>+caret: position 17 of child 0 {#text} of child 6 {DIV} of child 3 {DIV} of body
</ins></span></pre></div>
<a id="trunkLayoutTestspluginsfocusexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/plugins/focus-expected.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/plugins/focus-expected.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/LayoutTests/plugins/focus-expected.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -24,3 +24,4 @@
</span><span class="cx"> This tests focusing Embeds and Objects. See LayoutTests/java for Applet elements.
</span><span class="cx"> 
</span><span class="cx">    Fallback contents.     Fallback contents. Fallback contents.      
</span><ins>+
</ins></span></pre></div>
<a id="trunkSourceWebCoreCMakeListstxt"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/CMakeLists.txt (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/CMakeLists.txt        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/CMakeLists.txt        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -2627,12 +2627,14 @@
</span><span class="cx">     style/IdChangeInvalidation.cpp
</span><span class="cx">     style/InlineTextBoxStyle.cpp
</span><span class="cx">     style/RenderTreePosition.cpp
</span><ins>+    style/RenderTreeUpdater.cpp
</ins><span class="cx">     style/StyleChange.cpp
</span><span class="cx">     style/StyleFontSizeFunctions.cpp
</span><span class="cx">     style/StyleRelations.cpp
</span><span class="cx">     style/StyleResolveForDocument.cpp
</span><span class="cx">     style/StyleSharingResolver.cpp
</span><span class="cx">     style/StyleTreeResolver.cpp
</span><ins>+    style/StyleUpdate.cpp
</ins><span class="cx"> 
</span><span class="cx">     svg/SVGAElement.cpp
</span><span class="cx">     svg/SVGAltGlyphDefElement.cpp
</span></span></pre></div>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/ChangeLog        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -1,3 +1,218 @@
</span><ins>+2016-03-31  Antti Koivisto  &lt;antti@apple.com&gt;
+
+        Separate render tree updating from style resolve
+        https://bugs.webkit.org/show_bug.cgi?id=155298
+
+        Reviewed by Andreas Kling.
+
+        This patch splits computing document style and applying the results into two distinct steps:
+
+        Style::TreeResolver::resolve()
+                |
+                | Style::Update
+                V
+        RenderTreeUpdater::commit()
+
+        Style::TreeResolver::resolve() returns a Style::Update object that contains all the changes to be made
+        for the whole composed tree. RenderTreeUpdater then applies the changes updating, building or tearing
+        down portions of the render tree as needed.
+
+        Style::Update consists of a map that contains new style for each newly resolved element along with some
+        metadata. A separate map contains text nodes that require reconstruction. It also tracks change roots so
+        RenderTreeUpdater needs to traverse the changed subtrees only.
+
+        The patch eliminates the recursive render tree build code path replacing it with iterative functions.
+
+        This will enable future optimizations. For example we won't need to commit to immediate rendering
+        changes simply because some script or internal function requires up-to-date style.
+
+        * CMakeLists.txt:
+        * WebCore.xcodeproj/project.pbxproj:
+        * css/StyleResolver.cpp:
+        (WebCore::StyleResolver::State::State):
+        (WebCore::StyleResolver::styleForElement):
+        * css/StyleResolver.h:
+        (WebCore::StyleResolver::setOverrideDocumentElementStyle):
+        (WebCore::StyleResolver::State::State):
+
+            Root element style is needed for resolving other elements. Add a way to provide it without looking
+            into active document style.
+
+        * dom/Document.cpp:
+        (WebCore::Document::recalcStyle):
+
+            Resolve the document style and commit it immediately (for now).
+
+        (WebCore::Document::styleForElementIgnoringPendingStylesheets):
+        * dom/Document.h:
+        (WebCore::Document::setNeedsNotifyRemoveAllPendingStylesheet):
+        (WebCore::Document::inStyleRecalc):
+        (WebCore::Document::inRenderTreeUpdate):
+        * dom/Element.cpp:
+        (WebCore::Element::setChildIndex):
+
+            Setting the unique bit is now done by style relations update code.
+
+        * dom/Node.cpp:
+        (WebCore::Node::setNeedsStyleRecalc):
+
+            Prevent spurious style invalidation during render tree updating.
+
+        * rendering/RenderBox.cpp:
+        (WebCore::RenderBox::styleDidChange):
+
+            Capturing body element color for color:-webkit-text is now done by TreeResolver.
+
+        * rendering/RenderElement.h:
+        (WebCore::RenderElement::setAnimatableStyle): Deleted.
+
+            No longer used.
+
+        * style/RenderTreePosition.cpp:
+        (WebCore::RenderTreePosition::nextSiblingRenderer):
+
+            Skip over non-rendered slot elements.
+
+        * style/RenderTreeUpdater.cpp: Added.
+        (WebCore::RenderTreeUpdater::Parent::Parent):
+        (WebCore::RenderTreeUpdater::RenderTreeUpdater):
+        (WebCore::hasDisplayContents):
+        (WebCore::findRenderingRoot):
+        (WebCore::RenderTreeUpdater::commit):
+
+            Call updateRenderTree for each change root.
+
+        (WebCore::shouldCreateRenderer):
+        (WebCore::RenderTreeUpdater::updateRenderTree):
+
+            Iteratively traverse the composed tree starting for a change root.
+            Apply the changes calling updateElementRenderer and updateTextRenderer as needed.
+            Enter subtrees that haves changes to apply.
+
+        (WebCore::RenderTreeUpdater::renderTreePosition):
+
+            We may not create renderers for all elements (&lt;slot&gt; or more generally display:contents) that
+            have rendered descendants. Search the parent stack to find the valid position.
+
+        (WebCore::RenderTreeUpdater::pushParent):
+        (WebCore::RenderTreeUpdater::popParent):
+        (WebCore::RenderTreeUpdater::popParentsToDepth):
+
+            Maintain parent stack.
+
+        (WebCore::pseudoStyleCacheIsInvalid):
+        (WebCore::RenderTreeUpdater::updateElementRenderer):
+
+            Create, delete or update the renderer.
+
+        (WebCore::moveToFlowThreadIfNeeded):
+        (WebCore::RenderTreeUpdater::createRenderer):
+        (WebCore::textRendererIsNeeded):
+        (WebCore::createTextRenderer):
+        (WebCore::RenderTreeUpdater::updateTextRenderer):
+        (WebCore::RenderTreeUpdater::invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded):
+
+            This is moved from TreeResolver.
+
+        (WebCore::needsPseudoElement):
+        (WebCore::RenderTreeUpdater::updateBeforeOrAfterPseudoElement):
+
+            Pseudo elements are handled entirely during render tree construction. Compute their style and
+            create or delete them as needed.
+
+        * style/RenderTreeUpdater.h: Added.
+        (WebCore::RenderTreeUpdater::parent):
+        * style/StyleRelations.cpp:
+        (WebCore::Style::commitRelationsToRenderStyle):
+        (WebCore::Style::commitRelations):
+
+            Commit to Style::Update instead of the document if needed.
+
+        (WebCore::Style::commitRelationsToDocument): Deleted.
+        * style/StyleRelations.h:
+        * style/StyleSharingResolver.cpp:
+        (WebCore::Style::elementHasDirectionAuto):
+        (WebCore::Style::SharingResolver::resolve):
+
+            Fetch the shareable style from Style::Update instead of the active document style.
+
+        (WebCore::Style::SharingResolver::findSibling):
+        (WebCore::Style::SharingResolver::canShareStyleWithElement):
+        * style/StyleSharingResolver.h:
+        * style/StyleTreeResolver.cpp:
+        (WebCore::Style::TreeResolver::Parent::Parent):
+
+            No need for render tree position anymore.
+
+        (WebCore::Style::TreeResolver::popScope):
+        (WebCore::Style::TreeResolver::styleForElement):
+        (WebCore::Style::invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded):
+        (WebCore::Style::createTextRendererIfNeeded):
+        (WebCore::Style::updateTextRendererAfterContentChange):
+        (WebCore::Style::resetStyleForNonRenderedDescendants):
+        (WebCore::Style::detachChildren):
+        (WebCore::Style::detachSlotAssignees):
+        (WebCore::Style::detachRenderTree):
+        (WebCore::Style::TreeResolver::resolveElement):
+
+            Just resolve the style and return it, no more applying or entering render tree construction code paths.
+
+        (WebCore::Style::resolveTextNode):
+        (WebCore::Style::elementImplicitVisibility):
+        (WebCore::Style::TreeResolver::pushParent):
+        (WebCore::Style::TreeResolver::popParent):
+        (WebCore::Style::TreeResolver::popParentsToDepth):
+        (WebCore::Style::shouldResolvePseudoElement):
+        (WebCore::Style::TreeResolver::resolveComposedTree):
+
+            Add style changes to Style::Update.
+
+        (WebCore::Style::TreeResolver::resolve):
+
+            Return Style::Update object if non-empty.
+
+        (WebCore::Style::postResolutionCallbackQueue):
+        (WebCore::Style::shouldCreateRenderer): Deleted.
+        (WebCore::Style::moveToFlowThreadIfNeeded): Deleted.
+        (WebCore::Style::TreeResolver::createRenderer): Deleted.
+        (WebCore::Style::TreeResolver::createRenderTreeForChildren): Deleted.
+        (WebCore::Style::TreeResolver::createRenderTreeForShadowRoot): Deleted.
+        (WebCore::Style::beforeOrAfterPseudoElement): Deleted.
+        (WebCore::Style::setBeforeOrAfterPseudoElement): Deleted.
+        (WebCore::Style::clearBeforeOrAfterPseudoElement): Deleted.
+        (WebCore::Style::needsPseudoElement): Deleted.
+        (WebCore::Style::TreeResolver::createRenderTreeForBeforeOrAfterPseudoElement): Deleted.
+        (WebCore::Style::TreeResolver::createRenderTreeForSlotAssignees): Deleted.
+        (WebCore::Style::TreeResolver::createRenderTreeRecursively): Deleted.
+        (WebCore::Style::pseudoStyleCacheIsInvalid): Deleted.
+        (WebCore::Style::TreeResolver::resolveBeforeOrAfterPseudoElement): Deleted.
+
+            Remove the recursive render tree building code path.
+
+        * style/StyleTreeResolver.h:
+        (WebCore::Style::TreeResolver::scope):
+        * style/StyleUpdate.cpp: Added.
+        (WebCore::Style::Update::Update):
+        (WebCore::Style::Update::elementUpdate):
+        (WebCore::Style::Update::textUpdate):
+        (WebCore::Style::Update::elementStyle):
+        (WebCore::Style::Update::addElement):
+        (WebCore::Style::Update::addText):
+        (WebCore::Style::Update::addPossibleRoot):
+        * style/StyleUpdate.h: Added.
+        (WebCore::Style::Update::roots):
+        (WebCore::Style::Update::document):
+        * svg/SVGElement.h:
+        (WebCore::SVGElement::updateRelativeLengthsInformation):
+        * svg/SVGUseElement.cpp:
+        (WebCore::SVGUseElement::svgAttributeChanged):
+        (WebCore::SVGUseElement::willRecalcStyle):
+        (WebCore::SVGUseElement::willAttachRenderers): Deleted.
+
+            Switvh willAttachRenderers to willRecalcStyle as the former is now called too late.
+
+        * svg/SVGUseElement.h:
+
</ins><span class="cx"> 2016-03-31  Chris Fleizach  &lt;cfleizach@apple.com&gt;
</span><span class="cx"> 
</span><span class="cx">         AX: &lt;attachment&gt; element not accessible
</span></span></pre></div>
<a id="trunkSourceWebCoreWebCorexcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -6559,6 +6559,8 @@
</span><span class="cx">                 E424A3A01330DF1E00CF6DC9 /* LegacyTileGridTile.mm in Sources */ = {isa = PBXBuildFile; fileRef = E424A39F1330DF1E00CF6DC9 /* LegacyTileGridTile.mm */; };
</span><span class="cx">                 E425A49A18292B840020CFCF /* CollectionIndexCache.h in Headers */ = {isa = PBXBuildFile; fileRef = E425A49918292B840020CFCF /* CollectionIndexCache.h */; };
</span><span class="cx">                 E4295FA412B0614E00D1ACE0 /* ResourceLoadPriority.h in Headers */ = {isa = PBXBuildFile; fileRef = E4295FA312B0614E00D1ACE0 /* ResourceLoadPriority.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><ins>+                E42E76DA1C7AF76C00E3614D /* StyleUpdate.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E42E76D91C7AF76C00E3614D /* StyleUpdate.cpp */; };
+                E42E76DC1C7AF77600E3614D /* StyleUpdate.h in Headers */ = {isa = PBXBuildFile; fileRef = E42E76DB1C7AF77600E3614D /* StyleUpdate.h */; };
</ins><span class="cx">                 E43105B816750F0C00DB2FB8 /* NodeTraversal.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E43105B716750F0C00DB2FB8 /* NodeTraversal.cpp */; };
</span><span class="cx">                 E43105BB16750F1600DB2FB8 /* NodeTraversal.h in Headers */ = {isa = PBXBuildFile; fileRef = E43105BA16750F1600DB2FB8 /* NodeTraversal.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="cx">                 E43A023B17EB370A004CDD25 /* RenderElement.h in Headers */ = {isa = PBXBuildFile; fileRef = E43A023A17EB370A004CDD25 /* RenderElement.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="lines">@@ -6614,6 +6616,8 @@
</span><span class="cx">                 E45390490EAFD637003695C8 /* WebCoreSystemInterfaceIOS.mm in Sources */ = {isa = PBXBuildFile; fileRef = E45390380EAFD637003695C8 /* WebCoreSystemInterfaceIOS.mm */; };
</span><span class="cx">                 E453904D0EAFD637003695C8 /* WidgetIOS.mm in Sources */ = {isa = PBXBuildFile; fileRef = E453903C0EAFD637003695C8 /* WidgetIOS.mm */; };
</span><span class="cx">                 E45390AE0EAFF4B5003695C8 /* SystemMemoryIOS.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E45390AD0EAFF4B5003695C8 /* SystemMemoryIOS.cpp */; };
</span><ins>+                E46180291C8A06CD0026C02C /* RenderTreeUpdater.h in Headers */ = {isa = PBXBuildFile; fileRef = E46180281C8A06CD0026C02C /* RenderTreeUpdater.h */; };
+                E461802B1C8A06D90026C02C /* RenderTreeUpdater.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E461802A1C8A06D90026C02C /* RenderTreeUpdater.cpp */; };
</ins><span class="cx">                 E461802D1C8DD2900026C02C /* StyleRelations.h in Headers */ = {isa = PBXBuildFile; fileRef = E461802C1C8DD2900026C02C /* StyleRelations.h */; };
</span><span class="cx">                 E461802F1C8DD4D20026C02C /* StyleRelations.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E461802E1C8DD4D20026C02C /* StyleRelations.cpp */; };
</span><span class="cx">                 E461D65D1BB0C7F000CB5645 /* AuthorStyleSheets.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E461D65C1BB0C7F000CB5645 /* AuthorStyleSheets.cpp */; };
</span><span class="lines">@@ -14595,6 +14599,8 @@
</span><span class="cx">                 E424A39F1330DF1E00CF6DC9 /* LegacyTileGridTile.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = LegacyTileGridTile.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E425A49918292B840020CFCF /* CollectionIndexCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CollectionIndexCache.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E4295FA312B0614E00D1ACE0 /* ResourceLoadPriority.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ResourceLoadPriority.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><ins>+                E42E76D91C7AF76C00E3614D /* StyleUpdate.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StyleUpdate.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
+                E42E76DB1C7AF77600E3614D /* StyleUpdate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StyleUpdate.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</ins><span class="cx">                 E43105B716750F0C00DB2FB8 /* NodeTraversal.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = NodeTraversal.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E43105BA16750F1600DB2FB8 /* NodeTraversal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = NodeTraversal.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E43A023A17EB370A004CDD25 /* RenderElement.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RenderElement.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="lines">@@ -14642,6 +14648,8 @@
</span><span class="cx">                 E45390380EAFD637003695C8 /* WebCoreSystemInterfaceIOS.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = WebCoreSystemInterfaceIOS.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E453903C0EAFD637003695C8 /* WidgetIOS.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = WidgetIOS.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E45390AD0EAFF4B5003695C8 /* SystemMemoryIOS.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SystemMemoryIOS.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><ins>+                E46180281C8A06CD0026C02C /* RenderTreeUpdater.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RenderTreeUpdater.h; sourceTree = &quot;&lt;group&gt;&quot;; };
+                E461802A1C8A06D90026C02C /* RenderTreeUpdater.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = RenderTreeUpdater.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</ins><span class="cx">                 E461802C1C8DD2900026C02C /* StyleRelations.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StyleRelations.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E461802E1C8DD4D20026C02C /* StyleRelations.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StyleRelations.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 E461D65C1BB0C7F000CB5645 /* AuthorStyleSheets.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = AuthorStyleSheets.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="lines">@@ -23512,6 +23520,8 @@
</span><span class="cx">                                 1C0106FF192594DF008A4201 /* InlineTextBoxStyle.h */,
</span><span class="cx">                                 5824ABA81AE849C8009074B7 /* RenderTreePosition.cpp */,
</span><span class="cx">                                 5824ABA91AE849C8009074B7 /* RenderTreePosition.h */,
</span><ins>+                                E461802A1C8A06D90026C02C /* RenderTreeUpdater.cpp */,
+                                E46180281C8A06CD0026C02C /* RenderTreeUpdater.h */,
</ins><span class="cx">                                 E401E0A51C3C0CF700F34D10 /* StyleChange.cpp */,
</span><span class="cx">                                 E401E0A31C3C0B8300F34D10 /* StyleChange.h */,
</span><span class="cx">                                 E4D58EB617B4ED8900CBDCA8 /* StyleFontSizeFunctions.cpp */,
</span><span class="lines">@@ -23524,6 +23534,8 @@
</span><span class="cx">                                 E47A3AC41C5EAC7900CCBFA7 /* StyleSharingResolver.h */,
</span><span class="cx">                                 E4DEAA1517A93DC3000E0430 /* StyleTreeResolver.cpp */,
</span><span class="cx">                                 E4DEAA1617A93DC3000E0430 /* StyleTreeResolver.h */,
</span><ins>+                                E42E76D91C7AF76C00E3614D /* StyleUpdate.cpp */,
+                                E42E76DB1C7AF77600E3614D /* StyleUpdate.h */,
</ins><span class="cx">                         );
</span><span class="cx">                         path = style;
</span><span class="cx">                         sourceTree = &quot;&lt;group&gt;&quot;;
</span><span class="lines">@@ -25959,6 +25971,7 @@
</span><span class="cx">                                 5C4304B1191AC908000E2BC0 /* EXTShaderTextureLOD.h in Headers */,
</span><span class="cx">                                 7728694F14F8882500F484DC /* EXTTextureFilterAnisotropic.h in Headers */,
</span><span class="cx">                                 A75E8B890E1DE2D6007F2481 /* FEBlend.h in Headers */,
</span><ins>+                                E46180291C8A06CD0026C02C /* RenderTreeUpdater.h in Headers */,
</ins><span class="cx">                                 A75E8B8B0E1DE2D6007F2481 /* FEColorMatrix.h in Headers */,
</span><span class="cx">                                 A75E8B8D0E1DE2D6007F2481 /* FEComponentTransfer.h in Headers */,
</span><span class="cx">                                 A75E8B8F0E1DE2D6007F2481 /* FEComposite.h in Headers */,
</span><span class="lines">@@ -26151,6 +26164,7 @@
</span><span class="cx">                                 A8EA79F70A1916DF00A8EF5F /* HTMLDListElement.h in Headers */,
</span><span class="cx">                                 93F198E508245E59001E9ABC /* HTMLDocument.h in Headers */,
</span><span class="cx">                                 977B3867122883E900B81FF8 /* HTMLDocumentParser.h in Headers */,
</span><ins>+                                E42E76DC1C7AF77600E3614D /* StyleUpdate.h in Headers */,
</ins><span class="cx">                                 93309DE8099E64920056E581 /* htmlediting.h in Headers */,
</span><span class="cx">                                 93F198E608245E59001E9ABC /* HTMLElement.h in Headers */,
</span><span class="cx">                                 A17C81230F2A5CF7005DAAEB /* HTMLElementFactory.h in Headers */,
</span><span class="lines">@@ -30537,6 +30551,7 @@
</span><span class="cx">                                 A84EBD780CB8C89200079609 /* JSStyleSheetListCustom.cpp in Sources */,
</span><span class="cx">                                 E1FF8F64180745D800132674 /* JSSubtleCrypto.cpp in Sources */,
</span><span class="cx">                                 E1FF8F681807460800132674 /* JSSubtleCryptoCustom.cpp in Sources */,
</span><ins>+                                E461802B1C8A06D90026C02C /* RenderTreeUpdater.cpp in Sources */,
</ins><span class="cx">                                 B20111070AB7740500DB0E68 /* JSSVGAElement.cpp in Sources */,
</span><span class="cx">                                 24D9129113CA951E00D21915 /* JSSVGAltGlyphDefElement.cpp in Sources */,
</span><span class="cx">                                 6515EC910D9723FF0063D49A /* JSSVGAltGlyphElement.cpp in Sources */,
</span><span class="lines">@@ -31075,6 +31090,7 @@
</span><span class="cx">                                 0F43C85D189E10CF00019AE2 /* PerformanceTiming.cpp in Sources */,
</span><span class="cx">                                 FD581FB41520F93B003A7A75 /* PeriodicWave.cpp in Sources */,
</span><span class="cx">                                 49D5DC2D0F423A73008F20FD /* PerspectiveTransformOperation.cpp in Sources */,
</span><ins>+                                E42E76DA1C7AF76C00E3614D /* StyleUpdate.cpp in Sources */,
</ins><span class="cx">                                 D0FF2A5D11F8C45A007E74E0 /* PingLoader.cpp in Sources */,
</span><span class="cx">                                 CD7D33431C7A123F00041293 /* PixelBufferConformerCV.cpp in Sources */,
</span><span class="cx">                                 0FDF45A71BD1C6FD00E4FA8C /* PlatformCAAnimation.cpp in Sources */,
</span></span></pre></div>
<a id="trunkSourceWebCorecssStyleResolvercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/css/StyleResolver.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/css/StyleResolver.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/css/StyleResolver.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -335,7 +335,7 @@
</span><span class="cx">     m_matchedPropertiesCacheAdditionsSinceLastSweep = 0;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-StyleResolver::State::State(Element&amp; element, RenderStyle* parentStyle, const RenderRegion* regionForStyling, const SelectorFilter* selectorFilter)
</del><ins>+StyleResolver::State::State(Element&amp; element, RenderStyle* parentStyle, RenderStyle* documentElementStyle, const RenderRegion* regionForStyling, const SelectorFilter* selectorFilter)
</ins><span class="cx">     : m_element(&amp;element)
</span><span class="cx">     , m_parentStyle(parentStyle)
</span><span class="cx">     , m_regionForStyling(regionForStyling)
</span><span class="lines">@@ -348,7 +348,10 @@
</span><span class="cx"> 
</span><span class="cx">     auto&amp; document = element.document();
</span><span class="cx">     auto* documentElement = document.documentElement();
</span><del>-    m_rootElementStyle = (!documentElement || documentElement == &amp;element) ? document.renderStyle() : documentElement-&gt;renderStyle();
</del><ins>+    if (!documentElement || documentElement == &amp;element)
+        m_rootElementStyle = document.renderStyle();
+    else
+        m_rootElementStyle = documentElementStyle ? documentElementStyle : documentElement-&gt;renderStyle();
</ins><span class="cx"> 
</span><span class="cx">     updateConversionData();
</span><span class="cx"> }
</span><span class="lines">@@ -375,7 +378,7 @@
</span><span class="cx"> {
</span><span class="cx">     RELEASE_ASSERT(!m_inLoadPendingImages);
</span><span class="cx"> 
</span><del>-    m_state = State(element, parentStyle, regionForStyling, selectorFilter);
</del><ins>+    m_state = State(element, parentStyle, m_overrideDocumentElementStyle.get(), regionForStyling, selectorFilter);
</ins><span class="cx">     State&amp; state = m_state;
</span><span class="cx"> 
</span><span class="cx">     if (state.parentStyle()) {
</span></span></pre></div>
<a id="trunkSourceWebCorecssStyleResolverh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/css/StyleResolver.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/css/StyleResolver.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/css/StyleResolver.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -164,6 +164,8 @@
</span><span class="cx"> 
</span><span class="cx">     const MediaQueryEvaluator&amp; mediaQueryEvaluator() const { return *m_medium; }
</span><span class="cx"> 
</span><ins>+    void setOverrideDocumentElementStyle(RenderStyle* style) { m_overrideDocumentElementStyle = style; }
+
</ins><span class="cx"> private:
</span><span class="cx">     Ref&lt;RenderStyle&gt; styleForKeyframe(const RenderStyle*, const StyleKeyframe*, KeyframeValue&amp;);
</span><span class="cx"> 
</span><span class="lines">@@ -359,7 +361,7 @@
</span><span class="cx">     class State {
</span><span class="cx">     public:
</span><span class="cx">         State() { }
</span><del>-        State(Element&amp;, RenderStyle* parentStyle, const RenderRegion* regionForStyling = nullptr, const SelectorFilter* = nullptr);
</del><ins>+        State(Element&amp;, RenderStyle* parentStyle, RenderStyle* documentElementStyle = nullptr, const RenderRegion* regionForStyling = nullptr, const SelectorFilter* = nullptr);
</ins><span class="cx"> 
</span><span class="cx">     public:
</span><span class="cx">         void clear();
</span><span class="lines">@@ -524,6 +526,8 @@
</span><span class="cx"> 
</span><span class="cx">     bool m_matchAuthorAndUserStyles;
</span><span class="cx"> 
</span><ins>+    RefPtr&lt;RenderStyle&gt; m_overrideDocumentElementStyle;
+
</ins><span class="cx">     Vector&lt;std::unique_ptr&lt;MediaQueryResult&gt;&gt; m_viewportDependentMediaQueryResults;
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(CSS_DEVICE_ADAPTATION)
</span></span></pre></div>
<a id="trunkSourceWebCoredomDocumentcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/dom/Document.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/dom/Document.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/dom/Document.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -133,6 +133,7 @@
</span><span class="cx"> #include &quot;ProcessingInstruction.h&quot;
</span><span class="cx"> #include &quot;RenderChildIterator.h&quot;
</span><span class="cx"> #include &quot;RenderLayerCompositor.h&quot;
</span><ins>+#include &quot;RenderTreeUpdater.h&quot;
</ins><span class="cx"> #include &quot;RenderView.h&quot;
</span><span class="cx"> #include &quot;RenderWidget.h&quot;
</span><span class="cx"> #include &quot;ResourceLoadObserver.h&quot;
</span><span class="lines">@@ -1926,15 +1927,22 @@
</span><span class="cx">         }
</span><span class="cx"> 
</span><span class="cx">         Style::TreeResolver resolver(*this);
</span><del>-        resolver.resolve(change);
</del><ins>+        auto styleUpdate = resolver.resolve(change);
</ins><span class="cx"> 
</span><del>-        updatedCompositingLayers = frameView.updateCompositingLayersAfterStyleChange();
-
</del><span class="cx">         clearNeedsStyleRecalc();
</span><span class="cx">         clearChildNeedsStyleRecalc();
</span><span class="cx">         unscheduleStyleRecalc();
</span><span class="cx"> 
</span><span class="cx">         m_inStyleRecalc = false;
</span><ins>+
+        if (styleUpdate) {
+            TemporaryChange&lt;bool&gt; inRenderTreeUpdate(m_inRenderTreeUpdate, true);
+
+            RenderTreeUpdater updater(*this);
+            updater.commit(WTFMove(styleUpdate));
+        }
+
+        updatedCompositingLayers = frameView.updateCompositingLayersAfterStyleChange();
</ins><span class="cx">     }
</span><span class="cx"> 
</span><span class="cx">     // If we wanted to call implicitClose() during recalcStyle, do so now that we're finished.
</span><span class="lines">@@ -2052,7 +2060,10 @@
</span><span class="cx">     TemporaryChange&lt;bool&gt; change(m_ignorePendingStylesheets, true);
</span><span class="cx">     auto elementStyle = element.resolveStyle(parentStyle);
</span><span class="cx"> 
</span><del>-    Style::commitRelationsToDocument(WTFMove(elementStyle.relations));
</del><ins>+    if (elementStyle.relations) {
+        Style::Update emptyUpdate(*this);
+        Style::commitRelations(WTFMove(elementStyle.relations), emptyUpdate);
+    }
</ins><span class="cx"> 
</span><span class="cx">     return WTFMove(elementStyle.renderStyle);
</span><span class="cx"> }
</span></span></pre></div>
<a id="trunkSourceWebCoredomDocumenth"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/dom/Document.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/dom/Document.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/dom/Document.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -1244,7 +1244,8 @@
</span><span class="cx">     void setNeedsNotifyRemoveAllPendingStylesheet() { m_needsNotifyRemoveAllPendingStylesheet = true; }
</span><span class="cx">     void clearStyleResolver();
</span><span class="cx"> 
</span><del>-    bool inStyleRecalc() { return m_inStyleRecalc; }
</del><ins>+    bool inStyleRecalc() const { return m_inStyleRecalc; }
+    bool inRenderTreeUpdate() const { return m_inRenderTreeUpdate; }
</ins><span class="cx"> 
</span><span class="cx">     // Return a Locale for the default locale if the argument is null or empty.
</span><span class="cx">     Locale&amp; getCachedLocale(const AtomicString&amp; locale = nullAtom);
</span><span class="lines">@@ -1508,6 +1509,7 @@
</span><span class="cx">     bool m_pendingStyleRecalcShouldForce;
</span><span class="cx">     bool m_inStyleRecalc;
</span><span class="cx">     bool m_closeAfterStyleRecalc;
</span><ins>+    bool m_inRenderTreeUpdate { false };
</ins><span class="cx"> 
</span><span class="cx">     bool m_gotoAnchorNeededAfterStylesheetsLoad;
</span><span class="cx">     bool m_isDNSPrefetchEnabled;
</span></span></pre></div>
<a id="trunkSourceWebCoredomElementcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/dom/Element.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/dom/Element.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/dom/Element.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -2564,8 +2564,6 @@
</span><span class="cx"> void Element::setChildIndex(unsigned index)
</span><span class="cx"> {
</span><span class="cx">     ElementRareData&amp; rareData = ensureElementRareData();
</span><del>-    if (RenderStyle* style = renderStyle())
-        style-&gt;setUnique();
</del><span class="cx">     rareData.setChildIndex(index);
</span><span class="cx"> }
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoredomNodecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/dom/Node.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/dom/Node.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/dom/Node.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -772,6 +772,10 @@
</span><span class="cx">     if (!inRenderedDocument())
</span><span class="cx">         return;
</span><span class="cx"> 
</span><ins>+    // FIXME: This should eventually be an ASSERT.
+    if (document().inRenderTreeUpdate())
+        return;
+
</ins><span class="cx">     StyleChangeType existingChangeType = styleChangeType();
</span><span class="cx">     if (changeType &gt; existingChangeType)
</span><span class="cx">         setStyleChange(changeType);
</span></span></pre></div>
<a id="trunkSourceWebCorerenderingRenderBoxcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/rendering/RenderBox.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/rendering/RenderBox.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/rendering/RenderBox.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -381,10 +381,6 @@
</span><span class="cx">     bool isBodyRenderer = isBody();
</span><span class="cx">     bool isDocElementRenderer = isDocumentElementRenderer();
</span><span class="cx"> 
</span><del>-    // Set the text color if we're the body.
-    if (isBodyRenderer)
-        document().setTextColor(newStyle.visitedDependentColor(CSSPropertyColor));
-
</del><span class="cx">     if (isDocElementRenderer || isBodyRenderer) {
</span><span class="cx">         // Propagate the new writing mode and direction up to the RenderView.
</span><span class="cx">         auto* documentElementRenderer = document().documentElement()-&gt;renderer();
</span></span></pre></div>
<a id="trunkSourceWebCorerenderingRenderElementh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/rendering/RenderElement.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/rendering/RenderElement.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/rendering/RenderElement.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -50,9 +50,6 @@
</span><span class="cx">     // continue even if the style isn't different from the current style.
</span><span class="cx">     void setStyle(Ref&lt;RenderStyle&gt;&amp;&amp;, StyleDifference minimalStyleDifference = StyleDifferenceEqual);
</span><span class="cx"> 
</span><del>-    // Called to update a style that is allowed to trigger animations.
-    void setAnimatableStyle(Ref&lt;RenderStyle&gt;&amp;&amp;, StyleDifference minimalStyleDifference);
-
</del><span class="cx">     // The pseudo element style can be cached or uncached.  Use the cached method if the pseudo element doesn't respect
</span><span class="cx">     // any pseudo classes (and therefore has no concept of changing state).
</span><span class="cx">     RenderStyle* getCachedPseudoStyle(PseudoId, RenderStyle* parentStyle = nullptr) const;
</span><span class="lines">@@ -343,15 +340,6 @@
</span><span class="cx">     static bool s_noLongerAffectsParentBlock;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-inline void RenderElement::setAnimatableStyle(Ref&lt;RenderStyle&gt;&amp;&amp; style, StyleDifference minimalStyleDifference)
-{
-    Ref&lt;RenderStyle&gt; animatedStyle = WTFMove(style);
-    if (animation().updateAnimations(*this, animatedStyle, animatedStyle))
-        minimalStyleDifference = std::max(minimalStyleDifference, StyleDifferenceRecompositeLayer);
-    
-    setStyle(WTFMove(animatedStyle), minimalStyleDifference);
-}
-
</del><span class="cx"> inline void RenderElement::setAncestorLineBoxDirty(bool f)
</span><span class="cx"> {
</span><span class="cx">     m_ancestorLineBoxDirty = f;
</span></span></pre></div>
<a id="trunkSourceWebCorestyleRenderTreePositioncpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/style/RenderTreePosition.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/RenderTreePosition.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/style/RenderTreePosition.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -27,6 +27,7 @@
</span><span class="cx"> #include &quot;RenderTreePosition.h&quot;
</span><span class="cx"> 
</span><span class="cx"> #include &quot;ComposedTreeIterator.h&quot;
</span><ins>+#include &quot;HTMLSlotElement.h&quot;
</ins><span class="cx"> #include &quot;PseudoElement.h&quot;
</span><span class="cx"> #include &quot;RenderObject.h&quot;
</span><span class="cx"> #include &quot;ShadowRoot.h&quot;
</span><span class="lines">@@ -82,13 +83,22 @@
</span><span class="cx">     if (node.isAfterPseudoElement())
</span><span class="cx">         return nullptr;
</span><span class="cx"> 
</span><del>-    auto composedChildren = composedTreeChildren(*parentElement);
</del><ins>+    auto composedDescendants = composedTreeDescendants(*parentElement);
+    auto it = node.isBeforePseudoElement() ? composedDescendants.begin() : composedDescendants.at(node);
+    auto end = composedDescendants.end();
</ins><span class="cx"> 
</span><del>-    auto it = node.isBeforePseudoElement() ? composedChildren.begin() : composedChildren.at(node);
-    for (auto end = composedChildren.end(); it != end; ++it) {
-        RenderObject* renderer = it-&gt;renderer();
</del><ins>+    while (it != end) {
+        auto&amp; node = *it;
+        bool hasDisplayContents = is&lt;HTMLSlotElement&gt;(node);
+        if (hasDisplayContents) {
+            it.traverseNext();
+            continue;
+        }
+        RenderObject* renderer = node.renderer();
</ins><span class="cx">         if (renderer &amp;&amp; !isRendererReparented(*renderer))
</span><span class="cx">             return renderer;
</span><ins>+        
+        it.traverseNextSkippingChildren();
</ins><span class="cx">     }
</span><span class="cx">     if (PseudoElement* after = parentElement-&gt;afterPseudoElement())
</span><span class="cx">         return after-&gt;renderer();
</span></span></pre></div>
<a id="trunkSourceWebCorestyleRenderTreeUpdatercpp"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/style/RenderTreeUpdater.cpp (0 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/RenderTreeUpdater.cpp                                (rev 0)
+++ trunk/Source/WebCore/style/RenderTreeUpdater.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -0,0 +1,511 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include &quot;config.h&quot;
+#include &quot;RenderTreeUpdater.h&quot;
+
+#include &quot;AXObjectCache.h&quot;
+#include &quot;ComposedTreeAncestorIterator.h&quot;
+#include &quot;ComposedTreeIterator.h&quot;
+#include &quot;Document.h&quot;
+#include &quot;Element.h&quot;
+#include &quot;FlowThreadController.h&quot;
+#include &quot;HTMLSlotElement.h&quot;
+#include &quot;InspectorInstrumentation.h&quot;
+#include &quot;PseudoElement.h&quot;
+#include &quot;RenderFullScreen.h&quot;
+#include &quot;RenderNamedFlowThread.h&quot;
+#include &quot;StyleResolver.h&quot;
+#include &quot;StyleTreeResolver.h&quot;
+
+namespace WebCore {
+
+RenderTreeUpdater::Parent::Parent(ContainerNode&amp; root)
+    : element(is&lt;Document&gt;(root) ? nullptr : downcast&lt;Element&gt;(&amp;root))
+    , renderTreePosition(RenderTreePosition(*root.renderer()))
+{
+}
+
+RenderTreeUpdater::Parent::Parent(Element&amp; element, Style::Change styleChange)
+    : element(&amp;element)
+    , styleChange(styleChange)
+    , renderTreePosition(element.renderer() ? makeOptional(RenderTreePosition(*element.renderer())) : Nullopt)
+{
+}
+
+
+RenderTreeUpdater::RenderTreeUpdater(Document&amp; document)
+    : m_document(document)
+{
+}
+
+// Slots have implicit display:contents until it is supported for reals.
+static bool hasDisplayContents(const Node&amp; node)
+{
+    return is&lt;HTMLSlotElement&gt;(node);
+}
+
+static ContainerNode&amp; findRenderingRoot(ContainerNode&amp; node)
+{
+    auto&amp; document = node.document();
+    for (ComposedTreeAncestorIterator it(document, node), end(document); it != end; ++it) {
+        if (it-&gt;renderer())
+            return *it;
+        ASSERT(hasDisplayContents(*it));
+    }
+    ASSERT_NOT_REACHED();
+    return document;
+}
+
+void RenderTreeUpdater::commit(std::unique_ptr&lt;const Style::Update&gt; styleUpdate)
+{
+    ASSERT(&amp;m_document == &amp;styleUpdate-&gt;document());
+
+    if (!m_document.shouldCreateRenderers())
+        return;
+
+    m_styleUpdate = WTFMove(styleUpdate);
+
+    for (auto* root : m_styleUpdate-&gt;roots())
+        updateRenderTree(findRenderingRoot(*root));
+
+    m_styleUpdate = nullptr;
+}
+
+static bool shouldCreateRenderer(const Element&amp; element, const RenderElement&amp; parentRenderer)
+{
+    if (!parentRenderer.canHaveChildren() &amp;&amp; !(element.isPseudoElement() &amp;&amp; parentRenderer.canHaveGeneratedChildren()))
+        return false;
+    if (parentRenderer.element() &amp;&amp; !parentRenderer.element()-&gt;childShouldCreateRenderer(element))
+        return false;
+    return true;
+}
+
+void RenderTreeUpdater::updateRenderTree(ContainerNode&amp; root)
+{
+    ASSERT(root.renderer());
+    ASSERT(m_parentStack.isEmpty());
+
+    m_parentStack.append(Parent(root));
+
+    auto descendants = composedTreeDescendants(root);
+    auto it = descendants.begin();
+    auto end = descendants.end();
+
+    // FIXME: SVG &lt;use&gt; element may cause tree mutations during style recalc.
+    it.dropAssertions();
+
+    while (it != end) {
+        popParentsToDepth(it.depth());
+
+        auto&amp; node = *it;
+
+        if (auto* renderer = node.renderer())
+            renderTreePosition().invalidateNextSibling(*renderer);
+
+        if (is&lt;Text&gt;(node)) {
+            auto&amp; text = downcast&lt;Text&gt;(node);
+            if (parent().styleChange == Style::Detach || m_styleUpdate-&gt;textUpdate(text) || m_invalidatedWhitespaceOnlyTextSiblings.contains(&amp;text))
+                updateTextRenderer(text);
+
+            it.traverseNextSkippingChildren();
+            continue;
+        }
+
+        auto&amp; element = downcast&lt;Element&gt;(node);
+
+        auto* elementUpdate = m_styleUpdate-&gt;elementUpdate(element);
+
+        auto changeType = Style::NoChange;
+        if (elementUpdate) {
+            if (hasDisplayContents(element)) {
+                if (!shouldCreateRenderer(element, renderTreePosition().parent())) {
+                    it.traverseNextSkippingChildren();
+                    continue;
+                }
+                pushParent(element, parent().styleChange);
+                it.traverseNext();
+                continue;
+            }
+
+            updateElementRenderer(element, *elementUpdate);
+            changeType = elementUpdate-&gt;change;
+        }
+
+        if (!element.renderer() || !elementUpdate) {
+            it.traverseNextSkippingChildren();
+            continue;
+        }
+
+        pushParent(element, changeType);
+
+        it.traverseNext();
+    }
+
+    popParentsToDepth(0);
+
+    m_invalidatedWhitespaceOnlyTextSiblings.clear();
+}
+
+RenderTreePosition&amp; RenderTreeUpdater::renderTreePosition()
+{
+    for (unsigned i = m_parentStack.size(); i; --i) {
+        if (auto&amp; position = m_parentStack[i - 1].renderTreePosition)
+            return *position;
+    }
+    ASSERT_NOT_REACHED();
+    return *m_parentStack.last().renderTreePosition;
+}
+
+void RenderTreeUpdater::pushParent(Element&amp; element, Style::Change changeType)
+{
+    m_parentStack.append(Parent(element, changeType));
+
+    updateBeforeOrAfterPseudoElement(element, BEFORE);
+}
+
+void RenderTreeUpdater::popParent()
+{
+    auto&amp; parent = m_parentStack.last();
+
+    if (parent.element) {
+        updateBeforeOrAfterPseudoElement(*parent.element, AFTER);
+
+        if (parent.element-&gt;hasCustomStyleResolveCallbacks() &amp;&amp; parent.styleChange == Style::Detach &amp;&amp; parent.element-&gt;renderer())
+            parent.element-&gt;didAttachRenderers();
+    }
+    m_parentStack.removeLast();
+}
+
+void RenderTreeUpdater::popParentsToDepth(unsigned depth)
+{
+    ASSERT(m_parentStack.size() &gt;= depth);
+
+    while (m_parentStack.size() &gt; depth)
+        popParent();
+}
+
+static bool pseudoStyleCacheIsInvalid(RenderElement* renderer, RenderStyle* newStyle)
+{
+    const RenderStyle&amp; currentStyle = renderer-&gt;style();
+
+    const PseudoStyleCache* pseudoStyleCache = currentStyle.cachedPseudoStyles();
+    if (!pseudoStyleCache)
+        return false;
+
+    for (auto&amp; cache : *pseudoStyleCache) {
+        RefPtr&lt;RenderStyle&gt; newPseudoStyle;
+        PseudoId pseudoId = cache-&gt;styleType();
+        if (pseudoId == FIRST_LINE || pseudoId == FIRST_LINE_INHERITED)
+            newPseudoStyle = renderer-&gt;uncachedFirstLineStyle(newStyle);
+        else
+            newPseudoStyle = renderer-&gt;getUncachedPseudoStyle(PseudoStyleRequest(pseudoId), newStyle, newStyle);
+        if (!newPseudoStyle)
+            return true;
+        if (*newPseudoStyle != *cache) {
+            if (pseudoId &lt; FIRST_INTERNAL_PSEUDOID)
+                newStyle-&gt;setHasPseudoStyle(pseudoId);
+            newStyle-&gt;addCachedPseudoStyle(newPseudoStyle);
+            if (pseudoId == FIRST_LINE || pseudoId == FIRST_LINE_INHERITED) {
+                // FIXME: We should do an actual diff to determine whether a repaint vs. layout
+                // is needed, but for now just assume a layout will be required. The diff code
+                // in RenderObject::setStyle would need to be factored out so that it could be reused.
+                renderer-&gt;setNeedsLayoutAndPrefWidthsRecalc();
+            }
+            return true;
+        }
+    }
+    return false;
+}
+
+void RenderTreeUpdater::updateElementRenderer(Element&amp; element, const Style::ElementUpdate&amp; update)
+{
+    bool shouldTearDownRenderers = update.change == Style::Detach &amp;&amp; (element.renderer() || element.isNamedFlowContentNode());
+    if (shouldTearDownRenderers)
+        detachRenderTree(element, Style::ReattachDetach);
+
+    bool shouldCreateNewRenderer = !element.renderer() &amp;&amp; update.style;
+    if (shouldCreateNewRenderer) {
+        if (element.hasCustomStyleResolveCallbacks())
+            element.willAttachRenderers();
+        createRenderer(element, *update.style);
+        invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(element);
+        return;
+    }
+
+    if (!element.renderer())
+        return;
+    auto&amp; renderer = *element.renderer();
+
+    if (update.isSynthetic) {
+        renderer.setStyle(*update.style, StyleDifferenceRecompositeLayer);
+        return;
+    }
+
+    if (update.change == Style::NoChange) {
+        if (pseudoStyleCacheIsInvalid(&amp;renderer, update.style.get()) || (parent().styleChange == Style::Force &amp;&amp; renderer.requiresForcedStyleRecalcPropagation())) {
+            renderer.setStyle(*update.style, StyleDifferenceEqual);
+            return;
+        }
+        return;
+    }
+
+    renderer.setStyle(*update.style, StyleDifferenceEqual);
+}
+
+#if ENABLE(CSS_REGIONS)
+static RenderNamedFlowThread* moveToFlowThreadIfNeeded(Element&amp; element, const RenderStyle&amp; style)
+{
+    if (!element.shouldMoveToFlowThread(style))
+        return nullptr;
+
+    FlowThreadController&amp; flowThreadController = element.document().renderView()-&gt;flowThreadController();
+    RenderNamedFlowThread&amp; parentFlowRenderer = flowThreadController.ensureRenderFlowThreadWithName(style.flowThread());
+    flowThreadController.registerNamedFlowContentElement(element, parentFlowRenderer);
+    return &amp;parentFlowRenderer;
+}
+#endif
+
+void RenderTreeUpdater::createRenderer(Element&amp; element, RenderStyle&amp; style)
+{
+    if (!shouldCreateRenderer(element, renderTreePosition().parent()))
+        return;
+
+    RenderNamedFlowThread* parentFlowRenderer = nullptr;
+#if ENABLE(CSS_REGIONS)
+    parentFlowRenderer = moveToFlowThreadIfNeeded(element, style);
+#endif
+
+    if (!element.rendererIsNeeded(style))
+        return;
+
+    renderTreePosition().computeNextSibling(element);
+
+    RenderTreePosition insertionPosition = parentFlowRenderer
+        ? RenderTreePosition(*parentFlowRenderer, parentFlowRenderer-&gt;nextRendererForElement(element))
+        : renderTreePosition();
+
+    RenderElement* newRenderer = element.createElementRenderer(style, insertionPosition).leakPtr();
+    if (!newRenderer)
+        return;
+    if (!insertionPosition.canInsert(*newRenderer)) {
+        newRenderer-&gt;destroy();
+        return;
+    }
+
+    // Make sure the RenderObject already knows it is going to be added to a RenderFlowThread before we set the style
+    // for the first time. Otherwise code using inRenderFlowThread() in the styleWillChange and styleDidChange will fail.
+    newRenderer-&gt;setFlowThreadState(insertionPosition.parent().flowThreadState());
+
+    element.setRenderer(newRenderer);
+
+    Ref&lt;RenderStyle&gt; animatedStyle = newRenderer-&gt;style();
+    newRenderer-&gt;animation().updateAnimations(*newRenderer, animatedStyle, animatedStyle);
+    newRenderer-&gt;setStyleInternal(WTFMove(animatedStyle));
+
+    newRenderer-&gt;initializeStyle();
+
+#if ENABLE(FULLSCREEN_API)
+    if (m_document.webkitIsFullScreen() &amp;&amp; m_document.webkitCurrentFullScreenElement() == &amp;element) {
+        newRenderer = RenderFullScreen::wrapRenderer(newRenderer, &amp;insertionPosition.parent(), m_document);
+        if (!newRenderer)
+            return;
+    }
+#endif
+    // Note: Adding newRenderer instead of renderer(). renderer() may be a child of newRenderer.
+    insertionPosition.insert(*newRenderer);
+
+    if (AXObjectCache* cache = m_document.axObjectCache())
+        cache-&gt;updateCacheAfterNodeIsAttached(&amp;element);
+}
+
+static bool textRendererIsNeeded(const Text&amp; textNode, const RenderTreePosition&amp; renderTreePosition)
+{
+    const RenderElement&amp; parentRenderer = renderTreePosition.parent();
+    if (!parentRenderer.canHaveChildren())
+        return false;
+    if (parentRenderer.element() &amp;&amp; !parentRenderer.element()-&gt;childShouldCreateRenderer(textNode))
+        return false;
+    if (textNode.isEditingText())
+        return true;
+    if (!textNode.length())
+        return false;
+    if (!textNode.containsOnlyWhitespace())
+        return true;
+    // This text node has nothing but white space. We may still need a renderer in some cases.
+    if (parentRenderer.isTable() || parentRenderer.isTableRow() || parentRenderer.isTableSection() || parentRenderer.isRenderTableCol() || parentRenderer.isFrameSet())
+        return false;
+    if (parentRenderer.style().preserveNewline()) // pre/pre-wrap/pre-line always make renderers.
+        return true;
+
+    RenderObject* previousRenderer = renderTreePosition.previousSiblingRenderer(textNode);
+    if (previousRenderer &amp;&amp; previousRenderer-&gt;isBR()) // &lt;span&gt;&lt;br/&gt; &lt;br/&gt;&lt;/span&gt;
+        return false;
+
+    if (parentRenderer.isRenderInline()) {
+        // &lt;span&gt;&lt;div/&gt; &lt;div/&gt;&lt;/span&gt;
+        if (previousRenderer &amp;&amp; !previousRenderer-&gt;isInline())
+            return false;
+    } else {
+        if (parentRenderer.isRenderBlock() &amp;&amp; !parentRenderer.childrenInline() &amp;&amp; (!previousRenderer || !previousRenderer-&gt;isInline()))
+            return false;
+        
+        RenderObject* first = parentRenderer.firstChild();
+        while (first &amp;&amp; first-&gt;isFloatingOrOutOfFlowPositioned())
+            first = first-&gt;nextSibling();
+        RenderObject* nextRenderer = renderTreePosition.nextSiblingRenderer(textNode);
+        if (!first || nextRenderer == first) {
+            // Whitespace at the start of a block just goes away. Don't even make a render object for this text.
+            return false;
+        }
+    }
+    return true;
+}
+
+static void createTextRenderer(Text&amp; textNode, RenderTreePosition&amp; renderTreePosition)
+{
+    ASSERT(!textNode.renderer());
+
+    auto newRenderer = textNode.createTextRenderer(renderTreePosition.parent().style());
+    ASSERT(newRenderer);
+
+    renderTreePosition.computeNextSibling(textNode);
+
+    if (!renderTreePosition.canInsert(*newRenderer))
+        return;
+
+    // Make sure the RenderObject already knows it is going to be added to a RenderFlowThread before we set the style
+    // for the first time. Otherwise code using inRenderFlowThread() in the styleWillChange and styleDidChange will fail.
+    newRenderer-&gt;setFlowThreadState(renderTreePosition.parent().flowThreadState());
+
+    textNode.setRenderer(newRenderer.get());
+    renderTreePosition.insert(*newRenderer.leakPtr());
+}
+
+void RenderTreeUpdater::updateTextRenderer(Text&amp; text)
+{
+    bool hasRenderer = text.renderer();
+    bool needsRenderer = textRendererIsNeeded(text, renderTreePosition());
+    if (hasRenderer) {
+        if (needsRenderer)
+            return;
+        Style::detachTextRenderer(text);
+        invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(text);
+        return;
+    }
+    if (!needsRenderer)
+        return;
+    createTextRenderer(text, renderTreePosition());
+    invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(text);
+}
+
+void RenderTreeUpdater::invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(Node&amp; current)
+{
+    // FIXME: This needs to traverse in composed tree order.
+
+    // This function finds sibling text renderers where the results of textRendererIsNeeded may have changed as a result of
+    // the current node gaining or losing the renderer. This can only affect white space text nodes.
+    for (Node* sibling = current.nextSibling(); sibling; sibling = sibling-&gt;nextSibling()) {
+        if (is&lt;Element&gt;(*sibling)) {
+            if (m_styleUpdate-&gt;elementUpdate(downcast&lt;Element&gt;(*sibling)))
+                return;
+            // Text renderers beyond rendered elements can't be affected.
+            if (!sibling-&gt;renderer() || RenderTreePosition::isRendererReparented(*sibling-&gt;renderer()))
+                continue;
+            return;
+        }
+        if (!is&lt;Text&gt;(*sibling))
+            continue;
+        Text&amp; textSibling = downcast&lt;Text&gt;(*sibling);
+        if (m_styleUpdate-&gt;textUpdate(textSibling))
+            return;
+        if (!textSibling.containsOnlyWhitespace())
+            continue;
+        m_invalidatedWhitespaceOnlyTextSiblings.add(&amp;textSibling);
+    }
+}
+
+static bool needsPseudoElement(Element&amp; current, PseudoId pseudoId)
+{
+    if (!current.renderer() || !current.renderer()-&gt;canHaveGeneratedChildren())
+        return false;
+    if (current.isPseudoElement())
+        return false;
+    if (!pseudoElementRendererIsNeeded(current.renderer()-&gt;getCachedPseudoStyle(pseudoId)))
+        return false;
+    return true;
+}
+
+void RenderTreeUpdater::updateBeforeOrAfterPseudoElement(Element&amp; current, PseudoId pseudoId)
+{
+    PseudoElement* pseudoElement = pseudoId == BEFORE ? current.beforePseudoElement() : current.afterPseudoElement();
+
+    auto* renderer = pseudoElement ? pseudoElement-&gt;renderer() : nullptr;
+    if (renderer)
+        renderTreePosition().invalidateNextSibling(*renderer);
+
+    bool needsPseudoElement = WebCore::needsPseudoElement(current, pseudoId);
+    if (!needsPseudoElement) {
+        if (pseudoElement) {
+            if (pseudoId == BEFORE)
+                current.clearBeforePseudoElement();
+            else
+                current.clearAfterPseudoElement();
+        }
+        return;
+    }
+
+    Style::ElementUpdate elementUpdate;
+
+    Ref&lt;RenderStyle&gt; newStyle = *current.renderer()-&gt;getCachedPseudoStyle(pseudoId, &amp;current.renderer()-&gt;style());
+
+    if (renderer &amp;&amp; m_document.frame()-&gt;animation().updateAnimations(*renderer, newStyle, newStyle))
+        elementUpdate.isSynthetic = true;
+
+    elementUpdate.change = renderer ? Style::determineChange(renderer-&gt;style(), newStyle) : Style::Detach;
+    elementUpdate.style = WTFMove(newStyle);
+
+    if (elementUpdate.change == Style::NoChange)
+        return;
+
+    if (!pseudoElement) {
+        auto newPseudoElement = PseudoElement::create(current, pseudoId);
+        pseudoElement = newPseudoElement.ptr();
+        InspectorInstrumentation::pseudoElementCreated(m_document.page(), newPseudoElement);
+        if (pseudoId == BEFORE)
+            current.setBeforePseudoElement(WTFMove(newPseudoElement));
+        else
+            current.setAfterPseudoElement(WTFMove(newPseudoElement));
+    }
+
+    updateElementRenderer(*pseudoElement, elementUpdate);
+
+    if (elementUpdate.change == Style::Detach)
+        pseudoElement-&gt;didAttachRenderers();
+    else
+        pseudoElement-&gt;didRecalcStyle(elementUpdate.change);
+}
+
+}
</ins></span></pre></div>
<a id="trunkSourceWebCorestyleRenderTreeUpdaterh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/style/RenderTreeUpdater.h (0 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/RenderTreeUpdater.h                                (rev 0)
+++ trunk/Source/WebCore/style/RenderTreeUpdater.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -0,0 +1,85 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef RenderTreeUpdater_h
+#define RenderTreeUpdater_h
+
+#include &quot;RenderTreePosition.h&quot;
+#include &quot;StyleChange.h&quot;
+#include &quot;StyleUpdate.h&quot;
+#include &lt;wtf/HashMap.h&gt;
+#include &lt;wtf/HashSet.h&gt;
+#include &lt;wtf/ListHashSet.h&gt;
+#include &lt;wtf/RefPtr.h&gt;
+#include &lt;wtf/Vector.h&gt;
+
+namespace WebCore {
+
+class ContainerNode;
+class Document;
+class Element;
+class Node;
+class RenderStyle;
+class Text;
+
+class RenderTreeUpdater {
+public:
+    RenderTreeUpdater(Document&amp;);
+
+    void commit(std::unique_ptr&lt;const Style::Update&gt;);
+
+private:
+    void updateRenderTree(ContainerNode&amp; root);
+    void updateTextRenderer(Text&amp;);
+    void updateElementRenderer(Element&amp;, const Style::ElementUpdate&amp;);
+    void createRenderer(Element&amp;, RenderStyle&amp;);
+    void invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(Node&amp;);
+    void updateBeforeOrAfterPseudoElement(Element&amp;, PseudoId);
+
+    struct Parent {
+        Element* element { nullptr };
+        Style::Change styleChange { Style::NoChange };
+        Optional&lt;RenderTreePosition&gt; renderTreePosition;
+
+        Parent(ContainerNode&amp; root);
+        Parent(Element&amp;, Style::Change);
+    };
+    Parent&amp; parent() { return m_parentStack.last(); }
+    RenderTreePosition&amp; renderTreePosition();
+
+    void pushParent(Element&amp;, Style::Change);
+    void popParent();
+    void popParentsToDepth(unsigned depth);
+
+    Document&amp; m_document;
+    std::unique_ptr&lt;const Style::Update&gt; m_styleUpdate;
+
+    Vector&lt;Parent&gt; m_parentStack;
+
+    HashSet&lt;Text*&gt; m_invalidatedWhitespaceOnlyTextSiblings;
+};
+
+}
+#endif
</ins></span></pre></div>
<a id="trunkSourceWebCorestyleStyleRelationscpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/style/StyleRelations.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleRelations.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/style/StyleRelations.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -29,6 +29,7 @@
</span><span class="cx"> #include &quot;Element.h&quot;
</span><span class="cx"> #include &quot;NodeRenderStyle.h&quot;
</span><span class="cx"> #include &quot;RenderStyle.h&quot;
</span><ins>+#include &quot;StyleUpdate.h&quot;
</ins><span class="cx"> 
</span><span class="cx"> namespace WebCore {
</span><span class="cx"> namespace Style {
</span><span class="lines">@@ -85,7 +86,7 @@
</span><span class="cx">     return remainingRelations;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void commitRelationsToDocument(std::unique_ptr&lt;Relations&gt; relations)
</del><ins>+void commitRelations(std::unique_ptr&lt;Relations&gt; relations, Update&amp; update)
</ins><span class="cx"> {
</span><span class="cx">     if (!relations)
</span><span class="cx">         return;
</span><span class="lines">@@ -124,18 +125,20 @@
</span><span class="cx">             element.setChildrenAffectedByLastChildRules();
</span><span class="cx">             break;
</span><span class="cx">         case Relation::FirstChild:
</span><del>-            if (auto* style = element.renderStyle())
</del><ins>+            if (auto* style = update.elementStyle(element))
</ins><span class="cx">                 style-&gt;setFirstChildState();
</span><span class="cx">             break;
</span><span class="cx">         case Relation::LastChild:
</span><del>-            if (auto* style = element.renderStyle())
</del><ins>+            if (auto* style = update.elementStyle(element))
</ins><span class="cx">                 style-&gt;setLastChildState();
</span><span class="cx">             break;
</span><span class="cx">         case Relation::NthChildIndex:
</span><ins>+            if (auto* style = update.elementStyle(element))
+                style-&gt;setUnique();
</ins><span class="cx">             element.setChildIndex(relation.value);
</span><span class="cx">             break;
</span><span class="cx">         case Relation::Unique:
</span><del>-            if (auto* style = element.renderStyle())
</del><ins>+            if (auto* style = update.elementStyle(element))
</ins><span class="cx">                 style-&gt;setUnique();
</span><span class="cx">             break;
</span><span class="cx">         }
</span></span></pre></div>
<a id="trunkSourceWebCorestyleStyleRelationsh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/style/StyleRelations.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleRelations.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/style/StyleRelations.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -35,6 +35,8 @@
</span><span class="cx"> 
</span><span class="cx"> namespace Style {
</span><span class="cx"> 
</span><ins>+class Update;
+
</ins><span class="cx"> struct Relation {
</span><span class="cx">     enum Type {
</span><span class="cx">         AffectedByActive,
</span><span class="lines">@@ -66,7 +68,7 @@
</span><span class="cx"> using Relations = Vector&lt;Relation, 8&gt;;
</span><span class="cx"> 
</span><span class="cx"> std::unique_ptr&lt;Relations&gt; commitRelationsToRenderStyle(RenderStyle&amp;, const Element&amp;, const Relations&amp;);
</span><del>-void commitRelationsToDocument(std::unique_ptr&lt;Relations&gt;);
</del><ins>+void commitRelations(std::unique_ptr&lt;Relations&gt;, Update&amp;);
</ins><span class="cx"> 
</span><span class="cx"> }
</span><span class="cx"> }
</span></span></pre></div>
<a id="trunkSourceWebCorestyleStyleSharingResolvercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/style/StyleSharingResolver.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleSharingResolver.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/style/StyleSharingResolver.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -33,6 +33,7 @@
</span><span class="cx"> #include &quot;NodeRenderStyle.h&quot;
</span><span class="cx"> #include &quot;RenderStyle.h&quot;
</span><span class="cx"> #include &quot;SVGElement.h&quot;
</span><ins>+#include &quot;StyleUpdate.h&quot;
</ins><span class="cx"> #include &quot;StyledElement.h&quot;
</span><span class="cx"> #include &quot;VisitedLinkState.h&quot;
</span><span class="cx"> #include &quot;WebVTTElement.h&quot;
</span><span class="lines">@@ -44,6 +45,7 @@
</span><span class="cx"> static const unsigned cStyleSearchThreshold = 10;
</span><span class="cx"> 
</span><span class="cx"> struct SharingResolver::Context {
</span><ins>+    const Update&amp; update;
</ins><span class="cx">     const StyledElement&amp; element;
</span><span class="cx">     bool elementAffectedByClassRules;
</span><span class="cx">     EInsideLink elementLinkState;
</span><span class="lines">@@ -67,7 +69,7 @@
</span><span class="cx">     return is&lt;HTMLElement&gt;(element) &amp;&amp; downcast&lt;HTMLElement&gt;(element).hasDirectionAuto();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-RefPtr&lt;RenderStyle&gt; SharingResolver::resolve(const Element&amp; searchElement)
</del><ins>+RefPtr&lt;RenderStyle&gt; SharingResolver::resolve(const Element&amp; searchElement, const Update&amp; update)
</ins><span class="cx"> {
</span><span class="cx">     if (!is&lt;StyledElement&gt;(searchElement))
</span><span class="cx">         return nullptr;
</span><span class="lines">@@ -77,7 +79,7 @@
</span><span class="cx">     auto&amp; parentElement = *element.parentElement();
</span><span class="cx">     if (parentElement.shadowRoot())
</span><span class="cx">         return nullptr;
</span><del>-    if (!parentElement.renderStyle())
</del><ins>+    if (!update.elementStyle(parentElement))
</ins><span class="cx">         return nullptr;
</span><span class="cx">     // If the element has inline style it is probably unique.
</span><span class="cx">     if (element.inlineStyle())
</span><span class="lines">@@ -95,6 +97,7 @@
</span><span class="cx">         return nullptr;
</span><span class="cx"> 
</span><span class="cx">     Context context {
</span><ins>+        update,
</ins><span class="cx">         element,
</span><span class="cx">         element.hasClass() &amp;&amp; classNamesAffectedByRules(element.classNames()),
</span><span class="cx">         m_document.visitedLinkState().determineLinkState(element)
</span><span class="lines">@@ -127,7 +130,7 @@
</span><span class="cx"> 
</span><span class="cx">     m_elementsSharingStyle.add(&amp;element, shareElement);
</span><span class="cx"> 
</span><del>-    return RenderStyle::clone(shareElement-&gt;renderStyle());
</del><ins>+    return RenderStyle::clone(update.elementStyle(*shareElement));
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> StyledElement* SharingResolver::findSibling(const Context&amp; context, Node* node, unsigned&amp; count) const
</span><span class="lines">@@ -195,7 +198,7 @@
</span><span class="cx"> bool SharingResolver::canShareStyleWithElement(const Context&amp; context, const StyledElement&amp; candidateElement) const
</span><span class="cx"> {
</span><span class="cx">     auto&amp; element = context.element;
</span><del>-    auto* style = candidateElement.renderStyle();
</del><ins>+    auto* style = context.update.elementStyle(candidateElement);
</ins><span class="cx">     if (!style)
</span><span class="cx">         return false;
</span><span class="cx">     if (style-&gt;unique())
</span></span></pre></div>
<a id="trunkSourceWebCorestyleStyleSharingResolverh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/style/StyleSharingResolver.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleSharingResolver.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/style/StyleSharingResolver.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -42,11 +42,13 @@
</span><span class="cx"> 
</span><span class="cx"> namespace Style {
</span><span class="cx"> 
</span><ins>+class Update;
+
</ins><span class="cx"> class SharingResolver {
</span><span class="cx"> public:
</span><span class="cx">     SharingResolver(const Document&amp;, const DocumentRuleSets&amp;, const SelectorFilter&amp;);
</span><span class="cx"> 
</span><del>-    RefPtr&lt;RenderStyle&gt; resolve(const Element&amp;);
</del><ins>+    RefPtr&lt;RenderStyle&gt; resolve(const Element&amp;, const Update&amp;);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><span class="cx">     struct Context;
</span></span></pre></div>
<a id="trunkSourceWebCorestyleStyleTreeResolvercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/style/StyleTreeResolver.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleTreeResolver.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/style/StyleTreeResolver.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -4,7 +4,7 @@
</span><span class="cx">  *           (C) 2001 Peter Kelly (pmk@post.com)
</span><span class="cx">  *           (C) 2001 Dirk Mueller (mueller@kde.org)
</span><span class="cx">  *           (C) 2007 David Smith (catfish.man@gmail.com)
</span><del>- * Copyright (C) 2004-2010, 2012-2014 Apple Inc. All rights reserved.
</del><ins>+ * Copyright (C) 2004-2010, 2012-2016 Apple Inc. All rights reserved.
</ins><span class="cx">  *           (C) 2007 Eric Seidel (eric@webkit.org)
</span><span class="cx">  *
</span><span class="cx">  * This library is free software; you can redistribute it and/or
</span><span class="lines">@@ -26,27 +26,17 @@
</span><span class="cx"> #include &quot;config.h&quot;
</span><span class="cx"> #include &quot;StyleTreeResolver.h&quot;
</span><span class="cx"> 
</span><del>-#include &quot;AXObjectCache.h&quot;
-#include &quot;AnimationController.h&quot;
</del><span class="cx"> #include &quot;AuthorStyleSheets.h&quot;
</span><span class="cx"> #include &quot;CSSFontSelector.h&quot;
</span><span class="cx"> #include &quot;ComposedTreeAncestorIterator.h&quot;
</span><span class="cx"> #include &quot;ComposedTreeIterator.h&quot;
</span><span class="cx"> #include &quot;ElementIterator.h&quot;
</span><del>-#include &quot;ElementRareData.h&quot;
-#include &quot;FlowThreadController.h&quot;
</del><ins>+#include &quot;HTMLBodyElement.h&quot;
</ins><span class="cx"> #include &quot;HTMLSlotElement.h&quot;
</span><del>-#include &quot;InspectorInstrumentation.h&quot;
</del><span class="cx"> #include &quot;LoaderStrategy.h&quot;
</span><span class="cx"> #include &quot;MainFrame.h&quot;
</span><span class="cx"> #include &quot;NodeRenderStyle.h&quot;
</span><del>-#include &quot;NodeTraversal.h&quot;
</del><span class="cx"> #include &quot;PlatformStrategies.h&quot;
</span><del>-#include &quot;RenderFullScreen.h&quot;
-#include &quot;RenderNamedFlowThread.h&quot;
-#include &quot;RenderText.h&quot;
-#include &quot;RenderTreePosition.h&quot;
-#include &quot;RenderWidget.h&quot;
</del><span class="cx"> #include &quot;Settings.h&quot;
</span><span class="cx"> #include &quot;ShadowRoot.h&quot;
</span><span class="cx"> #include &quot;StyleResolver.h&quot;
</span><span class="lines">@@ -60,10 +50,7 @@
</span><span class="cx"> 
</span><span class="cx"> namespace Style {
</span><span class="cx"> 
</span><del>-enum DetachType { NormalDetach, ReattachDetach };
-
</del><span class="cx"> static void attachTextRenderer(Text&amp;, RenderTreePosition&amp;);
</span><del>-static void detachRenderTree(Element&amp;, DetachType);
</del><span class="cx"> static void resolveTextNode(Text&amp;, RenderTreePosition&amp;);
</span><span class="cx"> 
</span><span class="cx"> class SelectorFilterPusher {
</span><span class="lines">@@ -114,6 +101,10 @@
</span><span class="cx">     ensurePlaceholderStyle(document);
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+TreeResolver::~TreeResolver()
+{
+}
+
</ins><span class="cx"> TreeResolver::Scope::Scope(Document&amp; document)
</span><span class="cx">     : styleResolver(document.ensureStyleResolver())
</span><span class="cx">     , sharingResolver(document, styleResolver.ruleSets(), selectorFilter)
</span><span class="lines">@@ -131,16 +122,14 @@
</span><span class="cx"> TreeResolver::Parent::Parent(Document&amp; document, Change change)
</span><span class="cx">     : element(nullptr)
</span><span class="cx">     , style(*document.renderStyle())
</span><del>-    , renderTreePosition(*document.renderView())
</del><span class="cx">     , change(change)
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-TreeResolver::Parent::Parent(Element&amp; element, RenderStyle&amp; style, RenderTreePosition renderTreePosition, Change change)
</del><ins>+TreeResolver::Parent::Parent(Element&amp; element, ElementUpdate&amp; update)
</ins><span class="cx">     : element(&amp;element)
</span><del>-    , style(style)
-    , renderTreePosition(renderTreePosition)
-    , change(change)
</del><ins>+    , style(*update.style)
+    , change(update.change)
</ins><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -160,17 +149,6 @@
</span><span class="cx">     return m_scopeStack.removeLast();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-static bool shouldCreateRenderer(const Element&amp; element, const RenderElement&amp; parentRenderer)
-{
-    if (!element.document().shouldCreateRenderers())
-        return false;
-    if (!parentRenderer.canHaveChildren() &amp;&amp; !(element.isPseudoElement() &amp;&amp; parentRenderer.canHaveGeneratedChildren()))
-        return false;
-    if (parentRenderer.element() &amp;&amp; !parentRenderer.element()-&gt;childShouldCreateRenderer(element))
-        return false;
-    return true;
-}
-
</del><span class="cx"> Ref&lt;RenderStyle&gt; TreeResolver::styleForElement(Element&amp; element, RenderStyle&amp; inheritedStyle)
</span><span class="cx"> {
</span><span class="cx">     if (!m_document.haveStylesheetsLoaded() &amp;&amp; !element.renderer()) {
</span><span class="lines">@@ -178,89 +156,29 @@
</span><span class="cx">         return *placeholderStyle;
</span><span class="cx">     }
</span><span class="cx"> 
</span><ins>+    scope().styleResolver.setOverrideDocumentElementStyle(m_documentElementStyle.get());
+
</ins><span class="cx">     if (element.hasCustomStyleResolveCallbacks()) {
</span><del>-        RenderStyle* shadowHostStyle = scope().shadowRoot ? scope().shadowRoot-&gt;host()-&gt;renderStyle() : nullptr;
</del><ins>+        RenderStyle* shadowHostStyle = scope().shadowRoot ? m_update-&gt;elementStyle(*scope().shadowRoot-&gt;host()) : nullptr;
</ins><span class="cx">         if (auto customStyle = element.resolveCustomStyle(inheritedStyle, shadowHostStyle)) {
</span><del>-            Style::commitRelationsToDocument(WTFMove(customStyle-&gt;relations));
</del><ins>+            if (customStyle-&gt;relations)
+                commitRelations(WTFMove(customStyle-&gt;relations), *m_update);
+
</ins><span class="cx">             return WTFMove(customStyle-&gt;renderStyle);
</span><span class="cx">         }
</span><span class="cx">     }
</span><span class="cx"> 
</span><del>-    if (auto style = scope().sharingResolver.resolve(element))
</del><ins>+    if (auto style = scope().sharingResolver.resolve(element, *m_update))
</ins><span class="cx">         return *style;
</span><span class="cx"> 
</span><span class="cx">     auto elementStyle = scope().styleResolver.styleForElement(element, &amp;inheritedStyle, MatchAllRules, nullptr, &amp;scope().selectorFilter);
</span><span class="cx"> 
</span><del>-    Style::commitRelationsToDocument(WTFMove(elementStyle.relations));
</del><ins>+    if (elementStyle.relations)
+        commitRelations(WTFMove(elementStyle.relations), *m_update);
+
</ins><span class="cx">     return WTFMove(elementStyle.renderStyle);
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-#if ENABLE(CSS_REGIONS)
-static RenderNamedFlowThread* moveToFlowThreadIfNeeded(Element&amp; element, const RenderStyle&amp; style)
-{
-    if (!element.shouldMoveToFlowThread(style))
-        return 0;
-
-    FlowThreadController&amp; flowThreadController = element.document().renderView()-&gt;flowThreadController();
-    RenderNamedFlowThread&amp; parentFlowRenderer = flowThreadController.ensureRenderFlowThreadWithName(style.flowThread());
-    flowThreadController.registerNamedFlowContentElement(element, parentFlowRenderer);
-    return &amp;parentFlowRenderer;
-}
-#endif
-
-void TreeResolver::createRenderer(Element&amp; element, RenderTreePosition&amp; renderTreePosition, RefPtr&lt;RenderStyle&gt;&amp;&amp; resolvedStyle)
-{
-    ASSERT(shouldCreateRenderer(element, renderTreePosition.parent()));
-    ASSERT(resolvedStyle);
-
-    RenderNamedFlowThread* parentFlowRenderer = 0;
-#if ENABLE(CSS_REGIONS)
-    parentFlowRenderer = moveToFlowThreadIfNeeded(element, *resolvedStyle);
-#endif
-
-    if (!element.rendererIsNeeded(*resolvedStyle))
-        return;
-
-    renderTreePosition.computeNextSibling(element);
-
-    RenderTreePosition insertionPosition = parentFlowRenderer
-        ? RenderTreePosition(*parentFlowRenderer, parentFlowRenderer-&gt;nextRendererForElement(element))
-        : renderTreePosition;
-
-    RenderElement* newRenderer = element.createElementRenderer(resolvedStyle.releaseNonNull(), insertionPosition).leakPtr();
-    if (!newRenderer)
-        return;
-    if (!insertionPosition.canInsert(*newRenderer)) {
-        newRenderer-&gt;destroy();
-        return;
-    }
-
-    // Make sure the RenderObject already knows it is going to be added to a RenderFlowThread before we set the style
-    // for the first time. Otherwise code using inRenderFlowThread() in the styleWillChange and styleDidChange will fail.
-    newRenderer-&gt;setFlowThreadState(insertionPosition.parent().flowThreadState());
-
-    // Code below updateAnimations() can depend on Element::renderer() already being set.
-    element.setRenderer(newRenderer);
-
-    // FIXME: There's probably a better way to factor this.
-    // This just does what setAnimatedStyle() does, except with setStyleInternal() instead of setStyle().
-    Ref&lt;RenderStyle&gt; animatedStyle = newRenderer-&gt;style();
-    newRenderer-&gt;animation().updateAnimations(*newRenderer, animatedStyle, animatedStyle);
-    newRenderer-&gt;setStyleInternal(WTFMove(animatedStyle));
-
-    newRenderer-&gt;initializeStyle();
-
-#if ENABLE(FULLSCREEN_API)
-    if (m_document.webkitIsFullScreen() &amp;&amp; m_document.webkitCurrentFullScreenElement() == &amp;element) {
-        newRenderer = RenderFullScreen::wrapRenderer(newRenderer, &amp;insertionPosition.parent(), m_document);
-        if (!newRenderer)
-            return;
-    }
-#endif
-    // Note: Adding newRenderer instead of renderer(). renderer() may be a child of newRenderer.
-    insertionPosition.insert(*newRenderer);
-}
-
</del><span class="cx"> static void invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(Node&amp; current)
</span><span class="cx"> {
</span><span class="cx">     // FIXME: This needs to traverse in composed tree order.
</span><span class="lines">@@ -348,7 +266,6 @@
</span><span class="cx">     newRenderer-&gt;setFlowThreadState(renderTreePosition.parent().flowThreadState());
</span><span class="cx"> 
</span><span class="cx">     textNode.setRenderer(newRenderer.get());
</span><del>-    // Parent takes care of the animations, no need to call setAnimatableStyle.
</del><span class="cx">     renderTreePosition.insert(*newRenderer.leakPtr());
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -381,75 +298,11 @@
</span><span class="cx">         textNode.renderer()-&gt;setTextWithOffset(textNode.data(), offsetOfReplacedData, lengthOfReplacedData);
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void TreeResolver::createRenderTreeForChildren(ContainerNode&amp; current, RenderStyle&amp; inheritedStyle, RenderTreePosition&amp; renderTreePosition)
-{
-    for (Node* child = current.firstChild(); child; child = child-&gt;nextSibling()) {
-        ASSERT((!child-&gt;renderer() || child-&gt;isNamedFlowContentNode()) || current.shadowRoot());
-        if (child-&gt;renderer()) {
-            renderTreePosition.invalidateNextSibling(*child-&gt;renderer());
-            continue;
-        }
-        if (is&lt;Text&gt;(*child)) {
-            attachTextRenderer(downcast&lt;Text&gt;(*child), renderTreePosition);
-            continue;
-        }
-        if (is&lt;Element&gt;(*child))
-            createRenderTreeRecursively(downcast&lt;Element&gt;(*child), inheritedStyle, renderTreePosition, nullptr);
-    }
-}
-
-void TreeResolver::createRenderTreeForShadowRoot(ShadowRoot&amp; shadowRoot)
-{
-    ASSERT(shadowRoot.host());
-    ASSERT(shadowRoot.host()-&gt;renderer());
-
-    pushScope(shadowRoot);
-
-    auto&amp; renderer = *shadowRoot.host()-&gt;renderer();
-    RenderTreePosition renderTreePosition(renderer);
-    createRenderTreeForChildren(shadowRoot, renderer.style(), renderTreePosition);
-
-    popScope();
-
-    shadowRoot.clearNeedsStyleRecalc();
-    shadowRoot.clearChildNeedsStyleRecalc();
-}
-
-static PseudoElement* beforeOrAfterPseudoElement(Element&amp; current, PseudoId pseudoId)
-{
-    ASSERT(pseudoId == BEFORE || pseudoId == AFTER);
-    if (pseudoId == BEFORE)
-        return current.beforePseudoElement();
-    return current.afterPseudoElement();
-}
-
-static void setBeforeOrAfterPseudoElement(Element&amp; current, Ref&lt;PseudoElement&gt;&amp;&amp; pseudoElement, PseudoId pseudoId)
-{
-    ASSERT(pseudoId == BEFORE || pseudoId == AFTER);
-    if (pseudoId == BEFORE) {
-        current.setBeforePseudoElement(WTFMove(pseudoElement));
-        return;
-    }
-    current.setAfterPseudoElement(WTFMove(pseudoElement));
-}
-
-static void clearBeforeOrAfterPseudoElement(Element&amp; current, PseudoId pseudoId)
-{
-    ASSERT(pseudoId == BEFORE || pseudoId == AFTER);
-    if (pseudoId == BEFORE) {
-        current.clearBeforePseudoElement();
-        return;
-    }
-    current.clearAfterPseudoElement();
-}
-
</del><span class="cx"> static void resetStyleForNonRenderedDescendants(Element&amp; current)
</span><span class="cx"> {
</span><span class="cx">     // FIXME: This is not correct with shadow trees. This should be done with ComposedTreeIterator.
</span><del>-    ASSERT(!current.renderer());
</del><span class="cx">     bool elementNeedingStyleRecalcAffectsNextSiblingElementStyle = false;
</span><span class="cx">     for (auto&amp; child : childrenOfType&lt;Element&gt;(current)) {
</span><del>-        ASSERT(!child.renderer());
</del><span class="cx">         bool affectedByPreviousSibling = child.styleIsAffectedByPreviousSibling() &amp;&amp; elementNeedingStyleRecalcAffectsNextSiblingElementStyle;
</span><span class="cx">         if (child.needsStyleRecalc() || elementNeedingStyleRecalcAffectsNextSiblingElementStyle)
</span><span class="cx">             elementNeedingStyleRecalcAffectsNextSiblingElementStyle = child.affectsNextSiblingElementStyle();
</span><span class="lines">@@ -466,111 +319,6 @@
</span><span class="cx">     }
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-static bool needsPseudoElement(Element&amp; current, PseudoId pseudoId)
-{
-    if (!current.renderer() || !current.renderer()-&gt;canHaveGeneratedChildren())
-        return false;
-    if (current.isPseudoElement())
-        return false;
-    if (!pseudoElementRendererIsNeeded(current.renderer()-&gt;getCachedPseudoStyle(pseudoId)))
-        return false;
-    return true;
-}
-
-void TreeResolver::createRenderTreeForBeforeOrAfterPseudoElement(Element&amp; current, PseudoId pseudoId, RenderTreePosition&amp; renderTreePosition)
-{
-    if (!needsPseudoElement(current, pseudoId))
-        return;
-    Ref&lt;PseudoElement&gt; pseudoElement = PseudoElement::create(current, pseudoId);
-    InspectorInstrumentation::pseudoElementCreated(m_document.page(), pseudoElement.get());
-    setBeforeOrAfterPseudoElement(current, pseudoElement.copyRef(), pseudoId);
-    createRenderTreeRecursively(pseudoElement.get(), *current.renderStyle(), renderTreePosition, nullptr);
-}
-
-#if ENABLE(SHADOW_DOM) || ENABLE(DETAILS_ELEMENT)
-void TreeResolver::createRenderTreeForSlotAssignees(HTMLSlotElement&amp; slot, RenderStyle&amp; inheritedStyle, RenderTreePosition&amp; renderTreePosition)
-{
-    ASSERT(shouldCreateRenderer(slot, renderTreePosition.parent()));
-
-    if (auto* assignedNodes = slot.assignedNodes()) {
-        pushEnclosingScope();
-        for (auto* child : *assignedNodes) {
-            if (is&lt;Text&gt;(*child))
-                attachTextRenderer(downcast&lt;Text&gt;(*child), renderTreePosition);
-            else if (is&lt;Element&gt;(*child))
-                createRenderTreeRecursively(downcast&lt;Element&gt;(*child), inheritedStyle, renderTreePosition, nullptr);
-        }
-        popScope();
-    } else {
-        SelectorFilterPusher selectorFilterPusher(scope().selectorFilter, slot);
-        createRenderTreeForChildren(slot, inheritedStyle, renderTreePosition);
-    }
-
-    slot.clearNeedsStyleRecalc();
-    slot.clearChildNeedsStyleRecalc();
-}
-#endif
-
-void TreeResolver::createRenderTreeRecursively(Element&amp; current, RenderStyle&amp; inheritedStyle, RenderTreePosition&amp; renderTreePosition, RefPtr&lt;RenderStyle&gt;&amp;&amp; resolvedStyle)
-{
-    ASSERT(!current.renderer());
-
-    PostResolutionCallbackDisabler callbackDisabler(m_document);
-    WidgetHierarchyUpdatesSuspensionScope suspendWidgetHierarchyUpdates;
-
-    bool shouldCallCreateRenderer = shouldCreateRenderer(current, renderTreePosition.parent());
-
-    RefPtr&lt;RenderStyle&gt; style = resolvedStyle;
-    if (!style)
-        style = styleForElement(current, inheritedStyle);
-
-#if ENABLE(SHADOW_DOM) || ENABLE(DETAILS_ELEMENT)
-    if (is&lt;HTMLSlotElement&gt;(current)) {
-        if (shouldCallCreateRenderer &amp;&amp; current.rendererIsNeeded(*style))
-            createRenderTreeForSlotAssignees(downcast&lt;HTMLSlotElement&gt;(current), inheritedStyle, renderTreePosition);
-        return;
-    }
-#endif
-
-    if (current.hasCustomStyleResolveCallbacks())
-        current.willAttachRenderers();
-
-    if (shouldCallCreateRenderer)
-        createRenderer(current, renderTreePosition, style.releaseNonNull());
-
-    if (auto* renderer = current.renderer()) {
-        SelectorFilterPusher selectorFilterPusher(scope().selectorFilter, current, SelectorFilterPusher::NoPush);
-
-        RenderTreePosition childRenderTreePosition(*renderer);
-        createRenderTreeForBeforeOrAfterPseudoElement(current, BEFORE, childRenderTreePosition);
-
-        auto* shadowRoot = current.shadowRoot();
-        if (shadowRoot) {
-            selectorFilterPusher.push();
-            createRenderTreeForShadowRoot(*shadowRoot);
-        } else if (current.firstChild())
-            selectorFilterPusher.push();
-
-        bool skipChildren = shadowRoot;
-        if (!skipChildren)
-            createRenderTreeForChildren(current, renderer-&gt;style(), childRenderTreePosition);
-
-        if (AXObjectCache* cache = m_document.axObjectCache())
-            cache-&gt;updateCacheAfterNodeIsAttached(&amp;current);
-
-        createRenderTreeForBeforeOrAfterPseudoElement(current, AFTER, childRenderTreePosition);
-
-        current.updateFocusAppearanceAfterAttachIfNeeded();
-    } else
-        resetStyleForNonRenderedDescendants(current);
-
-    current.clearNeedsStyleRecalc();
-    current.clearChildNeedsStyleRecalc();
-
-    if (current.hasCustomStyleResolveCallbacks())
-        current.didAttachRenderers();
-}
-
</del><span class="cx"> static void detachChildren(ContainerNode&amp; current, DetachType detachType)
</span><span class="cx"> {
</span><span class="cx">     for (Node* child = current.firstChild(); child; child = child-&gt;nextSibling()) {
</span><span class="lines">@@ -606,7 +354,7 @@
</span><span class="cx"> }
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><del>-static void detachRenderTree(Element&amp; current, DetachType detachType)
</del><ins>+void detachRenderTree(Element&amp; current, DetachType detachType)
</ins><span class="cx"> {
</span><span class="cx">     WidgetHierarchyUpdatesSuspensionScope suspendWidgetHierarchyUpdates;
</span><span class="cx"> 
</span><span class="lines">@@ -637,79 +385,49 @@
</span><span class="cx">         current.didDetachRenderers();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-static bool pseudoStyleCacheIsInvalid(RenderElement* renderer, RenderStyle* newStyle)
</del><ins>+ElementUpdate TreeResolver::resolveElement(Element&amp; element)
</ins><span class="cx"> {
</span><del>-    const RenderStyle&amp; currentStyle = renderer-&gt;style();
</del><ins>+    auto newStyle = styleForElement(element, parent().style);
</ins><span class="cx"> 
</span><del>-    const PseudoStyleCache* pseudoStyleCache = currentStyle.cachedPseudoStyles();
-    if (!pseudoStyleCache)
-        return false;
</del><ins>+    auto* renderer = element.renderer();
</ins><span class="cx"> 
</span><del>-    for (auto&amp; cache : *pseudoStyleCache) {
-        RefPtr&lt;RenderStyle&gt; newPseudoStyle;
-        PseudoId pseudoId = cache-&gt;styleType();
-        if (pseudoId == FIRST_LINE || pseudoId == FIRST_LINE_INHERITED)
-            newPseudoStyle = renderer-&gt;uncachedFirstLineStyle(newStyle);
-        else
-            newPseudoStyle = renderer-&gt;getUncachedPseudoStyle(PseudoStyleRequest(pseudoId), newStyle, newStyle);
-        if (!newPseudoStyle)
-            return true;
-        if (*newPseudoStyle != *cache) {
-            if (pseudoId &lt; FIRST_INTERNAL_PSEUDOID)
-                newStyle-&gt;setHasPseudoStyle(pseudoId);
-            newStyle-&gt;addCachedPseudoStyle(newPseudoStyle);
-            if (pseudoId == FIRST_LINE || pseudoId == FIRST_LINE_INHERITED) {
-                // FIXME: We should do an actual diff to determine whether a repaint vs. layout
-                // is needed, but for now just assume a layout will be required. The diff code
-                // in RenderObject::setStyle would need to be factored out so that it could be reused.
-                renderer-&gt;setNeedsLayoutAndPrefWidthsRecalc();
-            }
-            return true;
-        }
-    }
-    return false;
-}
</del><ins>+    bool affectsRenderedSubtree = renderer || newStyle-&gt;display() != NONE || element.rendererIsNeeded(newStyle) || element.shouldMoveToFlowThread(newStyle);
+    if (!affectsRenderedSubtree)
+        return { };
</ins><span class="cx"> 
</span><del>-Change TreeResolver::resolveElement(Element&amp; current)
-{
-    Change localChange = Detach;
-    RefPtr&lt;RenderStyle&gt; newStyle;
-    RefPtr&lt;RenderStyle&gt; currentStyle = current.renderStyle();
</del><ins>+    ElementUpdate update;
</ins><span class="cx"> 
</span><del>-    if (currentStyle &amp;&amp; current.styleChangeType() != ReconstructRenderTree) {
-        Ref&lt;RenderStyle&gt; style(styleForElement(current, parent().style));
-        newStyle = style.ptr();
-        localChange = determineChange(*currentStyle, style);
-    }
-    if (localChange == Detach) {
-        if (current.renderer() || current.isNamedFlowContentNode())
-            detachRenderTree(current, ReattachDetach);
-#if ENABLE(SHADOW_DOM) || ENABLE(DETAILS_ELEMENT)
-        else if (is&lt;HTMLSlotElement&gt;(current))
-            detachRenderTree(current, ReattachDetach);
-#endif
-        createRenderTreeRecursively(current, parent().style, parent().renderTreePosition, newStyle.release());
-        invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(current);
</del><ins>+    bool needsNewRenderer = !renderer || element.styleChangeType() == ReconstructRenderTree || parent().change == Detach;
+    if (!needsNewRenderer &amp;&amp; m_document.frame()-&gt;animation().updateAnimations(*renderer, newStyle, newStyle))
+        update.isSynthetic = true;
</ins><span class="cx"> 
</span><del>-        return Detach;
-    }
</del><ins>+    update.change = needsNewRenderer ? Detach : determineChange(renderer-&gt;style(), newStyle);
+    update.style = WTFMove(newStyle);
</ins><span class="cx"> 
</span><del>-    if (RenderElement* renderer = current.renderer()) {
-        if (localChange != NoChange || pseudoStyleCacheIsInvalid(renderer, newStyle.get()) || (parent().change == Force &amp;&amp; renderer-&gt;requiresForcedStyleRecalcPropagation()) || current.styleChangeType() == SyntheticStyleChange)
-            renderer-&gt;setAnimatableStyle(*newStyle, current.styleChangeType() == SyntheticStyleChange ? StyleDifferenceRecompositeLayer : StyleDifferenceEqual);
-    }
</del><ins>+    if (element.styleChangeType() == SyntheticStyleChange)
+        update.isSynthetic = true;
</ins><span class="cx"> 
</span><del>-    // If &quot;rem&quot; units are used anywhere in the document, and if the document element's font size changes, then force font updating
-    // all the way down the tree. This is simpler than having to maintain a cache of objects (and such font size changes should be rare anyway).
-    if (m_document.authorStyleSheets().usesRemUnits() &amp;&amp; m_document.documentElement() == &amp;current &amp;&amp; localChange != NoChange &amp;&amp; currentStyle &amp;&amp; newStyle &amp;&amp; currentStyle-&gt;fontSize() != newStyle-&gt;fontSize()) {
-        // Cached RenderStyles may depend on the re units.
-        scope().styleResolver.invalidateMatchedPropertiesCache();
-        return Force;
</del><ins>+    if (&amp;element == m_document.documentElement()) {
+        m_documentElementStyle = update.style;
+
+        // If &quot;rem&quot; units are used anywhere in the document, and if the document element's font size changes, then force font updating
+        // all the way down the tree. This is simpler than having to maintain a cache of objects (and such font size changes should be rare anyway).
+        if (m_document.authorStyleSheets().usesRemUnits() &amp;&amp; update.change != NoChange &amp;&amp; renderer &amp;&amp; renderer-&gt;style().fontSize() != update.style-&gt;fontSize()) {
+            // Cached RenderStyles may depend on the rem units.
+            scope().styleResolver.invalidateMatchedPropertiesCache();
+            update.change = Force;
+        }
</ins><span class="cx">     }
</span><del>-    if (parent().change == Force || current.styleChangeType() &gt;= FullStyleChange)
-        return Force;
</del><span class="cx"> 
</span><del>-    return localChange;
</del><ins>+    // This is needed for resolving color:-webkit-text for subsequent elements.
+    // FIXME: We shouldn't mutate document when resolving style.
+    if (&amp;element == m_document.body())
+        m_document.setTextColor(update.style-&gt;visitedDependentColor(CSSPropertyColor));
+
+    if (update.change != Detach &amp;&amp; (parent().change == Force || element.styleChangeType() &gt;= FullStyleChange))
+        update.change = Force;
+
+    return update;
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void resolveTextNode(Text&amp; text, RenderTreePosition&amp; renderTreePosition)
</span><span class="lines">@@ -731,30 +449,6 @@
</span><span class="cx">     invalidateWhitespaceOnlyTextSiblingsAfterAttachIfNeeded(text);
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void TreeResolver::resolveBeforeOrAfterPseudoElement(Element&amp; current, Change change, PseudoId pseudoId, RenderTreePosition&amp; renderTreePosition)
-{
-    if (!current.renderer())
-        return;
-    PseudoElement* existingPseudoElement = beforeOrAfterPseudoElement(current, pseudoId);
-    if (!existingPseudoElement) {
-        createRenderTreeForBeforeOrAfterPseudoElement(current, pseudoId, renderTreePosition);
-        return;
-    }
-
-    if (existingPseudoElement-&gt;renderer())
-        renderTreePosition.invalidateNextSibling(*existingPseudoElement-&gt;renderer());
-
-    if (change == NoChange &amp;&amp; !existingPseudoElement-&gt;needsStyleRecalc())
-        return;
-
-    if (needsPseudoElement(current, pseudoId)) {
-        auto change = resolveElement(*existingPseudoElement);
-        existingPseudoElement-&gt;didRecalcStyle(change);
-        existingPseudoElement-&gt;clearNeedsStyleRecalc();
-    } else
-        clearBeforeOrAfterPseudoElement(current, pseudoId);
-}
-
</del><span class="cx"> #if PLATFORM(IOS)
</span><span class="cx"> static EVisibility elementImplicitVisibility(const Element* element)
</span><span class="cx"> {
</span><span class="lines">@@ -809,11 +503,11 @@
</span><span class="cx"> };
</span><span class="cx"> #endif // PLATFORM(IOS)
</span><span class="cx"> 
</span><del>-void TreeResolver::pushParent(Element&amp; element, RenderStyle&amp; style, RenderTreePosition renderTreePosition, Change change)
</del><ins>+void TreeResolver::pushParent(Element&amp; element, ElementUpdate&amp; update)
</ins><span class="cx"> {
</span><span class="cx">     scope().selectorFilter.pushParent(&amp;element);
</span><span class="cx"> 
</span><del>-    Parent parent(element, style, renderTreePosition, change);
</del><ins>+    Parent parent(element, update);
</ins><span class="cx"> 
</span><span class="cx">     if (auto* shadowRoot = element.shadowRoot()) {
</span><span class="cx">         pushScope(*shadowRoot);
</span><span class="lines">@@ -827,16 +521,12 @@
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><span class="cx">     m_parentStack.append(WTFMove(parent));
</span><del>-
-    resolveBeforeOrAfterPseudoElement(element, change, BEFORE, renderTreePosition);
</del><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void TreeResolver::popParent()
</span><span class="cx"> {
</span><span class="cx">     auto&amp; parentElement = *parent().element;
</span><span class="cx"> 
</span><del>-    resolveBeforeOrAfterPseudoElement(parentElement, parent().change, AFTER, parent().renderTreePosition);
-
</del><span class="cx">     parentElement.clearNeedsStyleRecalc();
</span><span class="cx">     parentElement.clearChildNeedsStyleRecalc();
</span><span class="cx"> 
</span><span class="lines">@@ -857,6 +547,15 @@
</span><span class="cx">         popParent();
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+static bool shouldResolvePseudoElement(PseudoElement* pseudoElement)
+{
+    if (!pseudoElement)
+        return false;
+    bool needsStyleRecalc = pseudoElement-&gt;needsStyleRecalc();
+    pseudoElement-&gt;clearNeedsStyleRecalc();
+    return needsStyleRecalc;
+}
+
</ins><span class="cx"> void TreeResolver::resolveComposedTree()
</span><span class="cx"> {
</span><span class="cx">     ASSERT(m_parentStack.size() == 1);
</span><span class="lines">@@ -878,12 +577,12 @@
</span><span class="cx">         ASSERT(node.containingShadowRoot() == scope().shadowRoot);
</span><span class="cx">         ASSERT(node.parentElement() == parent.element || is&lt;ShadowRoot&gt;(node.parentNode()) || node.parentElement()-&gt;shadowRoot());
</span><span class="cx"> 
</span><del>-        if (auto* existingRenderer = node.renderer())
-            parent.renderTreePosition.invalidateNextSibling(*existingRenderer);
-
</del><span class="cx">         if (is&lt;Text&gt;(node)) {
</span><del>-            if (node.needsStyleRecalc())
-                resolveTextNode(downcast&lt;Text&gt;(node), parent.renderTreePosition);
</del><ins>+            auto&amp; text = downcast&lt;Text&gt;(node);
+            if (text.styleChangeType() == ReconstructRenderTree &amp;&amp; parent.change != Detach)
+                m_update-&gt;addText(text, parent.element);
+
+            text.clearNeedsStyleRecalc();
</ins><span class="cx">             it.traverseNextSkippingChildren();
</span><span class="cx">             continue;
</span><span class="cx">         }
</span><span class="lines">@@ -895,9 +594,12 @@
</span><span class="cx">         if (element.needsStyleRecalc() || parent.elementNeedingStyleRecalcAffectsNextSiblingElementStyle)
</span><span class="cx">             parent.elementNeedingStyleRecalcAffectsNextSiblingElementStyle = element.affectsNextSiblingElementStyle();
</span><span class="cx"> 
</span><del>-        Change change = NoChange;
</del><ins>+        bool shouldResolveForPseudoElement = shouldResolvePseudoElement(element.beforePseudoElement()) || shouldResolvePseudoElement(element.afterPseudoElement());
</ins><span class="cx"> 
</span><del>-        bool shouldResolve = parent.change &gt;= Inherit || element.needsStyleRecalc() || affectedByPreviousSibling;
</del><ins>+        ElementUpdate update;
+        update.style = element.renderStyle();
+
+        bool shouldResolve = parent.change &gt;= Inherit || element.needsStyleRecalc() || shouldResolveForPseudoElement || affectedByPreviousSibling;
</ins><span class="cx">         if (shouldResolve) {
</span><span class="cx"> #if PLATFORM(IOS)
</span><span class="cx">             CheckForVisibilityChangeOnRecalcStyle checkForVisibilityChange(&amp;element, element.renderStyle());
</span><span class="lines">@@ -910,45 +612,48 @@
</span><span class="cx">                     continue;
</span><span class="cx">                 }
</span><span class="cx">             }
</span><del>-            change = resolveElement(element);
</del><span class="cx"> 
</span><del>-            element.clearNeedsStyleRecalc();
</del><ins>+            update = resolveElement(element);
</ins><span class="cx"> 
</span><span class="cx">             if (element.hasCustomStyleResolveCallbacks())
</span><del>-                element.didRecalcStyle(change);
</del><ins>+                element.didRecalcStyle(update.change);
</ins><span class="cx"> 
</span><del>-            if (change == Detach) {
-                it.traverseNextSkippingChildren();
-                continue;
-            }
</del><ins>+            if (affectedByPreviousSibling &amp;&amp; update.change != Detach)
+                update.change = Force;
</ins><span class="cx"> 
</span><del>-            if (affectedByPreviousSibling)
-                change = Force;
</del><ins>+            if (update.style)
+                m_update-&gt;addElement(element, parent.element, update);
+
+            element.clearNeedsStyleRecalc();
</ins><span class="cx">         }
</span><span class="cx"> 
</span><ins>+
</ins><span class="cx"> #if ENABLE(SHADOW_DOM) || ENABLE(DETAILS_ELEMENT)
</span><span class="cx">         if (is&lt;HTMLSlotElement&gt;(element)) {
</span><span class="cx">             // FIXME: We should compute style for the slot and use it as parent style.
</span><del>-            // FIXME: This should be display:contents check.
-            // Duplicate the style and render tree position from the current context.
-            pushParent(element, parent.style.get(), parent.renderTreePosition, change);
</del><ins>+            // Duplicate the style from the parent context.
+            ElementUpdate slotUpdate;
+            slotUpdate.style = parent.style.ptr();
+            slotUpdate.change = update.change;
+            if (!shouldResolve)
+                m_update-&gt;addElement(element, parent.element, update);
+            pushParent(element, slotUpdate);
</ins><span class="cx">             it.traverseNext();
</span><span class="cx">             continue;
</span><span class="cx">         }
</span><span class="cx"> #endif
</span><del>-        auto* renderer = element.renderer();
-        if (!renderer) {
</del><ins>+        if (!update.style) {
</ins><span class="cx">             resetStyleForNonRenderedDescendants(element);
</span><span class="cx">             element.clearChildNeedsStyleRecalc();
</span><span class="cx">         }
</span><span class="cx"> 
</span><del>-        bool shouldIterateChildren = renderer &amp;&amp; (element.childNeedsStyleRecalc() || change != NoChange);
</del><ins>+        bool shouldIterateChildren = update.style &amp;&amp; (element.childNeedsStyleRecalc() || update.change != NoChange);
</ins><span class="cx">         if (!shouldIterateChildren) {
</span><span class="cx">             it.traverseNextSkippingChildren();
</span><span class="cx">             continue;
</span><span class="cx">         }
</span><span class="cx"> 
</span><del>-        pushParent(element, renderer-&gt;style(), RenderTreePosition(*renderer), change);
</del><ins>+        pushParent(element, update);
</ins><span class="cx"> 
</span><span class="cx">         it.traverseNext();
</span><span class="cx">     }
</span><span class="lines">@@ -956,24 +661,24 @@
</span><span class="cx">     popParentsToDepth(1);
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void TreeResolver::resolve(Change change)
</del><ins>+std::unique_ptr&lt;const Update&gt; TreeResolver::resolve(Change change)
</ins><span class="cx"> {
</span><span class="cx">     auto&amp; renderView = *m_document.renderView();
</span><span class="cx"> 
</span><span class="cx">     Element* documentElement = m_document.documentElement();
</span><span class="cx">     if (!documentElement)
</span><del>-        return;
</del><ins>+        return nullptr;
</ins><span class="cx">     if (change != Force &amp;&amp; !documentElement-&gt;childNeedsStyleRecalc() &amp;&amp; !documentElement-&gt;needsStyleRecalc())
</span><del>-        return;
</del><ins>+        return nullptr;
</ins><span class="cx"> 
</span><ins>+    m_update = std::make_unique&lt;Update&gt;(m_document);
</ins><span class="cx">     m_scopeStack.append(adoptRef(*new Scope(m_document)));
</span><ins>+    m_parentStack.append(Parent(m_document, change));
</ins><span class="cx"> 
</span><span class="cx">     // Pseudo element removal and similar may only work with these flags still set. Reset them after the style recalc.
</span><span class="cx">     renderView.setUsesFirstLineRules(renderView.usesFirstLineRules() || scope().styleResolver.usesFirstLineRules());
</span><span class="cx">     renderView.setUsesFirstLetterRules(renderView.usesFirstLetterRules() || scope().styleResolver.usesFirstLetterRules());
</span><span class="cx"> 
</span><del>-    m_parentStack.append(Parent(m_document, change));
-
</del><span class="cx">     resolveComposedTree();
</span><span class="cx"> 
</span><span class="cx">     renderView.setUsesFirstLineRules(scope().styleResolver.usesFirstLineRules());
</span><span class="lines">@@ -981,11 +686,11 @@
</span><span class="cx"> 
</span><span class="cx">     m_parentStack.clear();
</span><span class="cx">     m_scopeStack.clear();
</span><del>-}
</del><span class="cx"> 
</span><del>-void detachRenderTree(Element&amp; element)
-{
-    detachRenderTree(element, NormalDetach);
</del><ins>+    if (m_update-&gt;roots().isEmpty())
+        return { };
+
+    return WTFMove(m_update);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> static Vector&lt;std::function&lt;void ()&gt;&gt;&amp; postResolutionCallbackQueue()
</span></span></pre></div>
<a id="trunkSourceWebCorestyleStyleTreeResolverh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/style/StyleTreeResolver.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleTreeResolver.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/style/StyleTreeResolver.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -32,7 +32,9 @@
</span><span class="cx"> #include &quot;SelectorFilter.h&quot;
</span><span class="cx"> #include &quot;StyleChange.h&quot;
</span><span class="cx"> #include &quot;StyleSharingResolver.h&quot;
</span><ins>+#include &quot;StyleUpdate.h&quot;
</ins><span class="cx"> #include &lt;functional&gt;
</span><ins>+#include &lt;wtf/HashMap.h&gt;
</ins><span class="cx"> #include &lt;wtf/RefPtr.h&gt;
</span><span class="cx"> 
</span><span class="cx"> namespace WebCore {
</span><span class="lines">@@ -47,33 +49,23 @@
</span><span class="cx"> class ShadowRoot;
</span><span class="cx"> class StyleResolver;
</span><span class="cx"> class Text;
</span><ins>+class TreeChange;
</ins><span class="cx"> 
</span><span class="cx"> namespace Style {
</span><span class="cx"> 
</span><span class="cx"> class TreeResolver {
</span><span class="cx"> public:
</span><span class="cx">     TreeResolver(Document&amp;);
</span><ins>+    ~TreeResolver();
</ins><span class="cx"> 
</span><del>-    void resolve(Change);
</del><ins>+    std::unique_ptr&lt;const Update&gt; resolve(Change);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><span class="cx">     Ref&lt;RenderStyle&gt; styleForElement(Element&amp;, RenderStyle&amp; inheritedStyle);
</span><span class="cx"> 
</span><span class="cx">     void resolveComposedTree();
</span><del>-    Change resolveElement(Element&amp;);
-    void resolveBeforeOrAfterPseudoElement(Element&amp;, Change, PseudoId, RenderTreePosition&amp;);
</del><ins>+    ElementUpdate resolveElement(Element&amp;);
</ins><span class="cx"> 
</span><del>-
-    void createRenderTreeRecursively(Element&amp;, RenderStyle&amp;, RenderTreePosition&amp;, RefPtr&lt;RenderStyle&gt;&amp;&amp; resolvedStyle);
-    void createRenderer(Element&amp;, RenderTreePosition&amp;, RefPtr&lt;RenderStyle&gt;&amp;&amp; resolvedStyle);
-    void createRenderTreeForBeforeOrAfterPseudoElement(Element&amp;, PseudoId, RenderTreePosition&amp;);
-    void createRenderTreeForChildren(ContainerNode&amp;, RenderStyle&amp;, RenderTreePosition&amp;);
-    void createRenderTreeForShadowRoot(ShadowRoot&amp;);
-
-#if ENABLE(SHADOW_DOM) || ENABLE(DETAILS_ELEMENT)
-    void createRenderTreeForSlotAssignees(HTMLSlotElement&amp;, RenderStyle&amp; inheritedStyle, RenderTreePosition&amp;);
-#endif
-
</del><span class="cx">     struct Scope : RefCounted&lt;Scope&gt; {
</span><span class="cx">         StyleResolver&amp; styleResolver;
</span><span class="cx">         SelectorFilter selectorFilter;
</span><span class="lines">@@ -88,13 +80,12 @@
</span><span class="cx">     struct Parent {
</span><span class="cx">         Element* element;
</span><span class="cx">         Ref&lt;RenderStyle&gt; style;
</span><del>-        RenderTreePosition renderTreePosition;
</del><span class="cx">         Change change;
</span><span class="cx">         bool didPushScope { false };
</span><span class="cx">         bool elementNeedingStyleRecalcAffectsNextSiblingElementStyle { false };
</span><span class="cx"> 
</span><span class="cx">         Parent(Document&amp;, Change);
</span><del>-        Parent(Element&amp;, RenderStyle&amp;, RenderTreePosition, Change);
</del><ins>+        Parent(Element&amp;, ElementUpdate&amp;);
</ins><span class="cx">     };
</span><span class="cx"> 
</span><span class="cx">     Scope&amp; scope() { return m_scopeStack.last(); }
</span><span class="lines">@@ -104,16 +95,21 @@
</span><span class="cx">     void pushEnclosingScope();
</span><span class="cx">     void popScope();
</span><span class="cx"> 
</span><del>-    void pushParent(Element&amp;, RenderStyle&amp;, RenderTreePosition, Change);
</del><ins>+    void pushParent(Element&amp;, ElementUpdate&amp;);
</ins><span class="cx">     void popParent();
</span><span class="cx">     void popParentsToDepth(unsigned depth);
</span><span class="cx"> 
</span><span class="cx">     Document&amp; m_document;
</span><ins>+    RefPtr&lt;RenderStyle&gt; m_documentElementStyle;
+
</ins><span class="cx">     Vector&lt;Ref&lt;Scope&gt;, 4&gt; m_scopeStack;
</span><span class="cx">     Vector&lt;Parent, 32&gt; m_parentStack;
</span><ins>+
+    std::unique_ptr&lt;Update&gt; m_update;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-void detachRenderTree(Element&amp;);
</del><ins>+enum DetachType { NormalDetach, ReattachDetach };
+void detachRenderTree(Element&amp;, DetachType = NormalDetach);
</ins><span class="cx"> void detachTextRenderer(Text&amp;);
</span><span class="cx"> 
</span><span class="cx"> void updateTextRendererAfterContentChange(Text&amp;, unsigned offsetOfReplacedData, unsigned lengthOfReplacedData);
</span></span></pre></div>
<a id="trunkSourceWebCorestyleStyleUpdatecpp"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/style/StyleUpdate.cpp (0 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleUpdate.cpp                                (rev 0)
+++ trunk/Source/WebCore/style/StyleUpdate.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -0,0 +1,93 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include &quot;config.h&quot;
+#include &quot;StyleUpdate.h&quot;
+
+#include &quot;ComposedTreeAncestorIterator.h&quot;
+#include &quot;Document.h&quot;
+#include &quot;Element.h&quot;
+#include &quot;NodeRenderStyle.h&quot;
+#include &quot;Text.h&quot;
+
+namespace WebCore {
+namespace Style {
+
+Update::Update(Document&amp; document)
+    : m_document(document)
+{
+}
+
+const ElementUpdate* Update::elementUpdate(const Element&amp; element) const
+{
+    auto it = m_elements.find(&amp;element);
+    if (it == m_elements.end())
+        return nullptr;
+    return &amp;it-&gt;value;
+}
+
+bool Update::textUpdate(const Text&amp; text) const
+{
+    return m_texts.contains(&amp;text);
+}
+
+RenderStyle* Update::elementStyle(const Element&amp; element) const
+{
+    if (auto* update = elementUpdate(element))
+        return update-&gt;style.get();
+    return element.renderStyle();
+}
+
+void Update::addElement(Element&amp; element, Element* parent, ElementUpdate&amp; change)
+{
+    ASSERT(!m_elements.contains(&amp;element));
+    ASSERT(!parent || composedTreeAncestors(element).first() == parent);
+
+    addPossibleRoot(parent);
+    m_elements.add(&amp;element, change);
+}
+
+void Update::addText(Text&amp; text, Element* parent)
+{
+    ASSERT(!m_texts.contains(&amp;text));
+    ASSERT(!parent || composedTreeAncestors(text).first() == parent);
+
+    addPossibleRoot(parent);
+    m_texts.add(&amp;text);
+}
+
+void Update::addPossibleRoot(Element* element)
+{
+    if (!element) {
+        m_roots.add(&amp;m_document);
+        return;
+    }
+    if (m_elements.contains(element))
+        return;
+    m_roots.add(element);
+}
+
+}
+}
</ins></span></pre></div>
<a id="trunkSourceWebCorestyleStyleUpdateh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/style/StyleUpdate.h (0 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/style/StyleUpdate.h                                (rev 0)
+++ trunk/Source/WebCore/style/StyleUpdate.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -0,0 +1,81 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef StyleUpdate_h
+#define StyleUpdate_h
+
+#include &quot;Node.h&quot;
+#include &quot;StyleChange.h&quot;
+#include &quot;StyleRelations.h&quot;
+#include &lt;wtf/HashMap.h&gt;
+#include &lt;wtf/HashSet.h&gt;
+#include &lt;wtf/ListHashSet.h&gt;
+#include &lt;wtf/RefPtr.h&gt;
+
+namespace WebCore {
+
+class ContainerNode;
+class Document;
+class Element;
+class Node;
+class RenderStyle;
+class Text;
+
+namespace Style {
+
+struct ElementUpdate {
+    RefPtr&lt;RenderStyle&gt; style;
+    Change change { NoChange };
+    bool isSynthetic { false };
+};
+
+class Update {
+public:
+    Update(Document&amp;);
+
+    const ListHashSet&lt;ContainerNode*&gt;&amp; roots() const { return m_roots; }
+
+    const ElementUpdate* elementUpdate(const Element&amp;) const;
+    bool textUpdate(const Text&amp;) const;
+
+    RenderStyle* elementStyle(const Element&amp;) const;
+
+    const Document&amp; document() const { return m_document; }
+
+    void addElement(Element&amp;, Element* parent, ElementUpdate&amp;);
+    void addText(Text&amp;, Element* parent);
+
+private:
+    void addPossibleRoot(Element*);
+
+    Document&amp; m_document;
+    ListHashSet&lt;ContainerNode*&gt; m_roots;
+    HashMap&lt;const Element*, ElementUpdate&gt; m_elements;
+    HashSet&lt;const Text*&gt; m_texts;
+};
+
+}
+}
+#endif
</ins></span></pre></div>
<a id="trunkSourceWebCoresvgSVGElementh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/svg/SVGElement.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/svg/SVGElement.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/svg/SVGElement.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -183,11 +183,12 @@
</span><span class="cx">     void updateRelativeLengthsInformation() { updateRelativeLengthsInformation(selfHasRelativeLengths(), this); }
</span><span class="cx">     void updateRelativeLengthsInformation(bool hasRelativeLengths, SVGElement*);
</span><span class="cx"> 
</span><ins>+    bool willRecalcStyle(Style::Change) override;
+
</ins><span class="cx">     class InstanceInvalidationGuard;
</span><span class="cx"> 
</span><span class="cx"> private:
</span><span class="cx">     RenderStyle* computedStyle(PseudoId = NOPSEUDO) final;
</span><del>-    bool willRecalcStyle(Style::Change) override;
</del><span class="cx"> 
</span><span class="cx">     virtual bool isSupported(StringImpl* feature, StringImpl* version) const;
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoresvgSVGUseElementcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/svg/SVGUseElement.cpp (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/svg/SVGUseElement.cpp        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/svg/SVGUseElement.cpp        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -178,11 +178,12 @@
</span><span class="cx">     SVGGraphicsElement::svgAttributeChanged(attrName);
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void SVGUseElement::willAttachRenderers()
</del><ins>+bool SVGUseElement::willRecalcStyle(Style::Change change)
</ins><span class="cx"> {
</span><ins>+    // FIXME: Shadow tree should be updated before style recalc.
</ins><span class="cx">     if (m_shadowTreeNeedsUpdate)
</span><span class="cx">         updateShadowTree();
</span><del>-    SVGGraphicsElement::willAttachRenderers();
</del><ins>+    return SVGGraphicsElement::willRecalcStyle(change);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> static HashSet&lt;AtomicString&gt; createAllowedElementSet()
</span></span></pre></div>
<a id="trunkSourceWebCoresvgSVGUseElementh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/svg/SVGUseElement.h (198942 => 198943)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/svg/SVGUseElement.h        2016-04-01 06:31:37 UTC (rev 198942)
+++ trunk/Source/WebCore/svg/SVGUseElement.h        2016-04-01 09:54:12 UTC (rev 198943)
</span><span class="lines">@@ -63,7 +63,7 @@
</span><span class="cx">     void buildPendingResource() override;
</span><span class="cx">     void parseAttribute(const QualifiedName&amp;, const AtomicString&amp;) override;
</span><span class="cx">     void svgAttributeChanged(const QualifiedName&amp;) override;
</span><del>-    void willAttachRenderers() override;
</del><ins>+    bool willRecalcStyle(Style::Change) override;
</ins><span class="cx">     RenderPtr&lt;RenderElement&gt; createElementRenderer(Ref&lt;RenderStyle&gt;&amp;&amp;, const RenderTreePosition&amp;) override;
</span><span class="cx">     void toClipPath(Path&amp;) override;
</span><span class="cx">     bool haveLoadedRequiredResources() override;
</span></span></pre>
</div>
</div>

</body>
</html>