<!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>[212074] branches/safari-603-branch</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/212074">212074</a></dd>
<dt>Author</dt> <dd>matthew_hanson@apple.com</dd>
<dt>Date</dt> <dd>2017-02-09 22:37:40 -0800 (Thu, 09 Feb 2017)</dd>
</dl>
<h3>Log Message</h3>
<pre>Merge <a href="http://trac.webkit.org/projects/webkit/changeset/211965">r211965</a>. rdar://problem/30149422</pre>
<h3>Modified Paths</h3>
<ul>
<li><a href="#branchessafari603branchLayoutTestsChangeLog">branches/safari-603-branch/LayoutTests/ChangeLog</a></li>
<li><a href="#branchessafari603branchSourceWebCoreChangeLog">branches/safari-603-branch/Source/WebCore/ChangeLog</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomCharacterDatacpp">branches/safari-603-branch/Source/WebCore/dom/CharacterData.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomContainerNodecpp">branches/safari-603-branch/Source/WebCore/dom/ContainerNode.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomContainerNodeh">branches/safari-603-branch/Source/WebCore/dom/ContainerNode.h</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomContainerNodeAlgorithmscpp">branches/safari-603-branch/Source/WebCore/dom/ContainerNodeAlgorithms.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomDocumentcpp">branches/safari-603-branch/Source/WebCore/dom/Document.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomElementcpp">branches/safari-603-branch/Source/WebCore/dom/Element.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomEventDispatchercpp">branches/safari-603-branch/Source/WebCore/dom/EventDispatcher.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomEventTargetcpp">branches/safari-603-branch/Source/WebCore/dom/EventTarget.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomNoEventDispatchAssertionh">branches/safari-603-branch/Source/WebCore/dom/NoEventDispatchAssertion.h</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomNodecpp">branches/safari-603-branch/Source/WebCore/dom/Node.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomScriptElementcpp">branches/safari-603-branch/Source/WebCore/dom/ScriptElement.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomScriptElementh">branches/safari-603-branch/Source/WebCore/dom/ScriptElement.h</a></li>
<li><a href="#branchessafari603branchSourceWebCoredomWebKitNamedFlowcpp">branches/safari-603-branch/Source/WebCore/dom/WebKitNamedFlow.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCorehtmlHTMLElementcpp">branches/safari-603-branch/Source/WebCore/html/HTMLElement.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCorehtmlHTMLElementh">branches/safari-603-branch/Source/WebCore/html/HTMLElement.h</a></li>
<li><a href="#branchessafari603branchSourceWebCorehtmlHTMLMediaElementcpp">branches/safari-603-branch/Source/WebCore/html/HTMLMediaElement.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCorehtmlHTMLScriptElementcpp">branches/safari-603-branch/Source/WebCore/html/HTMLScriptElement.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCorehtmlHTMLTextFormControlElementcpp">branches/safari-603-branch/Source/WebCore/html/HTMLTextFormControlElement.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCorehtmltrackVTTCuecpp">branches/safari-603-branch/Source/WebCore/html/track/VTTCue.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoreloadercacheCachedSVGFontcpp">branches/safari-603-branch/Source/WebCore/loader/cache/CachedSVGFont.cpp</a></li>
<li><a href="#branchessafari603branchSourceWebCoresvgSVGScriptElementcpp">branches/safari-603-branch/Source/WebCore/svg/SVGScriptElement.cpp</a></li>
</ul>
<h3>Added Paths</h3>
<ul>
<li><a href="#branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisadoptedexpectedtxt">branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted-expected.txt</a></li>
<li><a href="#branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisadoptedhtml">branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted.html</a></li>
<li><a href="#branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisremovedexpectedtxt">branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed-expected.txt</a></li>
<li><a href="#branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisremovedhtml">branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed.html</a></li>
</ul>
</div>
<div id="patch">
<h3>Diff</h3>
<a id="branchessafari603branchLayoutTestsChangeLog"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/LayoutTests/ChangeLog (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/LayoutTests/ChangeLog        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/LayoutTests/ChangeLog        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -1,5 +1,24 @@
</span><span class="cx"> 2017-02-09 Matthew Hanson <matthew_hanson@apple.com>
</span><span class="cx">
</span><ins>+ Merge r211965. rdar://problem/30149422
+
+ 2017-02-09 Ryosuke Niwa <rniwa@webkit.org>
+
+ Adopting a child node of a script element can run script
+ https://bugs.webkit.org/show_bug.cgi?id=167318
+
+ Reviewed by Darin Adler.
+
+ Added regression tests for adopting or removing a child node of a script element.
+ The script must not run when nodes are adopted or removed.
+
+ * fast/html/script-must-not-run-when-child-is-adopted-expected.txt: Added.
+ * fast/html/script-must-not-run-when-child-is-adopted.html: Added.
+ * fast/html/script-must-not-run-when-child-is-removed-expected.txt: Added.
+ * fast/html/script-must-not-run-when-child-is-removed.html: Added.
+
+2017-02-09 Matthew Hanson <matthew_hanson@apple.com>
+
</ins><span class="cx"> Merge r211968. rdar://problem/28062149
</span><span class="cx">
</span><span class="cx"> 2017-02-09 Yusuke Suzuki <utatane.tea@gmail.com>
</span></span></pre></div>
<a id="branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisadoptedexpectedtxt"></a>
<div class="addfile"><h4>Added: branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted-expected.txt (0 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted-expected.txt         (rev 0)
+++ branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted-expected.txt        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -0,0 +1,20 @@
</span><ins>+Adopting a script element must not run the script.
+
+On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
+
+
+Testing HTMLScriptElement
+PASS didRunScript is false
+PASS div.parentNode is not doc.body
+PASS div.parentNode is null
+PASS div.ownerDocument is document
+
+Testing SVGScriptElement
+PASS didRunScript is false
+PASS div.parentNode is not doc.body
+PASS div.parentNode is null
+PASS div.ownerDocument is document
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
</ins></span></pre></div>
<a id="branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisadoptedhtml"></a>
<div class="addfile"><h4>Added: branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted.html (0 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted.html         (rev 0)
+++ branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-adopted.html        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -0,0 +1,50 @@
</span><ins>+<!DOCTYPE html>
+<html>
+<body>
+<div id="test-container"></div>
+<script src="../../resources/js-test.js"></script>
+<script>
+
+description('Adopting a script element must not run the script.');
+
+let testContainer = document.getElementById('test-container');
+
+var doc;
+var didRunScript;
+var div;
+function runTest(createScriptElement)
+{
+ didRunScript = false;
+ div = document.createElement('div');
+
+ let iframe = document.createElement('iframe');
+ testContainer.appendChild(iframe);
+
+ doc = iframe.contentDocument;
+ let script = createScriptElement(doc);
+ script.type = 'invalid-type';
+ script.textContent = 'parent.didRunScript = true; document.body.appendChild(parent.div)';
+
+ script.appendChild(div);
+ doc.body.appendChild(script);
+
+ script.type = '';
+ document.adoptNode(div);
+ testContainer.innerHTML = '';
+
+ shouldBeFalse('didRunScript');
+ shouldNotBe('div.parentNode', 'doc.body');
+ shouldBe('div.parentNode', 'null');
+ shouldBe('div.ownerDocument', 'document');
+}
+
+debug('Testing HTMLScriptElement');
+runTest((doc) => doc.createElement('script'));
+
+debug('');
+debug('Testing SVGScriptElement');
+runTest((doc) => doc.createElementNS('http://www.w3.org/2000/svg', 'script'));
+
+</script>
+</body>
+</html>
</ins></span></pre></div>
<a id="branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisremovedexpectedtxt"></a>
<div class="addfile"><h4>Added: branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed-expected.txt (0 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed-expected.txt         (rev 0)
+++ branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed-expected.txt        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -0,0 +1,15 @@
</span><ins>+Adopting a script element must not run the script.
+
+On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
+
+
+PASS script = scriptElement("html"); script.removeChild(textChild); didRunScript is false
+PASS script = scriptElement("svg"); script.removeChild(textChild); didRunScript is false
+PASS script = scriptElement("html"); script.removeChild(elementChild); didRunScript is false
+PASS script = scriptElement("svg"); script.removeChild(elementChild); didRunScript is false
+PASS script = scriptElement("html"); script.removeChild(commentChild); didRunScript is false
+PASS script = scriptElement("svg"); script.removeChild(commentChild); didRunScript is false
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
</ins></span></pre></div>
<a id="branchessafari603branchLayoutTestsfasthtmlscriptmustnotrunwhenchildisremovedhtml"></a>
<div class="addfile"><h4>Added: branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed.html (0 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed.html         (rev 0)
+++ branches/safari-603-branch/LayoutTests/fast/html/script-must-not-run-when-child-is-removed.html        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -0,0 +1,51 @@
</span><ins>+<!DOCTYPE html>
+<html>
+<body>
+<div id="test-container"></div>
+<script src="../../resources/js-test.js"></script>
+<script>
+
+description('Adopting a script element must not run the script.');
+
+let testContainer = document.getElementById('test-container');
+
+var didRunScript;
+var textChild;
+var elementChild;
+var commentChild;
+function scriptElement(type)
+{
+ didRunScript = false;
+
+ let namespaceURI = type == 'html' ? 'http://www.w3.org/1999/xhtml' : 'http://www.w3.org/2000/svg';
+ let script = document.createElementNS(namespaceURI, 'script');
+ script.type = 'invalid-type';
+ script.textContent = 'didRunScript = true';
+
+ document.body.appendChild(script);
+
+ textChild = document.createTextNode('');
+ script.appendChild(textChild);
+
+ elementChild = document.createElement('div');
+ script.appendChild(elementChild);
+
+ commentChild = document.createComment('');
+ script.appendChild(commentChild);
+
+ script.type = "";
+ return script;
+}
+
+shouldBeFalse('script = scriptElement("html"); script.removeChild(textChild); didRunScript');
+shouldBeFalse('script = scriptElement("svg"); script.removeChild(textChild); didRunScript');
+
+shouldBeFalse('script = scriptElement("html"); script.removeChild(elementChild); didRunScript');
+shouldBeFalse('script = scriptElement("svg"); script.removeChild(elementChild); didRunScript');
+
+shouldBeFalse('script = scriptElement("html"); script.removeChild(commentChild); didRunScript');
+shouldBeFalse('script = scriptElement("svg"); script.removeChild(commentChild); didRunScript');
+
+</script>
+</body>
+</html>
</ins></span></pre></div>
<a id="branchessafari603branchSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/ChangeLog (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/ChangeLog        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/ChangeLog        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -1,5 +1,116 @@
</span><span class="cx"> 2017-02-09 Matthew Hanson <matthew_hanson@apple.com>
</span><span class="cx">
</span><ins>+ Merge r211965. rdar://problem/30149422
+
+ 2017-02-09 Ryosuke Niwa <rniwa@webkit.org>
+
+ Adopting a child node of a script element can run script
+ https://bugs.webkit.org/show_bug.cgi?id=167318
+
+ Reviewed by Darin Adler.
+
+ The bug was caused by ScriptElement::childrenChanged indiscriminately running the script.
+ Do this only if some node has been inserted as spec'ed:
+
+ https://html.spec.whatwg.org/multipage/scripting.html#script-processing-model
+ "The script element is connected and a node or document fragment is inserted into
+ the script element, after any script elements inserted at that time."
+
+ Split NonContentsChildChanged into NonContentsChildInserted and NonContentsChildRemoved to disambiguate
+ non-contents child such as text and element being removed or inserted. New behavior matches that of
+ Gecko and Chrome as well as the latest HTML5 specification.
+
+ Also deploy NoEventDispatchAssertion in more places. Unfortunately, this results in some DOM trees
+ internal to WebKit to be mutated while there is NoEventDispatchAssertion in the stack. Added a new RAII
+ object "EventAllowedScope" to temporarily disable this assertion within such a tree. CachedSVGFont's
+ ensureCustomFontData used to completely disable this assertion but we no longer have to do this either.
+
+ To clarify the new semantics, renamed isEventDispatchForbidden to isEventAllowedInMainThread with
+ the negated boolean value, and added a new variant isEventDispatchAllowedInSubtree, which checks
+ isEventDispatchForbidden() is true or if the node was one of an internal DOM node or its descendent
+ held by EventAllowedScope.
+
+ Inspired by https://chromium.googlesource.com/chromium/src/+/604e798ec6ee30f44d57a5c4a44ce3dab3a871ed
+
+ Tests: fast/html/script-must-not-run-when-child-is-adopted.html
+ fast/html/script-must-not-run-when-child-is-removed.html
+
+ * dom/CharacterData.cpp:
+ (WebCore::CharacterData::notifyParentAfterChange): Added NoEventDispatchAssertion.
+ * dom/ContainerNode.cpp:
+ (WebCore::ContainerNode::insertBefore): Added NoEventDispatchAssertion around TreeScope's adoptIfNeeded
+ and insertBeforeCommon as done elsewhere.
+ (WebCore::ContainerNode::appendChildCommon): Added NoEventDispatchAssertion.
+ (WebCore::ContainerNode::changeForChildInsertion): Use NonContentsChildInserted here.
+ (WebCore::ContainerNode::notifyChildRemoved): Added NoEventDispatchAssertion.
+ (WebCore::ContainerNode::replaceChild): Moved adoptIfNeeded into NoEventDispatchAssertion.
+ (WebCore::ContainerNode::removeChild): Added NoEventDispatchAssertion.
+ (WebCore::ContainerNode::parserRemoveChild): Added NoEventDispatchAssertion.
+ (WebCore::ContainerNode::removeChildren): Call childrenChanged in NoEventDispatchAssertion.
+ (WebCore::ContainerNode::appendChildWithoutPreInsertionValidityCheck): Moved adoptIfNeeded into
+ NoEventDispatchAssertion.
+ (WebCore::dispatchChildInsertionEvents): Check the forbidden-ness more precisely.
+ (WebCore::dispatchChildRemovalEvents): Ditto.
+ * dom/ContainerNode.h:
+ (WebCore::ContainerNode::ChildChange::isInsertion): Added.
+ * dom/ContainerNodeAlgorithms.cpp:
+ (WebCore::notifyChildNodeInserted): Check the forbidden-ness more precisely. Here, we check against
+ insertionPoint since EventAllowedScope checks against the root node.
+ * dom/Document.cpp:
+ (WebCore::Document::adoptNode): Assert the node to be adopted has not been inserted back, or else
+ remove() had resulted in an exception before calling TreeScope::adoptIfNeeded.
+ * dom/Element.cpp:
+ (WebCore::Element::childrenChanged):
+ * dom/NoEventDispatchAssertion.h:
+ (WebCore::NoEventDispatchAssertion::isEventDispatchForbidden): Added a new variant that takes a node.
+ If this node is a descendent of a node "marked as safe" by EventAllowedScope, then we don't consider
+ the event dispatch to be forbidden.
+ (WebCore::NoEventDispatchAssertion::dropTemporarily): Deleted.
+ (WebCore::NoEventDispatchAssertion::restoreDropped): Deleted.
+ (WebCore::NoEventDispatchAssertion::EventAllowedScope): Added. A RAII object which marks descendants of
+ a given node as "safe" for the purpose of checking isEventDispatchForbidden.
+ (WebCore::NoEventDispatchAssertion::EventAllowedScope::EventAllowedScope): Added. There can be a chain
+ of EventAllowedScope objects in the stack. s_currentScope points to the most recently instantiated
+ RAII object, and each instance remembers prior instance.
+ (WebCore::NoEventDispatchAssertion::EventAllowedScope::~EventAllowedScope): Added.
+ (WebCore::NoEventDispatchAssertion::EventAllowedScope::isAllowedNode): Added. Returns true if the given
+ node is a descendent of any node held by instances of EventAllowedScope.
+ (WebCore::NoEventDispatchAssertion::EventAllowedScope::isAllowedNodeInternal): Added. A helper function
+ for isAllowedNode.
+ * dom/Node.cpp:
+ (WebCore::Node::dispatchSubtreeModifiedEvent): Check the forbidden-ness more precisely.
+ * dom/ScriptElement.cpp:
+ (WebCore::ScriptElement::childrenChanged): Only prepare the script if we've inserted nodes.
+ (WebCore::ScriptElement::executeClassicScript): Assert isEventDispatchForbidden is false since running
+ arbitrary author scripts can, indeed, result dispatch any events.
+ * dom/ScriptElement.h:
+ * html/HTMLElement.cpp:
+ (WebCore::textToFragment): Made this a static local function and not return an exception since there
+ is no way appendChild called in this function can throw an exception.
+ (WebCore::HTMLElement::setInnerText): Create EventAllowedScope for the fragment. It's called called by
+ HTMLTextAreaElement's childrenChanged to update its UA shadow tree, and it's dispatching as event on
+ a new fragment can't execute arbitrary scripts since it has never been exposed to author scripts.
+ Because of the precise-ness of this check, this does not disable the assertion for "this" element.
+ HTMLTextFormControlElement::setInnerTextValue explicitly creates another EventAllowedScope to mark
+ the shadow tree into which the fragment is inserted safe.
+ (WebCore::HTMLElement::setOuterText):
+ * html/HTMLElement.h:
+ * html/HTMLScriptElement.cpp:
+ (WebCore::HTMLScriptElement::childrenChanged):
+ * html/HTMLTextFormControlElement.cpp:
+ (WebCore::HTMLTextFormControlElement::setInnerTextValue): See above (setInnerText).
+ * html/track/VTTCue.cpp:
+ (WebCore::VTTCue::createCueRenderingTree): Create EventAllowedScope for the cloned fragment here since
+ the VTT tree is never exposed to author scripts.
+ (WebCore::VTTCue::updateDisplayTree): Ditto.
+ * loader/cache/CachedSVGFont.cpp:
+ (WebCore::CachedSVGFont::ensureCustomFontData): Use EventAllowedScope to disable assertions only on
+ the new SVG document we just created instead of disabling for all DOM trees.
+ * svg/SVGScriptElement.cpp:
+ (WebCore::SVGScriptElement::childrenChanged):
+
+2017-02-09 Matthew Hanson <matthew_hanson@apple.com>
+
</ins><span class="cx"> Merge r211763. rdar://problem/30380075
</span><span class="cx">
</span><span class="cx"> 2017-02-06 Brent Fulgham <bfulgham@apple.com>
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomCharacterDatacpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/CharacterData.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/CharacterData.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/CharacterData.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -30,6 +30,7 @@
</span><span class="cx"> #include "MutationEvent.h"
</span><span class="cx"> #include "MutationObserverInterestGroup.h"
</span><span class="cx"> #include "MutationRecord.h"
</span><ins>+#include "NoEventDispatchAssertion.h"
</ins><span class="cx"> #include "ProcessingInstruction.h"
</span><span class="cx"> #include "RenderText.h"
</span><span class="cx"> #include "StyleInheritedData.h"
</span><span class="lines">@@ -207,6 +208,8 @@
</span><span class="cx">
</span><span class="cx"> void CharacterData::notifyParentAfterChange(ContainerNode::ChildChangeSource source)
</span><span class="cx"> {
</span><ins>+ NoEventDispatchAssertion assertNoEventDispatch;
+
</ins><span class="cx"> document().incDOMTreeVersion();
</span><span class="cx">
</span><span class="cx"> if (!parentNode())
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomContainerNodecpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/ContainerNode.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/ContainerNode.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/ContainerNode.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -73,6 +73,7 @@
</span><span class="cx">
</span><span class="cx"> #ifndef NDEBUG
</span><span class="cx"> unsigned NoEventDispatchAssertion::s_count = 0;
</span><ins>+NoEventDispatchAssertion::EventAllowedScope* NoEventDispatchAssertion::EventAllowedScope::s_currentScope = nullptr;
</ins><span class="cx"> #endif
</span><span class="cx">
</span><span class="cx"> static ExceptionOr<void> collectChildrenAndRemoveFromOldParent(Node& node, NodeVector& nodes)
</span><span class="lines">@@ -281,9 +282,12 @@
</span><span class="cx"> if (child->parentNode())
</span><span class="cx"> break;
</span><span class="cx">
</span><del>- treeScope().adoptIfNeeded(child);
</del><ins>+ {
+ NoEventDispatchAssertion assertNoEventDispatch;
</ins><span class="cx">
</span><del>- insertBeforeCommon(next, child);
</del><ins>+ treeScope().adoptIfNeeded(child);
+ insertBeforeCommon(next, child);
+ }
</ins><span class="cx">
</span><span class="cx"> updateTreeAfterInsertion(child);
</span><span class="cx"> }
</span><span class="lines">@@ -319,6 +323,8 @@
</span><span class="cx">
</span><span class="cx"> void ContainerNode::appendChildCommon(Node& child)
</span><span class="cx"> {
</span><ins>+ NoEventDispatchAssertion assertNoEventDispatch;
+
</ins><span class="cx"> child.setParentNode(this);
</span><span class="cx">
</span><span class="cx"> if (m_lastChild) {
</span><span class="lines">@@ -338,7 +344,7 @@
</span><span class="cx"> notifyChildNodeInserted(*this, child, postInsertionNotificationTargets);
</span><span class="cx">
</span><span class="cx"> ChildChange change;
</span><del>- change.type = child.isElementNode() ? ElementInserted : child.isTextNode() ? TextInserted : NonContentsChildChanged;
</del><ins>+ change.type = child.isElementNode() ? ElementInserted : child.isTextNode() ? TextInserted : NonContentsChildInserted;
</ins><span class="cx"> change.previousSiblingElement = ElementTraversal::previousSibling(child);
</span><span class="cx"> change.nextSiblingElement = ElementTraversal::nextSibling(child);
</span><span class="cx"> change.source = source;
</span><span class="lines">@@ -351,10 +357,11 @@
</span><span class="cx">
</span><span class="cx"> void ContainerNode::notifyChildRemoved(Node& child, Node* previousSibling, Node* nextSibling, ChildChangeSource source)
</span><span class="cx"> {
</span><ins>+ NoEventDispatchAssertion assertNoEventDispatch;
</ins><span class="cx"> notifyChildNodeRemoved(*this, child);
</span><span class="cx">
</span><span class="cx"> ChildChange change;
</span><del>- change.type = is<Element>(child) ? ElementRemoved : is<Text>(child) ? TextRemoved : NonContentsChildChanged;
</del><ins>+ change.type = is<Element>(child) ? ElementRemoved : is<Text>(child) ? TextRemoved : NonContentsChildRemoved;
</ins><span class="cx"> change.previousSiblingElement = (!previousSibling || is<Element>(*previousSibling)) ? downcast<Element>(previousSibling) : ElementTraversal::previousSibling(*previousSibling);
</span><span class="cx"> change.nextSiblingElement = (!nextSibling || is<Element>(*nextSibling)) ? downcast<Element>(nextSibling) : ElementTraversal::nextSibling(*nextSibling);
</span><span class="cx"> change.source = source;
</span><span class="lines">@@ -445,10 +452,9 @@
</span><span class="cx"> if (child->parentNode())
</span><span class="cx"> break;
</span><span class="cx">
</span><del>- treeScope().adoptIfNeeded(child);
-
</del><span class="cx"> {
</span><span class="cx"> NoEventDispatchAssertion assertNoEventDispatch;
</span><ins>+ treeScope().adoptIfNeeded(child);
</ins><span class="cx"> if (refChild)
</span><span class="cx"> insertBeforeCommon(*refChild, child.get());
</span><span class="cx"> else
</span><span class="lines">@@ -529,6 +535,7 @@
</span><span class="cx">
</span><span class="cx"> {
</span><span class="cx"> WidgetHierarchyUpdatesSuspensionScope suspendWidgetHierarchyUpdates;
</span><ins>+ NoEventDispatchAssertion assertNoEventDispatch;
</ins><span class="cx">
</span><span class="cx"> Node* prev = child->previousSibling();
</span><span class="cx"> Node* next = child->nextSibling();
</span><span class="lines">@@ -585,6 +592,8 @@
</span><span class="cx">
</span><span class="cx"> void ContainerNode::parserRemoveChild(Node& oldChild)
</span><span class="cx"> {
</span><ins>+ NoEventDispatchAssertion assertNoEventDispatch;
+
</ins><span class="cx"> ASSERT(oldChild.parentNode() == this);
</span><span class="cx"> ASSERT(!oldChild.isDocumentFragment());
</span><span class="cx">
</span><span class="lines">@@ -617,12 +626,11 @@
</span><span class="cx">
</span><span class="cx"> {
</span><span class="cx"> WidgetHierarchyUpdatesSuspensionScope suspendWidgetHierarchyUpdates;
</span><del>- {
- NoEventDispatchAssertion assertNoEventDispatch;
- while (RefPtr<Node> child = m_firstChild) {
- removeBetween(0, child->nextSibling(), *child);
- notifyChildNodeRemoved(*this, *child);
- }
</del><ins>+ NoEventDispatchAssertion assertNoEventDispatch;
+
+ while (RefPtr<Node> child = m_firstChild) {
+ removeBetween(0, child->nextSibling(), *child);
+ notifyChildNodeRemoved(*this, *child);
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> ChildChange change = { AllChildrenRemoved, nullptr, nullptr, ChildChangeSourceAPI };
</span><span class="lines">@@ -680,11 +688,10 @@
</span><span class="cx"> if (child->parentNode())
</span><span class="cx"> break;
</span><span class="cx">
</span><del>- treeScope().adoptIfNeeded(child);
-
</del><span class="cx"> // Append child to the end of the list
</span><span class="cx"> {
</span><span class="cx"> NoEventDispatchAssertion assertNoEventDispatch;
</span><ins>+ treeScope().adoptIfNeeded(child);
</ins><span class="cx"> appendChildCommon(child);
</span><span class="cx"> }
</span><span class="cx">
</span><span class="lines">@@ -754,7 +761,7 @@
</span><span class="cx"> if (child.isInShadowTree())
</span><span class="cx"> return;
</span><span class="cx">
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventDispatchAllowedInSubtree(child));
</ins><span class="cx">
</span><span class="cx"> RefPtr<Node> c = &child;
</span><span class="cx"> Ref<Document> document(child.document());
</span><span class="lines">@@ -776,7 +783,7 @@
</span><span class="cx"> return;
</span><span class="cx"> }
</span><span class="cx">
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventDispatchAllowedInSubtree(child));
</ins><span class="cx">
</span><span class="cx"> willCreatePossiblyOrphanedTreeByRemoval(&child);
</span><span class="cx"> InspectorInstrumentation::willRemoveDOMNode(child.document(), child);
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomContainerNodeh"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/ContainerNode.h (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/ContainerNode.h        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/ContainerNode.h        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -66,7 +66,7 @@
</span><span class="cx">
</span><span class="cx"> void cloneChildNodes(ContainerNode& clone);
</span><span class="cx">
</span><del>- enum ChildChangeType { ElementInserted, ElementRemoved, TextInserted, TextRemoved, TextChanged, AllChildrenRemoved, NonContentsChildChanged };
</del><ins>+ enum ChildChangeType { ElementInserted, ElementRemoved, TextInserted, TextRemoved, TextChanged, AllChildrenRemoved, NonContentsChildRemoved, NonContentsChildInserted, AllChildrenReplaced };
</ins><span class="cx"> enum ChildChangeSource { ChildChangeSourceParser, ChildChangeSourceAPI };
</span><span class="cx"> struct ChildChange {
</span><span class="cx"> ChildChangeType type;
</span><span class="lines">@@ -73,6 +73,25 @@
</span><span class="cx"> Element* previousSiblingElement;
</span><span class="cx"> Element* nextSiblingElement;
</span><span class="cx"> ChildChangeSource source;
</span><ins>+
+ bool isInsertion() const
+ {
+ switch (type) {
+ case ElementInserted:
+ case TextInserted:
+ case NonContentsChildInserted:
+ case AllChildrenReplaced:
+ return true;
+ case ElementRemoved:
+ case TextRemoved:
+ case TextChanged:
+ case AllChildrenRemoved:
+ case NonContentsChildRemoved:
+ return false;
+ }
+ ASSERT_NOT_REACHED();
+ return false;
+ }
</ins><span class="cx"> };
</span><span class="cx"> virtual void childrenChanged(const ChildChange&);
</span><span class="cx">
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomContainerNodeAlgorithmscpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/ContainerNodeAlgorithms.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/ContainerNodeAlgorithms.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/ContainerNodeAlgorithms.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -27,6 +27,7 @@
</span><span class="cx"> #include "ContainerNodeAlgorithms.h"
</span><span class="cx">
</span><span class="cx"> #include "HTMLFrameOwnerElement.h"
</span><ins>+#include "HTMLTextAreaElement.h"
</ins><span class="cx"> #include "InspectorInstrumentation.h"
</span><span class="cx"> #include "NoEventDispatchAssertion.h"
</span><span class="cx"> #include "ShadowRoot.h"
</span><span class="lines">@@ -90,7 +91,7 @@
</span><span class="cx">
</span><span class="cx"> void notifyChildNodeInserted(ContainerNode& insertionPoint, Node& node, NodeVector& postInsertionNotificationTargets)
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventDispatchAllowedInSubtree(insertionPoint));
</ins><span class="cx">
</span><span class="cx"> InspectorInstrumentation::didInsertDOMNode(node.document(), node);
</span><span class="cx">
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomDocumentcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/Document.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/Document.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/Document.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -1042,6 +1042,8 @@
</span><span class="cx"> auto result = source.remove();
</span><span class="cx"> if (result.hasException())
</span><span class="cx"> return result.releaseException();
</span><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(!source.inDocument());
+ ASSERT_WITH_SECURITY_IMPLICATION(!source.parentNode());
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> adoptIfNeeded(source);
</span><span class="lines">@@ -4095,7 +4097,7 @@
</span><span class="cx">
</span><span class="cx"> void Document::dispatchWindowEvent(Event& event, EventTarget* target)
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> if (!m_domWindow)
</span><span class="cx"> return;
</span><span class="cx"> m_domWindow->dispatchEvent(event, target);
</span><span class="lines">@@ -4103,7 +4105,7 @@
</span><span class="cx">
</span><span class="cx"> void Document::dispatchWindowLoadEvent()
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> if (!m_domWindow)
</span><span class="cx"> return;
</span><span class="cx"> m_domWindow->dispatchLoadEvent();
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomElementcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/Element.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/Element.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/Element.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -2035,6 +2035,7 @@
</span><span class="cx"> // For elements, we notify shadowRoot in Element::insertedInto and Element::removedFrom.
</span><span class="cx"> break;
</span><span class="cx"> case AllChildrenRemoved:
</span><ins>+ case AllChildrenReplaced:
</ins><span class="cx"> shadowRoot->didRemoveAllChildrenOfShadowHost();
</span><span class="cx"> break;
</span><span class="cx"> case TextInserted:
</span><span class="lines">@@ -2042,7 +2043,8 @@
</span><span class="cx"> case TextChanged:
</span><span class="cx"> shadowRoot->didChangeDefaultSlot();
</span><span class="cx"> break;
</span><del>- case NonContentsChildChanged:
</del><ins>+ case NonContentsChildInserted:
+ case NonContentsChildRemoved:
</ins><span class="cx"> break;
</span><span class="cx"> }
</span><span class="cx"> }
</span><span class="lines">@@ -2448,7 +2450,7 @@
</span><span class="cx">
</span><span class="cx"> void Element::dispatchFocusInEvent(const AtomicString& eventType, RefPtr<Element>&& oldFocusedElement)
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> ASSERT(eventType == eventNames().focusinEvent || eventType == eventNames().DOMFocusInEvent);
</span><span class="cx"> dispatchScopedEvent(FocusEvent::create(eventType, true, false, document().defaultView(), 0, WTFMove(oldFocusedElement)));
</span><span class="cx"> }
</span><span class="lines">@@ -2455,7 +2457,7 @@
</span><span class="cx">
</span><span class="cx"> void Element::dispatchFocusOutEvent(const AtomicString& eventType, RefPtr<Element>&& newFocusedElement)
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> ASSERT(eventType == eventNames().focusoutEvent || eventType == eventNames().DOMFocusOutEvent);
</span><span class="cx"> dispatchScopedEvent(FocusEvent::create(eventType, true, false, document().defaultView(), 0, WTFMove(newFocusedElement)));
</span><span class="cx"> }
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomEventDispatchercpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/EventDispatcher.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/EventDispatcher.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/EventDispatcher.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -129,7 +129,7 @@
</span><span class="cx">
</span><span class="cx"> bool EventDispatcher::dispatchEvent(Node& node, Event& event)
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> Ref<Node> protectedNode(node);
</span><span class="cx"> RefPtr<FrameView> view = node.document().view();
</span><span class="cx"> EventPath eventPath(node, event);
</span><span class="lines">@@ -148,7 +148,7 @@
</span><span class="cx"> if (!event.target())
</span><span class="cx"> return true;
</span><span class="cx">
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx">
</span><span class="cx"> InputElementClickState clickHandlingState;
</span><span class="cx"> if (is<HTMLInputElement>(node))
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomEventTargetcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/EventTarget.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/EventTarget.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/EventTarget.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -187,7 +187,7 @@
</span><span class="cx">
</span><span class="cx"> bool EventTarget::fireEventListeners(Event& event)
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> ASSERT(event.isInitialized());
</span><span class="cx">
</span><span class="cx"> auto* data = eventTargetData();
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomNoEventDispatchAssertionh"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/NoEventDispatchAssertion.h (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/NoEventDispatchAssertion.h        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/NoEventDispatchAssertion.h        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -23,6 +23,7 @@
</span><span class="cx">
</span><span class="cx"> #pragma once
</span><span class="cx">
</span><ins>+#include "ContainerNode.h"
</ins><span class="cx"> #include <wtf/MainThread.h>
</span><span class="cx">
</span><span class="cx"> namespace WebCore {
</span><span class="lines">@@ -53,35 +54,58 @@
</span><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="cx">
</span><del>- static bool isEventDispatchForbidden()
</del><ins>+ static bool isEventAllowedInMainThread()
</ins><span class="cx"> {
</span><span class="cx"> #if ASSERT_DISABLED
</span><del>- return false;
</del><ins>+ return true;
</ins><span class="cx"> #else
</span><del>- return isMainThread() && s_count;
</del><ins>+ return !isMainThread() || !s_count;
</ins><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="cx">
</span><del>- static unsigned dropTemporarily()
</del><ins>+ static bool isEventDispatchAllowedInSubtree(Node& node)
</ins><span class="cx"> {
</span><del>-#if ASSERT_DISABLED
- return 0;
-#else
- unsigned count = s_count;
- s_count = 0;
- return count;
-#endif
</del><ins>+ return isEventAllowedInMainThread() || EventAllowedScope::isAllowedNode(node);
</ins><span class="cx"> }
</span><span class="cx">
</span><del>- static void restoreDropped(unsigned count)
- {
-#if ASSERT_DISABLED
- UNUSED_PARAM(count);
</del><ins>+#if !ASSERT_DISABLED
+ class EventAllowedScope {
+ public:
+ explicit EventAllowedScope(ContainerNode& userAgentContentRoot)
+ : m_eventAllowedTreeRoot(userAgentContentRoot)
+ , m_previousScope(s_currentScope)
+ {
+ s_currentScope = this;
+ }
+
+ ~EventAllowedScope()
+ {
+ s_currentScope = m_previousScope;
+ }
+
+ static bool isAllowedNode(Node& node)
+ {
+ return s_currentScope && s_currentScope->isAllowedNodeInternal(node);
+ }
+
+ private:
+ bool isAllowedNodeInternal(Node& node)
+ {
+ return m_eventAllowedTreeRoot->contains(&node) || (m_previousScope && m_previousScope->isAllowedNodeInternal(node));
+ }
+
+ Ref<ContainerNode> m_eventAllowedTreeRoot;
+
+ EventAllowedScope* m_previousScope;
+ static EventAllowedScope* s_currentScope;
+ };
</ins><span class="cx"> #else
</span><del>- ASSERT(!s_count);
- s_count = count;
</del><ins>+ class EventAllowedScope {
+ public:
+ explicit EventAllowedScope(ContainerNode&) { }
+ static bool isAllowedNode(Node&) { return true; }
+ };
</ins><span class="cx"> #endif
</span><del>- }
</del><span class="cx">
</span><span class="cx"> #if !ASSERT_DISABLED
</span><span class="cx"> private:
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomNodecpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/Node.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/Node.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/Node.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -2199,7 +2199,7 @@
</span><span class="cx"> if (isInShadowTree())
</span><span class="cx"> return;
</span><span class="cx">
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventDispatchAllowedInSubtree(*this));
</ins><span class="cx">
</span><span class="cx"> if (!document().hasListenerType(Document::DOMSUBTREEMODIFIED_LISTENER))
</span><span class="cx"> return;
</span><span class="lines">@@ -2212,7 +2212,7 @@
</span><span class="cx">
</span><span class="cx"> bool Node::dispatchDOMActivateEvent(int detail, Event& underlyingEvent)
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> Ref<UIEvent> event = UIEvent::create(eventNames().DOMActivateEvent, true, true, document().defaultView(), detail);
</span><span class="cx"> event->setUnderlyingEvent(&underlyingEvent);
</span><span class="cx"> dispatchScopedEvent(event);
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomScriptElementcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/ScriptElement.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/ScriptElement.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/ScriptElement.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -42,6 +42,7 @@
</span><span class="cx"> #include "LoadableModuleScript.h"
</span><span class="cx"> #include "MIMETypeRegistry.h"
</span><span class="cx"> #include "Page.h"
</span><ins>+#include "NoEventDispatchAssertion.h"
</ins><span class="cx"> #include "PendingScript.h"
</span><span class="cx"> #include "SVGNames.h"
</span><span class="cx"> #include "SVGScriptElement.h"
</span><span class="lines">@@ -87,9 +88,9 @@
</span><span class="cx"> prepareScript(); // FIXME: Provide a real starting line number here.
</span><span class="cx"> }
</span><span class="cx">
</span><del>-void ScriptElement::childrenChanged()
</del><ins>+void ScriptElement::childrenChanged(const ContainerNode::ChildChange& childChange)
</ins><span class="cx"> {
</span><del>- if (!m_parserInserted && m_element.inDocument())
</del><ins>+ if (!m_parserInserted && childChange.isInsertion() && m_element.inDocument())
</ins><span class="cx"> prepareScript(); // FIXME: Provide a real starting line number here.
</span><span class="cx"> }
</span><span class="cx">
</span><span class="lines">@@ -395,6 +396,7 @@
</span><span class="cx">
</span><span class="cx"> void ScriptElement::executeClassicScript(const ScriptSourceCode& sourceCode)
</span><span class="cx"> {
</span><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx"> ASSERT(m_alreadyStarted);
</span><span class="cx">
</span><span class="cx"> if (sourceCode.isEmpty())
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomScriptElementh"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/ScriptElement.h (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/ScriptElement.h        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/ScriptElement.h        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -22,6 +22,7 @@
</span><span class="cx">
</span><span class="cx"> #include "CachedResourceClient.h"
</span><span class="cx"> #include "CachedResourceHandle.h"
</span><ins>+#include "ContainerNode.h"
</ins><span class="cx"> #include "LoadableScript.h"
</span><span class="cx"> #include "LoadableScriptClient.h"
</span><span class="cx"> #include "Timer.h"
</span><span class="lines">@@ -84,7 +85,7 @@
</span><span class="cx"> // Helper functions used by our parent classes.
</span><span class="cx"> bool shouldCallFinishedInsertingSubtree(ContainerNode&);
</span><span class="cx"> void finishedInsertingSubtree();
</span><del>- void childrenChanged();
</del><ins>+ void childrenChanged(const ContainerNode::ChildChange&);
</ins><span class="cx"> void handleSourceAttribute(const String& sourceURL);
</span><span class="cx"> void handleAsyncAttribute();
</span><span class="cx">
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoredomWebKitNamedFlowcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/dom/WebKitNamedFlow.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/dom/WebKitNamedFlow.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/dom/WebKitNamedFlow.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -212,7 +212,7 @@
</span><span class="cx">
</span><span class="cx"> void WebKitNamedFlow::dispatchRegionOversetChangeEvent()
</span><span class="cx"> {
</span><del>- ASSERT_WITH_SECURITY_IMPLICATION(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT_WITH_SECURITY_IMPLICATION(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx">
</span><span class="cx"> // If the flow is in the "NULL" state the event should not be dispatched any more.
</span><span class="cx"> if (flowState() == FlowStateNull)
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCorehtmlHTMLElementcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/html/HTMLElement.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/html/HTMLElement.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/html/HTMLElement.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -434,12 +434,14 @@
</span><span class="cx"> setAttributeEventListener(eventName, name, value);
</span><span class="cx"> }
</span><span class="cx">
</span><del>-ExceptionOr<Ref<DocumentFragment>> HTMLElement::textToFragment(const String& text)
</del><ins>+static Ref<DocumentFragment> textToFragment(Document& document, const String& text)
</ins><span class="cx"> {
</span><del>- auto fragment = DocumentFragment::create(document());
</del><ins>+ auto fragment = DocumentFragment::create(document);
</ins><span class="cx">
</span><ins>+ // It's safe to dispatch events on the new fragment since author scripts have no access to it yet.
+ NoEventDispatchAssertion::EventAllowedScope allowedScope(fragment);
+
</ins><span class="cx"> for (unsigned start = 0, length = text.length(); start < length; ) {
</span><del>-
</del><span class="cx"> // Find next line break.
</span><span class="cx"> UChar c = 0;
</span><span class="cx"> unsigned i;
</span><span class="lines">@@ -449,17 +451,11 @@
</span><span class="cx"> break;
</span><span class="cx"> }
</span><span class="cx">
</span><del>- auto appendResult = fragment->appendChild(Text::create(document(), text.substring(start, i - start)));
- if (appendResult.hasException())
- return appendResult.releaseException();
-
</del><ins>+ fragment->appendChild(Text::create(document, text.substring(start, i - start)));
</ins><span class="cx"> if (i == length)
</span><span class="cx"> break;
</span><span class="cx">
</span><del>- appendResult = fragment->appendChild(HTMLBRElement::create(document()));
- if (appendResult.hasException())
- return appendResult.releaseException();
-
</del><ins>+ fragment->appendChild(HTMLBRElement::create(document));
</ins><span class="cx"> // Make sure \r\n doesn't result in two line breaks.
</span><span class="cx"> if (c == '\r' && i + 1 < length && text[i + 1] == '\n')
</span><span class="cx"> ++i;
</span><span class="lines">@@ -467,7 +463,7 @@
</span><span class="cx"> start = i + 1; // Character after line break.
</span><span class="cx"> }
</span><span class="cx">
</span><del>- return WTFMove(fragment);
</del><ins>+ return fragment;
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> static inline bool shouldProhibitSetInnerOuterText(const HTMLElement& element)
</span><span class="lines">@@ -543,10 +539,11 @@
</span><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> // Add text nodes and <br> elements.
</span><del>- auto fragment = textToFragment(text);
- if (fragment.hasException())
- return fragment.releaseException();
- return replaceChildrenWithFragment(*this, fragment.releaseReturnValue());
</del><ins>+ auto fragment = textToFragment(document(), text);
+ // FIXME: This should use replaceAllChildren() once it accepts DocumentFragments as input.
+ // It's safe to dispatch events on the new fragment since author scripts have no access to it yet.
+ NoEventDispatchAssertion::EventAllowedScope allowedScope(fragment.get());
+ return replaceChildrenWithFragment(*this, WTFMove(fragment));
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> ExceptionOr<void> HTMLElement::setOuterText(const String& text)
</span><span class="lines">@@ -565,12 +562,9 @@
</span><span class="cx"> RefPtr<Node> newChild;
</span><span class="cx">
</span><span class="cx"> // Convert text to fragment with <br> tags instead of linebreaks if needed.
</span><del>- if (text.contains('\r') || text.contains('\n')) {
- auto result = textToFragment(text);
- if (result.hasException())
- return result.releaseException();
- newChild = result.releaseReturnValue();
- } else
</del><ins>+ if (text.contains('\r') || text.contains('\n'))
+ newChild = textToFragment(document(), text);
+ else
</ins><span class="cx"> newChild = Text::create(document(), text);
</span><span class="cx">
</span><span class="cx"> if (!parentNode())
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCorehtmlHTMLElementh"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/html/HTMLElement.h (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/html/HTMLElement.h        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/html/HTMLElement.h        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -135,8 +135,6 @@
</span><span class="cx">
</span><span class="cx"> virtual HTMLFormElement* virtualForm() const;
</span><span class="cx">
</span><del>- ExceptionOr<Ref<DocumentFragment>> textToFragment(const String&);
-
</del><span class="cx"> void dirAttributeChanged(const AtomicString&);
</span><span class="cx"> void adjustDirectionalityIfNeededAfterChildAttributeChanged(Element* child);
</span><span class="cx"> void adjustDirectionalityIfNeededAfterChildrenChanged(Element* beforeChange, ChildChangeType);
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCorehtmlHTMLMediaElementcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/html/HTMLMediaElement.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/html/HTMLMediaElement.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/html/HTMLMediaElement.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -1283,7 +1283,7 @@
</span><span class="cx"> // Some of the code paths below this function dispatch the BeforeLoad event. This ASSERT helps
</span><span class="cx"> // us catch those bugs more quickly without needing all the branches to align to actually
</span><span class="cx"> // trigger the event.
</span><del>- ASSERT(!NoEventDispatchAssertion::isEventDispatchForbidden());
</del><ins>+ ASSERT(NoEventDispatchAssertion::isEventAllowedInMainThread());
</ins><span class="cx">
</span><span class="cx"> // If we can't start a load right away, start it later.
</span><span class="cx"> if (!m_mediaSession->pageAllowsDataLoading(*this)) {
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCorehtmlHTMLScriptElementcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/html/HTMLScriptElement.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/html/HTMLScriptElement.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/html/HTMLScriptElement.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -55,7 +55,7 @@
</span><span class="cx"> void HTMLScriptElement::childrenChanged(const ChildChange& change)
</span><span class="cx"> {
</span><span class="cx"> HTMLElement::childrenChanged(change);
</span><del>- ScriptElement::childrenChanged();
</del><ins>+ ScriptElement::childrenChanged(change);
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> void HTMLScriptElement::parseAttribute(const QualifiedName& name, const AtomicString& value)
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCorehtmlHTMLTextFormControlElementcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/html/HTMLTextFormControlElement.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/html/HTMLTextFormControlElement.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/html/HTMLTextFormControlElement.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -40,6 +40,7 @@
</span><span class="cx"> #include "HTMLNames.h"
</span><span class="cx"> #include "HTMLParserIdioms.h"
</span><span class="cx"> #include "Logging.h"
</span><ins>+#include "NoEventDispatchAssertion.h"
</ins><span class="cx"> #include "NodeTraversal.h"
</span><span class="cx"> #include "Page.h"
</span><span class="cx"> #include "RenderTextControlSingleLine.h"
</span><span class="lines">@@ -557,11 +558,17 @@
</span><span class="cx"> cache->postNotification(this, AXObjectCache::AXValueChanged, TargetObservableParent);
</span><span class="cx"> }
</span><span class="cx"> #endif
</span><del>- innerText->setInnerText(value);
</del><span class="cx">
</span><del>- if (value.endsWith('\n') || value.endsWith('\r'))
- innerText->appendChild(HTMLBRElement::create(document()));
</del><ins>+ {
+ // Events dispatched on the inner text element cannot execute arbitrary author scripts.
+ NoEventDispatchAssertion::EventAllowedScope allowedScope(*userAgentShadowRoot());
</ins><span class="cx">
</span><ins>+ innerText->setInnerText(value);
+
+ if (value.endsWith('\n') || value.endsWith('\r'))
+ innerText->appendChild(HTMLBRElement::create(document()));
+ }
+
</ins><span class="cx"> #if HAVE(ACCESSIBILITY) && PLATFORM(COCOA)
</span><span class="cx"> if (textIsChanged && renderer()) {
</span><span class="cx"> if (AXObjectCache* cache = document().existingAXObjectCache())
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCorehtmltrackVTTCuecpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/html/track/VTTCue.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/html/track/VTTCue.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/html/track/VTTCue.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -42,6 +42,7 @@
</span><span class="cx"> #include "HTMLDivElement.h"
</span><span class="cx"> #include "HTMLSpanElement.h"
</span><span class="cx"> #include "Logging.h"
</span><ins>+#include "NoEventDispatchAssertion.h"
</ins><span class="cx"> #include "NodeTraversal.h"
</span><span class="cx"> #include "RenderVTTCue.h"
</span><span class="cx"> #include "Text.h"
</span><span class="lines">@@ -524,6 +525,10 @@
</span><span class="cx"> return nullptr;
</span><span class="cx">
</span><span class="cx"> auto clonedFragment = DocumentFragment::create(ownerDocument());
</span><ins>+
+ // The cloned fragment is never exposed to author scripts so it's safe to dispatch events here.
+ NoEventDispatchAssertion::EventAllowedScope noEventDispatchAssertionDisabledForScope(clonedFragment);
+
</ins><span class="cx"> m_webVTTNodeTree->cloneChildNodes(clonedFragment);
</span><span class="cx"> return WTFMove(clonedFragment);
</span><span class="cx"> }
</span><span class="lines">@@ -779,6 +784,9 @@
</span><span class="cx"> if (!track()->isRendered())
</span><span class="cx"> return;
</span><span class="cx">
</span><ins>+ // Mutating the VTT contents is safe because it's never exposed to author scripts.
+ NoEventDispatchAssertion::EventAllowedScope allowedScopeForCueHighlightBox(*m_cueHighlightBox);
+
</ins><span class="cx"> // Clear the contents of the set.
</span><span class="cx"> m_cueHighlightBox->removeChildren();
</span><span class="cx">
</span><span class="lines">@@ -787,6 +795,8 @@
</span><span class="cx"> if (!referenceTree)
</span><span class="cx"> return;
</span><span class="cx">
</span><ins>+ NoEventDispatchAssertion::EventAllowedScope allowedScopeForReferenceTree(*referenceTree);
+
</ins><span class="cx"> markFutureAndPastNodes(referenceTree.get(), startMediaTime(), movieTime);
</span><span class="cx"> m_cueHighlightBox->appendChild(*referenceTree);
</span><span class="cx"> }
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoreloadercacheCachedSVGFontcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/loader/cache/CachedSVGFont.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/loader/cache/CachedSVGFont.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/loader/cache/CachedSVGFont.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -69,17 +69,20 @@
</span><span class="cx"> bool CachedSVGFont::ensureCustomFontData(const AtomicString& remoteURI)
</span><span class="cx"> {
</span><span class="cx"> if (!m_externalSVGDocument && !errorOccurred() && !isLoading() && m_data) {
</span><del>- // We may get here during render tree updates when events are forbidden.
- // Frameless document can't run scripts or call back to the client so this is safe.
- auto count = NoEventDispatchAssertion::dropTemporarily();
</del><ins>+ bool sawError = false;
+ {
+ // We may get here during render tree updates when events are forbidden.
+ // Frameless document can't run scripts or call back to the client so this is safe.
+ m_externalSVGDocument = SVGDocument::create(nullptr, URL());
+ auto decoder = TextResourceDecoder::create("application/xml");
</ins><span class="cx">
</span><del>- m_externalSVGDocument = SVGDocument::create(nullptr, URL());
- RefPtr<TextResourceDecoder> decoder = TextResourceDecoder::create("application/xml");
- m_externalSVGDocument->setContent(decoder->decodeAndFlush(m_data->data(), m_data->size()));
</del><ins>+ NoEventDispatchAssertion::EventAllowedScope allowedScope(*m_externalSVGDocument);
</ins><span class="cx">
</span><del>- NoEventDispatchAssertion::restoreDropped(count);
</del><ins>+ m_externalSVGDocument->setContent(decoder->decodeAndFlush(m_data->data(), m_data->size()));
+ sawError = decoder->sawError();
+ }
</ins><span class="cx">
</span><del>- if (decoder->sawError())
</del><ins>+ if (sawError)
</ins><span class="cx"> m_externalSVGDocument = nullptr;
</span><span class="cx"> if (m_externalSVGDocument)
</span><span class="cx"> maybeInitializeExternalSVGFontElement(remoteURI);
</span></span></pre></div>
<a id="branchessafari603branchSourceWebCoresvgSVGScriptElementcpp"></a>
<div class="modfile"><h4>Modified: branches/safari-603-branch/Source/WebCore/svg/SVGScriptElement.cpp (212073 => 212074)</h4>
<pre class="diff"><span>
<span class="info">--- branches/safari-603-branch/Source/WebCore/svg/SVGScriptElement.cpp        2017-02-10 06:37:31 UTC (rev 212073)
+++ branches/safari-603-branch/Source/WebCore/svg/SVGScriptElement.cpp        2017-02-10 06:37:40 UTC (rev 212074)
</span><span class="lines">@@ -89,7 +89,7 @@
</span><span class="cx"> void SVGScriptElement::childrenChanged(const ChildChange& change)
</span><span class="cx"> {
</span><span class="cx"> SVGElement::childrenChanged(change);
</span><del>- ScriptElement::childrenChanged();
</del><ins>+ ScriptElement::childrenChanged(change);
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> bool SVGScriptElement::isURLAttribute(const Attribute& attribute) const
</span></span></pre>
</div>
</div>
</body>
</html>