зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1622028 - Log failed upgrades for HTTPS Only Mode. r=ckerschb,dragana
Differential Revision: https://phabricator.services.mozilla.com/D68026 --HG-- extra : moz-landing-system : lando
This commit is contained in:
Родитель
40755c31a8
Коммит
b9a66ff272
|
@ -147,4 +147,6 @@ XFOSameOrigin = Load denied by X-Frame-Options: “%1$S” from “%2$S”, site
|
|||
# LOCALIZATION NOTE: %1$S is the URL of the upgraded request; %2$S is the upgraded scheme.
|
||||
HTTPSOnlyUpgradeRequest = Upgrading insecure request “%1$S” to use “%2$S”.
|
||||
# LOCALIZATION NOTE: %1$S is the URL of request.
|
||||
HTTPSOnlyNoUpgrade = Request for “%1$S” was not upgraded because it had the NoUpgrade-flag.
|
||||
HTTPSOnlyNoUpgradeException = Not upgrading insecure request “%1$S” because it is exempt.
|
||||
# LOCALIZATION NOTE: %1$S is the URL of the failed request; %2$S is an error-code.
|
||||
HTTPSOnlyFailedRequest = Upgrading insecure request “%1$S” failed. (%2$S)
|
||||
|
|
|
@ -21,6 +21,7 @@ EXPORTS.mozilla.dom += [
|
|||
'nsCSPContext.h',
|
||||
'nsCSPService.h',
|
||||
'nsCSPUtils.h',
|
||||
'nsHTTPSOnlyStreamListener.h',
|
||||
'nsHTTPSOnlyUtils.h',
|
||||
'nsMixedContentBlocker.h',
|
||||
'PolicyTokenizer.h',
|
||||
|
@ -49,6 +50,7 @@ UNIFIED_SOURCES += [
|
|||
'nsCSPParser.cpp',
|
||||
'nsCSPService.cpp',
|
||||
'nsCSPUtils.cpp',
|
||||
'nsHTTPSOnlyStreamListener.cpp',
|
||||
'nsHTTPSOnlyUtils.cpp',
|
||||
'nsMixedContentBlocker.cpp',
|
||||
'PolicyTokenizer.cpp',
|
||||
|
|
|
@ -0,0 +1,66 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nsHTTPSOnlyStreamListener.h"
|
||||
#include "nsHTTPSOnlyUtils.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIChannel.h"
|
||||
#include "nsIRequest.h"
|
||||
#include "nsITransportSecurityInfo.h"
|
||||
#include "nsIURI.h"
|
||||
#include "nsPrintfCString.h"
|
||||
|
||||
NS_IMPL_ISUPPORTS(nsHTTPSOnlyStreamListener, nsIStreamListener,
|
||||
nsIRequestObserver)
|
||||
|
||||
nsHTTPSOnlyStreamListener::nsHTTPSOnlyStreamListener(
|
||||
nsIStreamListener* aListener) {
|
||||
mListener = aListener;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTTPSOnlyStreamListener::OnDataAvailable(nsIRequest* aRequest,
|
||||
nsIInputStream* aInputStream,
|
||||
uint64_t aOffset, uint32_t aCount) {
|
||||
return mListener->OnDataAvailable(aRequest, aInputStream, aOffset, aCount);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTTPSOnlyStreamListener::OnStartRequest(nsIRequest* request) {
|
||||
return mListener->OnStartRequest(request);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsHTTPSOnlyStreamListener::OnStopRequest(nsIRequest* request,
|
||||
nsresult aStatus) {
|
||||
// If the request failed we'll log it to the console with the error-code
|
||||
if (NS_FAILED(aStatus)) {
|
||||
nsresult rv;
|
||||
// Try to query for the channel-object
|
||||
nsCOMPtr<nsIChannel> channel = do_QueryInterface(request, &rv);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
nsCOMPtr<nsILoadInfo> loadInfo = channel->LoadInfo();
|
||||
uint32_t innerWindowId = loadInfo->GetInnerWindowID();
|
||||
|
||||
nsCOMPtr<nsIURI> uri;
|
||||
rv = channel->GetURI(getter_AddRefs(uri));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
// Logging URI as well as Module- and Error-Code
|
||||
AutoTArray<nsString, 2> params = {
|
||||
NS_ConvertUTF8toUTF16(uri->GetSpecOrDefault()),
|
||||
NS_ConvertUTF8toUTF16(nsPrintfCString("M%u-C%u",
|
||||
NS_ERROR_GET_MODULE(aStatus),
|
||||
NS_ERROR_GET_CODE(aStatus)))};
|
||||
nsHTTPSOnlyUtils::LogLocalizedString(
|
||||
"HTTPSOnlyFailedRequest", params, nsIScriptError::errorFlag,
|
||||
innerWindowId, !!loadInfo->GetOriginAttributes().mPrivateBrowsingId,
|
||||
uri);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return mListener->OnStopRequest(request, aStatus);
|
||||
}
|
|
@ -0,0 +1,32 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsHTTPSOnlyStreamListener_h___
|
||||
#define nsHTTPSOnlyStreamListener_h___
|
||||
|
||||
#include "nsIStreamListener.h"
|
||||
#include "nsCOMPtr.h"
|
||||
|
||||
/**
|
||||
* This event listener gets registered for requests that have been upgraded
|
||||
* using the HTTPS-only mode to log failed upgrades to the console.
|
||||
*/
|
||||
class nsHTTPSOnlyStreamListener : public nsIStreamListener {
|
||||
public:
|
||||
// nsISupports methods
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIREQUESTOBSERVER
|
||||
NS_DECL_NSISTREAMLISTENER
|
||||
|
||||
explicit nsHTTPSOnlyStreamListener(nsIStreamListener* aListener);
|
||||
|
||||
private:
|
||||
virtual ~nsHTTPSOnlyStreamListener() = default;
|
||||
|
||||
nsCOMPtr<nsIStreamListener> mListener;
|
||||
};
|
||||
|
||||
#endif /* nsHTTPSOnlyStreamListener_h___ */
|
|
@ -18,14 +18,16 @@ bool nsHTTPSOnlyUtils::ShouldUpgradeRequest(nsIURI* aURI,
|
|||
return false;
|
||||
}
|
||||
// 2. Check if NoUpgrade-flag is set in LoadInfo
|
||||
if (aLoadInfo->GetHttpsOnlyNoUpgrade()) {
|
||||
uint32_t httpsOnlyStatus = aLoadInfo->GetHttpsOnlyStatus();
|
||||
if (httpsOnlyStatus & nsILoadInfo::HTTPS_ONLY_EXEMPT) {
|
||||
// Let's log to the console, that we didn't upgrade this request
|
||||
uint32_t innerWindowId = aLoadInfo->GetInnerWindowID();
|
||||
AutoTArray<nsString, 2> params = {
|
||||
AutoTArray<nsString, 1> params = {
|
||||
NS_ConvertUTF8toUTF16(aURI->GetSpecOrDefault())};
|
||||
nsHTTPSOnlyUtils::LogLocalizedString(
|
||||
"HTTPSOnlyNoUpgrade", params, nsIScriptError::infoFlag, innerWindowId,
|
||||
!!aLoadInfo->GetOriginAttributes().mPrivateBrowsingId, aURI);
|
||||
"HTTPSOnlyNoUpgradeException", params, nsIScriptError::infoFlag,
|
||||
innerWindowId, !!aLoadInfo->GetOriginAttributes().mPrivateBrowsingId,
|
||||
aURI);
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -46,6 +48,14 @@ bool nsHTTPSOnlyUtils::ShouldUpgradeRequest(nsIURI* aURI,
|
|||
innerWindowId, !!aLoadInfo->GetOriginAttributes().mPrivateBrowsingId,
|
||||
aURI);
|
||||
|
||||
// If the status was not determined before, we now indicate that the request
|
||||
// will get upgraded, but no event-listener has been registered yet.
|
||||
if (httpsOnlyStatus & nsILoadInfo::HTTPS_ONLY_UNINITIALIZED) {
|
||||
httpsOnlyStatus ^= nsILoadInfo::HTTPS_ONLY_UNINITIALIZED;
|
||||
httpsOnlyStatus |= nsILoadInfo::HTTPS_ONLY_UPGRADED_LISTENER_NOT_REGISTERED;
|
||||
aLoadInfo->SetHttpsOnlyStatus(httpsOnlyStatus);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -79,32 +89,8 @@ void nsHTTPSOnlyUtils::LogMessage(const nsAString& aMessage, uint32_t aFlags,
|
|||
aInnerWindowID, aURI);
|
||||
} else {
|
||||
// Send to browser console
|
||||
LogSimpleConsoleError(message, category.get(), aFromPrivateWindow,
|
||||
true /* from chrome context */, aFlags);
|
||||
nsContentUtils::LogSimpleConsoleError(
|
||||
message, category.get(), aFromPrivateWindow,
|
||||
true /* from chrome context */, aFlags);
|
||||
}
|
||||
}
|
||||
|
||||
/* static */
|
||||
void nsHTTPSOnlyUtils::LogSimpleConsoleError(const nsAString& aErrorText,
|
||||
const char* aCategory,
|
||||
bool aFromPrivateWindow,
|
||||
bool aFromChromeContext,
|
||||
uint32_t aErrorFlags) {
|
||||
nsCOMPtr<nsIScriptError> scriptError =
|
||||
do_CreateInstance(NS_SCRIPTERROR_CONTRACTID);
|
||||
if (!scriptError) {
|
||||
return;
|
||||
}
|
||||
nsCOMPtr<nsIConsoleService> console =
|
||||
do_GetService(NS_CONSOLESERVICE_CONTRACTID);
|
||||
if (!console) {
|
||||
return;
|
||||
}
|
||||
nsresult rv = scriptError->Init(aErrorText, EmptyString(), EmptyString(), 0,
|
||||
0, aErrorFlags, aCategory, aFromPrivateWindow,
|
||||
aFromChromeContext);
|
||||
if (NS_FAILED(rv)) {
|
||||
return;
|
||||
}
|
||||
console->LogMessage(scriptError);
|
||||
}
|
||||
|
|
|
@ -46,19 +46,6 @@ class nsHTTPSOnlyUtils {
|
|||
static void LogMessage(const nsAString& aMessage, uint32_t aFlags,
|
||||
uint64_t aInnerWindowID, bool aFromPrivateWindow,
|
||||
nsIURI* aURI = nullptr);
|
||||
|
||||
/**
|
||||
* Report simple error message to the browser console
|
||||
* @param aErrorText the error message
|
||||
* @param aCategory Name of the module reporting error
|
||||
* @param aFromPrivateWindow Whether from private window or not
|
||||
* @param aFromChromeContext Whether from chrome context or not
|
||||
* @param [aErrorFlags] See nsIScriptError.
|
||||
*/
|
||||
static void LogSimpleConsoleError(
|
||||
const nsAString& aErrorText, const char* aCategory,
|
||||
bool aFromPrivateWindow, bool aFromChromeContext,
|
||||
uint32_t aErrorFlags = nsIScriptError::errorFlag);
|
||||
};
|
||||
|
||||
#endif /* nsHTTPSOnlyUtils_h___ */
|
||||
|
|
|
@ -580,7 +580,7 @@ nsresult LoadInfoToLoadInfoArgs(nsILoadInfo* aLoadInfo,
|
|||
aLoadInfo->GetDocumentHasLoaded(),
|
||||
aLoadInfo->GetAllowListFutureDocumentsCreatedFromThisRedirectChain(),
|
||||
cspNonce, aLoadInfo->GetSkipContentSniffing(),
|
||||
aLoadInfo->GetHttpsOnlyNoUpgrade(),
|
||||
aLoadInfo->GetHttpsOnlyStatus(),
|
||||
aLoadInfo->GetIsFromProcessingFrameAttributes(), cookieJarSettingsArgs,
|
||||
aLoadInfo->GetRequestBlockingReason(), maybeCspToInheritInfo));
|
||||
|
||||
|
@ -778,7 +778,7 @@ nsresult LoadInfoArgsToLoadInfo(
|
|||
loadInfoArgs.documentHasLoaded(),
|
||||
loadInfoArgs.allowListFutureDocumentsCreatedFromThisRedirectChain(),
|
||||
loadInfoArgs.cspNonce(), loadInfoArgs.skipContentSniffing(),
|
||||
loadInfoArgs.httpsOnlyNoUpgrade(), loadInfoArgs.requestBlockingReason(),
|
||||
loadInfoArgs.httpsOnlyStatus(), loadInfoArgs.requestBlockingReason(),
|
||||
loadingContext);
|
||||
|
||||
if (loadInfoArgs.isFromProcessingFrameAttributes()) {
|
||||
|
@ -794,8 +794,8 @@ void LoadInfoToParentLoadInfoForwarder(
|
|||
if (!aLoadInfo) {
|
||||
*aForwarderArgsOut = ParentLoadInfoForwarderArgs(
|
||||
false, false, Nothing(), nsILoadInfo::TAINTING_BASIC,
|
||||
false, // SkipContentSniffing
|
||||
false, // HttpsOnlyNoUpgrade
|
||||
false, // SkipContentSniffing
|
||||
nsILoadInfo::HTTPS_ONLY_UNINITIALIZED, // httpsOnlyStatus
|
||||
false, // serviceWorkerTaintingSynthesized
|
||||
false, // documentHasUserInteracted
|
||||
false, // documentHasLoaded
|
||||
|
@ -830,7 +830,7 @@ void LoadInfoToParentLoadInfoForwarder(
|
|||
*aForwarderArgsOut = ParentLoadInfoForwarderArgs(
|
||||
aLoadInfo->GetAllowInsecureRedirectToDataURI(),
|
||||
aLoadInfo->GetBypassCORSChecks(), ipcController, tainting,
|
||||
aLoadInfo->GetSkipContentSniffing(), aLoadInfo->GetHttpsOnlyNoUpgrade(),
|
||||
aLoadInfo->GetSkipContentSniffing(), aLoadInfo->GetHttpsOnlyStatus(),
|
||||
aLoadInfo->GetServiceWorkerTaintingSynthesized(),
|
||||
aLoadInfo->GetDocumentHasUserInteracted(),
|
||||
aLoadInfo->GetDocumentHasLoaded(),
|
||||
|
@ -869,7 +869,7 @@ nsresult MergeParentLoadInfoForwarder(
|
|||
rv = aLoadInfo->SetSkipContentSniffing(aForwarderArgs.skipContentSniffing());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
rv = aLoadInfo->SetHttpsOnlyNoUpgrade(aForwarderArgs.httpsOnlyNoUpgrade());
|
||||
rv = aLoadInfo->SetHttpsOnlyStatus(aForwarderArgs.httpsOnlyStatus());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
MOZ_ALWAYS_SUCCEEDS(aLoadInfo->SetDocumentHasUserInteracted(
|
||||
|
|
|
@ -103,7 +103,7 @@ LoadInfo::LoadInfo(
|
|||
mDocumentHasLoaded(false),
|
||||
mAllowListFutureDocumentsCreatedFromThisRedirectChain(false),
|
||||
mSkipContentSniffing(false),
|
||||
mHttpsOnlyNoUpgrade(false),
|
||||
mHttpsOnlyStatus(nsILoadInfo::HTTPS_ONLY_UNINITIALIZED),
|
||||
mIsFromProcessingFrameAttributes(false) {
|
||||
MOZ_ASSERT(mLoadingPrincipal);
|
||||
MOZ_ASSERT(mTriggeringPrincipal);
|
||||
|
@ -366,7 +366,7 @@ LoadInfo::LoadInfo(nsPIDOMWindowOuter* aOuterWindow,
|
|||
mDocumentHasLoaded(false),
|
||||
mAllowListFutureDocumentsCreatedFromThisRedirectChain(false),
|
||||
mSkipContentSniffing(false),
|
||||
mHttpsOnlyNoUpgrade(false),
|
||||
mHttpsOnlyStatus(nsILoadInfo::HTTPS_ONLY_UNINITIALIZED),
|
||||
mIsFromProcessingFrameAttributes(false) {
|
||||
// Top-level loads are never third-party
|
||||
// Grab the information we can out of the window.
|
||||
|
@ -467,7 +467,7 @@ LoadInfo::LoadInfo(dom::CanonicalBrowsingContext* aBrowsingContext,
|
|||
mDocumentHasLoaded(false),
|
||||
mAllowListFutureDocumentsCreatedFromThisRedirectChain(false),
|
||||
mSkipContentSniffing(false),
|
||||
mHttpsOnlyNoUpgrade(false),
|
||||
mHttpsOnlyStatus(nsILoadInfo::HTTPS_ONLY_UNINITIALIZED),
|
||||
mIsFromProcessingFrameAttributes(false) {
|
||||
// Top-level loads are never third-party
|
||||
// Grab the information we can out of the window.
|
||||
|
@ -568,7 +568,7 @@ LoadInfo::LoadInfo(const LoadInfo& rhs)
|
|||
rhs.mAllowListFutureDocumentsCreatedFromThisRedirectChain),
|
||||
mCspNonce(rhs.mCspNonce),
|
||||
mSkipContentSniffing(rhs.mSkipContentSniffing),
|
||||
mHttpsOnlyNoUpgrade(rhs.mHttpsOnlyNoUpgrade),
|
||||
mHttpsOnlyStatus(rhs.mHttpsOnlyStatus),
|
||||
mIsFromProcessingFrameAttributes(rhs.mIsFromProcessingFrameAttributes) {}
|
||||
|
||||
LoadInfo::LoadInfo(
|
||||
|
@ -606,7 +606,7 @@ LoadInfo::LoadInfo(
|
|||
bool aDocumentHasLoaded,
|
||||
bool aAllowListFutureDocumentsCreatedFromThisRedirectChain,
|
||||
const nsAString& aCspNonce, bool aSkipContentSniffing,
|
||||
bool aHttpsOnlyNoUpgrade, uint32_t aRequestBlockingReason,
|
||||
uint32_t aHttpsOnlyStatus, uint32_t aRequestBlockingReason,
|
||||
nsINode* aLoadingContext)
|
||||
: mLoadingPrincipal(aLoadingPrincipal),
|
||||
mTriggeringPrincipal(aTriggeringPrincipal),
|
||||
|
@ -663,7 +663,7 @@ LoadInfo::LoadInfo(
|
|||
aAllowListFutureDocumentsCreatedFromThisRedirectChain),
|
||||
mCspNonce(aCspNonce),
|
||||
mSkipContentSniffing(aSkipContentSniffing),
|
||||
mHttpsOnlyNoUpgrade(aHttpsOnlyNoUpgrade),
|
||||
mHttpsOnlyStatus(aHttpsOnlyStatus),
|
||||
mIsFromProcessingFrameAttributes(false) {
|
||||
// Only top level TYPE_DOCUMENT loads can have a null loadingPrincipal
|
||||
MOZ_ASSERT(mLoadingPrincipal ||
|
||||
|
@ -1470,14 +1470,14 @@ LoadInfo::SetSkipContentSniffing(bool aSkipContentSniffing) {
|
|||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
LoadInfo::GetHttpsOnlyNoUpgrade(bool* aHttpsOnlyNoUpgrade) {
|
||||
*aHttpsOnlyNoUpgrade = mHttpsOnlyNoUpgrade;
|
||||
LoadInfo::GetHttpsOnlyStatus(uint32_t* aHttpsOnlyStatus) {
|
||||
*aHttpsOnlyStatus = mHttpsOnlyStatus;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
LoadInfo::SetHttpsOnlyNoUpgrade(bool aHttpsOnlyNoUpgrade) {
|
||||
mHttpsOnlyNoUpgrade = aHttpsOnlyNoUpgrade;
|
||||
LoadInfo::SetHttpsOnlyStatus(uint32_t aHttpsOnlyStatus) {
|
||||
mHttpsOnlyStatus = aHttpsOnlyStatus;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
|
|
@ -163,7 +163,7 @@ class LoadInfo final : public nsILoadInfo {
|
|||
bool aDocumentHasUserInteracted, bool aDocumentHasLoaded,
|
||||
bool aAllowListFutureDocumentsCreatedFromThisRedirectChain,
|
||||
const nsAString& aCspNonce, bool aSkipContentSniffing,
|
||||
bool aHttpsOnlyNoUpgrade, uint32_t aRequestBlockingReason,
|
||||
uint32_t aHttpsOnlyStatus, uint32_t aRequestBlockingReason,
|
||||
nsINode* aLoadingContext);
|
||||
LoadInfo(const LoadInfo& rhs);
|
||||
|
||||
|
@ -259,7 +259,7 @@ class LoadInfo final : public nsILoadInfo {
|
|||
bool mAllowListFutureDocumentsCreatedFromThisRedirectChain;
|
||||
nsString mCspNonce;
|
||||
bool mSkipContentSniffing;
|
||||
bool mHttpsOnlyNoUpgrade;
|
||||
uint32_t mHttpsOnlyStatus;
|
||||
|
||||
// Is true if this load was triggered by processing the attributes of the
|
||||
// browsing context container.
|
||||
|
|
|
@ -209,7 +209,9 @@ static inline already_AddRefed<nsIChannel> SetupIPCheckChannel(bool ipv4) {
|
|||
{
|
||||
// Prevent HTTPS-Only Mode from upgrading the OCSP request.
|
||||
nsCOMPtr<nsILoadInfo> loadInfo = channel->LoadInfo();
|
||||
loadInfo->SetHttpsOnlyNoUpgrade(true);
|
||||
uint32_t httpsOnlyStatus = loadInfo->GetHttpsOnlyStatus();
|
||||
httpsOnlyStatus |= nsILoadInfo::HTTPS_ONLY_EXEMPT;
|
||||
loadInfo->SetHttpsOnlyStatus(httpsOnlyStatus);
|
||||
}
|
||||
|
||||
NS_ENSURE_SUCCESS(rv, nullptr);
|
||||
|
|
|
@ -587,12 +587,12 @@ already_AddRefed<nsIContentSecurityPolicy> TRRLoadInfo::GetCspToInherit() {
|
|||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
TRRLoadInfo::GetHttpsOnlyNoUpgrade(bool* aHttpsOnlyNoUpgrade) {
|
||||
TRRLoadInfo::GetHttpsOnlyStatus(uint32_t* aHttpsOnlyStatus) {
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
TRRLoadInfo::SetHttpsOnlyNoUpgrade(bool aHttpsOnlyNoUpgrade) {
|
||||
TRRLoadInfo::SetHttpsOnlyStatus(uint32_t aHttpsOnlyStatus) {
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
|
|
|
@ -416,10 +416,37 @@ interface nsILoadInfo : nsISupports
|
|||
[infallible] attribute boolean skipContentSniffing;
|
||||
|
||||
/**
|
||||
* If httpsOnlyNoUpgrade is true, the request won't get upgraded by the
|
||||
* HTTPS-Only Mode.
|
||||
* (default) If this flag is set, it has not yet been determined if the
|
||||
* HTTPS-Only mode will upgrade the request.
|
||||
*/
|
||||
[infallible] attribute boolean httpsOnlyNoUpgrade;
|
||||
const unsigned long HTTPS_ONLY_UNINITIALIZED = (1 << 0);
|
||||
|
||||
/**
|
||||
* Indicates that the request will get upgraded, and the HTTPS-Only
|
||||
* StreamListener got registered.
|
||||
*/
|
||||
const unsigned long HTTPS_ONLY_UPGRADED_LISTENER_NOT_REGISTERED = (1 << 1);
|
||||
|
||||
/**
|
||||
* Indicates that this is the first time the request gets upgraded, and thus
|
||||
* the HTTPS-Only StreamListener hasn't been registered yet. Even though there
|
||||
* might be multiple channels per request that have to be upgraded (e.g.,
|
||||
* because of redirects), the StreamListener only has to be attached to one
|
||||
* channel.
|
||||
*/
|
||||
const unsigned long HTTPS_ONLY_UPGRADED_LISTENER_REGISTERED = (1 << 2);
|
||||
|
||||
/**
|
||||
* This flag can be manually set if the HTTPS-Only mode should exempt the
|
||||
* request and not upgrade it. (e.g in the case of OCSP.
|
||||
*/
|
||||
const unsigned long HTTPS_ONLY_EXEMPT = (1 << 3);
|
||||
|
||||
/**
|
||||
* Upgrade state of HTTPS-Only Mode. The flag HTTPS_ONLY_EXEMPT can get
|
||||
* set on requests that should be excempt from an upgrade.
|
||||
*/
|
||||
[infallible] attribute unsigned long httpsOnlyStatus;
|
||||
|
||||
/**
|
||||
* True if this request is embedded in a context that can't be third-party
|
||||
|
|
|
@ -145,7 +145,7 @@ struct LoadInfoArgs
|
|||
bool allowListFutureDocumentsCreatedFromThisRedirectChain;
|
||||
nsString cspNonce;
|
||||
bool skipContentSniffing;
|
||||
bool httpsOnlyNoUpgrade;
|
||||
uint32_t httpsOnlyStatus;
|
||||
bool isFromProcessingFrameAttributes;
|
||||
CookieJarSettingsArgs cookieJarSettings;
|
||||
uint32_t requestBlockingReason;
|
||||
|
@ -184,9 +184,8 @@ struct ParentLoadInfoForwarderArgs
|
|||
// that flag is set to true so we skip content sniffing for that browsing
|
||||
bool skipContentSniffing;
|
||||
|
||||
// If httpsOnlyNoUpgrade is true, the request won't get upgraded by the
|
||||
// HTTPS-Only Mode.
|
||||
bool httpsOnlyNoUpgrade;
|
||||
// Upgrade state of HTTPS-Only Mode
|
||||
uint32_t httpsOnlyStatus;
|
||||
|
||||
// We must also note that the tainting value was explicitly set
|
||||
// by the service worker.
|
||||
|
|
|
@ -885,7 +885,7 @@ nsresult nsCORSListenerProxy::UpdateChannel(nsIChannel* aChannel,
|
|||
// from the netwerk, hence we shouldn't require CORS in that specific case.
|
||||
if (CheckInsecureUpgradePreventsCORS(mRequestingPrincipal, aChannel)) {
|
||||
// Check if HTTPS-Only Mode is enabled
|
||||
if (!loadInfo->GetHttpsOnlyNoUpgrade() &&
|
||||
if (!(loadInfo->GetHttpsOnlyStatus() & nsILoadInfo::HTTPS_ONLY_EXEMPT) &&
|
||||
StaticPrefs::dom_security_https_only_mode()) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
|
|
@ -118,6 +118,7 @@
|
|||
#include "nsINetworkLinkService.h"
|
||||
#include "mozilla/dom/Promise.h"
|
||||
#include "mozilla/dom/ServiceWorkerUtils.h"
|
||||
#include "mozilla/dom/nsHTTPSOnlyStreamListener.h"
|
||||
#include "mozilla/net/AsyncUrlChannelClassifier.h"
|
||||
#include "mozilla/net/CookieJarSettings.h"
|
||||
#include "mozilla/net/NeckoChannelParams.h"
|
||||
|
@ -622,6 +623,20 @@ nsresult nsHttpChannel::OnBeforeConnect() {
|
|||
mPrivateBrowsing, mAllowSTS, originAttributes,
|
||||
shouldUpgrade, std::move(resultCallback),
|
||||
willCallback);
|
||||
// If the request gets upgraded because of the HTTPS-Only mode, but no
|
||||
// event listener has been registered so far, we want to do that here.
|
||||
uint32_t httpOnlyStatus = mLoadInfo->GetHttpsOnlyStatus();
|
||||
if (httpOnlyStatus &
|
||||
nsILoadInfo::HTTPS_ONLY_UPGRADED_LISTENER_NOT_REGISTERED) {
|
||||
RefPtr<nsHTTPSOnlyStreamListener> httpsOnlyListener =
|
||||
new nsHTTPSOnlyStreamListener(mListener);
|
||||
mListener = httpsOnlyListener;
|
||||
|
||||
httpOnlyStatus ^=
|
||||
nsILoadInfo::HTTPS_ONLY_UPGRADED_LISTENER_NOT_REGISTERED;
|
||||
httpOnlyStatus |= nsILoadInfo::HTTPS_ONLY_UPGRADED_LISTENER_REGISTERED;
|
||||
mLoadInfo->SetHttpsOnlyStatus(httpOnlyStatus);
|
||||
}
|
||||
LOG(
|
||||
("nsHttpChannel::OnBeforeConnect "
|
||||
"[this=%p willCallback=%d rv=%" PRIx32 "]\n",
|
||||
|
|
|
@ -268,7 +268,9 @@ OCSPRequest::Run() {
|
|||
nsCOMPtr<nsILoadInfo> loadInfo = channel->LoadInfo();
|
||||
|
||||
// Prevent HTTPS-Only Mode from upgrading the OCSP request.
|
||||
loadInfo->SetHttpsOnlyNoUpgrade(true);
|
||||
uint32_t httpsOnlyStatus = loadInfo->GetHttpsOnlyStatus();
|
||||
httpsOnlyStatus |= nsILoadInfo::HTTPS_ONLY_EXEMPT;
|
||||
loadInfo->SetHttpsOnlyStatus(httpsOnlyStatus);
|
||||
|
||||
// For OCSP requests, only the first party domain and private browsing id
|
||||
// aspects of origin attributes are used. This means that:
|
||||
|
|
|
@ -38,7 +38,7 @@ function URLFetcher(url, timeout) {
|
|||
// We except this from being classified
|
||||
xhr.channel.loadFlags |= Ci.nsIChannel.LOAD_BYPASS_URL_CLASSIFIER;
|
||||
// Prevent HTTPS-Only Mode from upgrading the request.
|
||||
xhr.channel.loadInfo.httpsOnlyNoUpgrade = true;
|
||||
xhr.channel.loadInfo.httpsOnlyStatus |= Ci.nsILoadInfo.HTTPS_ONLY_EXEMPT;
|
||||
|
||||
// We don't want to follow _any_ redirects
|
||||
xhr.channel.QueryInterface(Ci.nsIHttpChannel).redirectionLimit = 0;
|
||||
|
|
|
@ -355,7 +355,10 @@ function downloadFile(url, options = { httpsOnlyNoUpgrade: false }) {
|
|||
xhr.responseType = "arraybuffer";
|
||||
try {
|
||||
xhr.open("GET", url);
|
||||
xhr.channel.loadInfo.httpsOnlyNoUpgrade = options.httpsOnlyNoUpgrade;
|
||||
if (options.httpsOnlyNoUpgrade) {
|
||||
xhr.channel.loadInfo.httpsOnlyStatus |=
|
||||
Ci.nsILoadInfo.HTTPS_ONLY_EXEMPT;
|
||||
}
|
||||
// Use conservative TLS settings. See bug 1325501.
|
||||
// TODO move to ServiceRequest.
|
||||
if (xhr.channel instanceof Ci.nsIHttpChannelInternal) {
|
||||
|
|
Загрузка…
Ссылка в новой задаче