Skip to content

Commit

Permalink
Store CSP delivered via meta tag as a valid HTTP header.
Browse files Browse the repository at this point in the history
https://bugs.webkit.org/show_bug.cgi?id=249596
rdar://103170891

Reviewed by Brent Fulgham.

A CSP delivered via a meta tag could have invalid HTTP header values in it. Take for example this:

<meta http-equiv="Content-Security-Policy" content="
    default-src 'none';
    script-src 'self';
    img-src 'self'">

The value of the CSP header that the ContentSecurityPolicyDirectiveList will get will be the raw
string including whitespace and most importantly newline characters. These newline characters are
invalid characters in an HTTP header[0].

The parsing algorithm for CSP handles this appropriately and creates a valid CSP for the document. However,
if a script in the document then creates blob URLs which are navigated to or otherwise fetched, the Network
process will return a ResourceResponse object with a Content-Security-Policy header that contains the newlines.
This is caught by the ResourceResponseBase::containsInvalidHTTPHeaders function which causes the fetch to fail.

To combat this we can simply strip the newline characters from the meta-delivered CSP and store the policy as a
valid HTTP header.

[0] https://fetch.spec.whatwg.org/#header-value

* Source/WebCore/page/csp/ContentSecurityPolicyDirectiveList.cpp:
(WebCore::ContentSecurityPolicyDirectiveList::parse):

Canonical link: https://commits.webkit.org/258110@main
  • Loading branch information
rreno committed Dec 20, 2022
1 parent b5a473c commit 0445ac5
Showing 1 changed file with 10 additions and 1 deletion.
11 changes: 10 additions & 1 deletion Source/WebCore/page/csp/ContentSecurityPolicyDirectiveList.cpp
Expand Up @@ -30,6 +30,7 @@
#include "ContentSecurityPolicyDirectiveNames.h"
#include "Document.h"
#include "Frame.h"
#include "HTTPParsers.h"
#include "ParsingUtilities.h"
#include "SecurityContext.h"
#include <wtf/text/StringParsingBuffer.h>
Expand Down Expand Up @@ -444,7 +445,15 @@ const ContentSecurityPolicyDirective* ContentSecurityPolicyDirectiveList::violat
//
void ContentSecurityPolicyDirectiveList::parse(const String& policy, ContentSecurityPolicy::PolicyFrom policyFrom)
{
m_header = policy;
// A meta tag delievered CSP could contain invalid HTTP header values depending on how it was formatted in the document.
// We want to store the CSP as a valid HTTP header for e.g. blob URL inheritance.
if (policyFrom == ContentSecurityPolicy::PolicyFrom::HTTPEquivMeta) {
m_header = stripLeadingAndTrailingHTTPSpaces(policy).removeCharacters([](auto c) {
return c == 0x00 || c == '\r' || c == '\n';
});
} else
m_header = policy;

if (policy.isEmpty())
return;

Expand Down

0 comments on commit 0445ac5

Please sign in to comment.