223 lines
6.2 KiB
JavaScript
223 lines
6.2 KiB
JavaScript
// Bug 1658264 - Https-Only: HTTPS-Only and iFrames
|
|
// https://bugzilla.mozilla.org/show_bug.cgi?id=1658264
|
|
"use strict";
|
|
|
|
// > How does this test work?
|
|
// We're sending a request to file_iframe_test.sjs with various
|
|
// browser-configurations. The sjs-file returns a website with two iFrames
|
|
// loading the same sjs-file again. One iFrame is same origin (example.com) and
|
|
// the other cross-origin (example.org) Each request gets saved in a semicolon
|
|
// seperated list of strings. The sjs-file gets initialized with the
|
|
// query-string "setup" and the result string can be polled with "results". Each
|
|
// string has this format: {top/com/org}-{queryString}-{scheme}. In the end
|
|
// we're just checking if all expected requests were recorded and had the
|
|
// correct scheme. Requests that are meant to fail should explicitly not be
|
|
// contained in the list of results.
|
|
|
|
// The test loads all tabs and evaluates when all have finished loading
|
|
// it may take quite a long time.
|
|
// This requires more twice as much as the default 45 seconds per test:
|
|
requestLongerTimeout(2);
|
|
SimpleTest.requestCompleteLog();
|
|
|
|
add_task(async function () {
|
|
await setup();
|
|
|
|
// Using this variable to parallelize and collect tests
|
|
let testSet = [];
|
|
|
|
/*
|
|
* HTTPS-Only Mode disabled
|
|
*/
|
|
await SpecialPowers.pushPrefEnv({
|
|
set: [["dom.security.https_only_mode", false]],
|
|
});
|
|
|
|
// Top-Level scheme: HTTP
|
|
// NOTE(freddyb): Test case temporarily disabled. See bug 1735565
|
|
/*testSet.push(
|
|
runTest({
|
|
queryString: "test1.1",
|
|
topLevelScheme: "http",
|
|
|
|
expectedTopLevel: "http",
|
|
expectedSameOrigin: "http",
|
|
expectedCrossOrigin: "http",
|
|
})
|
|
);*/
|
|
// Top-Level scheme: HTTPS
|
|
testSet.push(
|
|
runTest({
|
|
queryString: "test1.2",
|
|
topLevelScheme: "https",
|
|
|
|
expectedTopLevel: "https",
|
|
expectedSameOrigin: "fail",
|
|
expectedCrossOrigin: "fail",
|
|
})
|
|
);
|
|
|
|
await Promise.all(testSet);
|
|
testSet = [];
|
|
/*
|
|
* HTTPS-Only Mode enabled, no exception
|
|
*/
|
|
await SpecialPowers.pushPrefEnv({
|
|
set: [["dom.security.https_only_mode", true]],
|
|
});
|
|
|
|
// Top-Level scheme: HTTP
|
|
testSet.push(
|
|
runTest({
|
|
queryString: "test2.1",
|
|
topLevelScheme: "http",
|
|
|
|
expectedTopLevel: "https",
|
|
expectedSameOrigin: "https",
|
|
expectedCrossOrigin: "https",
|
|
})
|
|
);
|
|
// Top-Level scheme: HTTPS
|
|
testSet.push(
|
|
runTest({
|
|
queryString: "test2.2",
|
|
topLevelScheme: "https",
|
|
|
|
expectedTopLevel: "https",
|
|
expectedSameOrigin: "https",
|
|
expectedCrossOrigin: "https",
|
|
})
|
|
);
|
|
|
|
await Promise.all(testSet);
|
|
testSet = [];
|
|
|
|
/*
|
|
* HTTPS-Only enabled, with exceptions
|
|
* for http://example.org and http://example.com
|
|
*/
|
|
// Exempting example.org (cross-site) should not affect anything
|
|
await SpecialPowers.pushPermissions([
|
|
{
|
|
type: "https-only-load-insecure",
|
|
allow: true,
|
|
context: "http://example.org",
|
|
},
|
|
]);
|
|
await SpecialPowers.pushPermissions([
|
|
{
|
|
type: "https-only-load-insecure",
|
|
allow: true,
|
|
context: "http://example.com",
|
|
},
|
|
]);
|
|
|
|
// Top-Level scheme: HTTP
|
|
await runTest({
|
|
queryString: "test3.1",
|
|
topLevelScheme: "http",
|
|
|
|
expectedTopLevel: "http",
|
|
expectedSameOrigin: "http",
|
|
expectedCrossOrigin: "http",
|
|
});
|
|
|
|
await SpecialPowers.popPermissions();
|
|
await SpecialPowers.pushPermissions([
|
|
{
|
|
type: "https-only-load-insecure",
|
|
allow: true,
|
|
context: "https://example.com",
|
|
},
|
|
]);
|
|
// Top-Level scheme: HTTPS
|
|
await runTest({
|
|
queryString: "test3.2",
|
|
topLevelScheme: "https",
|
|
|
|
expectedTopLevel: "https",
|
|
expectedSameOrigin: "fail",
|
|
expectedCrossOrigin: "fail",
|
|
});
|
|
|
|
// Remove permissions again (has to be done manually for some reason?)
|
|
await SpecialPowers.popPermissions();
|
|
await SpecialPowers.popPermissions();
|
|
|
|
await evaluate();
|
|
});
|
|
|
|
const SERVER_URL = scheme =>
|
|
`${scheme}://example.com/browser/dom/security/test/https-only/file_iframe_test.sjs?`;
|
|
let shouldContain = [];
|
|
let shouldNotContain = [];
|
|
|
|
async function setup() {
|
|
info(`TEST-CASE-setup - A`);
|
|
const response = await fetch(SERVER_URL("https") + "setup");
|
|
info(`TEST-CASE-setup - B`);
|
|
const txt = await response.text();
|
|
info(`TEST-CASE-setup - C`);
|
|
if (txt != "ok") {
|
|
ok(false, "Failed to setup test server.");
|
|
finish();
|
|
}
|
|
}
|
|
|
|
async function evaluate() {
|
|
info(`TEST-CASE-evaluate - A`);
|
|
const response = await fetch(SERVER_URL("https") + "results");
|
|
info(`TEST-CASE-evaluate - B`);
|
|
const requestResults = (await response.text()).split(";");
|
|
info(`TEST-CASE-evaluate - C`);
|
|
|
|
shouldContain.map(str =>
|
|
ok(requestResults.includes(str), `Results should contain '${str}'.`)
|
|
);
|
|
shouldNotContain.map(str =>
|
|
ok(!requestResults.includes(str), `Results shouldn't contain '${str}'.`)
|
|
);
|
|
}
|
|
|
|
async function runTest(test) {
|
|
const queryString = test.queryString;
|
|
info(`TEST-CASE-${test.queryString} - runTest BEGIN`);
|
|
await BrowserTestUtils.withNewTab("about:blank", async function (browser) {
|
|
let loaded = BrowserTestUtils.browserLoaded(
|
|
browser,
|
|
false, // includeSubFrames
|
|
SERVER_URL(test.expectedTopLevel) + queryString,
|
|
false // maybeErrorPage
|
|
);
|
|
BrowserTestUtils.startLoadingURIString(
|
|
browser,
|
|
SERVER_URL(test.topLevelScheme) + queryString
|
|
);
|
|
info(`TEST-CASE-${test.queryString} - Before 'await loaded'`);
|
|
await loaded;
|
|
info(`TEST-CASE-${test.queryString} - After 'await loaded'`);
|
|
});
|
|
info(`TEST-CASE-${test.queryString} - After 'await withNewTab'`);
|
|
|
|
if (test.expectedTopLevel !== "fail") {
|
|
shouldContain.push(`top-${queryString}-${test.expectedTopLevel}`);
|
|
} else {
|
|
shouldNotContain.push(`top-${queryString}-http`);
|
|
shouldNotContain.push(`top-${queryString}-https`);
|
|
}
|
|
|
|
if (test.expectedSameOrigin !== "fail") {
|
|
shouldContain.push(`com-${queryString}-${test.expectedSameOrigin}`);
|
|
} else {
|
|
shouldNotContain.push(`com-${queryString}-http`);
|
|
shouldNotContain.push(`com-${queryString}-https`);
|
|
}
|
|
|
|
if (test.expectedCrossOrigin !== "fail") {
|
|
shouldContain.push(`org-${queryString}-${test.expectedCrossOrigin}`);
|
|
} else {
|
|
shouldNotContain.push(`org-${queryString}-http`);
|
|
shouldNotContain.push(`org-${queryString}-https`);
|
|
}
|
|
info(`TEST-CASE-${test.queryString} - runTest END`);
|
|
}
|