<!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>[185337] 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/185337">185337</a></dd>
<dt>Author</dt> <dd>cdumez@apple.com</dd>
<dt>Date</dt> <dd>2015-06-08 16:44:29 -0700 (Mon, 08 Jun 2015)</dd>
</dl>

<h3>Log Message</h3>
<pre>WebContent crash in WebCore::Page::sessionID() const + 0 (Page.cpp:1660)
https://bugs.webkit.org/show_bug.cgi?id=145748
&lt;rdar://problem/21226577&gt;

Reviewed by Brady Eidson.

Source/WebCore:

We would sometimes crash when pruning the PageCache because it was
possible for frames to still be loading while in the PageCache and
we would try to stop the load when the CachedFrame is destroyed. This
code path was not supposed to be exercised as we were not supposed to
have pages still loading inside the PageCache.

<a href="http://trac.webkit.org/projects/webkit/changeset/185017">r185017</a> made sure we don't insert into the PageCache pages that are
still loading. However, nothing was preventing content from starting
new loads in their 'pagehide' event handlers, *after* the decision
to put the page in the PageCache was made.

This patch prevents content from starting loads from a 'pagehide'
event handler so that we can no longer have content that is loading
inside the PageCache. 'ping' image loads still go through though as
these are specially handled and use PingLoaders.

Tests: http/tests/navigation/image-load-in-pagehide-handler.html
       http/tests/navigation/subframe-pagehide-handler-starts-load.html
       http/tests/navigation/subframe-pagehide-handler-starts-load2.html

* loader/FrameLoader.cpp:
(WebCore::FrameLoader::FrameLoader):
(WebCore::FrameLoader::stopLoading):
(WebCore::FrameLoader::loadURL):
(WebCore::FrameLoader::loadWithDocumentLoader):
(WebCore::FrameLoader::stopAllLoaders):
(WebCore::FrameLoader::handleBeforeUnloadEvent):
* loader/FrameLoader.h:
(WebCore::FrameLoader::pageDismissalEventBeingDispatched):
(WebCore::FrameLoader::PageDismissalEventType::PageDismissalEventType):
(WebCore::FrameLoader::PageDismissalEventType::operator Page::DismissalType):

Add wrapper class for m_pageDismissalEventBeingDispatched member type.
The wrapper takes care of updating the m_dismissalEventBeingDispatched
member on the Page every time the member on FrameLoader is updated. We
now cache this information on the Page so that clients can cheaply
query if a dismissal event is being dispatched in any of the Page's
frame, without having to traverse the frame tree.

* loader/ImageLoader.cpp:
(WebCore::pageIsBeingDismissed):

* loader/cache/CachedResource.cpp:
(WebCore::CachedResource::load):

Abort the load early if we are currently dispatching a 'pagehide'
event. We don't allow new loads at such point because we've already
made the decision to add the Page to the PageCache.

* loader/cache/CachedResourceLoader.cpp:
(WebCore::CachedResourceLoader::requestImage):

* page/Chrome.cpp:
(WebCore::Chrome::runModal): Deleted.
(WebCore::Chrome::setToolbarsVisible): Deleted.
(WebCore::Chrome::toolbarsVisible): Deleted.
(WebCore::Chrome::runJavaScriptConfirm): Deleted.
(WebCore::Chrome::runJavaScriptPrompt): Deleted.
(WebCore::Chrome::shouldInterruptJavaScript): Deleted.
* page/Chrome.h:
* page/ChromeClient.h:
* page/DOMWindow.cpp:
(WebCore::DOMWindow::canShowModalDialogNow):

Drop ChromeClient::shouldRunModalDialogDuringPageDismissal() and code
using it as it is unused and I did not think it was worth updating
this code.

* page/Page.h:
(WebCore::Page::dismissalEventBeingDispatched):
(WebCore::Page::setDismissalEventBeingDispatched):

Add a m_dismissalEventBeingDispatched member to the Page so that we can
easily query if a dismissal event is being dispatched in any of the
frames, without having to traverse the frame tree. I suspect more call
sites of FrameLoader::pageDismissalEventBeingDispatched() may actually
want this but I did not make such change in this patch. It is important
to check all the frames and not simply the current one because a frame's
pagehide event handler may trigger a load in another frame.

LayoutTests:

* http/tests/navigation/image-load-in-pagehide-handler-expected.txt: Added.
* http/tests/navigation/image-load-in-pagehide-handler.html: Added.
* http/tests/navigation/resources/image-load-in-pagehide-handler-2.html: Added.

Add layout test to make sure that ping loads in 'pagehide' handlers are
still going through after this change.

* http/tests/navigation/resources/frame-do-load.html: Added.
* http/tests/navigation/resources/frame-pagehide-starts-load-in-subframe.html: Added.
* http/tests/navigation/resources/frame-pagehide-starts-load.html: Added.
* http/tests/navigation/subframe-pagehide-handler-starts-load-expected.txt: Added.
* http/tests/navigation/subframe-pagehide-handler-starts-load.html: Added.
* http/tests/navigation/subframe-pagehide-handler-starts-load2-expected.txt: Added.
* http/tests/navigation/subframe-pagehide-handler-starts-load2.html: Added.

