diff --git a/browser/base/content/aboutNetError.js b/browser/base/content/aboutNetError.js
index cebc8d49aafb..8847c20f4120 100644
--- a/browser/base/content/aboutNetError.js
+++ b/browser/base/content/aboutNetError.js
@@ -74,6 +74,18 @@ function showPrefChangeContainer() {
addAutofocus("#prefResetButton", "beforeend");
}
+function showTls10Container() {
+ const panel = document.getElementById("enableTls10Container");
+ panel.style.display = "block";
+ document.getElementById("netErrorButtonContainer").style.display = "none";
+ const button = document.getElementById("enableTls10Button");
+ button.addEventListener("click", function enableTls10(e) {
+ RPMSetBoolPref("security.tls.version.enable-deprecated", true);
+ retryThis(button);
+ });
+ addAutofocus("#enableTls10Button", "beforeend");
+}
+
function setupAdvancedButton() {
// Get the hostname and add it to the panel
var panel = document.getElementById("badCertAdvancedPanel");
@@ -264,26 +276,36 @@ function initPage() {
if (err == "nssFailure2") {
setupErrorUI();
- RPMAddMessageListener("HasChangedCertPrefs", msg => {
- let hasChangedCertPrefs = msg.data.hasChangedCertPrefs;
+ const errorCode = document.getNetErrorInfo().errorCodeString;
+ const isTlsVersionError = (errorCode == "SSL_ERROR_UNSUPPORTED_VERSION");
+ const tls10OverrideEnabled = RPMGetBoolPref(
+ "security.tls.version.enable-deprecated"
+ );
- let errorCode = document.getNetErrorInfo().errorCodeString;
- let hasPrefStyleError = [
+ if (isTlsVersionError && !tls10OverrideEnabled) {
+ // This is probably a TLS 1.0 server; offer to re-enable.
+ showTls10Container();
+ } else {
+ const hasPrefStyleError = [
"interrupted", // This happens with subresources that are above the max tls
- "SSL_ERROR_PROTOCOL_VERSION_ALERT",
- "SSL_ERROR_UNSUPPORTED_VERSION",
- "SSL_ERROR_NO_CYPHER_OVERLAP",
"SSL_ERROR_NO_CIPHERS_SUPPORTED",
+ "SSL_ERROR_NO_CYPHER_OVERLAP",
+ "SSL_ERROR_PROTOCOL_VERSION_ALERT",
+ "SSL_ERROR_UNSUPPORTED_VERSION"
].some(substring => {
return substring == errorCode;
});
- // If it looks like an error that is user config based
- if (hasPrefStyleError && hasChangedCertPrefs) {
- showPrefChangeContainer();
+ if (hasPrefStyleError) {
+ RPMAddMessageListener("HasChangedCertPrefs", msg => {
+ if (msg.data.hasChangedCertPrefs) {
+ // Configuration overrides might have caused this; offer to reset.
+ showPrefChangeContainer();
+ }
+ });
+ RPMSendAsyncMessage("GetChangedCertPrefs");
}
- });
- RPMSendAsyncMessage("GetChangedCertPrefs");
+ }
}
if (err == "sslv3Used") {
diff --git a/browser/base/content/aboutNetError.xhtml b/browser/base/content/aboutNetError.xhtml
index 4b73f65204a6..bfb46365a8d7 100644
--- a/browser/base/content/aboutNetError.xhtml
+++ b/browser/base/content/aboutNetError.xhtml
@@ -181,6 +181,14 @@
+
+
diff --git a/browser/base/content/test/about/browser_aboutNetError.js b/browser/base/content/test/about/browser_aboutNetError.js
index d64c0c204341..387c616112d2 100644
--- a/browser/base/content/test/about/browser_aboutNetError.js
+++ b/browser/base/content/test/about/browser_aboutNetError.js
@@ -3,23 +3,25 @@
"use strict";
-const LOW_TLS_VERSION = "https://tls1.example.com/";
+const SSL3_PAGE = "https://ssl3.example.com/";
+const TLS10_PAGE = "https://tls1.example.com/";
+const TLS12_PAGE = "https://tls12.example.com/";
-add_task(async function checkReturnToPreviousPage() {
+add_task(async function resetToDefaultConfig() {
info(
- "Loading a TLS page that isn't supported, ensure we have a fix button and clicking it then loads the page"
+ "Change TLS config to cause page load to fail, check that reset button is shown and that it works"
);
// Set ourselves up for TLS error
- Services.prefs.setIntPref("security.tls.version.max", 3);
- Services.prefs.setIntPref("security.tls.version.min", 3);
+ Services.prefs.setIntPref("security.tls.version.min", 1); // TLS 1.0
+ Services.prefs.setIntPref("security.tls.version.max", 1);
let browser;
let pageLoaded;
await BrowserTestUtils.openNewForegroundTab(
gBrowser,
() => {
- gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, LOW_TLS_VERSION);
+ gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, TLS12_PAGE);
browser = gBrowser.selectedBrowser;
pageLoaded = BrowserTestUtils.waitForErrorPage(browser);
},
@@ -29,59 +31,54 @@ add_task(async function checkReturnToPreviousPage() {
info("Loading and waiting for the net error");
await pageLoaded;
- // NB: This code assumes that the error page and the test page load in the
- // same process. If this test starts to fail, it could be because they load
- // in different processes.
- await ContentTask.spawn(browser, LOW_TLS_VERSION, async function(
- LOW_TLS_VERSION_
- ) {
- ok(
- content.document.getElementById("prefResetButton").getBoundingClientRect()
- .left >= 0,
- "Should have a visible button"
- );
+ // Setup an observer for the target page.
+ const finalLoadComplete = BrowserTestUtils.browserLoaded(
+ browser,
+ false,
+ TLS12_PAGE
+ );
+ await ContentTask.spawn(browser, null, async function() {
+ const doc = content.document;
ok(
- content.document.documentURI.startsWith("about:neterror"),
+ doc.documentURI.startsWith("about:neterror"),
"Should be showing error page"
);
- let doc = content.document;
- let prefResetButton = doc.getElementById("prefResetButton");
+ const prefResetButton = doc.getElementById("prefResetButton");
+ ok(
+ ContentTaskUtils.is_visible(prefResetButton),
+ "prefResetButton should be visible"
+ );
is(
prefResetButton.getAttribute("autofocus"),
"true",
"prefResetButton has autofocus"
);
prefResetButton.click();
-
- await ContentTaskUtils.waitForEvent(this, "pageshow", true);
-
- is(
- content.document.documentURI,
- LOW_TLS_VERSION_,
- "Should not be showing page"
- );
});
+ info("Waiting for the TLS 1.2 page to load after the click");
+ await finalLoadComplete;
+
+ Services.prefs.clearUserPref("security.tls.version.min");
+ Services.prefs.clearUserPref("security.tls.version.max");
BrowserTestUtils.removeTab(gBrowser.selectedTab);
});
add_task(async function checkLearnMoreLink() {
- info(
- "Loading a TLS page that isn't supported and checking the learn more link"
- );
+ info("Load an unsupported TLS page and check for a learn more link");
// Set ourselves up for TLS error
- Services.prefs.setIntPref("security.tls.version.max", 3);
Services.prefs.setIntPref("security.tls.version.min", 3);
+ Services.prefs.setIntPref("security.tls.version.max", 4);
let browser;
let pageLoaded;
await BrowserTestUtils.openNewForegroundTab(
gBrowser,
() => {
- gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, LOW_TLS_VERSION);
+ gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, TLS10_PAGE);
browser = gBrowser.selectedBrowser;
pageLoaded = BrowserTestUtils.waitForErrorPage(browser);
},
@@ -91,16 +88,16 @@ add_task(async function checkLearnMoreLink() {
info("Loading and waiting for the net error");
await pageLoaded;
- let baseURL = Services.urlFormatter.formatURLPref("app.support.baseURL");
+ const baseURL = Services.urlFormatter.formatURLPref("app.support.baseURL");
await ContentTask.spawn(browser, baseURL, function(_baseURL) {
+ const doc = content.document;
ok(
- content.document.documentURI.startsWith("about:neterror"),
+ doc.documentURI.startsWith("about:neterror"),
"Should be showing error page"
);
- let doc = content.document;
- let learnMoreLink = doc.getElementById("learnMoreLink");
+ const learnMoreLink = doc.getElementById("learnMoreLink");
ok(
ContentTaskUtils.is_visible(learnMoreLink),
"Learn More link is visible"
@@ -108,7 +105,120 @@ add_task(async function checkLearnMoreLink() {
is(learnMoreLink.getAttribute("href"), _baseURL + "connection-not-secure");
});
- Services.prefs.clearUserPref("security.tls.version.max");
Services.prefs.clearUserPref("security.tls.version.min");
+ Services.prefs.clearUserPref("security.tls.version.max");
+ BrowserTestUtils.removeTab(gBrowser.selectedTab);
+});
+
+add_task(async function checkEnable10() {
+ info(
+ "Load a page with a deprecated TLS version, an option to enable TLS 1.0 is offered and it works"
+ );
+
+ Services.prefs.setIntPref("security.tls.version.min", 3);
+ // Disable TLS 1.3 so that we trigger a SSL_ERROR_UNSUPPORTED_VERSION.
+ // As NSS generates an alert rather than negotiating a lower version
+ // if we use the supported_versions extension from TLS 1.3.
+ Services.prefs.setIntPref("security.tls.version.max", 3);
+
+ let browser;
+ let pageLoaded;
+ await BrowserTestUtils.openNewForegroundTab(
+ gBrowser,
+ () => {
+ gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, TLS10_PAGE);
+ browser = gBrowser.selectedBrowser;
+ pageLoaded = BrowserTestUtils.waitForErrorPage(browser);
+ },
+ false
+ );
+
+ info("Loading and waiting for the net error");
+ await pageLoaded;
+
+ // Setup an observer for the target page.
+ const finalLoadComplete = BrowserTestUtils.browserLoaded(
+ browser,
+ false,
+ TLS10_PAGE
+ );
+
+ await ContentTask.spawn(browser, null, async function() {
+ const doc = content.document;
+ ok(
+ doc.documentURI.startsWith("about:neterror"),
+ "Should be showing error page"
+ );
+
+ const enableTls10Button = doc.getElementById("enableTls10Button");
+ ok(
+ ContentTaskUtils.is_visible(enableTls10Button),
+ "Option to re-enable TLS 1.0 is visible"
+ );
+ enableTls10Button.click();
+
+ // It should not also offer to reset preferences instead.
+ const prefResetButton = doc.getElementById("prefResetButton");
+ ok(
+ !ContentTaskUtils.is_visible(prefResetButton),
+ "prefResetButton should NOT be visible"
+ );
+ });
+
+ info("Waiting for the TLS 1.0 page to load after the click");
+ await finalLoadComplete;
+
+ Services.prefs.clearUserPref("security.tls.version.min");
+ Services.prefs.clearUserPref("security.tls.version.max");
+ Services.prefs.clearUserPref("security.tls.version.enable-deprecated");
+ BrowserTestUtils.removeTab(gBrowser.selectedTab);
+});
+
+add_task(async function dontOffer10WhenAlreadyEnabled() {
+ info("An option to enable TLS 1.0 is not offered if already enabled");
+
+ Services.prefs.setIntPref("security.tls.version.min", 3);
+ Services.prefs.setIntPref("security.tls.version.max", 3);
+ Services.prefs.setBoolPref("security.tls.version.enable-deprecated", true);
+
+ let browser;
+ let pageLoaded;
+ await BrowserTestUtils.openNewForegroundTab(
+ gBrowser,
+ () => {
+ gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, SSL3_PAGE);
+ browser = gBrowser.selectedBrowser;
+ pageLoaded = BrowserTestUtils.waitForErrorPage(browser);
+ },
+ false
+ );
+
+ info("Loading and waiting for the net error");
+ await pageLoaded;
+
+ await ContentTask.spawn(browser, null, async function() {
+ const doc = content.document;
+ ok(
+ doc.documentURI.startsWith("about:neterror"),
+ "Should be showing error page"
+ );
+
+ const enableTls10Button = doc.getElementById("enableTls10Button");
+ ok(
+ !ContentTaskUtils.is_visible(enableTls10Button),
+ "Option to re-enable TLS 1.0 is not visible"
+ );
+
+ // It should offer to reset preferences instead.
+ const prefResetButton = doc.getElementById("prefResetButton");
+ ok(
+ ContentTaskUtils.is_visible(prefResetButton),
+ "prefResetButton should be visible"
+ );
+ });
+
+ Services.prefs.clearUserPref("security.tls.version.min");
+ Services.prefs.clearUserPref("security.tls.version.max");
+ Services.prefs.clearUserPref("security.tls.version.enable-deprecated");
BrowserTestUtils.removeTab(gBrowser.selectedTab);
});
diff --git a/browser/locales/en-US/chrome/overrides/netError.dtd b/browser/locales/en-US/chrome/overrides/netError.dtd
index e0b0ce9b5bc4..83962a608717 100644
--- a/browser/locales/en-US/chrome/overrides/netError.dtd
+++ b/browser/locales/en-US/chrome/overrides/netError.dtd
@@ -230,5 +230,9 @@ was trying to connect. -->
+
+
+
+
The page you are trying to view cannot be shown because an error in the network protocol was detected.
- Please contact the website owners to inform them of this problem.
">
diff --git a/browser/themes/shared/aboutNetError.css b/browser/themes/shared/aboutNetError.css
index 8f176f2bd7e3..e3c0221e9bc6 100644
--- a/browser/themes/shared/aboutNetError.css
+++ b/browser/themes/shared/aboutNetError.css
@@ -47,6 +47,10 @@ button:disabled {
margin-top: 2em;
}
+#enableTls10Container {
+ display: none;
+}
+
#prefChangeContainer {
display: none;
}
diff --git a/toolkit/components/remotepagemanager/MessagePort.jsm b/toolkit/components/remotepagemanager/MessagePort.jsm
index ba04f12457d8..fc2b932a8afb 100644
--- a/toolkit/components/remotepagemanager/MessagePort.jsm
+++ b/toolkit/components/remotepagemanager/MessagePort.jsm
@@ -56,9 +56,10 @@ let RPMAccessManager = {
"about:neterror": {
getFormatURLPref: ["app.support.baseURL"],
getBoolPref: [
- "security.ssl.errorReporting.enabled",
- "security.ssl.errorReporting.automatic",
"security.certerror.hideAddException",
+ "security.ssl.errorReporting.automatic",
+ "security.ssl.errorReporting.enabled",
+ "security.tls.version.enable-deprecated",
],
},
"about:privatebrowsing": {
diff --git a/toolkit/modules/AsyncPrefs.jsm b/toolkit/modules/AsyncPrefs.jsm
index b7b0118c5631..1a756afbb3dc 100644
--- a/toolkit/modules/AsyncPrefs.jsm
+++ b/toolkit/modules/AsyncPrefs.jsm
@@ -26,6 +26,8 @@ const kAllowedPrefs = new Set([
"reader.color_scheme",
"reader.content_width",
"reader.line_height",
+
+ "security.tls.version.enable-deprecated",
]);
const kPrefTypeMap = new Map([