зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1521808 - Implement process switching based on Cross-Opener-Origin-Policy header r=nika,qdot
* New topLevel loads get the nsILoadInfo.openerPolicy of the current top level document * Parsing the Cross-Opener-Origin-Policy of a channel will update mLoadInfo.openerPolicy and this value will get propagated to the child process. * SessionStore now checks nsIHttpChannel.hasCrossOriginOpenerPolicyMismatch (preffed off) and performs a process switch if needed Differential Revision: https://phabricator.services.mozilla.com/D19000 --HG-- rename : toolkit/components/remotebrowserutils/tests/browser/browser_httpResponseProcessSelection.js => toolkit/components/remotebrowserutils/tests/browser/browser_httpCrossOriginOpenerPolicy.js extra : moz-landing-system : lando
This commit is contained in:
Родитель
1c83ed37de
Коммит
005dcbada4
|
@ -2315,7 +2315,8 @@ var SessionStoreInternal = {
|
|||
// Examine the channel response to see if we should change the process
|
||||
// performing the given load.
|
||||
onExamineResponse(aChannel) {
|
||||
if (!E10SUtils.useHttpResponseProcessSelection()) {
|
||||
if (!E10SUtils.useHttpResponseProcessSelection() &&
|
||||
!E10SUtils.useCrossOriginOpenerPolicy()) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -2364,7 +2365,9 @@ var SessionStoreInternal = {
|
|||
useRemoteTabs,
|
||||
browser.remoteType,
|
||||
currentPrincipal);
|
||||
if (browser.remoteType == remoteType) {
|
||||
if (browser.remoteType == remoteType &&
|
||||
(!E10SUtils.useCrossOriginOpenerPolicy() ||
|
||||
!aChannel.hasCrossOriginOpenerPolicyMismatch())) {
|
||||
return; // Already in compatible process.
|
||||
}
|
||||
|
||||
|
|
|
@ -9831,8 +9831,6 @@ nsresult nsDocShell::DoURILoad(nsDocShellLoadState* aLoadState,
|
|||
securityFlags |= nsILoadInfo::SEC_SANDBOXED;
|
||||
}
|
||||
|
||||
// TODO: pass openerPolicy through loadInfo?
|
||||
|
||||
RefPtr<LoadInfo> loadInfo =
|
||||
(contentPolicyType == nsIContentPolicy::TYPE_DOCUMENT)
|
||||
? new LoadInfo(loadingWindow, aLoadState->TriggeringPrincipal(),
|
||||
|
@ -9856,6 +9854,12 @@ nsresult nsDocShell::DoURILoad(nsDocShellLoadState* aLoadState,
|
|||
(contentPolicyType == nsIContentPolicy::TYPE_DOCUMENT ||
|
||||
GetIsMozBrowser());
|
||||
|
||||
if (isTopLevelDoc && GetDocument() && GetDocument()->GetChannel()) {
|
||||
nsCOMPtr<nsILoadInfo> oldLoadInfo =
|
||||
GetDocument()->GetChannel()->GetLoadInfo();
|
||||
loadInfo->SetOpenerPolicy(oldLoadInfo->GetOpenerPolicy());
|
||||
}
|
||||
|
||||
OriginAttributes attrs;
|
||||
|
||||
// Inherit origin attributes from PrincipalToInherit if inheritAttrs is
|
||||
|
|
|
@ -711,7 +711,8 @@ nsresult MergeParentLoadInfoForwarder(
|
|||
aLoadInfo->MaybeIncreaseTainting(aForwarderArgs.tainting());
|
||||
}
|
||||
|
||||
// TODO: merge openerPolicy
|
||||
MOZ_ALWAYS_SUCCEEDS(
|
||||
aLoadInfo->SetOpenerPolicy(aForwarderArgs.openerPolicy()));
|
||||
|
||||
MOZ_ALWAYS_SUCCEEDS(aLoadInfo->SetDocumentHasUserInteracted(
|
||||
aForwarderArgs.documentHasUserInteracted()));
|
||||
|
|
|
@ -7264,6 +7264,8 @@ nsHttpChannel::HasCrossOriginOpenerPolicyMismatch(bool *aMismatch) {
|
|||
nsILoadInfo::CrossOriginOpenerPolicy resultPolicy =
|
||||
GetCrossOriginOpenerPolicy(head);
|
||||
|
||||
mLoadInfo->SetOpenerPolicy(resultPolicy);
|
||||
|
||||
// We use the top window principal as the documentOrigin
|
||||
if (!mTopWindowPrincipal) {
|
||||
GetTopWindowPrincipal(getter_AddRefs(mTopWindowPrincipal));
|
||||
|
|
|
@ -4,6 +4,8 @@ support-files =
|
|||
dummy_page.html
|
||||
print_postdata.sjs
|
||||
307redirect.sjs
|
||||
coop_header.sjs
|
||||
|
||||
[browser_RemoteWebNavigation.js]
|
||||
[browser_httpResponseProcessSelection.js]
|
||||
[browser_httpCrossOriginOpenerPolicy.js]
|
||||
|
|
|
@ -0,0 +1,51 @@
|
|||
"use strict";
|
||||
|
||||
const {E10SUtils} = ChromeUtils.import("resource://gre/modules/E10SUtils.jsm");
|
||||
|
||||
const PREF_NAME = "browser.tabs.remote.useCrossOriginOpenerPolicy";
|
||||
|
||||
function httpURL(filename, host = "https://example.com") {
|
||||
let root = getRootDirectory(gTestPath)
|
||||
.replace("chrome://mochitests/content", host);
|
||||
return root + filename;
|
||||
}
|
||||
|
||||
async function test_coop(start, target, expectedProcessSwitch) {
|
||||
return BrowserTestUtils.withNewTab({
|
||||
gBrowser, url: start,
|
||||
}, async function(browser) {
|
||||
info(`Test tab ready: ${start}`);
|
||||
|
||||
let firstProcessID = await ContentTask.spawn(browser, null, () => {
|
||||
return Services.appinfo.processID;
|
||||
});
|
||||
|
||||
info(`firstProcessID: ${firstProcessID}`);
|
||||
|
||||
BrowserTestUtils.loadURI(browser, target);
|
||||
await BrowserTestUtils.browserLoaded(browser);
|
||||
|
||||
info(`Navigated to: ${target}`);
|
||||
let secondProcessID = await ContentTask.spawn(browser, null, () => {
|
||||
return Services.appinfo.processID;
|
||||
});
|
||||
|
||||
is(firstProcessID != secondProcessID, expectedProcessSwitch, `from: ${start} to ${target}`);
|
||||
});
|
||||
}
|
||||
|
||||
add_task(async function test_disabled() {
|
||||
await SpecialPowers.pushPrefEnv({set: [[PREF_NAME, false]]});
|
||||
await test_coop(httpURL("coop_header.sjs", "https://example.com"), httpURL("coop_header.sjs", "https://example.com"), false);
|
||||
await test_coop(httpURL("coop_header.sjs?same-origin", "http://example.com"), httpURL("coop_header.sjs", "http://example.com"), false);
|
||||
await test_coop(httpURL("coop_header.sjs", "http://example.com"), httpURL("coop_header.sjs?same-origin", "http://example.com"), false);
|
||||
await test_coop(httpURL("coop_header.sjs?same-origin", "http://example.com"), httpURL("coop_header.sjs?same-site", "http://example.com"), false); // assuming we don't have fission yet :)
|
||||
});
|
||||
|
||||
add_task(async function test_enabled() {
|
||||
await SpecialPowers.pushPrefEnv({set: [[PREF_NAME, true]]});
|
||||
await test_coop(httpURL("coop_header.sjs", "https://example.com"), httpURL("coop_header.sjs", "https://example.com"), false);
|
||||
await test_coop(httpURL("coop_header.sjs", "https://example.com"), httpURL("coop_header.sjs?same-origin", "https://example.org"), true);
|
||||
await test_coop(httpURL("coop_header.sjs?same-origin", "https://example.com"), httpURL("coop_header.sjs", "https://example.org"), true);
|
||||
await test_coop(httpURL("coop_header.sjs?same-origin", "https://example.com"), httpURL("coop_header.sjs?same-site", "https://example.org"), true);
|
||||
});
|
|
@ -0,0 +1,13 @@
|
|||
function handleRequest(request, response)
|
||||
{
|
||||
response.setStatusLine(request.httpVersion, 200, "OK");
|
||||
|
||||
let coop = request.queryString;
|
||||
if (coop.length > 0) {
|
||||
response.setHeader("Cross-Origin-Opener-Policy", unescape(coop), false);
|
||||
}
|
||||
|
||||
response.setHeader("Content-Type", "text/html; charset=utf-8", false);
|
||||
|
||||
response.write("<!DOCTYPE html><html><body><p>Hello world</p></body></html>");
|
||||
}
|
|
@ -17,6 +17,9 @@ XPCOMUtils.defineLazyPreferenceGetter(this, "useSeparatePrivilegedContentProcess
|
|||
"browser.tabs.remote.separatePrivilegedContentProcess", false);
|
||||
XPCOMUtils.defineLazyPreferenceGetter(this, "useHttpResponseProcessSelection",
|
||||
"browser.tabs.remote.useHTTPResponseProcessSelection", false);
|
||||
XPCOMUtils.defineLazyPreferenceGetter(this, "useCrossOriginOpenerPolicy",
|
||||
"browser.tabs.remote.useCrossOriginOpenerPolicy", false);
|
||||
|
||||
ChromeUtils.defineModuleGetter(this, "Utils",
|
||||
"resource://gre/modules/sessionstore/Utils.jsm");
|
||||
|
||||
|
@ -95,6 +98,9 @@ var E10SUtils = {
|
|||
useHttpResponseProcessSelection() {
|
||||
return useHttpResponseProcessSelection;
|
||||
},
|
||||
useCrossOriginOpenerPolicy() {
|
||||
return useCrossOriginOpenerPolicy;
|
||||
},
|
||||
|
||||
canLoadURIInRemoteType(aURL, aRemoteType = DEFAULT_REMOTE_TYPE,
|
||||
aPreferredRemoteType = undefined) {
|
||||
|
|
Загрузка…
Ссылка в новой задаче