Add layout tests to make sure we don't crash if a frame starts an XHR load
from the 'pagehide' event handler. One of the tests covers the case where a
frame's pagehide handler starts a load in a subframe as this case is
requires a bit more handling.</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkLayoutTestsChangeLog">trunk/LayoutTests/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreloaderFrameLoadercpp">trunk/Source/WebCore/loader/FrameLoader.cpp</a></li>
<li><a href="#trunkSourceWebCoreloaderFrameLoaderh">trunk/Source/WebCore/loader/FrameLoader.h</a></li>
<li><a href="#trunkSourceWebCoreloaderImageLoadercpp">trunk/Source/WebCore/loader/ImageLoader.cpp</a></li>
<li><a href="#trunkSourceWebCoreloadercacheCachedResourcecpp">trunk/Source/WebCore/loader/cache/CachedResource.cpp</a></li>
<li><a href="#trunkSourceWebCoreloadercacheCachedResourceLoadercpp">trunk/Source/WebCore/loader/cache/CachedResourceLoader.cpp</a></li>
<li><a href="#trunkSourceWebCorepageChromecpp">trunk/Source/WebCore/page/Chrome.cpp</a></li>
<li><a href="#trunkSourceWebCorepageChromeh">trunk/Source/WebCore/page/Chrome.h</a></li>
<li><a href="#trunkSourceWebCorepageChromeClienth">trunk/Source/WebCore/page/ChromeClient.h</a></li>
<li><a href="#trunkSourceWebCorepageDOMWindowcpp">trunk/Source/WebCore/page/DOMWindow.cpp</a></li>
<li><a href="#trunkSourceWebCorepagePageh">trunk/Source/WebCore/page/Page.h</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkLayoutTestshttptestsnavigationimageloadinpagehidehandlerexpectedtxt">trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler-expected.txt</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationimageloadinpagehidehandlerhtml">trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler.html</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationresourcesframedoloadhtml">trunk/LayoutTests/http/tests/navigation/resources/frame-do-load.html</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationresourcesframepagehidestartsloadinsubframehtml">trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load-in-subframe.html</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationresourcesframepagehidestartsloadhtml">trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load.html</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationresourcesimageloadinpagehidehandler2html">trunk/LayoutTests/http/tests/navigation/resources/image-load-in-pagehide-handler-2.html</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsloadexpectedtxt">trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load-expected.txt</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsloadhtml">trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load.html</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsload2expectedtxt">trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2-expected.txt</a></li>
<li><a href="#trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsload2html">trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2.html</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkLayoutTestsChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/ChangeLog (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/ChangeLog        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/LayoutTests/ChangeLog        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -1,3 +1,31 @@
</span><ins>+2015-06-08  Chris Dumez  &lt;cdumez@apple.com&gt;
+
+        WebContent crash in WebCore::Page::sessionID() const + 0 (Page.cpp:1660)
+        https://bugs.webkit.org/show_bug.cgi?id=145748
+        &lt;rdar://problem/21226577&gt;
+
+        Reviewed by Brady Eidson.
+
+        * http/tests/navigation/image-load-in-pagehide-handler-expected.txt: Added.
+        * http/tests/navigation/image-load-in-pagehide-handler.html: Added.
+        * http/tests/navigation/resources/image-load-in-pagehide-handler-2.html: Added.
+
+        Add layout test to make sure that ping loads in 'pagehide' handlers are
+        still going through after this change.
+
+        * http/tests/navigation/resources/frame-do-load.html: Added.
+        * http/tests/navigation/resources/frame-pagehide-starts-load-in-subframe.html: Added.
+        * http/tests/navigation/resources/frame-pagehide-starts-load.html: Added.
+        * http/tests/navigation/subframe-pagehide-handler-starts-load-expected.txt: Added.
+        * http/tests/navigation/subframe-pagehide-handler-starts-load.html: Added.
+        * http/tests/navigation/subframe-pagehide-handler-starts-load2-expected.txt: Added.
+        * http/tests/navigation/subframe-pagehide-handler-starts-load2.html: Added.
+
+        Add layout tests to make sure we don't crash if a frame starts an XHR load
+        from the 'pagehide' event handler. One of the tests covers the case where a
+        frame's pagehide handler starts a load in a subframe as this case is
+        requires a bit more handling.
+
</ins><span class="cx"> 2015-06-08  Chris Fleizach  &lt;cfleizach@apple.com&gt;
</span><span class="cx"> 
</span><span class="cx">         AX: improve list heuristics (presentational use versus actual lists)
</span></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationimageloadinpagehidehandlerexpectedtxt"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler-expected.txt (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler-expected.txt                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler-expected.txt        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+Ping sent successfully
+HTTP_REFERER: http://127.0.0.1:8000/navigation/image-load-in-pagehide-handler.html
+REQUEST_METHOD: GET
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationimageloadinpagehidehandlerhtml"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler.html (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler.html                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/image-load-in-pagehide-handler.html        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,30 @@
</span><ins>+&lt;html&gt;&lt;head&gt;
+&lt;title&gt;Image load in pagehide handler&lt;/title&gt;
+&lt;script&gt;
+
+var testCalled = false;
+
+function test() {
+    if (!testCalled) {
+        if (window.testRunner) {
+            testRunner.dumpAsText();
+            testRunner.overridePreference(&quot;WebKitUsesPageCachePreferenceKey&quot;, 1);
+            testRunner.waitUntilDone();
+        }
+        testCalled = true;
+        return;
+    }
+    location.assign(&quot;resources/image-load-in-pagehide-handler-2.html&quot;);
+}
+
+function ping() {
+    var img = new Image(1, 1);
+    img.src = &quot;resources/save-Ping.php&quot;;
+}
+
+&lt;/script&gt;
+&lt;/head&gt;
+&lt;body onload=&quot;test();&quot; onpagehide=&quot;ping();&quot;&gt;
+&lt;img src=&quot;resources/delete-ping.php&quot; onload=&quot;test();&quot; onerror=&quot;test();&quot;&gt;&lt;/img&gt;
+&lt;p&gt;Tests that ping loads in 'pagehide' handlers go through.&lt;/p&gt;
+&lt;/body&gt;&lt;/html&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationresourcesframedoloadhtml"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/resources/frame-do-load.html (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/resources/frame-do-load.html                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/resources/frame-do-load.html        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,13 @@
</span><ins>+&lt;!DOCTYPE html&gt;
+&lt;html&gt;
+&lt;body&gt;
+&lt;script&gt;
+function doLoad()
+{
+    var xhr = new XMLHttpRequest();
+    xhr.open(&quot;GET&quot;, &quot;resources/slow-resource.pl?delay=3000&quot;, true);
+    xhr.send();
+}
+&lt;/script&gt;
+&lt;/body&gt;
+&lt;/html&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationresourcesframepagehidestartsloadinsubframehtml"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load-in-subframe.html (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load-in-subframe.html                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load-in-subframe.html        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,13 @@
</span><ins>+&lt;!DOCTYPE html&gt;
+&lt;html&gt;
+&lt;body&gt;
+&lt;iframe src=&quot;frame-do-load.html&quot; id=&quot;doLoadSubframe&quot;&gt;&lt;/iframe&gt;
+&lt;script&gt;
+window.addEventListener(&quot;pagehide&quot;, function(event) {
+    // Start load in subframe.
+    var subframe = document.getElementById(&quot;doLoadSubframe&quot;);
+    subframe.contentWindow.doLoad();
+}, false);
+&lt;/script&gt;
+&lt;/body&gt;
+&lt;/html&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationresourcesframepagehidestartsloadhtml"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load.html (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load.html                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/resources/frame-pagehide-starts-load.html        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,12 @@
</span><ins>+&lt;!DOCTYPE html&gt;
+&lt;html&gt;
+&lt;body&gt;
+&lt;script&gt;
+window.addEventListener(&quot;pagehide&quot;, function(event) {
+    var xhr = new XMLHttpRequest();
+    xhr.open(&quot;GET&quot;, &quot;resources/slow-resource.pl?delay=3000&quot;, true);
+    xhr.send();
+}, false);
+&lt;/script&gt;
+&lt;/body&gt;
+&lt;/html&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationresourcesimageloadinpagehidehandler2html"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/resources/image-load-in-pagehide-handler-2.html (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/resources/image-load-in-pagehide-handler-2.html                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/resources/image-load-in-pagehide-handler-2.html        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,3 @@
</span><ins>+&lt;script&gt;
+location.href = 'check-ping.php?test=/navigation/image-load-in-pagehide-handler.html';
+&lt;/script&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsloadexpectedtxt"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load-expected.txt (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load-expected.txt                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load-expected.txt        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,13 @@
</span><ins>+Tests that we don't crash when a load is started in a subframe on 'pagehide' handling
+
+On success, you will see a series of &quot;PASS&quot; messages, followed by &quot;TEST COMPLETE&quot;.
+
+
+pageshow - not from cache
+pagehide - entering cache
+pageshow - from cache
+PASS Page did enter and was restored from the page cache
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsloadhtml"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load.html (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load.html                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load.html        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,47 @@
</span><ins>+&lt;!DOCTYPE html&gt;
+&lt;html&gt;
+&lt;body onload=&quot;runTest()&quot;&gt;
+&lt;script src=&quot;/resources/js-test-pre.js&quot;&gt;&lt;/script&gt;
+&lt;script&gt;
+description(&quot;Tests that we don't crash when a load is started in a subframe on 'pagehide' handling&quot;);
+window.jsTestIsAsync = true;
+var totalLoaded = 0;
+
+if (window.testRunner)
+    testRunner.overridePreference(&quot;WebKitUsesPageCachePreferenceKey&quot;, 1);
+
+window.addEventListener(&quot;pageshow&quot;, function(event) {
+    debug(&quot;pageshow - &quot; + (event.persisted ? &quot;&quot; : &quot;not &quot;) + &quot;from cache&quot;);
+
+    if (event.persisted) {
+        testPassed(&quot;Page did enter and was restored from the page cache&quot;);
+        finishJSTest();
+    }
+}, false);
+
+window.addEventListener(&quot;pagehide&quot;, function(event) {
+    debug(&quot;pagehide - &quot; + (event.persisted ? &quot;&quot; : &quot;not &quot;) + &quot;entering cache&quot;);
+    if (!event.persisted) {
+        testFailed(&quot;Page did not enter the page cache.&quot;);
+        finishJSTest();
+    }
+}, false);
+
+function runTest() {
+    totalLoaded++;
+    if (totalLoaded &lt; 2)
+      return;
+
+    // This needs to happen in a setTimeout because a navigation inside the onload handler would
+    // not create a history entry.
+    setTimeout(function() {
+      // Force a back navigation back to this page.
+      window.location.href = &quot;resources/page-cache-helper.html&quot;;
+    }, 4000);
+}
+
+&lt;/script&gt;
+&lt;iframe id=&quot;testFrame&quot; src=&quot;resources/frame-pagehide-starts-load.html&quot; onload=&quot;runTest()&quot;&gt;&lt;/iframe&gt;
+&lt;script src=&quot;/resources/js-test-post.js&quot;&gt;&lt;/script&gt;
+&lt;/body&gt;
+&lt;/html&gt;
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsload2expectedtxt"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2-expected.txt (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2-expected.txt                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2-expected.txt        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,13 @@
</span><ins>+Tests that we don't crash when a load is started in a subframe on 'pagehide' handling
+
+On success, you will see a series of &quot;PASS&quot; messages, followed by &quot;TEST COMPLETE&quot;.
+
+
+pageshow - not from cache
+pagehide - entering cache
+pageshow - from cache
+PASS Page did enter and was restored from the page cache
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
</ins></span></pre></div>
<a id="trunkLayoutTestshttptestsnavigationsubframepagehidehandlerstartsload2html"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2.html (0 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2.html                                (rev 0)
+++ trunk/LayoutTests/http/tests/navigation/subframe-pagehide-handler-starts-load2.html        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -0,0 +1,47 @@
</span><ins>+&lt;!DOCTYPE html&gt;
+&lt;html&gt;
+&lt;body onload=&quot;runTest()&quot;&gt;
+&lt;script src=&quot;/resources/js-test-pre.js&quot;&gt;&lt;/script&gt;
+&lt;script&gt;
+description(&quot;Tests that we don't crash when a load is started in a subframe on 'pagehide' handling&quot;);
+window.jsTestIsAsync = true;
+var totalLoaded = 0;
+
+if (window.testRunner)
+    testRunner.overridePreference(&quot;WebKitUsesPageCachePreferenceKey&quot;, 1);
+
+window.addEventListener(&quot;pageshow&quot;, function(event) {
+    debug(&quot;pageshow - &quot; + (event.persisted ? &quot;&quot; : &quot;not &quot;) + &quot;from cache&quot;);
+
+    if (event.persisted) {
+        testPassed(&quot;Page did enter and was restored from the page cache&quot;);
+        finishJSTest();
+    }
+}, false);
+
+window.addEventListener(&quot;pagehide&quot;, function(event) {
+    debug(&quot;pagehide - &quot; + (event.persisted ? &quot;&quot; : &quot;not &quot;) + &quot;entering cache&quot;);
+    if (!event.persisted) {
+        testFailed(&quot;Page did not enter the page cache.&quot;);
+        finishJSTest();
+    }
+}, false);
+
+function runTest() {
+    totalLoaded++;
+    if (totalLoaded &lt; 2)
+      return;
+
+    // This needs to happen in a setTimeout because a navigation inside the onload handler would
+    // not create a history entry.
+    setTimeout(function() {
+      // Force a back navigation back to this page.
+      window.location.href = &quot;resources/page-cache-helper.html&quot;;
+    }, 4000);
+}
+
+&lt;/script&gt;
+&lt;iframe id=&quot;testFrame&quot; src=&quot;resources/frame-pagehide-starts-load-in-subframe.html&quot; onload=&quot;runTest()&quot;&gt;&lt;/iframe&gt;
+&lt;script src=&quot;/resources/js-test-post.js&quot;&gt;&lt;/script&gt;
+&lt;/body&gt;
+&lt;/html&gt;
</ins></span></pre></div>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/ChangeLog        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -1,3 +1,91 @@
</span><ins>+2015-06-08  Chris Dumez  &lt;cdumez@apple.com&gt;
+
+        WebContent crash in WebCore::Page::sessionID() const + 0 (Page.cpp:1660)
+        https://bugs.webkit.org/show_bug.cgi?id=145748
+        &lt;rdar://problem/21226577&gt;
+
+        Reviewed by Brady Eidson.
+
+        We would sometimes crash when pruning the PageCache because it was
+        possible for frames to still be loading while in the PageCache and
+        we would try to stop the load when the CachedFrame is destroyed. This
+        code path was not supposed to be exercised as we were not supposed to
+        have pages still loading inside the PageCache.
+
+        r185017 made sure we don't insert into the PageCache pages that are
+        still loading. However, nothing was preventing content from starting
+        new loads in their 'pagehide' event handlers, *after* the decision
+        to put the page in the PageCache was made.
+
+        This patch prevents content from starting loads from a 'pagehide'
+        event handler so that we can no longer have content that is loading
+        inside the PageCache. 'ping' image loads still go through though as
+        these are specially handled and use PingLoaders.
+
+        Tests: http/tests/navigation/image-load-in-pagehide-handler.html
+               http/tests/navigation/subframe-pagehide-handler-starts-load.html
+               http/tests/navigation/subframe-pagehide-handler-starts-load2.html
+
+        * loader/FrameLoader.cpp:
+        (WebCore::FrameLoader::FrameLoader):
+        (WebCore::FrameLoader::stopLoading):
+        (WebCore::FrameLoader::loadURL):
+        (WebCore::FrameLoader::loadWithDocumentLoader):
+        (WebCore::FrameLoader::stopAllLoaders):
+        (WebCore::FrameLoader::handleBeforeUnloadEvent):
+        * loader/FrameLoader.h:
+        (WebCore::FrameLoader::pageDismissalEventBeingDispatched):
+        (WebCore::FrameLoader::PageDismissalEventType::PageDismissalEventType):
+        (WebCore::FrameLoader::PageDismissalEventType::operator Page::DismissalType):
+
+        Add wrapper class for m_pageDismissalEventBeingDispatched member type.
+        The wrapper takes care of updating the m_dismissalEventBeingDispatched
+        member on the Page every time the member on FrameLoader is updated. We
+        now cache this information on the Page so that clients can cheaply
+        query if a dismissal event is being dispatched in any of the Page's
+        frame, without having to traverse the frame tree.
+
+        * loader/ImageLoader.cpp:
+        (WebCore::pageIsBeingDismissed):
+
+        * loader/cache/CachedResource.cpp:
+        (WebCore::CachedResource::load):
+
+        Abort the load early if we are currently dispatching a 'pagehide'
+        event. We don't allow new loads at such point because we've already
+        made the decision to add the Page to the PageCache.
+
+        * loader/cache/CachedResourceLoader.cpp:
+        (WebCore::CachedResourceLoader::requestImage):
+
+        * page/Chrome.cpp:
+        (WebCore::Chrome::runModal): Deleted.
+        (WebCore::Chrome::setToolbarsVisible): Deleted.
+        (WebCore::Chrome::toolbarsVisible): Deleted.
+        (WebCore::Chrome::runJavaScriptConfirm): Deleted.
+        (WebCore::Chrome::runJavaScriptPrompt): Deleted.
+        (WebCore::Chrome::shouldInterruptJavaScript): Deleted.
+        * page/Chrome.h:
+        * page/ChromeClient.h:
+        * page/DOMWindow.cpp:
+        (WebCore::DOMWindow::canShowModalDialogNow):
+
+        Drop ChromeClient::shouldRunModalDialogDuringPageDismissal() and code
+        using it as it is unused and I did not think it was worth updating
+        this code.
+
+        * page/Page.h:
+        (WebCore::Page::dismissalEventBeingDispatched):
+        (WebCore::Page::setDismissalEventBeingDispatched):
+
+        Add a m_dismissalEventBeingDispatched member to the Page so that we can
+        easily query if a dismissal event is being dispatched in any of the
+        frames, without having to traverse the frame tree. I suspect more call
+        sites of FrameLoader::pageDismissalEventBeingDispatched() may actually
+        want this but I did not make such change in this patch. It is important
+        to check all the frames and not simply the current one because a frame's
+        pagehide event handler may trigger a load in another frame.
+
</ins><span class="cx"> 2015-06-08  Hunseop Jeong  &lt;hs85.jeong@samsung.com&gt;
</span><span class="cx"> 
</span><span class="cx">         Replaced 0 with nullptr in WebCore/Modules.
</span></span></pre></div>
<a id="trunkSourceWebCoreloaderFrameLoadercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/loader/FrameLoader.cpp (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/loader/FrameLoader.cpp        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/loader/FrameLoader.cpp        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -84,7 +84,6 @@
</span><span class="cx"> #include &quot;MIMETypeRegistry.h&quot;
</span><span class="cx"> #include &quot;MainFrame.h&quot;
</span><span class="cx"> #include &quot;MemoryCache.h&quot;
</span><del>-#include &quot;Page.h&quot;
</del><span class="cx"> #include &quot;PageCache.h&quot;
</span><span class="cx"> #include &quot;PageThrottler.h&quot;
</span><span class="cx"> #include &quot;PageTransitionEvent.h&quot;
</span><span class="lines">@@ -226,7 +225,7 @@
</span><span class="cx">     , m_isExecutingJavaScriptFormAction(false)
</span><span class="cx">     , m_didCallImplicitClose(true)
</span><span class="cx">     , m_wasUnloadEventEmitted(false)
</span><del>-    , m_pageDismissalEventBeingDispatched(NoDismissal)
</del><ins>+    , m_pageDismissalEventBeingDispatched(frame)
</ins><span class="cx">     , m_isComplete(false)
</span><span class="cx">     , m_needsClear(false)
</span><span class="cx">     , m_checkTimer(*this, &amp;FrameLoader::checkTimerFired)
</span><span class="lines">@@ -425,9 +424,9 @@
</span><span class="cx">                 Element* currentFocusedElement = m_frame.document()-&gt;focusedElement();
</span><span class="cx">                 if (currentFocusedElement &amp;&amp; currentFocusedElement-&gt;toInputElement())
</span><span class="cx">                     currentFocusedElement-&gt;toInputElement()-&gt;endEditing();
</span><del>-                if (m_pageDismissalEventBeingDispatched == NoDismissal) {
</del><ins>+                if (m_pageDismissalEventBeingDispatched == Page::DismissalType::None) {
</ins><span class="cx">                     if (unloadEventPolicy == UnloadEventPolicyUnloadAndPageHide) {
</span><del>-                        m_pageDismissalEventBeingDispatched = PageHideDismissal;
</del><ins>+                        m_pageDismissalEventBeingDispatched = Page::DismissalType::PageHide;
</ins><span class="cx">                         m_frame.document()-&gt;domWindow()-&gt;dispatchEvent(PageTransitionEvent::create(eventNames().pagehideEvent, m_frame.document()-&gt;inPageCache()), m_frame.document());
</span><span class="cx">                     }
</span><span class="cx"> 
</span><span class="lines">@@ -440,7 +439,7 @@
</span><span class="cx">                         // while dispatching the event, so protect it to prevent writing the end
</span><span class="cx">                         // time into freed memory.
</span><span class="cx">                         RefPtr&lt;DocumentLoader&gt; documentLoader = m_provisionalDocumentLoader;
</span><del>-                        m_pageDismissalEventBeingDispatched = UnloadDismissal;
</del><ins>+                        m_pageDismissalEventBeingDispatched = Page::DismissalType::Unload;
</ins><span class="cx">                         if (documentLoader &amp;&amp; !documentLoader-&gt;timing().unloadEventStart() &amp;&amp; !documentLoader-&gt;timing().unloadEventEnd()) {
</span><span class="cx">                             DocumentLoadTiming&amp; timing = documentLoader-&gt;timing();
</span><span class="cx">                             ASSERT(timing.navigationStart());
</span><span class="lines">@@ -451,7 +450,7 @@
</span><span class="cx">                             m_frame.document()-&gt;domWindow()-&gt;dispatchEvent(unloadEvent, m_frame.document());
</span><span class="cx">                     }
</span><span class="cx">                 }
</span><del>-                m_pageDismissalEventBeingDispatched = NoDismissal;
</del><ins>+                m_pageDismissalEventBeingDispatched = Page::DismissalType::None;
</ins><span class="cx">                 if (m_frame.document())
</span><span class="cx">                     m_frame.document()-&gt;updateStyleIfNeeded();
</span><span class="cx">                 m_wasUnloadEventEmitted = true;
</span><span class="lines">@@ -1227,7 +1226,7 @@
</span><span class="cx">         return;
</span><span class="cx">     }
</span><span class="cx"> 
</span><del>-    if (m_pageDismissalEventBeingDispatched != NoDismissal)
</del><ins>+    if (m_pageDismissalEventBeingDispatched != Page::DismissalType::None)
</ins><span class="cx">         return;
</span><span class="cx"> 
</span><span class="cx">     NavigationAction action(request, newLoadType, isFormSubmission, event, frameLoadRequest.shouldOpenExternalURLsPolicy());
</span><span class="lines">@@ -1418,7 +1417,7 @@
</span><span class="cx"> 
</span><span class="cx">     ASSERT(m_frame.view());
</span><span class="cx"> 
</span><del>-    if (m_pageDismissalEventBeingDispatched != NoDismissal)
</del><ins>+    if (m_pageDismissalEventBeingDispatched != Page::DismissalType::None)
</ins><span class="cx">         return;
</span><span class="cx"> 
</span><span class="cx">     if (m_frame.document())
</span><span class="lines">@@ -1592,7 +1591,7 @@
</span><span class="cx"> void FrameLoader::stopAllLoaders(ClearProvisionalItemPolicy clearProvisionalItemPolicy)
</span><span class="cx"> {
</span><span class="cx">     ASSERT(!m_frame.document() || !m_frame.document()-&gt;inPageCache());
</span><del>-    if (m_pageDismissalEventBeingDispatched != NoDismissal)
</del><ins>+    if (m_pageDismissalEventBeingDispatched != Page::DismissalType::None)
</ins><span class="cx">         return;
</span><span class="cx"> 
</span><span class="cx">     // If this method is called from within this method, infinite recursion can occur (3442218). Avoid this.
</span><span class="lines">@@ -2848,7 +2847,7 @@
</span><span class="cx">         return true;
</span><span class="cx">     
</span><span class="cx">     RefPtr&lt;BeforeUnloadEvent&gt; beforeUnloadEvent = BeforeUnloadEvent::create();
</span><del>-    m_pageDismissalEventBeingDispatched = BeforeUnloadDismissal;
</del><ins>+    m_pageDismissalEventBeingDispatched = Page::DismissalType::BeforeUnload;
</ins><span class="cx"> 
</span><span class="cx">     // We store the frame's page in a local variable because the frame might get detached inside dispatchEvent.
</span><span class="cx">     Page* page = m_frame.page();
</span><span class="lines">@@ -2856,7 +2855,7 @@
</span><span class="cx">     domWindow-&gt;dispatchEvent(beforeUnloadEvent.get(), domWindow-&gt;document());
</span><span class="cx">     page-&gt;decrementFrameHandlingBeforeUnloadEventCount();
</span><span class="cx"> 
</span><del>-    m_pageDismissalEventBeingDispatched = NoDismissal;
</del><ins>+    m_pageDismissalEventBeingDispatched = Page::DismissalType::None;
</ins><span class="cx"> 
</span><span class="cx">     if (!beforeUnloadEvent-&gt;defaultPrevented())
</span><span class="cx">         document-&gt;defaultEventHandler(beforeUnloadEvent.get());
</span><span class="lines">@@ -3553,4 +3552,14 @@
</span><span class="cx">     return WTF::move(frame);
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+auto FrameLoader::PageDismissalEventType::operator=(Page::DismissalType dismissalType) -&gt; PageDismissalEventType&amp;
+{
+    m_dismissalEventBeingDispatched = dismissalType;
+
+    if (auto* page = m_frame.page())
+        page-&gt;setDismissalEventBeingDispatched(dismissalType);
+
+    return *this;
+}
+
</ins><span class="cx"> } // namespace WebCore
</span></span></pre></div>
<a id="trunkSourceWebCoreloaderFrameLoaderh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/loader/FrameLoader.h (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/loader/FrameLoader.h        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/loader/FrameLoader.h        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -38,6 +38,7 @@
</span><span class="cx"> #include &quot;IconURL.h&quot;
</span><span class="cx"> #include &quot;LayoutMilestones.h&quot;
</span><span class="cx"> #include &quot;MixedContentChecker.h&quot;
</span><ins>+#include &quot;Page.h&quot;
</ins><span class="cx"> #include &quot;PageThrottler.h&quot;
</span><span class="cx"> #include &quot;ResourceHandleTypes.h&quot;
</span><span class="cx"> #include &quot;ResourceLoadNotifier.h&quot;
</span><span class="lines">@@ -271,13 +272,7 @@
</span><span class="cx">     
</span><span class="cx">     void started();
</span><span class="cx"> 
</span><del>-    enum PageDismissalType {
-        NoDismissal = 0,
-        BeforeUnloadDismissal = 1,
-        PageHideDismissal = 2,
-        UnloadDismissal = 3
-    };
-    PageDismissalType pageDismissalEventBeingDispatched() const { return m_pageDismissalEventBeingDispatched; }
</del><ins>+    Page::DismissalType pageDismissalEventBeingDispatched() const { return m_pageDismissalEventBeingDispatched; }
</ins><span class="cx"> 
</span><span class="cx">     WEBCORE_EXPORT NetworkingContext* networkingContext() const;
</span><span class="cx"> 
</span><span class="lines">@@ -417,7 +412,22 @@
</span><span class="cx"> 
</span><span class="cx">     bool m_didCallImplicitClose;
</span><span class="cx">     bool m_wasUnloadEventEmitted;
</span><del>-    PageDismissalType m_pageDismissalEventBeingDispatched;
</del><ins>+
+    class PageDismissalEventType {
+    public:
+        PageDismissalEventType(Frame&amp; frame)
+            : m_frame(frame)
+        { }
+
+        PageDismissalEventType&amp; operator=(Page::DismissalType);
+        operator Page::DismissalType() const { return m_dismissalEventBeingDispatched; }
+
+    private:
+        Frame&amp; m_frame;
+        Page::DismissalType m_dismissalEventBeingDispatched { Page::DismissalType::None };
+    };
+
+    PageDismissalEventType m_pageDismissalEventBeingDispatched;
</ins><span class="cx">     bool m_isComplete;
</span><span class="cx"> 
</span><span class="cx">     RefPtr&lt;SerializedScriptValue&gt; m_pendingStateObject;
</span></span></pre></div>
<a id="trunkSourceWebCoreloaderImageLoadercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/loader/ImageLoader.cpp (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/loader/ImageLoader.cpp        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/loader/ImageLoader.cpp        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -84,7 +84,7 @@
</span><span class="cx"> static inline bool pageIsBeingDismissed(Document&amp; document)
</span><span class="cx"> {
</span><span class="cx">     Frame* frame = document.frame();
</span><del>-    return frame &amp;&amp; frame-&gt;loader().pageDismissalEventBeingDispatched() != FrameLoader::NoDismissal;
</del><ins>+    return frame &amp;&amp; frame-&gt;loader().pageDismissalEventBeingDispatched() != Page::DismissalType::None;
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> ImageLoader::ImageLoader(Element&amp; element)
</span></span></pre></div>
<a id="trunkSourceWebCoreloadercacheCachedResourcecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/loader/cache/CachedResource.cpp (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/loader/cache/CachedResource.cpp        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/loader/cache/CachedResource.cpp        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -214,6 +214,12 @@
</span><span class="cx">         return;
</span><span class="cx">     }
</span><span class="cx"> 
</span><ins>+    // Prevent 'pagehide' event handlers from starting new loads as we are in the PageCache.
+    if (cachedResourceLoader.frame()-&gt;page() &amp;&amp; cachedResourceLoader.frame()-&gt;page()-&gt;dismissalEventBeingDispatched() == Page::DismissalType::PageHide) {
+        failBeforeStarting();
+        return;
+    }
+
</ins><span class="cx">     FrameLoader&amp; frameLoader = cachedResourceLoader.frame()-&gt;loader();
</span><span class="cx">     if (options.securityCheck() == DoSecurityCheck &amp;&amp; (frameLoader.state() == FrameStateProvisional || !frameLoader.activeDocumentLoader() || frameLoader.activeDocumentLoader()-&gt;isStopping())) {
</span><span class="cx">         failBeforeStarting();
</span></span></pre></div>
<a id="trunkSourceWebCoreloadercacheCachedResourceLoadercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/loader/cache/CachedResourceLoader.cpp (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/loader/cache/CachedResourceLoader.cpp        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/loader/cache/CachedResourceLoader.cpp        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -176,7 +176,7 @@
</span><span class="cx"> CachedResourceHandle&lt;CachedImage&gt; CachedResourceLoader::requestImage(CachedResourceRequest&amp; request)
</span><span class="cx"> {
</span><span class="cx">     if (Frame* frame = this-&gt;frame()) {
</span><del>-        if (frame-&gt;loader().pageDismissalEventBeingDispatched() != FrameLoader::NoDismissal) {
</del><ins>+        if (frame-&gt;loader().pageDismissalEventBeingDispatched() != Page::DismissalType::None) {
</ins><span class="cx">             URL requestURL = request.resourceRequest().url();
</span><span class="cx">             if (requestURL.isValid() &amp;&amp; canRequest(CachedResource::ImageResource, requestURL, request.options(), request.forPreload()))
</span><span class="cx">                 PingLoader::loadImage(*frame, requestURL);
</span></span></pre></div>
<a id="trunkSourceWebCorepageChromecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/page/Chrome.cpp (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/page/Chrome.cpp        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/page/Chrome.cpp        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -213,23 +213,6 @@
</span><span class="cx">     return m_client.canRunModal();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-static bool canRunModalIfDuringPageDismissal(Page&amp; page, ChromeClient::DialogType dialog, const String&amp; message)
-{
-    for (Frame* frame = &amp;page.mainFrame(); frame; frame = frame-&gt;tree().traverseNext()) {
-        FrameLoader::PageDismissalType dismissal = frame-&gt;loader().pageDismissalEventBeingDispatched();
-        if (dismissal != FrameLoader::NoDismissal)
-            return page.chrome().client().shouldRunModalDialogDuringPageDismissal(dialog, message, dismissal);
-    }
-    return true;
-}
-
-bool Chrome::canRunModalNow() const
-{
-    // If loads are blocked, we can't run modal because the contents
-    // of the modal dialog will never show up!
-    return canRunModal() &amp;&amp; canRunModalIfDuringPageDismissal(m_page, ChromeClient::HTMLDialog, String());
-}
-
</del><span class="cx"> void Chrome::runModal() const
</span><span class="cx"> {
</span><span class="cx">     // Defer callbacks in all the other pages in this group, so we don't try to run JavaScript
</span><span class="lines">@@ -309,9 +292,6 @@
</span><span class="cx"> 
</span><span class="cx"> void Chrome::runJavaScriptAlert(Frame* frame, const String&amp; message)
</span><span class="cx"> {
</span><del>-    if (!canRunModalIfDuringPageDismissal(m_page, ChromeClient::AlertDialog, message))
-        return;
-
</del><span class="cx">     // Defer loads in case the client method runs a new event loop that would
</span><span class="cx">     // otherwise cause the load to continue while we're in the middle of executing JavaScript.
</span><span class="cx">     PageGroupLoadDeferrer deferrer(m_page, true);
</span><span class="lines">@@ -327,9 +307,6 @@
</span><span class="cx"> 
</span><span class="cx"> bool Chrome::runJavaScriptConfirm(Frame* frame, const String&amp; message)
</span><span class="cx"> {
</span><del>-    if (!canRunModalIfDuringPageDismissal(m_page, ChromeClient::ConfirmDialog, message))
-        return false;
-
</del><span class="cx">     // Defer loads in case the client method runs a new event loop that would
</span><span class="cx">     // otherwise cause the load to continue while we're in the middle of executing JavaScript.
</span><span class="cx">     PageGroupLoadDeferrer deferrer(m_page, true);
</span><span class="lines">@@ -346,9 +323,6 @@
</span><span class="cx"> 
</span><span class="cx"> bool Chrome::runJavaScriptPrompt(Frame* frame, const String&amp; prompt, const String&amp; defaultValue, String&amp; result)
</span><span class="cx"> {
</span><del>-    if (!canRunModalIfDuringPageDismissal(m_page, ChromeClient::PromptDialog, prompt))
-        return false;
-
</del><span class="cx">     // Defer loads in case the client method runs a new event loop that would
</span><span class="cx">     // otherwise cause the load to continue while we're in the middle of executing JavaScript.
</span><span class="cx">     PageGroupLoadDeferrer deferrer(m_page, true);
</span></span></pre></div>
<a id="trunkSourceWebCorepageChromeh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/page/Chrome.h (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/page/Chrome.h        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/page/Chrome.h        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -120,7 +120,6 @@
</span><span class="cx">     WEBCORE_EXPORT void show() const;
</span><span class="cx"> 
</span><span class="cx">     bool canRunModal() const;
</span><del>-    bool canRunModalNow() const;
</del><span class="cx">     void runModal() const;
</span><span class="cx"> 
</span><span class="cx">     void setToolbarsVisible(bool) const;
</span></span></pre></div>
<a id="trunkSourceWebCorepageChromeClienth"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/page/ChromeClient.h (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/page/ChromeClient.h        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/page/ChromeClient.h        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -382,14 +382,6 @@
</span><span class="cx"> 
</span><span class="cx">     virtual WTF::Optional&lt;ScrollbarOverlayStyle&gt; preferredScrollbarOverlayStyle() { return ScrollbarOverlayStyleDefault; }
</span><span class="cx"> 
</span><del>-    enum DialogType {
-        AlertDialog = 0,
-        ConfirmDialog = 1,
-        PromptDialog = 2,
-        HTMLDialog = 3
-    };
-    virtual bool shouldRunModalDialogDuringPageDismissal(const DialogType&amp;, const String&amp; dialogMessage, FrameLoader::PageDismissalType) const { UNUSED_PARAM(dialogMessage); return true; }
-
</del><span class="cx">     virtual void wheelEventHandlersChanged(bool hasHandlers) = 0;
</span><span class="cx">         
</span><span class="cx">     virtual bool isSVGImageChromeClient() const { return false; }
</span></span></pre></div>
<a id="trunkSourceWebCorepageDOMWindowcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/page/DOMWindow.cpp (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/page/DOMWindow.cpp        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/page/DOMWindow.cpp        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -387,7 +387,7 @@
</span><span class="cx">     Page* page = frame-&gt;page();
</span><span class="cx">     if (!page)
</span><span class="cx">         return false;
</span><del>-    return page-&gt;chrome().canRunModalNow();
</del><ins>+    return page-&gt;chrome().canRunModal();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DOMWindow::DOMWindow(Document* document)
</span></span></pre></div>
<a id="trunkSourceWebCorepagePageh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/page/Page.h (185336 => 185337)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/page/Page.h        2015-06-08 23:36:22 UTC (rev 185336)
+++ trunk/Source/WebCore/page/Page.h        2015-06-08 23:44:29 UTC (rev 185337)
</span><span class="lines">@@ -152,6 +152,15 @@
</span><span class="cx">     MainFrame&amp; mainFrame() { ASSERT(m_mainFrame); return *m_mainFrame; }
</span><span class="cx">     const MainFrame&amp; mainFrame() const { ASSERT(m_mainFrame); return *m_mainFrame; }
</span><span class="cx"> 
</span><ins>+    enum class DismissalType {
+        None,
+        BeforeUnload,
+        PageHide,
+        Unload
+    };
+    DismissalType dismissalEventBeingDispatched() const { return m_dismissalEventBeingDispatched; }
+    void setDismissalEventBeingDispatched(DismissalType dismissalType) { m_dismissalEventBeingDispatched = dismissalType; }
+
</ins><span class="cx">     bool openedByDOM() const;
</span><span class="cx">     void setOpenedByDOM();
</span><span class="cx"> 
</span><span class="lines">@@ -607,6 +616,7 @@
</span><span class="cx">     bool m_isClosing;
</span><span class="cx"> 
</span><span class="cx">     MediaProducer::MediaStateFlags m_mediaState { MediaProducer::IsNotPlaying };
</span><ins>+    DismissalType m_dismissalEventBeingDispatched { DismissalType::None };
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> inline PageGroup&amp; Page::group()
</span></span></pre>
</div>
</div>

</body>
</html>