OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. |
| 4 |
| 5 #include "build/build_config.h" |
| 6 |
| 7 #if defined(OS_WIN) |
| 8 #include <ws2tcpip.h> |
| 9 #else |
| 10 #include <netdb.h> |
| 11 #endif |
| 12 |
| 13 #include <string> |
| 14 |
| 15 #include "base/message_loop.h" |
| 16 #include "googleurl/src/gurl.h" |
| 17 #include "net/base/address_list.h" |
| 18 #include "net/base/test_completion_callback.h" |
| 19 #include "net/socket_stream/socket_stream.h" |
| 20 #include "net/websockets/websocket_throttle.h" |
| 21 #include "testing/gtest/include/gtest/gtest.h" |
| 22 #include "testing/platform_test.h" |
| 23 |
| 24 class DummySocketStreamDelegate : public net::SocketStream::Delegate { |
| 25 public: |
| 26 DummySocketStreamDelegate() {} |
| 27 virtual ~DummySocketStreamDelegate() {} |
| 28 virtual void OnConnected( |
| 29 net::SocketStream* socket, int max_pending_send_allowed) {} |
| 30 virtual void OnSentData(net::SocketStream* socket, int amount_sent) {} |
| 31 virtual void OnReceivedData(net::SocketStream* socket, |
| 32 const char* data, int len) {} |
| 33 virtual void OnClose(net::SocketStream* socket) {} |
| 34 }; |
| 35 |
| 36 namespace net { |
| 37 |
| 38 class WebSocketThrottleTest : public PlatformTest { |
| 39 protected: |
| 40 struct addrinfo *AddAddr(int a1, int a2, int a3, int a4, |
| 41 struct addrinfo* next) { |
| 42 struct addrinfo* addrinfo = new struct addrinfo; |
| 43 memset(addrinfo, 0, sizeof(struct addrinfo)); |
| 44 addrinfo->ai_family = AF_INET; |
| 45 int addrlen = sizeof(struct sockaddr_in); |
| 46 addrinfo->ai_addrlen = addrlen; |
| 47 addrinfo->ai_addr = reinterpret_cast<sockaddr*>(new char[addrlen]); |
| 48 memset(addrinfo->ai_addr, 0, sizeof(addrlen)); |
| 49 struct sockaddr_in* addr = |
| 50 reinterpret_cast<sockaddr_in*>(addrinfo->ai_addr); |
| 51 int addrint = ((a1 & 0xff) << 24) | |
| 52 ((a2 & 0xff) << 16) | |
| 53 ((a3 & 0xff) << 8) | |
| 54 ((a4 & 0xff)); |
| 55 memcpy(&addr->sin_addr, &addrint, sizeof(int)); |
| 56 addrinfo->ai_next = next; |
| 57 return addrinfo; |
| 58 } |
| 59 void DeleteAddrInfo(struct addrinfo* head) { |
| 60 if (!head) |
| 61 return; |
| 62 struct addrinfo* next; |
| 63 for (struct addrinfo* a = head; a != NULL; a = next) { |
| 64 next = a->ai_next; |
| 65 delete [] a->ai_addr; |
| 66 delete a; |
| 67 } |
| 68 } |
| 69 |
| 70 static void SetAddressList(SocketStream* socket, struct addrinfo* head) { |
| 71 socket->CopyAddrInfo(head); |
| 72 } |
| 73 }; |
| 74 |
| 75 TEST_F(WebSocketThrottleTest, Throttle) { |
| 76 WebSocketThrottle::Init(); |
| 77 DummySocketStreamDelegate delegate; |
| 78 |
| 79 WebSocketThrottle* throttle = Singleton<WebSocketThrottle>::get(); |
| 80 |
| 81 EXPECT_EQ(throttle, |
| 82 SocketStreamThrottle::GetSocketStreamThrottleForScheme("ws")); |
| 83 EXPECT_EQ(throttle, |
| 84 SocketStreamThrottle::GetSocketStreamThrottleForScheme("wss")); |
| 85 |
| 86 // For host1: 1.2.3.4, 1.2.3.5, 1.2.3.6 |
| 87 struct addrinfo* addr = AddAddr(1, 2, 3, 4, NULL); |
| 88 addr = AddAddr(1, 2, 3, 5, addr); |
| 89 addr = AddAddr(1, 2, 3, 6, addr); |
| 90 scoped_refptr<SocketStream> s1 = |
| 91 new SocketStream(GURL("ws://host1/"), &delegate); |
| 92 WebSocketThrottleTest::SetAddressList(s1, addr); |
| 93 DeleteAddrInfo(addr); |
| 94 |
| 95 TestCompletionCallback callback_s1; |
| 96 EXPECT_EQ(OK, throttle->OnStartOpenConnection(s1, &callback_s1)); |
| 97 |
| 98 // For host2: 1.2.3.4 |
| 99 addr = AddAddr(1, 2, 3, 4, NULL); |
| 100 scoped_refptr<SocketStream> s2 = |
| 101 new SocketStream(GURL("ws://host2/"), &delegate); |
| 102 WebSocketThrottleTest::SetAddressList(s2, addr); |
| 103 DeleteAddrInfo(addr); |
| 104 |
| 105 TestCompletionCallback callback_s2; |
| 106 EXPECT_EQ(ERR_IO_PENDING, throttle->OnStartOpenConnection(s2, &callback_s2)); |
| 107 |
| 108 // For host3: 1.2.3.5 |
| 109 addr = AddAddr(1, 2, 3, 5, NULL); |
| 110 scoped_refptr<SocketStream> s3 = |
| 111 new SocketStream(GURL("ws://host3/"), &delegate); |
| 112 WebSocketThrottleTest::SetAddressList(s3, addr); |
| 113 DeleteAddrInfo(addr); |
| 114 |
| 115 TestCompletionCallback callback_s3; |
| 116 EXPECT_EQ(ERR_IO_PENDING, throttle->OnStartOpenConnection(s3, &callback_s3)); |
| 117 |
| 118 // For host4: 1.2.3.4, 1.2.3.6 |
| 119 addr = AddAddr(1, 2, 3, 4, NULL); |
| 120 addr = AddAddr(1, 2, 3, 6, addr); |
| 121 scoped_refptr<SocketStream> s4 = |
| 122 new SocketStream(GURL("ws://host4/"), &delegate); |
| 123 WebSocketThrottleTest::SetAddressList(s4, addr); |
| 124 DeleteAddrInfo(addr); |
| 125 |
| 126 TestCompletionCallback callback_s4; |
| 127 EXPECT_EQ(ERR_IO_PENDING, throttle->OnStartOpenConnection(s4, &callback_s4)); |
| 128 |
| 129 static const char kHeader[] = "HTTP/1.1 101 Web Socket Protocol\r\n"; |
| 130 EXPECT_EQ(OK, |
| 131 throttle->OnRead(s1.get(), kHeader, sizeof(kHeader) - 1, NULL)); |
| 132 EXPECT_FALSE(callback_s2.have_result()); |
| 133 EXPECT_FALSE(callback_s3.have_result()); |
| 134 EXPECT_FALSE(callback_s4.have_result()); |
| 135 |
| 136 static const char kHeader2[] = |
| 137 "Upgrade: WebSocket\r\n" |
| 138 "Connection: Upgrade\r\n" |
| 139 "WebSocket-Origin: http://www.google.com\r\n" |
| 140 "WebSocket-Location: ws://websocket.chromium.org\r\n" |
| 141 "\r\n"; |
| 142 EXPECT_EQ(OK, |
| 143 throttle->OnRead(s1.get(), kHeader2, sizeof(kHeader2) - 1, NULL)); |
| 144 MessageLoopForIO::current()->RunAllPending(); |
| 145 EXPECT_TRUE(callback_s2.have_result()); |
| 146 EXPECT_TRUE(callback_s3.have_result()); |
| 147 EXPECT_FALSE(callback_s4.have_result()); |
| 148 |
| 149 throttle->OnClose(s1.get()); |
| 150 MessageLoopForIO::current()->RunAllPending(); |
| 151 EXPECT_FALSE(callback_s4.have_result()); |
| 152 s1->DetachDelegate(); |
| 153 |
| 154 throttle->OnClose(s2.get()); |
| 155 MessageLoopForIO::current()->RunAllPending(); |
| 156 EXPECT_TRUE(callback_s4.have_result()); |
| 157 s2->DetachDelegate(); |
| 158 |
| 159 throttle->OnClose(s3.get()); |
| 160 MessageLoopForIO::current()->RunAllPending(); |
| 161 s3->DetachDelegate(); |
| 162 throttle->OnClose(s4.get()); |
| 163 s4->DetachDelegate(); |
| 164 } |
| 165 |
| 166 } |
OLD | NEW |