diff options
author | Gregory Terzian <gterzian@users.noreply.github.com> | 2018-05-20 23:49:15 +0800 |
---|---|---|
committer | Gregory Terzian <gterzian@users.noreply.github.com> | 2018-05-22 18:11:45 +0800 |
commit | 57c0d82944969f7ee645c9208f41fb24e8561d43 (patch) | |
tree | 9f0e61c53b8ce41180add6e63c1d564b944613c6 | |
parent | a297e8f2881d0d1927160d2ebc0e4b26d71f2534 (diff) | |
download | servo-57c0d82944969f7ee645c9208f41fb24e8561d43.tar.gz servo-57c0d82944969f7ee645c9208f41fb24e8561d43.zip |
prevent overwriting of salvageable state in later prompt/unload steps
5 files changed, 101 insertions, 5 deletions
diff --git a/components/script/dom/document.rs b/components/script/dom/document.rs index 3b6b92246f1..16adcd7edbd 100644 --- a/components/script/dom/document.rs +++ b/components/script/dom/document.rs @@ -1654,7 +1654,9 @@ impl Document { ); // TODO: Step 6, decrease the event loop's termination nesting level by 1. // Step 7 - self.salvageable.set(!has_listeners); + if has_listeners { + self.salvageable.set(false); + } let mut can_unload = true; // TODO: Step 8 send a message to embedder to prompt user. // Step 9 @@ -1662,9 +1664,11 @@ impl Document { for iframe in self.iter_iframes() { // TODO: handle the case of cross origin iframes. let document = document_from_node(&*iframe); - if !document.prompt_to_unload(true) { - self.salvageable.set(document.salvageable()); - can_unload = false; + can_unload = document.prompt_to_unload(true); + if !document.salvageable() { + self.salvageable.set(false); + } + if !can_unload { break; } } @@ -1715,7 +1719,9 @@ impl Document { ); self.fired_unload.set(true); // Step 9 - self.salvageable.set(!has_listeners); + if has_listeners { + self.salvageable.set(false); + } } // TODO: Step 8, decrease the event loop's termination nesting level by 1. diff --git a/tests/wpt/metadata/MANIFEST.json b/tests/wpt/metadata/MANIFEST.json index 1e38218000f..1cfd355612e 100644 --- a/tests/wpt/metadata/MANIFEST.json +++ b/tests/wpt/metadata/MANIFEST.json @@ -277161,6 +277161,16 @@ {} ] ], + "html/browsers/browsing-the-web/unloading-documents/prompt/004-1.html": [ + [ + {} + ] + ], + "html/browsers/browsing-the-web/unloading-documents/prompt/004-2.html": [ + [ + {} + ] + ], "html/browsers/browsing-the-web/unloading-documents/prompt/manual-001.html": [ [ {} @@ -333024,6 +333034,12 @@ {} ] ], + "html/browsers/browsing-the-web/unloading-documents/prompt/004.html": [ + [ + "/html/browsers/browsing-the-web/unloading-documents/prompt/004.html", + {} + ] + ], "html/browsers/browsing-the-web/unloading-documents/unload/001.html": [ [ "/html/browsers/browsing-the-web/unloading-documents/unload/001.html", @@ -564777,6 +564793,18 @@ "c37ad1ea3a1c8e389f6066c95c7b2745648e9e7e", "testharness" ], + "html/browsers/browsing-the-web/unloading-documents/prompt/004-1.html": [ + "3530a94754361d436b6c20496bea07eb0bec4893", + "support" + ], + "html/browsers/browsing-the-web/unloading-documents/prompt/004-2.html": [ + "01dc2c7f9c673781291a5afbdb40ca0f0919e797", + "support" + ], + "html/browsers/browsing-the-web/unloading-documents/prompt/004.html": [ + "4c8485a929926005115dd0f8e2d2a2d8e1673c6f", + "testharness" + ], "html/browsers/browsing-the-web/unloading-documents/prompt/manual-001.html": [ "895580cf70904918397da755527c5dda3f227b8a", "support" diff --git a/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004-1.html b/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004-1.html new file mode 100644 index 00000000000..a3ca82f520a --- /dev/null +++ b/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004-1.html @@ -0,0 +1,28 @@ +<!doctype html> +004-1 +<script> +var handleBeforeUnload = function() { + parent.beforeunload_fired = true; + removeListener(); + setTimeout(function() { + parent.timeout_fired = true; + }, 1000); +} + +var removeListener = function() { + assert_true(window.removeEventListener('beforeunload', handleBeforeUnload, false)); +} + +window.addEventListener('beforeunload', handleBeforeUnload, false); + +onload = function() { + if (!parent.loaded) { + parent.loaded = true; + location="004-2.html?" + Math.random(); + } +} +</script> +// child frame with no onbeforeunload listener. Should leave the parent as unsalvageable. +// Adding the iframe prevents potential implementation bugs where the the recursive steps of #prompt-to-unload-a-document +// would overwrite the salvageable state of the parent. +<iframe></iframe> diff --git a/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004-2.html b/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004-2.html new file mode 100644 index 00000000000..1a605b1b3d5 --- /dev/null +++ b/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004-2.html @@ -0,0 +1,5 @@ +<!doctype html> +004-2 +<script> +onload = function() {setTimeout(parent.t.step_func(function() {parent.start_test(); history.go(-1)}), 100)} +</script> diff --git a/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004.html b/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004.html new file mode 100644 index 00000000000..7076a4dd18e --- /dev/null +++ b/tests/wpt/web-platform-tests/html/browsers/browsing-the-web/unloading-documents/prompt/004.html @@ -0,0 +1,29 @@ +<!doctype html> +<title>salvagable state of document after setting beforeunload listener</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<div id="log"></div> +<script> +var t = async_test(); + +var loaded = false; +var beforeunload_fired = false; +var timeout_fired = false; + +function start_test() { + step_timeout( + t.step_func(function() { + assert_true(beforeunload_fired); + assert_false(timeout_fired); + t.done() + }), 1000); +} + +onload = function() { + var iframe = document.getElementsByTagName("iframe")[0] + onload = null; + iframe.src="004-1.html?" + Math.random(); +}; + +</script> +<iframe></iframe> |