From edb0abd581ab3a36924a7ee6d05b265a547bd22f Mon Sep 17 00:00:00 2001 From: Justin Lebar Date: Thu, 4 Oct 2012 00:44:50 -0400 Subject: [PATCH] Bug 789392 - Allow mozapp frames to window.close() themselves. r=bz --- dom/base/nsGlobalWindow.cpp | 7 +- dom/browser-element/mochitest/Makefile.in | 4 ++ .../mochitest/browserElement_CloseApp.js | 71 +++++++++++++++++++ .../file_browserElement_CloseApp.html | 12 ++++ .../test_browserElement_inproc_CloseApp.html | 13 ++++ .../test_browserElement_oop_CloseApp.html | 13 ++++ testing/mochitest/android.json | 1 + 7 files changed, 118 insertions(+), 3 deletions(-) create mode 100644 dom/browser-element/mochitest/browserElement_CloseApp.js create mode 100644 dom/browser-element/mochitest/file_browserElement_CloseApp.html create mode 100644 dom/browser-element/mochitest/test_browserElement_inproc_CloseApp.html create mode 100644 dom/browser-element/mochitest/test_browserElement_oop_CloseApp.html diff --git a/dom/base/nsGlobalWindow.cpp b/dom/base/nsGlobalWindow.cpp index 13df49e27e85..c2d8d51b2cb7 100644 --- a/dom/base/nsGlobalWindow.cpp +++ b/dom/base/nsGlobalWindow.cpp @@ -6548,9 +6548,10 @@ nsGlobalWindow::Close() return NS_OK; } - // Don't allow scripts from content to close windows - // that were not opened by script - if (!mHadOriginalOpener && !nsContentUtils::IsCallerTrustedForWrite()) { + // Don't allow scripts from content to close non-app windows that were not + // opened by script. + if (!mDocShell->GetIsApp() && + !mHadOriginalOpener && !nsContentUtils::IsCallerTrustedForWrite()) { bool allowClose = Preferences::GetBool("dom.allow_scripts_to_close_windows", true); if (!allowClose) { diff --git a/dom/browser-element/mochitest/Makefile.in b/dom/browser-element/mochitest/Makefile.in index 9872ee6ee2fd..500b91aa8bfd 100644 --- a/dom/browser-element/mochitest/Makefile.in +++ b/dom/browser-element/mochitest/Makefile.in @@ -93,6 +93,9 @@ MOCHITEST_FILES = \ browserElement_CloseFromOpener.js \ test_browserElement_inproc_CloseFromOpener.html \ file_browserElement_CloseFromOpener.html \ + browserElement_CloseApp.js \ + test_browserElement_inproc_CloseApp.html \ + file_browserElement_CloseApp.html \ browserElement_OpenWindow.js \ test_browserElement_inproc_OpenWindow.html \ file_browserElement_Open1.html \ @@ -181,6 +184,7 @@ MOCHITEST_FILES += \ test_browserElement_oop_PromptConfirm.html \ test_browserElement_oop_Close.html \ test_browserElement_oop_CloseFromOpener.html \ + test_browserElement_oop_CloseApp.html \ test_browserElement_oop_OpenWindow.html \ test_browserElement_oop_OpenWindowInFrame.html \ test_browserElement_oop_OpenWindowRejected.html \ diff --git a/dom/browser-element/mochitest/browserElement_CloseApp.js b/dom/browser-element/mochitest/browserElement_CloseApp.js new file mode 100644 index 000000000000..785742022773 --- /dev/null +++ b/dom/browser-element/mochitest/browserElement_CloseApp.js @@ -0,0 +1,71 @@ +/* Any copyright is dedicated to the public domain. + http://creativecommons.org/publicdomain/zero/1.0/ */ + +// Bug 789392 - Test that apps frames can trigger mozbrowserclose by calling +// window.close(), but browser frames cannot. +"use strict"; + +SimpleTest.waitForExplicitFinish(); + +function runTest() { + browserElementTestHelpers.setEnabledPref(true); + browserElementTestHelpers.addPermission(); + SpecialPowers.addPermission("embed-apps", true, window.document); + + addEventListener('unload', function() { + SpecialPowers.removePermission("embed-apps", window.document); + }); + + // Our app frame and browser frame load the same content. That content calls + // window.close() and then alert(). We should get a mozbrowserclose event on + // the app frame before the mozbrowsershowmodalprompt, but not on the browser + // frame. + + var appFrame = document.createElement('iframe'); + appFrame.mozbrowser = true; + appFrame.setAttribute('mozapp', 'http://example.org/manifest.webapp'); + + var browserFrame = document.createElement('iframe'); + browserFrame.mozbrowser = true; + + var gotAppFrameClose = false; + appFrame.addEventListener('mozbrowserclose', function() { + ok(true, "Got close from app frame."); + gotAppFrameClose = true; + }); + + var gotAppFrameAlert = false; + appFrame.addEventListener('mozbrowsershowmodalprompt', function() { + ok(gotAppFrameClose, "Should have gotten app frame close by now."); + ok(!gotAppFrameAlert, "Just one alert from the app frame."); + gotAppFrameAlert = true; + if (gotBrowserFrameAlert && gotAppFrameAlert) { + SimpleTest.finish(); + } + }); + + browserFrame.addEventListener('mozbrowserclose', function() { + ok(false, "Got close from browser frame."); + }); + + var gotBrowserFrameAlert = false; + browserFrame.addEventListener('mozbrowsershowmodalprompt', function() { + ok(!gotBrowserFrameAlert, "Just one browser frame alert."); + gotBrowserFrameAlert = true; + if (gotBrowserFrameAlert && gotAppFrameAlert) { + SimpleTest.finish(); + } + }); + + document.body.appendChild(appFrame); + document.body.appendChild(browserFrame); + + appFrame.src = 'http://example.org/tests/dom/browser-element/mochitest/file_browserElement_CloseApp.html'; + browserFrame.src = 'http://example.org/tests/dom/browser-element/mochitest/file_browserElement_CloseApp.html'; +} + +// The test harness sets dom.allow_scripts_to_close_windows to true (as of +// writing, anyway). But that means that browser tabs can close themselves, +// which is what we want to test /can't/ happen! For the purposes of this +// test (and normal browser operation), this pref should be false. +SpecialPowers.pushPrefEnv({'set': [['dom.allow_scripts_to_close_windows', false]]}, runTest); diff --git a/dom/browser-element/mochitest/file_browserElement_CloseApp.html b/dom/browser-element/mochitest/file_browserElement_CloseApp.html new file mode 100644 index 000000000000..091183aa6fc0 --- /dev/null +++ b/dom/browser-element/mochitest/file_browserElement_CloseApp.html @@ -0,0 +1,12 @@ + + + +file_browserElement_CloseApp.html + + + + + diff --git a/dom/browser-element/mochitest/test_browserElement_inproc_CloseApp.html b/dom/browser-element/mochitest/test_browserElement_inproc_CloseApp.html new file mode 100644 index 000000000000..67acc9dbbb8f --- /dev/null +++ b/dom/browser-element/mochitest/test_browserElement_inproc_CloseApp.html @@ -0,0 +1,13 @@ + + + + Test for Bug 789392 + + + + + + + + \ No newline at end of file diff --git a/dom/browser-element/mochitest/test_browserElement_oop_CloseApp.html b/dom/browser-element/mochitest/test_browserElement_oop_CloseApp.html new file mode 100644 index 000000000000..67acc9dbbb8f --- /dev/null +++ b/dom/browser-element/mochitest/test_browserElement_oop_CloseApp.html @@ -0,0 +1,13 @@ + + + + Test for Bug 789392 + + + + + + + + \ No newline at end of file diff --git a/testing/mochitest/android.json b/testing/mochitest/android.json index 05790b01bc23..e984fc806868 100644 --- a/testing/mochitest/android.json +++ b/testing/mochitest/android.json @@ -130,6 +130,7 @@ "dom/browser-element/mochitest/test_browserElement_inproc_AppFramePermission.html": "", "dom/browser-element/mochitest/test_browserElement_inproc_AppWindowNamespace.html": "TIMED_OUT, bug 783509", "dom/browser-element/mochitest/test_browserElement_inproc_SecurityChange.html": "TIMED_OUT, bug 766586", + "dom/browser-element/mochitest/test_browserElement_inproc_CloseApp.html": "FAILS, bug 796982", "dom/devicestorage": "bug 781789 & bug 782275", "dom/imptests/editing/conformancetest/test_event.html": "", "dom/imptests/editing/conformancetest/test_runtest.html": "",