Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(818)

Unified Diff: Source/core/frame/csp/ContentSecurityPolicy.cpp

Issue 553423002: CSP: Use a specified frame for reporting 'frame-ancestors' violations. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Feedback, tests, and rebase. Created 6 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « Source/core/frame/csp/ContentSecurityPolicy.h ('k') | Source/core/loader/DocumentLoader.cpp » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: Source/core/frame/csp/ContentSecurityPolicy.cpp
diff --git a/Source/core/frame/csp/ContentSecurityPolicy.cpp b/Source/core/frame/csp/ContentSecurityPolicy.cpp
index 80af84f042786d4b885d3329b8afde7e1ac9fc02..3a17d992d178f27499432c74fded97f6e7afdeac 100644
--- a/Source/core/frame/csp/ContentSecurityPolicy.cpp
+++ b/Source/core/frame/csp/ContentSecurityPolicy.cpp
@@ -338,11 +338,11 @@ bool isAllowedByAllWithURL(const CSPDirectiveListVector& policies, const KURL& u
return true;
}
-template<bool (CSPDirectiveList::*allowed)(LocalFrame*, ContentSecurityPolicy::ReportingStatus) const>
-bool isAllowedByAllWithFrame(const CSPDirectiveListVector& policies, LocalFrame* frame, ContentSecurityPolicy::ReportingStatus reportingStatus)
+template<bool (CSPDirectiveList::*allowed)(LocalFrame*, const KURL&, ContentSecurityPolicy::ReportingStatus) const>
+bool isAllowedByAllWithFrame(const CSPDirectiveListVector& policies, LocalFrame* frame, const KURL& url, ContentSecurityPolicy::ReportingStatus reportingStatus)
{
for (size_t i = 0; i < policies.size(); ++i) {
- if (!(policies[i].get()->*allowed)(frame, reportingStatus))
+ if (!(policies[i].get()->*allowed)(frame, url, reportingStatus))
return false;
}
return true;
@@ -509,9 +509,9 @@ bool ContentSecurityPolicy::allowBaseURI(const KURL& url, ContentSecurityPolicy:
return isAllowedByAllWithURL<&CSPDirectiveList::allowBaseURI>(m_policies, url, reportingStatus);
}
-bool ContentSecurityPolicy::allowAncestors(LocalFrame* frame, ContentSecurityPolicy::ReportingStatus reportingStatus) const
+bool ContentSecurityPolicy::allowAncestors(LocalFrame* frame, const KURL& url, ContentSecurityPolicy::ReportingStatus reportingStatus) const
{
- return isAllowedByAllWithFrame<&CSPDirectiveList::allowAncestors>(m_policies, frame, reportingStatus);
+ return isAllowedByAllWithFrame<&CSPDirectiveList::allowAncestors>(m_policies, frame, url, reportingStatus);
}
bool ContentSecurityPolicy::allowChildContextFromSource(const KURL& url, ContentSecurityPolicy::ReportingStatus reportingStatus) const
@@ -603,9 +603,17 @@ static String stripURLForUseInReport(Document* document, const KURL& url)
static void gatherSecurityPolicyViolationEventData(SecurityPolicyViolationEventInit& init, Document* document, const String& directiveText, const String& effectiveDirective, const KURL& blockedURL, const String& header)
{
- init.documentURI = document->url().string();
+ if (equalIgnoringCase(effectiveDirective, ContentSecurityPolicy::FrameAncestors)) {
+ // If this load was blocked via 'frame-ancestors', then the URL of |document| has not yet
+ // been initialized. In this case, we'll set both 'documentURI' and 'blockedURI' to the
+ // blocked document's URL.
+ init.documentURI = blockedURL.string();
+ init.blockedURI = blockedURL.string();
+ } else {
+ init.documentURI = document->url().string();
+ init.blockedURI = stripURLForUseInReport(document, blockedURL);
+ }
init.referrer = document->referrer();
- init.blockedURI = stripURLForUseInReport(document, blockedURL);
init.violatedDirective = directiveText;
init.effectiveDirective = effectiveDirective;
init.originalPolicy = header;
@@ -631,14 +639,12 @@ static void gatherSecurityPolicyViolationEventData(SecurityPolicyViolationEventI
}
}
-void ContentSecurityPolicy::reportViolation(const String& directiveText, const String& effectiveDirective, const String& consoleMessage, const KURL& blockedURL, const Vector<String>& reportEndpoints, const String& header)
+void ContentSecurityPolicy::reportViolation(const String& directiveText, const String& effectiveDirective, const String& consoleMessage, const KURL& blockedURL, const Vector<String>& reportEndpoints, const String& header, LocalFrame* contextFrame)
{
- // FIXME: Support sending 'frame-ancestor' reports (which occur before we're bound to an execution context)
- if (!m_executionContext)
- return;
+ ASSERT((m_executionContext && !contextFrame) || (equalIgnoringCase(effectiveDirective, ContentSecurityPolicy::FrameAncestors) && contextFrame));
// FIXME: Support sending reports from worker.
- Document* document = this->document();
+ Document* document = contextFrame ? contextFrame->document() : this->document();
if (!document)
return;
@@ -689,8 +695,15 @@ void ContentSecurityPolicy::reportViolation(const String& directiveText, const S
RefPtr<FormData> report = FormData::create(stringifiedReport.utf8());
- for (size_t i = 0; i < reportEndpoints.size(); ++i)
+ for (size_t i = 0; i < reportEndpoints.size(); ++i) {
+ // If we have a context frame we're dealing with 'frame-ancestors' and we don't have our
+ // own execution context. Use the frame's document to complete the endpoint URL, overriding
+ // its URL with the blocked document's URL.
+ ASSERT(!contextFrame || !m_executionContext);
+ ASSERT(!contextFrame || equalIgnoringCase(effectiveDirective, FrameAncestors));
+ KURL endpoint = contextFrame ? frame->document()->completeURLWithOverride(reportEndpoints[i], blockedURL) : completeURL(reportEndpoints[i]);
PingLoader::sendViolationReport(frame, completeURL(reportEndpoints[i]), report, PingLoader::ContentSecurityPolicyViolationReport);
+ }
didSendViolationReport(stringifiedReport);
}
@@ -807,9 +820,11 @@ void ContentSecurityPolicy::logToConsole(const String& message, MessageLevel lev
logToConsole(ConsoleMessage::create(SecurityMessageSource, level, message));
}
-void ContentSecurityPolicy::logToConsole(PassRefPtrWillBeRawPtr<ConsoleMessage> consoleMessage)
+void ContentSecurityPolicy::logToConsole(PassRefPtrWillBeRawPtr<ConsoleMessage> consoleMessage, LocalFrame* frame)
{
- if (m_executionContext)
+ if (frame)
+ frame->document()->addConsoleMessage(consoleMessage);
+ else if (m_executionContext)
m_executionContext->addConsoleMessage(consoleMessage);
else
m_consoleMessages.append(consoleMessage);
« no previous file with comments | « Source/core/frame/csp/ContentSecurityPolicy.h ('k') | Source/core/loader/DocumentLoader.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698