Diff
Modified: trunk/Source/WebCore/CMakeLists.txt (94127 => 94128)
--- trunk/Source/WebCore/CMakeLists.txt 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/CMakeLists.txt 2011-08-30 23:55:52 UTC (rev 94128)
@@ -1133,6 +1133,7 @@
platform/network/FormData.cpp
platform/network/HTTPHeaderMap.cpp
platform/network/HTTPParsers.cpp
+ platform/network/HTTPValidation.cpp
platform/network/MIMEHeader.cpp
platform/network/NetworkStateNotifier.cpp
platform/network/ProtectionSpace.cpp
Modified: trunk/Source/WebCore/ChangeLog (94127 => 94128)
--- trunk/Source/WebCore/ChangeLog 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/ChangeLog 2011-08-30 23:55:52 UTC (rev 94128)
@@ -1,3 +1,31 @@
+2011-08-30 Bill Budge <[email protected]>
+
+ This patch makes the XMLHttpRequest method/header validation logic available as
+ static methods so URL loaders can perform the same checks for untrusted HTTP requests
+ coming from plugins.
+ https://bugs.webkit.org/show_bug.cgi?id=66909
+
+ Reviewed by David Levin.
+
+ No new tests. Exposes no new functionality.
+
+ * CMakeLists.txt:
+ * GNUmakefile.list.am:
+ * WebCore.gypi:
+ * WebCore.pro:
+ * WebCore.vcproj/WebCore.vcproj:
+ * platform/network/HTTPValidation.cpp: Added.
+ (WebCore::isValidHTTPToken):
+ (WebCore::isValidHTTPHeaderValue):
+ * platform/network/HTTPValidation.h: Added.
+ * xml/XMLHttpRequest.cpp:
+ (WebCore::XMLHttpRequest::isAllowedHTTPMethod):
+ (WebCore::XMLHttpRequest::uppercaseKnownHTTPMethod):
+ (WebCore::XMLHttpRequest::isAllowedHTTPHeader):
+ (WebCore::XMLHttpRequest::open):
+ (WebCore::XMLHttpRequest::setRequestHeader):
+ * xml/XMLHttpRequest.h:
+
2011-08-30 Chris Rogers <[email protected]>
Don't allow nodes of one context to be connected to nodes of another context
Modified: trunk/Source/WebCore/GNUmakefile.list.am (94127 => 94128)
--- trunk/Source/WebCore/GNUmakefile.list.am 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/GNUmakefile.list.am 2011-08-30 23:55:52 UTC (rev 94128)
@@ -2706,6 +2706,8 @@
Source/WebCore/platform/network/HTTPHeaderMap.h \
Source/WebCore/platform/network/HTTPParsers.cpp \
Source/WebCore/platform/network/HTTPParsers.h \
+ Source/WebCore/platform/network/HTTPValidation.cpp \
+ Source/WebCore/platform/network/HTTPValidation.h \
Source/WebCore/platform/network/MIMEHeader.cpp \
Source/WebCore/platform/network/MIMEHeader.h \
Source/WebCore/platform/network/NetworkingContext.h \
Modified: trunk/Source/WebCore/WebCore.gypi (94127 => 94128)
--- trunk/Source/WebCore/WebCore.gypi 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/WebCore.gypi 2011-08-30 23:55:52 UTC (rev 94128)
@@ -4138,6 +4138,8 @@
'platform/network/HTTPHeaderMap.cpp',
'platform/network/HTTPParsers.cpp',
'platform/network/HTTPParsers.h',
+ 'platform/network/HTTPValidation.cpp',
+ 'platform/network/HTTPValidation.h',
'platform/network/MIMEHeader.cpp',
'platform/network/NetworkStateNotifier.cpp',
'platform/network/NetworkStateNotifier.h',
Modified: trunk/Source/WebCore/WebCore.pro (94127 => 94128)
--- trunk/Source/WebCore/WebCore.pro 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/WebCore.pro 2011-08-30 23:55:52 UTC (rev 94128)
@@ -1050,6 +1050,7 @@
platform/network/FormDataBuilder.cpp \
platform/network/HTTPHeaderMap.cpp \
platform/network/HTTPParsers.cpp \
+ platform/network/HTTPValidation.cpp \
platform/network/MIMEHeader.cpp \
platform/network/NetworkStateNotifier.cpp \
platform/network/ProtectionSpace.cpp \
@@ -2061,6 +2062,7 @@
platform/network/FormData.h \
platform/network/HTTPHeaderMap.h \
platform/network/HTTPParsers.h \
+ platform/network/HTTPValidation.h \
platform/network/HTTPStatusCodes.h \
platform/network/MIMESniffing.h \
platform/network/NetworkingContext.h \
Modified: trunk/Source/WebCore/WebCore.vcproj/WebCore.vcproj (94127 => 94128)
--- trunk/Source/WebCore/WebCore.vcproj/WebCore.vcproj 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/WebCore.vcproj/WebCore.vcproj 2011-08-30 23:55:52 UTC (rev 94128)
@@ -30445,6 +30445,14 @@
>
</File>
<File
+ RelativePath="..\platform\network\HTTPValidation.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\platform\network\HTTPValidation.h"
+ >
+ </File>
+ <File
RelativePath="..\platform\network\MIMEHeader.cpp"
>
</File>
Added: trunk/Source/WebCore/platform/network/HTTPValidation.cpp (0 => 94128)
--- trunk/Source/WebCore/platform/network/HTTPValidation.cpp (rev 0)
+++ trunk/Source/WebCore/platform/network/HTTPValidation.cpp 2011-08-30 23:55:52 UTC (rev 94128)
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2011 Alexey Proskuryakov ([email protected])
+ * Copyright (C) 2011 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "HTTPValidation.h"
+
+#include "PlatformString.h"
+#include <wtf/text/CString.h>
+
+namespace WebCore {
+
+// Determines if a string is a valid token, as defined by
+// "token" in section 2.2 of RFC 2616.
+bool isValidHTTPToken(const String& name)
+{
+ unsigned length = name.length();
+ for (unsigned i = 0; i < length; i++) {
+ UChar c = name[i];
+
+ if (c >= 127 || c <= 32)
+ return false;
+
+ if (c == '(' || c == ')' || c == '<' || c == '>' || c == '@'
+ || c == ',' || c == ';' || c == ':' || c == '\\' || c == '\"'
+ || c == '/' || c == '[' || c == ']' || c == '?' || c == '='
+ || c == '{' || c == '}')
+ return false;
+ }
+
+ return length > 0;
+}
+
+bool isValidHTTPHeaderValue(const String& name)
+{
+ // FIXME: This should really match name against
+ // field-value in section 4.2 of RFC 2616.
+
+ return !name.contains('\r') && !name.contains('\n');
+}
+
+}
Added: trunk/Source/WebCore/platform/network/HTTPValidation.h (0 => 94128)
--- trunk/Source/WebCore/platform/network/HTTPValidation.h (rev 0)
+++ trunk/Source/WebCore/platform/network/HTTPValidation.h 2011-08-30 23:55:52 UTC (rev 94128)
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2011 Alexey Proskuryakov ([email protected])
+ * Copyright (C) 2011 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef HTTPValidation_h
+#define HTTPValidation_h
+
+#include <wtf/Forward.h>
+
+namespace WebCore {
+
+bool isValidHTTPToken(const String&);
+bool isValidHTTPHeaderValue(const String&);
+
+}
+
+#endif
Modified: trunk/Source/WebCore/xml/XMLHttpRequest.cpp (94127 => 94128)
--- trunk/Source/WebCore/xml/XMLHttpRequest.cpp 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/xml/XMLHttpRequest.cpp 2011-08-30 23:55:52 UTC (rev 94128)
@@ -2,7 +2,7 @@
* Copyright (C) 2004, 2006, 2008 Apple Inc. All rights reserved.
* Copyright (C) 2005-2007 Alexey Proskuryakov <[email protected]>
* Copyright (C) 2007, 2008 Julien Chaffraix <[email protected]>
- * Copyright (C) 2008 David Levin <[email protected]>
+ * Copyright (C) 2008, 2011 Google Inc. All rights reserved.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -36,6 +36,7 @@
#include "ExceptionCode.h"
#include "File.h"
#include "HTTPParsers.h"
+#include "HTTPValidation.h"
#include "InspectorInstrumentation.h"
#include "ResourceError.h"
#include "ResourceRequest.h"
@@ -104,35 +105,6 @@
m_forbiddenRequestHeaders.add("via");
}
-// Determines if a string is a valid token, as defined by
-// "token" in section 2.2 of RFC 2616.
-static bool isValidToken(const String& name)
-{
- unsigned length = name.length();
- for (unsigned i = 0; i < length; i++) {
- UChar c = name[i];
-
- if (c >= 127 || c <= 32)
- return false;
-
- if (c == '(' || c == ')' || c == '<' || c == '>' || c == '@' ||
- c == ',' || c == ';' || c == ':' || c == '\\' || c == '\"' ||
- c == '/' || c == '[' || c == ']' || c == '?' || c == '=' ||
- c == '{' || c == '}')
- return false;
- }
-
- return length > 0;
-}
-
-static bool isValidHeaderValue(const String& name)
-{
- // FIXME: This should really match name against
- // field-value in section 4.2 of RFC 2616.
-
- return !name.contains('\r') && !name.contains('\n');
-}
-
static bool isSetCookieHeader(const AtomicString& name)
{
return equalIgnoringCase(name, "set-cookie") || equalIgnoringCase(name, "set-cookie2");
@@ -398,6 +370,32 @@
}
#endif
+bool XMLHttpRequest::isAllowedHTTPMethod(const String& method)
+{
+ return !equalIgnoringCase(method, "TRACE")
+ && !equalIgnoringCase(method, "TRACK")
+ && !equalIgnoringCase(method, "CONNECT");
+}
+
+String XMLHttpRequest::uppercaseKnownHTTPMethod(const String& method)
+{
+ if (equalIgnoringCase(method, "COPY") || equalIgnoringCase(method, "DELETE") || equalIgnoringCase(method, "GET")
+ || equalIgnoringCase(method, "HEAD") || equalIgnoringCase(method, "INDEX") || equalIgnoringCase(method, "LOCK")
+ || equalIgnoringCase(method, "M-POST") || equalIgnoringCase(method, "MKCOL") || equalIgnoringCase(method, "MOVE")
+ || equalIgnoringCase(method, "OPTIONS") || equalIgnoringCase(method, "POST") || equalIgnoringCase(method, "PROPFIND")
+ || equalIgnoringCase(method, "PROPPATCH") || equalIgnoringCase(method, "PUT") || equalIgnoringCase(method, "UNLOCK")) {
+ return method.upper();
+ }
+ return method;
+}
+
+bool XMLHttpRequest::isAllowedHTTPHeader(const String& name)
+{
+ initializeXMLHttpRequestStaticData();
+ return !staticData->m_forbiddenRequestHeaders.contains(name) && !name.startsWith(staticData->m_proxyHeaderPrefix, false)
+ && !name.startsWith(staticData->m_secHeaderPrefix, false);
+}
+
void XMLHttpRequest::open(const String& method, const KURL& url, ExceptionCode& ec)
{
open(method, url, true, ec);
@@ -418,29 +416,20 @@
ASSERT(m_state == UNSENT);
- if (!isValidToken(method)) {
+ if (!isValidHTTPToken(method)) {
ec = SYNTAX_ERR;
return;
}
- // Method names are case sensitive. But since Firefox uppercases method names it knows, we'll do the same.
- String methodUpper(method.upper());
-
- if (methodUpper == "TRACE" || methodUpper == "TRACK" || methodUpper == "CONNECT") {
+ if (!isAllowedHTTPMethod(method)) {
ec = SECURITY_ERR;
return;
}
+ m_method = uppercaseKnownHTTPMethod(method);
+
m_url = url;
- if (methodUpper == "COPY" || methodUpper == "DELETE" || methodUpper == "GET" || methodUpper == "HEAD"
- || methodUpper == "INDEX" || methodUpper == "LOCK" || methodUpper == "M-POST" || methodUpper == "MKCOL" || methodUpper == "MOVE"
- || methodUpper == "OPTIONS" || methodUpper == "POST" || methodUpper == "PROPFIND" || methodUpper == "PROPPATCH" || methodUpper == "PUT"
- || methodUpper == "UNLOCK")
- m_method = methodUpper;
- else
- m_method = method;
-
m_async = async;
ASSERT(!m_loader);
@@ -835,13 +824,13 @@
return;
}
- if (!isValidToken(name) || !isValidHeaderValue(value)) {
+ if (!isValidHTTPToken(name) || !isValidHTTPHeaderValue(value)) {
ec = SYNTAX_ERR;
return;
}
// A privileged script (e.g. a Dashboard widget) can set any headers.
- if (!securityOrigin()->canLoadLocalResources() && !isSafeRequestHeader(name)) {
+ if (!securityOrigin()->canLoadLocalResources() && !isAllowedHTTPHeader(name)) {
reportUnsafeUsage(scriptExecutionContext(), "Refused to set unsafe header \"" + name + "\"");
return;
}
@@ -856,12 +845,6 @@
result.first->second += ", " + value;
}
-bool XMLHttpRequest::isSafeRequestHeader(const String& name) const
-{
- return !staticData->m_forbiddenRequestHeaders.contains(name) && !name.startsWith(staticData->m_proxyHeaderPrefix, false)
- && !name.startsWith(staticData->m_secHeaderPrefix, false);
-}
-
String XMLHttpRequest::getRequestHeader(const AtomicString& name) const
{
return m_requestHeaders.get(name);
Modified: trunk/Source/WebCore/xml/XMLHttpRequest.h (94127 => 94128)
--- trunk/Source/WebCore/xml/XMLHttpRequest.h 2011-08-30 23:45:53 UTC (rev 94127)
+++ trunk/Source/WebCore/xml/XMLHttpRequest.h 2011-08-30 23:55:52 UTC (rev 94128)
@@ -1,6 +1,7 @@
/*
* Copyright (C) 2003, 2006, 2008 Apple Inc. All rights reserved.
* Copyright (C) 2005, 2006 Alexey Proskuryakov <[email protected]>
+ * Copyright (C) 2011 Google Inc. All rights reserved.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -110,6 +111,11 @@
Blob* optionalResponseBlob() const { return m_responseBlob.get(); }
#endif
+ // Expose HTTP validation methods for other untrusted requests.
+ static bool isAllowedHTTPMethod(const String&);
+ static String uppercaseKnownHTTPMethod(const String&);
+ static bool isAllowedHTTPHeader(const String&);
+
void setResponseType(const String&, ExceptionCode&);
String responseType();
ResponseTypeCode responseTypeCode() const { return m_responseTypeCode; }
@@ -163,7 +169,6 @@
String getRequestHeader(const AtomicString& name) const;
void setRequestHeaderInternal(const AtomicString& name, const String& value);
- bool isSafeRequestHeader(const String&) const;
void changeState(State newState);
void callReadyStateChangeListener();