mirror of
https://github.com/mozilla/gecko-dev.git
synced 2025-02-25 20:01:50 +00:00
Bug 1476592 - Remove the cache from nsCSPContext - part 2 - sendViolationReports parameter, r=ckerschb, r=aosmond
This commit is contained in:
parent
277949ed10
commit
44ce53c72e
@ -304,7 +304,8 @@ interface nsIContentSecurityPolicy : nsISerializable
|
||||
in nsIURI aRequestOrigin,
|
||||
in nsISupports aContext,
|
||||
in ACString aMimeTypeGuess,
|
||||
in nsIURI aOriginalURIIfRedirect);
|
||||
in nsIURI aOriginalURIIfRedirect,
|
||||
in bool aSendViolationReports);
|
||||
|
||||
%{ C++
|
||||
// nsIObserver topic to fire when the policy encounters a violation.
|
||||
|
@ -123,6 +123,7 @@ nsCSPContext::ShouldLoad(nsContentPolicyType aContentType,
|
||||
nsISupports* aRequestContext,
|
||||
const nsACString& aMimeTypeGuess,
|
||||
nsIURI* aOriginalURIIfRedirect,
|
||||
bool aSendViolationReports,
|
||||
int16_t* outDecision)
|
||||
{
|
||||
if (CSPCONTEXTLOGENABLED()) {
|
||||
@ -182,7 +183,7 @@ nsCSPContext::ShouldLoad(nsContentPolicyType aContentType,
|
||||
nonce,
|
||||
isPreload,
|
||||
false, // allow fallback to default-src
|
||||
true, // send violation reports
|
||||
aSendViolationReports,
|
||||
true, // send blocked URI in violation reports
|
||||
parserCreated);
|
||||
|
||||
|
@ -188,6 +188,7 @@ CSPService::ShouldLoad(nsIURI *aContentLocation,
|
||||
requestContext,
|
||||
aMimeTypeGuess,
|
||||
nullptr, // no redirect, aOriginal URL is null.
|
||||
aLoadInfo->GetSendCSPViolationEvents(),
|
||||
aDecision);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
@ -212,6 +213,7 @@ CSPService::ShouldLoad(nsIURI *aContentLocation,
|
||||
requestContext,
|
||||
aMimeTypeGuess,
|
||||
nullptr, // no redirect, aOriginal URL is null.
|
||||
aLoadInfo->GetSendCSPViolationEvents(),
|
||||
aDecision);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
}
|
||||
@ -324,6 +326,7 @@ CSPService::AsyncOnChannelRedirect(nsIChannel *oldChannel,
|
||||
requestContext, // nsISupports
|
||||
EmptyCString(), // ACString - MIME guess
|
||||
originalUri, // Original nsIURI
|
||||
true, // aSendViolationReports
|
||||
&aDecision);
|
||||
|
||||
// if the preload policy already denied the load, then there
|
||||
@ -348,6 +351,7 @@ CSPService::AsyncOnChannelRedirect(nsIChannel *oldChannel,
|
||||
requestContext, // nsISupports
|
||||
EmptyCString(), // ACString - MIME guess
|
||||
originalUri, // Original nsIURI
|
||||
true, // aSendViolationReports
|
||||
&aDecision);
|
||||
}
|
||||
|
||||
|
@ -152,7 +152,7 @@ function run_test() {
|
||||
// shouldLoad creates and sends out the report here.
|
||||
csp.shouldLoad(Ci.nsIContentPolicy.TYPE_SCRIPT,
|
||||
NetUtil.newURI("http://blocked.test/foo.js"),
|
||||
null, null, null, null);
|
||||
null, null, null, null, true);
|
||||
});
|
||||
|
||||
// test that inline script violations cause a report in report-only policy
|
||||
@ -202,7 +202,7 @@ function run_test() {
|
||||
// shouldLoad creates and sends out the report here.
|
||||
csp.shouldLoad(Ci.nsIContentPolicy.TYPE_IMAGE,
|
||||
NetUtil.newURI("data:image/png;base64," + base64data),
|
||||
null, null, null, null);
|
||||
null, null, null, null, true);
|
||||
});
|
||||
|
||||
// test that only the uri's scheme is reported for globally unique identifiers
|
||||
@ -211,7 +211,7 @@ function run_test() {
|
||||
// shouldLoad creates and sends out the report here.
|
||||
csp.shouldLoad(Ci.nsIContentPolicy.TYPE_SUBDOCUMENT,
|
||||
NetUtil.newURI("intent://mymaps.com/maps?um=1&ie=UTF-8&fb=1&sll"),
|
||||
null, null, null, null);
|
||||
null, null, null, null, true);
|
||||
});
|
||||
|
||||
// test fragment removal
|
||||
@ -222,7 +222,7 @@ function run_test() {
|
||||
// shouldLoad creates and sends out the report here.
|
||||
csp.shouldLoad(Ci.nsIContentPolicy.TYPE_SCRIPT,
|
||||
NetUtil.newURI(selfSpec + "#bar"),
|
||||
null, null, null, null);
|
||||
null, null, null, null, true);
|
||||
});
|
||||
|
||||
// test scheme of ftp:
|
||||
@ -231,6 +231,6 @@ function run_test() {
|
||||
// shouldLoad creates and sends out the report here.
|
||||
csp.shouldLoad(Ci.nsIContentPolicy.TYPE_SCRIPT,
|
||||
NetUtil.newURI("ftp://blocked.test/profile.png"),
|
||||
null, null, null, null);
|
||||
null, null, null, null, true);
|
||||
});
|
||||
}
|
||||
|
@ -616,7 +616,8 @@ static bool
|
||||
ShouldLoadCachedImage(imgRequest* aImgRequest,
|
||||
nsISupports* aLoadingContext,
|
||||
nsIPrincipal* aTriggeringPrincipal,
|
||||
nsContentPolicyType aPolicyType)
|
||||
nsContentPolicyType aPolicyType,
|
||||
bool aSendCSPViolationReports)
|
||||
{
|
||||
/* Call content policies on cached images - Bug 1082837
|
||||
* Cached images are keyed off of the first uri in a redirect chain.
|
||||
@ -650,6 +651,8 @@ ShouldLoadCachedImage(imgRequest* aImgRequest,
|
||||
nsILoadInfo::SEC_ONLY_FOR_EXPLICIT_CONTENTSEC_CHECK,
|
||||
aPolicyType);
|
||||
|
||||
secCheckLoadInfo->SetSendCSPViolationEvents(aSendCSPViolationReports);
|
||||
|
||||
int16_t decision = nsIContentPolicy::REJECT_REQUEST;
|
||||
rv = NS_CheckContentLoadPolicy(contentLocation,
|
||||
secCheckLoadInfo,
|
||||
@ -746,7 +749,8 @@ ValidateSecurityInfo(imgRequest* request, bool forcePrincipalCheck,
|
||||
}
|
||||
|
||||
// Content Policy Check on Cached Images
|
||||
return ShouldLoadCachedImage(request, aCX, triggeringPrincipal, aPolicyType);
|
||||
return ShouldLoadCachedImage(request, aCX, triggeringPrincipal, aPolicyType,
|
||||
/* aSendCSPViolationReports */ false);
|
||||
}
|
||||
|
||||
static nsresult
|
||||
@ -1797,7 +1801,8 @@ imgLoader::ValidateRequestWithNewChannel(imgRequest* request,
|
||||
nsContentPolicyType aLoadPolicyType,
|
||||
imgRequestProxy** aProxyRequest,
|
||||
nsIPrincipal* aTriggeringPrincipal,
|
||||
int32_t aCORSMode)
|
||||
int32_t aCORSMode,
|
||||
bool* aNewChannelCreated)
|
||||
{
|
||||
// now we need to insert a new channel request object inbetween the real
|
||||
// request and the proxy that basically delays loading the image until it
|
||||
@ -1853,6 +1858,10 @@ imgLoader::ValidateRequestWithNewChannel(imgRequest* request,
|
||||
return false;
|
||||
}
|
||||
|
||||
if (aNewChannelCreated) {
|
||||
*aNewChannelCreated = true;
|
||||
}
|
||||
|
||||
RefPtr<imgRequestProxy> req;
|
||||
rv = CreateNewProxyForRequest(request, aLoadGroup, aLoadingDocument,
|
||||
aObserver, aLoadFlags, getter_AddRefs(req));
|
||||
@ -1917,6 +1926,7 @@ imgLoader::ValidateEntry(imgCacheEntry* aEntry,
|
||||
nsLoadFlags aLoadFlags,
|
||||
nsContentPolicyType aLoadPolicyType,
|
||||
bool aCanMakeNewChannel,
|
||||
bool* aNewChannelCreated,
|
||||
imgRequestProxy** aProxyRequest,
|
||||
nsIPrincipal* aTriggeringPrincipal,
|
||||
int32_t aCORSMode)
|
||||
@ -2036,7 +2046,7 @@ imgLoader::ValidateEntry(imgCacheEntry* aEntry,
|
||||
aCX, aLoadingDocument,
|
||||
aLoadFlags, aLoadPolicyType,
|
||||
aProxyRequest, aTriggeringPrincipal,
|
||||
aCORSMode);
|
||||
aCORSMode, aNewChannelCreated);
|
||||
}
|
||||
|
||||
return !validateRequest;
|
||||
@ -2341,10 +2351,12 @@ imgLoader::LoadImage(nsIURI* aURI,
|
||||
imgCacheTable& cache = GetCache(key);
|
||||
|
||||
if (cache.Get(key, getter_AddRefs(entry)) && entry) {
|
||||
bool newChannelCreated = false;
|
||||
if (ValidateEntry(entry, aURI, aInitialDocumentURI, aReferrerURI,
|
||||
aReferrerPolicy, aLoadGroup, aObserver, aLoadingDocument,
|
||||
aLoadingDocument, requestFlags, aContentPolicyType, true,
|
||||
_retval, aTriggeringPrincipal, corsmode)) {
|
||||
&newChannelCreated, _retval, aTriggeringPrincipal,
|
||||
corsmode)) {
|
||||
request = entry->GetRequest();
|
||||
|
||||
// If this entry has no proxies, its request has no reference to the
|
||||
@ -2363,6 +2375,18 @@ imgLoader::LoadImage(nsIURI* aURI,
|
||||
|
||||
entry->Touch();
|
||||
|
||||
if (!newChannelCreated) {
|
||||
// This is ugly but it's needed to report CSP violations. We have 3
|
||||
// scenarios:
|
||||
// - we don't have cache. We are not in this if() stmt. A new channel is
|
||||
// created and that triggers the CSP checks.
|
||||
// - We have a cache entry and this is blocked by CSP directives.
|
||||
DebugOnly<bool> shouldLoad =
|
||||
ShouldLoadCachedImage(request, aLoadingDocument, aTriggeringPrincipal,
|
||||
aContentPolicyType,
|
||||
/* aSendCSPViolationReports */ true);
|
||||
MOZ_ASSERT(shouldLoad);
|
||||
}
|
||||
} else {
|
||||
// We can't use this entry. We'll try to load it off the network, and if
|
||||
// successful, overwrite the old entry in the cache with a new one.
|
||||
@ -2613,7 +2637,7 @@ imgLoader::LoadImageWithChannel(nsIChannel* channel,
|
||||
|
||||
if (ValidateEntry(entry, uri, nullptr, nullptr, RP_Unset,
|
||||
nullptr, aObserver, aCX, doc, requestFlags,
|
||||
policyType, false, nullptr,
|
||||
policyType, false, nullptr, nullptr,
|
||||
nullptr, imgIRequest::CORS_NONE)) {
|
||||
request = entry->GetRequest();
|
||||
} else {
|
||||
|
@ -413,6 +413,7 @@ private: // methods
|
||||
nsLoadFlags aLoadFlags,
|
||||
nsContentPolicyType aContentPolicyType,
|
||||
bool aCanMakeNewChannel,
|
||||
bool* aNewChannelCreated,
|
||||
imgRequestProxy** aProxyRequest,
|
||||
nsIPrincipal* aLoadingPrincipal,
|
||||
int32_t aCORSMode);
|
||||
@ -429,7 +430,8 @@ private: // methods
|
||||
nsContentPolicyType aContentPolicyType,
|
||||
imgRequestProxy** aProxyRequest,
|
||||
nsIPrincipal* aLoadingPrincipal,
|
||||
int32_t aCORSMode);
|
||||
int32_t aCORSMode,
|
||||
bool* aNewChannelCreated);
|
||||
|
||||
nsresult CreateNewProxyForRequest(imgRequest* aRequest,
|
||||
nsILoadGroup* aLoadGroup,
|
||||
|
@ -431,6 +431,7 @@ LoadInfoToLoadInfoArgs(nsILoadInfo *aLoadInfo,
|
||||
aLoadInfo->GetInitialSecurityCheckDone(),
|
||||
aLoadInfo->GetIsInThirdPartyContext(),
|
||||
aLoadInfo->GetIsDocshellReload(),
|
||||
aLoadInfo->GetSendCSPViolationEvents(),
|
||||
aLoadInfo->GetOriginAttributes(),
|
||||
redirectChainIncludingInternalRedirects,
|
||||
redirectChain,
|
||||
@ -587,6 +588,7 @@ LoadInfoArgsToLoadInfo(const OptionalLoadInfoArgs& aOptionalLoadInfoArgs,
|
||||
loadInfoArgs.initialSecurityCheckDone(),
|
||||
loadInfoArgs.isInThirdPartyContext(),
|
||||
loadInfoArgs.isDocshellReload(),
|
||||
loadInfoArgs.sendCSPViolationEvents(),
|
||||
loadInfoArgs.originAttributes(),
|
||||
redirectChainIncludingInternalRedirects,
|
||||
redirectChain,
|
||||
|
@ -82,6 +82,7 @@ LoadInfo::LoadInfo(nsIPrincipal* aLoadingPrincipal,
|
||||
, mInitialSecurityCheckDone(false)
|
||||
, mIsThirdPartyContext(false)
|
||||
, mIsDocshellReload(false)
|
||||
, mSendCSPViolationEvents(true)
|
||||
, mForcePreflight(false)
|
||||
, mIsPreflight(false)
|
||||
, mLoadTriggeredFromExternal(false)
|
||||
@ -315,6 +316,7 @@ LoadInfo::LoadInfo(nsPIDOMWindowOuter* aOuterWindow,
|
||||
, mInitialSecurityCheckDone(false)
|
||||
, mIsThirdPartyContext(false) // NB: TYPE_DOCUMENT implies not third-party.
|
||||
, mIsDocshellReload(false)
|
||||
, mSendCSPViolationEvents(true)
|
||||
, mForcePreflight(false)
|
||||
, mIsPreflight(false)
|
||||
, mLoadTriggeredFromExternal(false)
|
||||
@ -401,6 +403,7 @@ LoadInfo::LoadInfo(const LoadInfo& rhs)
|
||||
, mInitialSecurityCheckDone(rhs.mInitialSecurityCheckDone)
|
||||
, mIsThirdPartyContext(rhs.mIsThirdPartyContext)
|
||||
, mIsDocshellReload(rhs.mIsDocshellReload)
|
||||
, mSendCSPViolationEvents(rhs.mSendCSPViolationEvents)
|
||||
, mOriginAttributes(rhs.mOriginAttributes)
|
||||
, mRedirectChainIncludingInternalRedirects(
|
||||
rhs.mRedirectChainIncludingInternalRedirects)
|
||||
@ -447,6 +450,7 @@ LoadInfo::LoadInfo(nsIPrincipal* aLoadingPrincipal,
|
||||
bool aInitialSecurityCheckDone,
|
||||
bool aIsThirdPartyContext,
|
||||
bool aIsDocshellReload,
|
||||
bool aSendCSPViolationEvents,
|
||||
const OriginAttributes& aOriginAttributes,
|
||||
RedirectHistoryArray& aRedirectChainIncludingInternalRedirects,
|
||||
RedirectHistoryArray& aRedirectChain,
|
||||
@ -488,6 +492,7 @@ LoadInfo::LoadInfo(nsIPrincipal* aLoadingPrincipal,
|
||||
, mInitialSecurityCheckDone(aInitialSecurityCheckDone)
|
||||
, mIsThirdPartyContext(aIsThirdPartyContext)
|
||||
, mIsDocshellReload(aIsDocshellReload)
|
||||
, mSendCSPViolationEvents(aSendCSPViolationEvents)
|
||||
, mOriginAttributes(aOriginAttributes)
|
||||
, mAncestorPrincipals(std::move(aAncestorPrincipals))
|
||||
, mAncestorOuterWindowIDs(aAncestorOuterWindowIDs)
|
||||
@ -839,6 +844,20 @@ LoadInfo::SetIsDocshellReload(bool aValue)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
LoadInfo::GetSendCSPViolationEvents(bool* aResult)
|
||||
{
|
||||
*aResult = mSendCSPViolationEvents;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
LoadInfo::SetSendCSPViolationEvents(bool aValue)
|
||||
{
|
||||
mSendCSPViolationEvents = aValue;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
LoadInfo::GetExternalContentPolicyType(nsContentPolicyType* aResult)
|
||||
{
|
||||
|
@ -124,6 +124,7 @@ private:
|
||||
bool aInitialSecurityCheckDone,
|
||||
bool aIsThirdPartyRequest,
|
||||
bool aIsDocshellReload,
|
||||
bool aSendCSPViolationEvents,
|
||||
const OriginAttributes& aOriginAttributes,
|
||||
RedirectHistoryArray& aRedirectChainIncludingInternalRedirects,
|
||||
RedirectHistoryArray& aRedirectChain,
|
||||
@ -194,6 +195,7 @@ private:
|
||||
bool mInitialSecurityCheckDone;
|
||||
bool mIsThirdPartyContext;
|
||||
bool mIsDocshellReload;
|
||||
bool mSendCSPViolationEvents;
|
||||
OriginAttributes mOriginAttributes;
|
||||
RedirectHistoryArray mRedirectChainIncludingInternalRedirects;
|
||||
RedirectHistoryArray mRedirectChain;
|
||||
|
@ -502,6 +502,12 @@ interface nsILoadInfo : nsISupports
|
||||
*/
|
||||
readonly attribute nsContentPolicyType externalContentPolicyType;
|
||||
|
||||
/**
|
||||
* CSP uses this parameter to send or not CSP violation events.
|
||||
* Default value: true.
|
||||
*/
|
||||
[infallible] attribute boolean sendCSPViolationEvents;
|
||||
|
||||
%{ C++
|
||||
inline nsContentPolicyType GetExternalContentPolicyType()
|
||||
{
|
||||
|
@ -65,6 +65,7 @@ struct LoadInfoArgs
|
||||
bool initialSecurityCheckDone;
|
||||
bool isInThirdPartyContext;
|
||||
bool isDocshellReload;
|
||||
bool sendCSPViolationEvents;
|
||||
OriginAttributes originAttributes;
|
||||
RedirectHistoryEntryInfo[] redirectChainIncludingInternalRedirects;
|
||||
RedirectHistoryEntryInfo[] redirectChain;
|
||||
|
@ -1,5 +0,0 @@
|
||||
[media-src-7_1_2.sub.html]
|
||||
expected: TIMEOUT
|
||||
[Test that securitypolicyviolation events are fired]
|
||||
expected: TIMEOUT
|
||||
|
@ -1,5 +0,0 @@
|
||||
[media-src-7_2_2.sub.html]
|
||||
expected: TIMEOUT
|
||||
[Test that securitypolicyviolation events are fired]
|
||||
expected: TIMEOUT
|
||||
|
@ -1,5 +0,0 @@
|
||||
[media-src-blocked.sub.html]
|
||||
expected: TIMEOUT
|
||||
[Test that securitypolicyviolation events are fired]
|
||||
expected: TIMEOUT
|
||||
|
@ -0,0 +1,3 @@
|
||||
[fetch-csp.https.html]
|
||||
[Verify CSP control of fetch() in a Service Worker]
|
||||
expected: FAIL
|
@ -2,6 +2,3 @@
|
||||
[Script: Ed25519-with-CSP, passes, valid key, valid signature.]
|
||||
expected: FAIL
|
||||
|
||||
[Script: Ed25519-with-CSP, fails, valid key, valid signature, key not in CSP.]
|
||||
expected: FAIL
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user