Firefox · DOM
CVE-2026-84137
Logic Error in DOM
Overview
Low
Severity
—
CVSS
No
Exploited ITW
Fixed
Fix Status
Changed Functions
| Function | Change | Notes |
|---|---|---|
add_taskdom/documentpip/tests/browser/browser_pip_exits_fs.js |
modified |
Files Changed
dom/documentpip/tests/browser/browser.tomldom/documentpip/tests/browser/browser_pip_exits_fs.jstoolkit/components/windowwatcher/nsWindowWatcher.cpp
Patch
diff --git a/dom/documentpip/tests/browser/browser.toml b/dom/documentpip/tests/browser/browser.toml
index 239ad3eba6a..d6bf145aa2e 100644
--- a/dom/documentpip/tests/browser/browser.toml
+++ b/dom/documentpip/tests/browser/browser.toml
@@ -14,6 +14,8 @@ skip-if = [
["browser_pip_closes_once.js"]
+["browser_pip_exits_fs.js"]
+
["browser_pip_extensions.js"]
["browser_pip_fullscreen_disallowed.js"]
diff --git a/dom/documentpip/tests/browser/browser_pip_exits_fs.js b/dom/documentpip/tests/browser/browser_pip_exits_fs.js
new file mode 100644
index 00000000000..a7dd78c181b
--- /dev/null
+++ b/dom/documentpip/tests/browser/browser_pip_exits_fs.js
@@ -0,0 +1,46 @@
+/* Any copyright is dedicated to the Public Domain.
+ http://creativecommons.org/publicdomain/zero/1.0/ */
+
+"use strict";
+
+const { DOMFullscreenTestUtils } = ChromeUtils.importESModule(
+ "resource://testing-common/DOMFullscreenTestUtils.sys.mjs"
+);
+
+DOMFullscreenTestUtils.init(this, window);
+
+add_task(async function opening_pip_exits_fullscreen() {
+ await SpecialPowers.pushPrefEnv({
+ set: [["full-screen-api.exit-on.windowOpen", true]],
+ });
+
+ const tab = await BrowserTestUtils.openNewForegroundTab({
+ gBrowser,
+ opening: "https://example.com",
+ waitForLoad: true,
+ });
+ const browser = tab.linkedBrowser;
+
+ await DOMFullscreenTestUtils.changeFullscreen(browser, true);
+ ok(document.fullscreen, "Browser should be in fullscreen");
+
+ // Opening a document PiP window should exit fullscreen.
+ let fullscreenExited = DOMFullscreenTestUtils.waitForFullScreenState(
+ browser,
+ false
+ );
+ const chromePiPPromise = BrowserTestUtils.waitForNewWindow();
+ await SpecialPowers.spawn(browser, [], async () => {
+ content.document.notifyUserGestureActivation();
+ // Must use wrappedJSObject for LegacyIsCallerChromeOrNativeCode to be false
+ await content.wrappedJSObject.documentPictureInPicture.requestWindow();
+ });
+ const chromePiP = await chromePiPPromise;
+ await fullscreenExited;
+
+ ok(!document.fullscreen, "Browser should have exited fullscreen");
+
+ // Cleanup.
+ await BrowserTestUtils.closeWindow(chromePiP);
+ BrowserTestUtils.removeTab(tab);
+});
diff --git a/toolkit/components/windowwatcher/nsWindowWatcher.cpp b/toolkit/components/windowwatcher/nsWindowWatcher.cpp
index 95df4d57026..62aad2e351c 100644
--- a/toolkit/components/windowwatcher/nsWindowWatcher.cpp
+++ b/toolkit/components/windowwatcher/nsWindowWatcher.cpp
@@ -1517,7 +1517,9 @@ nsresult nsWindowWatcher::OpenWindowInternal(
}
}
// If a website opens a popup exit DOM fullscreen
- if (StaticPrefs::full_screen_api_exit_on_windowOpen() && aCalledFromJS &&
+ if (StaticPrefs::full_screen_api_exit_on_windowOpen() &&
+ (aCalledFromJS ||
+ chromeFlags & nsIWebBrowserChrome::CHROME_DOCUMENT_PIP) &&
!hasChromeParent && !isCallerChrome && parentOuterWin) {
Document::AsyncExitFullscreen(parentOuterWin->GetDoc());
}
Loading diff…
Regression Test / PoC
shipped with the fix
diff --git a/dom/documentpip/tests/browser/browser.toml b/dom/documentpip/tests/browser/browser.toml
index 239ad3eba6a..d6bf145aa2e 100644
--- a/dom/documentpip/tests/browser/browser.toml
+++ b/dom/documentpip/tests/browser/browser.toml
@@ -14,6 +14,8 @@ skip-if = [
["browser_pip_closes_once.js"]
+["browser_pip_exits_fs.js"]
+
["browser_pip_extensions.js"]
["browser_pip_fullscreen_disallowed.js"]
diff --git a/dom/documentpip/tests/browser/browser_pip_exits_fs.js b/dom/documentpip/tests/browser/browser_pip_exits_fs.js
new file mode 100644
index 00000000000..a7dd78c181b
--- /dev/null
+++ b/dom/documentpip/tests/browser/browser_pip_exits_fs.js
@@ -0,0 +1,46 @@
+/* Any copyright is dedicated to the Public Domain.
+ http://creativecommons.org/publicdomain/zero/1.0/ */
+
+"use strict";
+
+const { DOMFullscreenTestUtils } = ChromeUtils.importESModule(
+ "resource://testing-common/DOMFullscreenTestUtils.sys.mjs"
+);
+
+DOMFullscreenTestUtils.init(this, window);
+
+add_task(async function opening_pip_exits_fullscreen() {
+ await SpecialPowers.pushPrefEnv({
+ set: [["full-screen-api.exit-on.windowOpen", true]],
+ });
+
+ const tab = await BrowserTestUtils.openNewForegroundTab({
+ gBrowser,
+ opening: "https://example.com",
+ waitForLoad: true,
+ });
+ const browser = tab.linkedBrowser;
+
+ await DOMFullscreenTestUtils.changeFullscreen(browser, true);
+ ok(document.fullscreen, "Browser should be in fullscreen");
+
+ // Opening a document PiP window should exit fullscreen.
+ let fullscreenExited = DOMFullscreenTestUtils.waitForFullScreenState(
+ browser,
+ false
+ );
+ const chromePiPPromise = BrowserTestUtils.waitForNewWindow();
+ await SpecialPowers.spawn(browser, [], async () => {
+ content.document.notifyUserGestureActivation();
+ // Must use wrappedJSObject for LegacyIsCallerChromeOrNativeCode to be false
+ await content.wrappedJSObject.documentPictureInPicture.requestWindow();
+ });
+ const chromePiP = await chromePiPPromise;
+ await fullscreenExited;
+
+ ok(!document.fullscreen, "Browser should have exited fullscreen");
+
+ // Cleanup.
+ await BrowserTestUtils.closeWindow(chromePiP);
+ BrowserTestUtils.removeTab(tab);
+});
Loading diff…
References
On This Page