Bug 1379762 part 2. Use a more reliable test to figure out when we can skip firing onload in nsDocumentViewer::LoadComplete. r=smaug

Unfortunately, GetRestoringDocument can be false by the time we reach
LoadComplete, if part of the restoration process managed to set up and then
remove onload blockers.  If that happens, we still don't want to fire a load
event for a document that has already has one fired.

Note that we could also use a boolean on the document to record whether we've
fired a load event, as long as we were careful to unset it when the readyState
transitions backwards from COMPLETE (e.g. document.open).  It's not clear which
approach is more robust.
This commit is contained in:
Boris Zbarsky 2017-07-17 23:21:41 -04:00
Родитель 24a1bc48da
Коммит 8fd50f23d4
4 изменённых файлов: 59 добавлений и 2 удалений

Просмотреть файл

@ -0,0 +1,43 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Bug 1379762</title>
</head>
<script type="text/just-data">
onunload = null; // enable bfcache
++opener.testCount;
onpageshow = function(e) {
opener.ok(!e.persisted, "Pageshow should not be coming from bfcache " + opener.testCount);
}
if (opener.testCount == 1) {
onload = function () {
setTimeout(function() {
document.write(testScript);
}, 0);
}
} else if (opener.testCount == 2) {
// Do this async, just in case.
setTimeout(function() {
history.back();
}, 0);
} else if (opener.testCount == 3) {
// Do this async, just in case.
setTimeout(function() {
history.forward();
}, 0);
} else if (opener.testCount == 4) {
onload = function() {
opener.nextTest();
window.close();
}
}
</script>
<script>
var data = document.querySelector("script[type='text/just-data']").textContent;
// Store the string that does all out work in a global variable, so we can
// get at it later.
var testScript = "<script>" + data + "</" + "script>";
document.write(testScript);
</script>
</html>

Просмотреть файл

@ -64,7 +64,7 @@ skip-if = (toolkit == 'android') || (!debug && (os == 'mac' || os == 'win')) # B
skip-if = (toolkit == 'android') || (debug && e10s) #too slow on Android 4.3 aws only; bug 1030403; bug 1263213 for debug e10s
[test_sessionhistory.html]
skip-if = toolkit == 'android' #RANDOM
support-files = file_bug1379762-1.html
support-files = file_bug1379762-1.html file_bug1379762-2.html
[test_sibling-matching-parent.html]
[test_sibling-off-domain.html]
[test_triggeringprincipal_frame_nav.html]

Просмотреть файл

@ -34,6 +34,7 @@ var testFiles =
"file_bug1300461.html",
"file_bug1326251.html",
"file_bug1379762-1.html",
"file_bug1379762-2.html",
];
var testCount = 0; // Used by the test files.

Просмотреть файл

@ -1063,7 +1063,13 @@ nsDocumentViewer::LoadComplete(nsresult aStatus)
nsIDocShell *docShell = window->GetDocShell();
NS_ENSURE_TRUE(docShell, NS_ERROR_UNEXPECTED);
docShell->GetRestoringDocument(&restoring);
// Unfortunately, docShell->GetRestoringDocument() might no longer be set
// correctly. In particular, it can be false by now if someone took it upon
// themselves to block onload from inside restoration and unblock it later.
// But we can detect the restoring case very simply: by whether our
// document's readyState is COMPLETE.
restoring = (mDocument->GetReadyStateEnum() ==
nsIDocument::READYSTATE_COMPLETE);
if (!restoring) {
NS_ASSERTION(mDocument->IsXULDocument() || // readyState for XUL is bogus
mDocument->GetReadyStateEnum() ==
@ -1074,6 +1080,13 @@ nsDocumentViewer::LoadComplete(nsresult aStatus)
nsIDocument::READYSTATE_UNINITIALIZED &&
NS_IsAboutBlank(mDocument->GetDocumentURI())),
"Bad readystate");
#ifdef DEBUG
bool docShellThinksWeAreRestoring;
docShell->GetRestoringDocument(&docShellThinksWeAreRestoring);
MOZ_ASSERT(!docShellThinksWeAreRestoring,
"How can docshell think we are restoring if we don't have a "
"READYSTATE_COMPLETE document?");
#endif // DEBUG
nsCOMPtr<nsIDocument> d = mDocument;
mDocument->SetReadyStateInternal(nsIDocument::READYSTATE_COMPLETE);