diff options
author | Ben Murdoch <benm@google.com> | 2011-05-24 11:24:40 +0100 |
---|---|---|
committer | Ben Murdoch <benm@google.com> | 2011-06-02 09:53:15 +0100 |
commit | 81bc750723a18f21cd17d1b173cd2a4dda9cea6e (patch) | |
tree | 7a9e5ed86ff429fd347a25153107221543909b19 /Source/WebCore/websockets | |
parent | 94088a6d336c1dd80a1e734af51e96abcbb689a7 (diff) | |
download | external_webkit-81bc750723a18f21cd17d1b173cd2a4dda9cea6e.zip external_webkit-81bc750723a18f21cd17d1b173cd2a4dda9cea6e.tar.gz external_webkit-81bc750723a18f21cd17d1b173cd2a4dda9cea6e.tar.bz2 |
Merge WebKit at r80534: Intial merge by Git
Change-Id: Ia7a83357124c9e1cdb1debf55d9661ec0bd09a61
Diffstat (limited to 'Source/WebCore/websockets')
-rw-r--r-- | Source/WebCore/websockets/WebSocketHandshake.cpp | 138 | ||||
-rw-r--r-- | Source/WebCore/websockets/WebSocketHandshake.h | 26 |
2 files changed, 78 insertions, 86 deletions
diff --git a/Source/WebCore/websockets/WebSocketHandshake.cpp b/Source/WebCore/websockets/WebSocketHandshake.cpp index 84779f5..30efd2a 100644 --- a/Source/WebCore/websockets/WebSocketHandshake.cpp +++ b/Source/WebCore/websockets/WebSocketHandshake.cpp @@ -44,8 +44,8 @@ #include "ScriptCallStack.h" #include "ScriptExecutionContext.h" #include "SecurityOrigin.h" +#include <wtf/CryptographicallyRandomNumber.h> #include <wtf/MD5.h> -#include <wtf/RandomNumber.h> #include <wtf/StdLibExtras.h> #include <wtf/StringExtras.h> #include <wtf/Vector.h> @@ -92,24 +92,39 @@ static String trimConsoleMessage(const char* p, size_t len) return s; } +static uint32_t randomNumberLessThan(uint32_t n) +{ + if (!n) + return 0; + if (n == std::numeric_limits<uint32_t>::max()) + return cryptographicallyRandomNumber(); + uint32_t max = std::numeric_limits<uint32_t>::max() - (std::numeric_limits<uint32_t>::max() % n); + ASSERT(!(max % n)); + uint32_t v; + do { + v = cryptographicallyRandomNumber(); + } while (v >= max); + return v % n; +} + static void generateSecWebSocketKey(uint32_t& number, String& key) { - uint32_t space = static_cast<uint32_t>(randomNumber() * 12) + 1; + uint32_t space = randomNumberLessThan(12) + 1; uint32_t max = 4294967295U / space; - number = static_cast<uint32_t>(randomNumber() * max); + number = randomNumberLessThan(max); uint32_t product = number * space; String s = String::number(product); - int n = static_cast<int>(randomNumber() * 12) + 1; + int n = randomNumberLessThan(12) + 1; DEFINE_STATIC_LOCAL(String, randomChars, (randomCharacterInSecWebSocketKey)); for (int i = 0; i < n; i++) { - int pos = static_cast<int>(randomNumber() * (s.length() + 1)); - int chpos = static_cast<int>(randomNumber() * randomChars.length()); + int pos = randomNumberLessThan(s.length() + 1); + int chpos = randomNumberLessThan(randomChars.length()); s.insert(randomChars.substring(chpos, 1), pos); } DEFINE_STATIC_LOCAL(String, spaceChar, (" ")); for (uint32_t i = 0; i < space; i++) { - int pos = static_cast<int>(randomNumber() * (s.length() - 1)) + 1; + int pos = randomNumberLessThan(s.length() - 1) + 1; s.insert(spaceChar, pos); } ASSERT(s[0] != ' '); @@ -119,8 +134,7 @@ static void generateSecWebSocketKey(uint32_t& number, String& key) static void generateKey3(unsigned char key3[8]) { - for (int i = 0; i < 8; i++) - key3[i] = randomNumber() * 256; + cryptographicallyRandomValues(key3, 8); } static void setChallengeNumber(unsigned char* buf, uint32_t number) @@ -290,12 +304,6 @@ WebSocketHandshakeRequest WebSocketHandshake::clientHandshakeRequest() const void WebSocketHandshake::reset() { m_mode = Incomplete; - - m_wsOrigin = String(); - m_wsLocation = String(); - m_wsProtocol = String(); - m_setCookie = String(); - m_setCookie2 = String(); } void WebSocketHandshake::clearScriptExecutionContext() @@ -335,7 +343,6 @@ int WebSocketHandshake::readServerHandshake(const char* header, size_t len) m_mode = Failed; return len; } - processHeaders(); if (!checkResponseHeaders()) { LOG(Network, "header process failed"); m_mode = Failed; @@ -360,54 +367,39 @@ WebSocketHandshake::Mode WebSocketHandshake::mode() const return m_mode; } -const String& WebSocketHandshake::serverWebSocketOrigin() const -{ - return m_wsOrigin; -} - -void WebSocketHandshake::setServerWebSocketOrigin(const String& webSocketOrigin) -{ - m_wsOrigin = webSocketOrigin; -} - -const String& WebSocketHandshake::serverWebSocketLocation() const -{ - return m_wsLocation; -} - -void WebSocketHandshake::setServerWebSocketLocation(const String& webSocketLocation) +String WebSocketHandshake::serverWebSocketOrigin() const { - m_wsLocation = webSocketLocation; + return m_response.headerFields().get("sec-websocket-origin"); } -const String& WebSocketHandshake::serverWebSocketProtocol() const +String WebSocketHandshake::serverWebSocketLocation() const { - return m_wsProtocol; + return m_response.headerFields().get("sec-websocket-location"); } -void WebSocketHandshake::setServerWebSocketProtocol(const String& webSocketProtocol) +String WebSocketHandshake::serverWebSocketProtocol() const { - m_wsProtocol = webSocketProtocol; + return m_response.headerFields().get("sec-websocket-protocol"); } -const String& WebSocketHandshake::serverSetCookie() const +String WebSocketHandshake::serverSetCookie() const { - return m_setCookie; + return m_response.headerFields().get("set-cookie"); } -void WebSocketHandshake::setServerSetCookie(const String& setCookie) +String WebSocketHandshake::serverSetCookie2() const { - m_setCookie = setCookie; + return m_response.headerFields().get("set-cookie2"); } -const String& WebSocketHandshake::serverSetCookie2() const +String WebSocketHandshake::serverUpgrade() const { - return m_setCookie2; + return m_response.headerFields().get("upgrade"); } -void WebSocketHandshake::setServerSetCookie2(const String& setCookie2) +String WebSocketHandshake::serverConnection() const { - m_setCookie2 = setCookie2; + return m_response.headerFields().get("connection"); } const WebSocketHandshakeResponse& WebSocketHandshake::serverHandshakeResponse() const @@ -550,7 +542,7 @@ const char* WebSocketHandshake::readHTTPHeaders(const char* start, const char* e m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "CR doesn't follow LF after value at " + trimConsoleMessage(p, end - p), 0, clientOrigin(), 0); return 0; } - AtomicString nameStr(String::fromUTF8(name.data(), name.size())); + AtomicString nameStr = AtomicString::fromUTF8(name.data(), name.size()); String valueStr = String::fromUTF8(value.data(), value.size()); if (nameStr.isNull()) { m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "invalid UTF-8 sequence in header name", 0, clientOrigin(), 0); @@ -567,38 +559,50 @@ const char* WebSocketHandshake::readHTTPHeaders(const char* start, const char* e return 0; } -void WebSocketHandshake::processHeaders() -{ - ASSERT(m_mode == Normal); - const HTTPHeaderMap& headers = m_response.headerFields(); - m_wsOrigin = headers.get("sec-websocket-origin"); - m_wsLocation = headers.get("sec-websocket-location"); - m_wsProtocol = headers.get("sec-websocket-protocol"); - m_setCookie = headers.get("set-cookie"); - m_setCookie2 = headers.get("set-cookie2"); -} - bool WebSocketHandshake::checkResponseHeaders() { - if (m_wsOrigin.isNull()) { - m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'sec-websocket-origin' header is missing", 0, clientOrigin(), 0); + const String& serverWebSocketLocation = this->serverWebSocketLocation(); + const String& serverWebSocketOrigin = this->serverWebSocketOrigin(); + const String& serverWebSocketProtocol = this->serverWebSocketProtocol(); + const String& serverUpgrade = this->serverUpgrade(); + const String& serverConnection = this->serverConnection(); + + if (serverUpgrade.isNull()) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'Upgrade' header is missing", 0, clientOrigin(), 0); + return false; + } + if (serverConnection.isNull()) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'Connection' header is missing", 0, clientOrigin(), 0); + return false; + } + if (serverWebSocketOrigin.isNull()) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'Sec-WebSocket-Origin' header is missing", 0, clientOrigin(), 0); + return false; + } + if (serverWebSocketLocation.isNull()) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'Sec-WebSocket-Location' header is missing", 0, clientOrigin(), 0); + return false; + } + + if (!equalIgnoringCase(serverUpgrade, "websocket")) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'Upgrade' header value is not 'WebSocket'", 0, clientOrigin(), 0); return false; } - if (m_wsLocation.isNull()) { - m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'sec-websocket-location' header is missing", 0, clientOrigin(), 0); + if (!equalIgnoringCase(serverConnection, "upgrade")) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: 'Connection' header value is not 'Upgrade'", 0, clientOrigin(), 0); return false; } - if (clientOrigin() != m_wsOrigin) { - m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: origin mismatch: " + clientOrigin() + " != " + m_wsOrigin, 0, clientOrigin(), 0); + if (clientOrigin() != serverWebSocketOrigin) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: origin mismatch: " + clientOrigin() + " != " + serverWebSocketOrigin, 0, clientOrigin(), 0); return false; } - if (clientLocation() != m_wsLocation) { - m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: location mismatch: " + clientLocation() + " != " + m_wsLocation, 0, clientOrigin(), 0); + if (clientLocation() != serverWebSocketLocation) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: location mismatch: " + clientLocation() + " != " + serverWebSocketLocation, 0, clientOrigin(), 0); return false; } - if (!m_clientProtocol.isEmpty() && m_clientProtocol != m_wsProtocol) { - m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: protocol mismatch: " + m_clientProtocol + " != " + m_wsProtocol, 0, clientOrigin(), 0); + if (!m_clientProtocol.isEmpty() && m_clientProtocol != serverWebSocketProtocol) { + m_context->addMessage(JSMessageSource, LogMessageType, ErrorMessageLevel, "Error during WebSocket handshake: protocol mismatch: " + m_clientProtocol + " != " + serverWebSocketProtocol, 0, clientOrigin(), 0); return false; } return true; diff --git a/Source/WebCore/websockets/WebSocketHandshake.h b/Source/WebCore/websockets/WebSocketHandshake.h index 371d852..90916a7 100644 --- a/Source/WebCore/websockets/WebSocketHandshake.h +++ b/Source/WebCore/websockets/WebSocketHandshake.h @@ -72,19 +72,13 @@ namespace WebCore { int readServerHandshake(const char* header, size_t len); Mode mode() const; - const String& serverWebSocketOrigin() const; - void setServerWebSocketOrigin(const String& webSocketOrigin); - - const String& serverWebSocketLocation() const; - void setServerWebSocketLocation(const String& webSocketLocation); - - const String& serverWebSocketProtocol() const; - void setServerWebSocketProtocol(const String& webSocketProtocol); - - const String& serverSetCookie() const; - void setServerSetCookie(const String& setCookie); - const String& serverSetCookie2() const; - void setServerSetCookie2(const String& setCookie2); + String serverWebSocketOrigin() const; + String serverWebSocketLocation() const; + String serverWebSocketProtocol() const; + String serverSetCookie() const; + String serverSetCookie2() const; + String serverUpgrade() const; + String serverConnection() const; const WebSocketHandshakeResponse& serverHandshakeResponse() const; @@ -105,12 +99,6 @@ namespace WebCore { Mode m_mode; - String m_wsOrigin; - String m_wsLocation; - String m_wsProtocol; - String m_setCookie; - String m_setCookie2; - String m_secWebSocketKey1; String m_secWebSocketKey2; unsigned char m_key3[8]; |