Fix variable shadowing warnings in UDPSocketWin on VS2015
[chromium-blink-merge.git] / net / socket / websocket_transport_client_socket_pool_unittest.cc
blob03bdf4390964baee2dadf9d265003241b90351e7
1 // Copyright 2014 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.
5 #include "net/socket/websocket_transport_client_socket_pool.h"
7 #include <queue>
8 #include <vector>
10 #include "base/bind.h"
11 #include "base/bind_helpers.h"
12 #include "base/callback.h"
13 #include "base/macros.h"
14 #include "base/message_loop/message_loop.h"
15 #include "base/run_loop.h"
16 #include "base/strings/stringprintf.h"
17 #include "base/time/time.h"
18 #include "net/base/capturing_net_log.h"
19 #include "net/base/ip_endpoint.h"
20 #include "net/base/load_timing_info.h"
21 #include "net/base/load_timing_info_test_util.h"
22 #include "net/base/net_errors.h"
23 #include "net/base/net_util.h"
24 #include "net/base/test_completion_callback.h"
25 #include "net/dns/mock_host_resolver.h"
26 #include "net/socket/client_socket_handle.h"
27 #include "net/socket/client_socket_pool_histograms.h"
28 #include "net/socket/socket_test_util.h"
29 #include "net/socket/stream_socket.h"
30 #include "net/socket/transport_client_socket_pool_test_util.h"
31 #include "net/socket/websocket_endpoint_lock_manager.h"
32 #include "testing/gtest/include/gtest/gtest.h"
34 namespace net {
36 namespace {
38 const int kMaxSockets = 32;
39 const int kMaxSocketsPerGroup = 6;
40 const RequestPriority kDefaultPriority = LOW;
42 // RunLoop doesn't support this natively but it is easy to emulate.
43 void RunLoopForTimePeriod(base::TimeDelta period) {
44 base::RunLoop run_loop;
45 base::Closure quit_closure(run_loop.QuitClosure());
46 base::MessageLoop::current()->PostDelayedTask(
47 FROM_HERE, quit_closure, period);
48 run_loop.Run();
51 class WebSocketTransportClientSocketPoolTest : public ::testing::Test {
52 protected:
53 WebSocketTransportClientSocketPoolTest()
54 : params_(new TransportSocketParams(
55 HostPortPair("www.google.com", 80),
56 false,
57 false,
58 OnHostResolutionCallback(),
59 TransportSocketParams::COMBINE_CONNECT_AND_WRITE_DEFAULT)),
60 histograms_(new ClientSocketPoolHistograms("TCPUnitTest")),
61 host_resolver_(new MockHostResolver),
62 client_socket_factory_(&net_log_),
63 pool_(kMaxSockets,
64 kMaxSocketsPerGroup,
65 histograms_.get(),
66 host_resolver_.get(),
67 &client_socket_factory_,
68 NULL) {}
70 ~WebSocketTransportClientSocketPoolTest() override {
71 RunUntilIdle();
72 // ReleaseAllConnections() calls RunUntilIdle() after releasing each
73 // connection.
74 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
75 EXPECT_TRUE(WebSocketEndpointLockManager::GetInstance()->IsEmpty());
78 static void RunUntilIdle() { base::RunLoop().RunUntilIdle(); }
80 int StartRequest(const std::string& group_name, RequestPriority priority) {
81 scoped_refptr<TransportSocketParams> params(
82 new TransportSocketParams(
83 HostPortPair("www.google.com", 80),
84 false,
85 false,
86 OnHostResolutionCallback(),
87 TransportSocketParams::COMBINE_CONNECT_AND_WRITE_DEFAULT));
88 return test_base_.StartRequestUsingPool(
89 &pool_, group_name, priority, params);
92 int GetOrderOfRequest(size_t index) {
93 return test_base_.GetOrderOfRequest(index);
96 bool ReleaseOneConnection(ClientSocketPoolTest::KeepAlive keep_alive) {
97 return test_base_.ReleaseOneConnection(keep_alive);
100 void ReleaseAllConnections(ClientSocketPoolTest::KeepAlive keep_alive) {
101 test_base_.ReleaseAllConnections(keep_alive);
104 TestSocketRequest* request(int i) { return test_base_.request(i); }
106 ScopedVector<TestSocketRequest>* requests() { return test_base_.requests(); }
107 size_t completion_count() const { return test_base_.completion_count(); }
109 CapturingNetLog net_log_;
110 scoped_refptr<TransportSocketParams> params_;
111 scoped_ptr<ClientSocketPoolHistograms> histograms_;
112 scoped_ptr<MockHostResolver> host_resolver_;
113 MockTransportClientSocketFactory client_socket_factory_;
114 WebSocketTransportClientSocketPool pool_;
115 ClientSocketPoolTest test_base_;
116 ScopedWebSocketEndpointZeroUnlockDelay zero_unlock_delay_;
118 private:
119 DISALLOW_COPY_AND_ASSIGN(WebSocketTransportClientSocketPoolTest);
122 TEST_F(WebSocketTransportClientSocketPoolTest, Basic) {
123 TestCompletionCallback callback;
124 ClientSocketHandle handle;
125 int rv = handle.Init(
126 "a", params_, LOW, callback.callback(), &pool_, BoundNetLog());
127 EXPECT_EQ(ERR_IO_PENDING, rv);
128 EXPECT_FALSE(handle.is_initialized());
129 EXPECT_FALSE(handle.socket());
131 EXPECT_EQ(OK, callback.WaitForResult());
132 EXPECT_TRUE(handle.is_initialized());
133 EXPECT_TRUE(handle.socket());
134 TestLoadTimingInfoConnectedNotReused(handle);
137 // Make sure that WebSocketTransportConnectJob passes on its priority to its
138 // HostResolver request on Init.
139 TEST_F(WebSocketTransportClientSocketPoolTest, SetResolvePriorityOnInit) {
140 for (int i = MINIMUM_PRIORITY; i <= MAXIMUM_PRIORITY; ++i) {
141 RequestPriority priority = static_cast<RequestPriority>(i);
142 TestCompletionCallback callback;
143 ClientSocketHandle handle;
144 EXPECT_EQ(ERR_IO_PENDING,
145 handle.Init("a",
146 params_,
147 priority,
148 callback.callback(),
149 &pool_,
150 BoundNetLog()));
151 EXPECT_EQ(priority, host_resolver_->last_request_priority());
155 TEST_F(WebSocketTransportClientSocketPoolTest, InitHostResolutionFailure) {
156 host_resolver_->rules()->AddSimulatedFailure("unresolvable.host.name");
157 TestCompletionCallback callback;
158 ClientSocketHandle handle;
159 HostPortPair host_port_pair("unresolvable.host.name", 80);
160 scoped_refptr<TransportSocketParams> dest(new TransportSocketParams(
161 host_port_pair, false, false, OnHostResolutionCallback(),
162 TransportSocketParams::COMBINE_CONNECT_AND_WRITE_DEFAULT));
163 EXPECT_EQ(ERR_IO_PENDING,
164 handle.Init("a",
165 dest,
166 kDefaultPriority,
167 callback.callback(),
168 &pool_,
169 BoundNetLog()));
170 EXPECT_EQ(ERR_NAME_NOT_RESOLVED, callback.WaitForResult());
173 TEST_F(WebSocketTransportClientSocketPoolTest, InitConnectionFailure) {
174 client_socket_factory_.set_default_client_socket_type(
175 MockTransportClientSocketFactory::MOCK_FAILING_CLIENT_SOCKET);
176 TestCompletionCallback callback;
177 ClientSocketHandle handle;
178 EXPECT_EQ(ERR_IO_PENDING,
179 handle.Init("a",
180 params_,
181 kDefaultPriority,
182 callback.callback(),
183 &pool_,
184 BoundNetLog()));
185 EXPECT_EQ(ERR_CONNECTION_FAILED, callback.WaitForResult());
187 // Make the host resolutions complete synchronously this time.
188 host_resolver_->set_synchronous_mode(true);
189 EXPECT_EQ(ERR_CONNECTION_FAILED,
190 handle.Init("a",
191 params_,
192 kDefaultPriority,
193 callback.callback(),
194 &pool_,
195 BoundNetLog()));
198 TEST_F(WebSocketTransportClientSocketPoolTest, PendingRequestsFinishFifo) {
199 // First request finishes asynchronously.
200 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
201 EXPECT_EQ(OK, request(0)->WaitForResult());
203 // Make all subsequent host resolutions complete synchronously.
204 host_resolver_->set_synchronous_mode(true);
206 // Rest of them wait for the first socket to be released.
207 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
208 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
209 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
210 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
211 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
213 ReleaseAllConnections(ClientSocketPoolTest::KEEP_ALIVE);
215 EXPECT_EQ(6, client_socket_factory_.allocation_count());
217 // One initial asynchronous request and then 5 pending requests.
218 EXPECT_EQ(6U, completion_count());
220 // The requests finish in FIFO order.
221 EXPECT_EQ(1, GetOrderOfRequest(1));
222 EXPECT_EQ(2, GetOrderOfRequest(2));
223 EXPECT_EQ(3, GetOrderOfRequest(3));
224 EXPECT_EQ(4, GetOrderOfRequest(4));
225 EXPECT_EQ(5, GetOrderOfRequest(5));
226 EXPECT_EQ(6, GetOrderOfRequest(6));
228 // Make sure we test order of all requests made.
229 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(7));
232 TEST_F(WebSocketTransportClientSocketPoolTest, PendingRequests_NoKeepAlive) {
233 // First request finishes asynchronously.
234 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
235 EXPECT_EQ(OK, request(0)->WaitForResult());
237 // Make all subsequent host resolutions complete synchronously.
238 host_resolver_->set_synchronous_mode(true);
240 // Rest of them wait for the first socket to be released.
241 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
242 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
243 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
244 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
245 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
247 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
249 // The pending requests should finish successfully.
250 EXPECT_EQ(OK, request(1)->WaitForResult());
251 EXPECT_EQ(OK, request(2)->WaitForResult());
252 EXPECT_EQ(OK, request(3)->WaitForResult());
253 EXPECT_EQ(OK, request(4)->WaitForResult());
254 EXPECT_EQ(OK, request(5)->WaitForResult());
256 EXPECT_EQ(static_cast<int>(requests()->size()),
257 client_socket_factory_.allocation_count());
259 // First asynchronous request, and then last 5 pending requests.
260 EXPECT_EQ(6U, completion_count());
263 // This test will start up a RequestSocket() and then immediately Cancel() it.
264 // The pending host resolution will eventually complete, and destroy the
265 // ClientSocketPool which will crash if the group was not cleared properly.
266 TEST_F(WebSocketTransportClientSocketPoolTest, CancelRequestClearGroup) {
267 TestCompletionCallback callback;
268 ClientSocketHandle handle;
269 EXPECT_EQ(ERR_IO_PENDING,
270 handle.Init("a",
271 params_,
272 kDefaultPriority,
273 callback.callback(),
274 &pool_,
275 BoundNetLog()));
276 handle.Reset();
279 TEST_F(WebSocketTransportClientSocketPoolTest, TwoRequestsCancelOne) {
280 ClientSocketHandle handle;
281 TestCompletionCallback callback;
282 ClientSocketHandle handle2;
283 TestCompletionCallback callback2;
285 EXPECT_EQ(ERR_IO_PENDING,
286 handle.Init("a",
287 params_,
288 kDefaultPriority,
289 callback.callback(),
290 &pool_,
291 BoundNetLog()));
292 EXPECT_EQ(ERR_IO_PENDING,
293 handle2.Init("a",
294 params_,
295 kDefaultPriority,
296 callback2.callback(),
297 &pool_,
298 BoundNetLog()));
300 handle.Reset();
302 EXPECT_EQ(OK, callback2.WaitForResult());
303 handle2.Reset();
306 TEST_F(WebSocketTransportClientSocketPoolTest, ConnectCancelConnect) {
307 client_socket_factory_.set_default_client_socket_type(
308 MockTransportClientSocketFactory::MOCK_PENDING_CLIENT_SOCKET);
309 ClientSocketHandle handle;
310 TestCompletionCallback callback;
311 EXPECT_EQ(ERR_IO_PENDING,
312 handle.Init("a",
313 params_,
314 kDefaultPriority,
315 callback.callback(),
316 &pool_,
317 BoundNetLog()));
319 handle.Reset();
321 TestCompletionCallback callback2;
322 EXPECT_EQ(ERR_IO_PENDING,
323 handle.Init("a",
324 params_,
325 kDefaultPriority,
326 callback2.callback(),
327 &pool_,
328 BoundNetLog()));
330 host_resolver_->set_synchronous_mode(true);
331 // At this point, handle has two ConnectingSockets out for it. Due to the
332 // setting the mock resolver into synchronous mode, the host resolution for
333 // both will return in the same loop of the MessageLoop. The client socket
334 // is a pending socket, so the Connect() will asynchronously complete on the
335 // next loop of the MessageLoop. That means that the first
336 // ConnectingSocket will enter OnIOComplete, and then the second one will.
337 // If the first one is not cancelled, it will advance the load state, and
338 // then the second one will crash.
340 EXPECT_EQ(OK, callback2.WaitForResult());
341 EXPECT_FALSE(callback.have_result());
343 handle.Reset();
346 TEST_F(WebSocketTransportClientSocketPoolTest, CancelRequest) {
347 // First request finishes asynchronously.
348 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
349 EXPECT_EQ(OK, request(0)->WaitForResult());
351 // Make all subsequent host resolutions complete synchronously.
352 host_resolver_->set_synchronous_mode(true);
354 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
355 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
356 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
357 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
358 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
360 // Cancel a request.
361 const size_t index_to_cancel = 2;
362 EXPECT_FALSE(request(index_to_cancel)->handle()->is_initialized());
363 request(index_to_cancel)->handle()->Reset();
365 ReleaseAllConnections(ClientSocketPoolTest::KEEP_ALIVE);
367 EXPECT_EQ(5, client_socket_factory_.allocation_count());
369 EXPECT_EQ(1, GetOrderOfRequest(1));
370 EXPECT_EQ(2, GetOrderOfRequest(2));
371 EXPECT_EQ(ClientSocketPoolTest::kRequestNotFound,
372 GetOrderOfRequest(3)); // Canceled request.
373 EXPECT_EQ(3, GetOrderOfRequest(4));
374 EXPECT_EQ(4, GetOrderOfRequest(5));
375 EXPECT_EQ(5, GetOrderOfRequest(6));
377 // Make sure we test order of all requests made.
378 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(7));
381 class RequestSocketCallback : public TestCompletionCallbackBase {
382 public:
383 RequestSocketCallback(ClientSocketHandle* handle,
384 WebSocketTransportClientSocketPool* pool)
385 : handle_(handle),
386 pool_(pool),
387 within_callback_(false),
388 callback_(base::Bind(&RequestSocketCallback::OnComplete,
389 base::Unretained(this))) {}
391 ~RequestSocketCallback() override {}
393 const CompletionCallback& callback() const { return callback_; }
395 private:
396 void OnComplete(int result) {
397 SetResult(result);
398 ASSERT_EQ(OK, result);
400 if (!within_callback_) {
401 // Don't allow reuse of the socket. Disconnect it and then release it and
402 // run through the MessageLoop once to get it completely released.
403 handle_->socket()->Disconnect();
404 handle_->Reset();
406 base::MessageLoop::ScopedNestableTaskAllower allow(
407 base::MessageLoop::current());
408 base::MessageLoop::current()->RunUntilIdle();
410 within_callback_ = true;
411 scoped_refptr<TransportSocketParams> dest(
412 new TransportSocketParams(
413 HostPortPair("www.google.com", 80),
414 false,
415 false,
416 OnHostResolutionCallback(),
417 TransportSocketParams::COMBINE_CONNECT_AND_WRITE_DEFAULT));
418 int rv =
419 handle_->Init("a", dest, LOWEST, callback(), pool_, BoundNetLog());
420 EXPECT_EQ(OK, rv);
424 ClientSocketHandle* const handle_;
425 WebSocketTransportClientSocketPool* const pool_;
426 bool within_callback_;
427 CompletionCallback callback_;
429 DISALLOW_COPY_AND_ASSIGN(RequestSocketCallback);
432 TEST_F(WebSocketTransportClientSocketPoolTest, RequestTwice) {
433 ClientSocketHandle handle;
434 RequestSocketCallback callback(&handle, &pool_);
435 scoped_refptr<TransportSocketParams> dest(
436 new TransportSocketParams(
437 HostPortPair("www.google.com", 80),
438 false,
439 false,
440 OnHostResolutionCallback(),
441 TransportSocketParams::COMBINE_CONNECT_AND_WRITE_DEFAULT));
442 int rv = handle.Init(
443 "a", dest, LOWEST, callback.callback(), &pool_, BoundNetLog());
444 ASSERT_EQ(ERR_IO_PENDING, rv);
446 // The callback is going to request "www.google.com". We want it to complete
447 // synchronously this time.
448 host_resolver_->set_synchronous_mode(true);
450 EXPECT_EQ(OK, callback.WaitForResult());
452 handle.Reset();
455 // Make sure that pending requests get serviced after active requests get
456 // cancelled.
457 TEST_F(WebSocketTransportClientSocketPoolTest,
458 CancelActiveRequestWithPendingRequests) {
459 client_socket_factory_.set_default_client_socket_type(
460 MockTransportClientSocketFactory::MOCK_PENDING_CLIENT_SOCKET);
462 // Queue up all the requests
463 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
464 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
465 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
466 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
467 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
468 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
469 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
470 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
471 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
473 // Now, kMaxSocketsPerGroup requests should be active. Let's cancel them.
474 ASSERT_LE(kMaxSocketsPerGroup, static_cast<int>(requests()->size()));
475 for (int i = 0; i < kMaxSocketsPerGroup; i++)
476 request(i)->handle()->Reset();
478 // Let's wait for the rest to complete now.
479 for (size_t i = kMaxSocketsPerGroup; i < requests()->size(); ++i) {
480 EXPECT_EQ(OK, request(i)->WaitForResult());
481 request(i)->handle()->Reset();
484 EXPECT_EQ(requests()->size() - kMaxSocketsPerGroup, completion_count());
487 // Make sure that pending requests get serviced after active requests fail.
488 TEST_F(WebSocketTransportClientSocketPoolTest,
489 FailingActiveRequestWithPendingRequests) {
490 client_socket_factory_.set_default_client_socket_type(
491 MockTransportClientSocketFactory::MOCK_PENDING_FAILING_CLIENT_SOCKET);
493 const int kNumRequests = 2 * kMaxSocketsPerGroup + 1;
494 ASSERT_LE(kNumRequests, kMaxSockets); // Otherwise the test will hang.
496 // Queue up all the requests
497 for (int i = 0; i < kNumRequests; i++)
498 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
500 for (int i = 0; i < kNumRequests; i++)
501 EXPECT_EQ(ERR_CONNECTION_FAILED, request(i)->WaitForResult());
504 // The lock on the endpoint is released when a ClientSocketHandle is reset.
505 TEST_F(WebSocketTransportClientSocketPoolTest, LockReleasedOnHandleReset) {
506 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
507 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
508 EXPECT_EQ(OK, request(0)->WaitForResult());
509 EXPECT_FALSE(request(1)->handle()->is_initialized());
510 request(0)->handle()->Reset();
511 RunUntilIdle();
512 EXPECT_TRUE(request(1)->handle()->is_initialized());
515 // The lock on the endpoint is released when a ClientSocketHandle is deleted.
516 TEST_F(WebSocketTransportClientSocketPoolTest, LockReleasedOnHandleDelete) {
517 TestCompletionCallback callback;
518 scoped_ptr<ClientSocketHandle> handle(new ClientSocketHandle);
519 int rv = handle->Init(
520 "a", params_, LOW, callback.callback(), &pool_, BoundNetLog());
521 EXPECT_EQ(ERR_IO_PENDING, rv);
523 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
524 EXPECT_EQ(OK, callback.WaitForResult());
525 EXPECT_FALSE(request(0)->handle()->is_initialized());
526 handle.reset();
527 RunUntilIdle();
528 EXPECT_TRUE(request(0)->handle()->is_initialized());
531 // A new connection is performed when the lock on the previous connection is
532 // explicitly released.
533 TEST_F(WebSocketTransportClientSocketPoolTest,
534 ConnectionProceedsOnExplicitRelease) {
535 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
536 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
537 EXPECT_EQ(OK, request(0)->WaitForResult());
538 EXPECT_FALSE(request(1)->handle()->is_initialized());
539 WebSocketTransportClientSocketPool::UnlockEndpoint(request(0)->handle());
540 RunUntilIdle();
541 EXPECT_TRUE(request(1)->handle()->is_initialized());
544 // A connection which is cancelled before completion does not block subsequent
545 // connections.
546 TEST_F(WebSocketTransportClientSocketPoolTest,
547 CancelDuringConnectionReleasesLock) {
548 MockTransportClientSocketFactory::ClientSocketType case_types[] = {
549 MockTransportClientSocketFactory::MOCK_STALLED_CLIENT_SOCKET,
550 MockTransportClientSocketFactory::MOCK_PENDING_CLIENT_SOCKET};
552 client_socket_factory_.set_client_socket_types(case_types,
553 arraysize(case_types));
555 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
556 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
557 RunUntilIdle();
558 pool_.CancelRequest("a", request(0)->handle());
559 EXPECT_EQ(OK, request(1)->WaitForResult());
562 // Test the case of the IPv6 address stalling, and falling back to the IPv4
563 // socket which finishes first.
564 TEST_F(WebSocketTransportClientSocketPoolTest,
565 IPv6FallbackSocketIPv4FinishesFirst) {
566 WebSocketTransportClientSocketPool pool(kMaxSockets,
567 kMaxSocketsPerGroup,
568 histograms_.get(),
569 host_resolver_.get(),
570 &client_socket_factory_,
571 NULL);
573 MockTransportClientSocketFactory::ClientSocketType case_types[] = {
574 // This is the IPv6 socket.
575 MockTransportClientSocketFactory::MOCK_STALLED_CLIENT_SOCKET,
576 // This is the IPv4 socket.
577 MockTransportClientSocketFactory::MOCK_PENDING_CLIENT_SOCKET};
579 client_socket_factory_.set_client_socket_types(case_types, 2);
581 // Resolve an AddressList with an IPv6 address first and then an IPv4 address.
582 host_resolver_->rules()->AddIPLiteralRule(
583 "*", "2:abcd::3:4:ff,2.2.2.2", std::string());
585 TestCompletionCallback callback;
586 ClientSocketHandle handle;
587 int rv =
588 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
589 EXPECT_EQ(ERR_IO_PENDING, rv);
590 EXPECT_FALSE(handle.is_initialized());
591 EXPECT_FALSE(handle.socket());
593 EXPECT_EQ(OK, callback.WaitForResult());
594 EXPECT_TRUE(handle.is_initialized());
595 EXPECT_TRUE(handle.socket());
596 IPEndPoint endpoint;
597 handle.socket()->GetLocalAddress(&endpoint);
598 EXPECT_EQ(kIPv4AddressSize, endpoint.address().size());
599 EXPECT_EQ(2, client_socket_factory_.allocation_count());
602 // Test the case of the IPv6 address being slow, thus falling back to trying to
603 // connect to the IPv4 address, but having the connect to the IPv6 address
604 // finish first.
605 TEST_F(WebSocketTransportClientSocketPoolTest,
606 IPv6FallbackSocketIPv6FinishesFirst) {
607 WebSocketTransportClientSocketPool pool(kMaxSockets,
608 kMaxSocketsPerGroup,
609 histograms_.get(),
610 host_resolver_.get(),
611 &client_socket_factory_,
612 NULL);
614 MockTransportClientSocketFactory::ClientSocketType case_types[] = {
615 // This is the IPv6 socket.
616 MockTransportClientSocketFactory::MOCK_DELAYED_CLIENT_SOCKET,
617 // This is the IPv4 socket.
618 MockTransportClientSocketFactory::MOCK_STALLED_CLIENT_SOCKET};
620 client_socket_factory_.set_client_socket_types(case_types, 2);
621 client_socket_factory_.set_delay(base::TimeDelta::FromMilliseconds(
622 TransportConnectJobHelper::kIPv6FallbackTimerInMs + 50));
624 // Resolve an AddressList with an IPv6 address first and then an IPv4 address.
625 host_resolver_->rules()->AddIPLiteralRule(
626 "*", "2:abcd::3:4:ff,2.2.2.2", std::string());
628 TestCompletionCallback callback;
629 ClientSocketHandle handle;
630 int rv =
631 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
632 EXPECT_EQ(ERR_IO_PENDING, rv);
633 EXPECT_FALSE(handle.is_initialized());
634 EXPECT_FALSE(handle.socket());
636 EXPECT_EQ(OK, callback.WaitForResult());
637 EXPECT_TRUE(handle.is_initialized());
638 EXPECT_TRUE(handle.socket());
639 IPEndPoint endpoint;
640 handle.socket()->GetLocalAddress(&endpoint);
641 EXPECT_EQ(kIPv6AddressSize, endpoint.address().size());
642 EXPECT_EQ(2, client_socket_factory_.allocation_count());
645 TEST_F(WebSocketTransportClientSocketPoolTest,
646 IPv6NoIPv4AddressesToFallbackTo) {
647 WebSocketTransportClientSocketPool pool(kMaxSockets,
648 kMaxSocketsPerGroup,
649 histograms_.get(),
650 host_resolver_.get(),
651 &client_socket_factory_,
652 NULL);
654 client_socket_factory_.set_default_client_socket_type(
655 MockTransportClientSocketFactory::MOCK_DELAYED_CLIENT_SOCKET);
657 // Resolve an AddressList with only IPv6 addresses.
658 host_resolver_->rules()->AddIPLiteralRule(
659 "*", "2:abcd::3:4:ff,3:abcd::3:4:ff", std::string());
661 TestCompletionCallback callback;
662 ClientSocketHandle handle;
663 int rv =
664 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
665 EXPECT_EQ(ERR_IO_PENDING, rv);
666 EXPECT_FALSE(handle.is_initialized());
667 EXPECT_FALSE(handle.socket());
669 EXPECT_EQ(OK, callback.WaitForResult());
670 EXPECT_TRUE(handle.is_initialized());
671 EXPECT_TRUE(handle.socket());
672 IPEndPoint endpoint;
673 handle.socket()->GetLocalAddress(&endpoint);
674 EXPECT_EQ(kIPv6AddressSize, endpoint.address().size());
675 EXPECT_EQ(1, client_socket_factory_.allocation_count());
678 TEST_F(WebSocketTransportClientSocketPoolTest, IPv4HasNoFallback) {
679 WebSocketTransportClientSocketPool pool(kMaxSockets,
680 kMaxSocketsPerGroup,
681 histograms_.get(),
682 host_resolver_.get(),
683 &client_socket_factory_,
684 NULL);
686 client_socket_factory_.set_default_client_socket_type(
687 MockTransportClientSocketFactory::MOCK_DELAYED_CLIENT_SOCKET);
689 // Resolve an AddressList with only IPv4 addresses.
690 host_resolver_->rules()->AddIPLiteralRule("*", "1.1.1.1", std::string());
692 TestCompletionCallback callback;
693 ClientSocketHandle handle;
694 int rv =
695 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
696 EXPECT_EQ(ERR_IO_PENDING, rv);
697 EXPECT_FALSE(handle.is_initialized());
698 EXPECT_FALSE(handle.socket());
700 EXPECT_EQ(OK, callback.WaitForResult());
701 EXPECT_TRUE(handle.is_initialized());
702 EXPECT_TRUE(handle.socket());
703 IPEndPoint endpoint;
704 handle.socket()->GetLocalAddress(&endpoint);
705 EXPECT_EQ(kIPv4AddressSize, endpoint.address().size());
706 EXPECT_EQ(1, client_socket_factory_.allocation_count());
709 // If all IPv6 addresses fail to connect synchronously, then IPv4 connections
710 // proceeed immediately.
711 TEST_F(WebSocketTransportClientSocketPoolTest, IPv6InstantFail) {
712 WebSocketTransportClientSocketPool pool(kMaxSockets,
713 kMaxSocketsPerGroup,
714 histograms_.get(),
715 host_resolver_.get(),
716 &client_socket_factory_,
717 NULL);
719 MockTransportClientSocketFactory::ClientSocketType case_types[] = {
720 // First IPv6 socket.
721 MockTransportClientSocketFactory::MOCK_FAILING_CLIENT_SOCKET,
722 // Second IPv6 socket.
723 MockTransportClientSocketFactory::MOCK_FAILING_CLIENT_SOCKET,
724 // This is the IPv4 socket.
725 MockTransportClientSocketFactory::MOCK_CLIENT_SOCKET};
727 client_socket_factory_.set_client_socket_types(case_types,
728 arraysize(case_types));
730 // Resolve an AddressList with two IPv6 addresses and then an IPv4 address.
731 host_resolver_->rules()->AddIPLiteralRule(
732 "*", "2:abcd::3:4:ff,2:abcd::3:5:ff,2.2.2.2", std::string());
733 host_resolver_->set_synchronous_mode(true);
734 TestCompletionCallback callback;
735 ClientSocketHandle handle;
736 int rv =
737 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
738 EXPECT_EQ(OK, rv);
739 ASSERT_TRUE(handle.socket());
741 IPEndPoint endpoint;
742 handle.socket()->GetPeerAddress(&endpoint);
743 EXPECT_EQ("2.2.2.2", endpoint.ToStringWithoutPort());
746 // If all IPv6 addresses fail before the IPv4 fallback timeout, then the IPv4
747 // connections proceed immediately.
748 TEST_F(WebSocketTransportClientSocketPoolTest, IPv6RapidFail) {
749 WebSocketTransportClientSocketPool pool(kMaxSockets,
750 kMaxSocketsPerGroup,
751 histograms_.get(),
752 host_resolver_.get(),
753 &client_socket_factory_,
754 NULL);
756 MockTransportClientSocketFactory::ClientSocketType case_types[] = {
757 // First IPv6 socket.
758 MockTransportClientSocketFactory::MOCK_PENDING_FAILING_CLIENT_SOCKET,
759 // Second IPv6 socket.
760 MockTransportClientSocketFactory::MOCK_PENDING_FAILING_CLIENT_SOCKET,
761 // This is the IPv4 socket.
762 MockTransportClientSocketFactory::MOCK_CLIENT_SOCKET};
764 client_socket_factory_.set_client_socket_types(case_types,
765 arraysize(case_types));
767 // Resolve an AddressList with two IPv6 addresses and then an IPv4 address.
768 host_resolver_->rules()->AddIPLiteralRule(
769 "*", "2:abcd::3:4:ff,2:abcd::3:5:ff,2.2.2.2", std::string());
771 TestCompletionCallback callback;
772 ClientSocketHandle handle;
773 int rv =
774 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
775 EXPECT_EQ(ERR_IO_PENDING, rv);
776 EXPECT_FALSE(handle.socket());
778 base::Time start(base::Time::NowFromSystemTime());
779 EXPECT_EQ(OK, callback.WaitForResult());
780 EXPECT_LT(base::Time::NowFromSystemTime() - start,
781 base::TimeDelta::FromMilliseconds(
782 TransportConnectJobHelper::kIPv6FallbackTimerInMs));
783 ASSERT_TRUE(handle.socket());
785 IPEndPoint endpoint;
786 handle.socket()->GetPeerAddress(&endpoint);
787 EXPECT_EQ("2.2.2.2", endpoint.ToStringWithoutPort());
790 // If two sockets connect successfully, the one which connected first wins (this
791 // can only happen if the sockets are different types, since sockets of the same
792 // type do not race).
793 TEST_F(WebSocketTransportClientSocketPoolTest, FirstSuccessWins) {
794 WebSocketTransportClientSocketPool pool(kMaxSockets,
795 kMaxSocketsPerGroup,
796 histograms_.get(),
797 host_resolver_.get(),
798 &client_socket_factory_,
799 NULL);
801 client_socket_factory_.set_default_client_socket_type(
802 MockTransportClientSocketFactory::MOCK_TRIGGERABLE_CLIENT_SOCKET);
804 // Resolve an AddressList with an IPv6 addresses and an IPv4 address.
805 host_resolver_->rules()->AddIPLiteralRule(
806 "*", "2:abcd::3:4:ff,2.2.2.2", std::string());
808 TestCompletionCallback callback;
809 ClientSocketHandle handle;
810 int rv =
811 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
812 EXPECT_EQ(ERR_IO_PENDING, rv);
813 ASSERT_FALSE(handle.socket());
815 base::Closure ipv6_connect_trigger =
816 client_socket_factory_.WaitForTriggerableSocketCreation();
817 base::Closure ipv4_connect_trigger =
818 client_socket_factory_.WaitForTriggerableSocketCreation();
820 ipv4_connect_trigger.Run();
821 ipv6_connect_trigger.Run();
823 EXPECT_EQ(OK, callback.WaitForResult());
824 ASSERT_TRUE(handle.socket());
826 IPEndPoint endpoint;
827 handle.socket()->GetPeerAddress(&endpoint);
828 EXPECT_EQ("2.2.2.2", endpoint.ToStringWithoutPort());
831 // We should not report failure until all connections have failed.
832 TEST_F(WebSocketTransportClientSocketPoolTest, LastFailureWins) {
833 WebSocketTransportClientSocketPool pool(kMaxSockets,
834 kMaxSocketsPerGroup,
835 histograms_.get(),
836 host_resolver_.get(),
837 &client_socket_factory_,
838 NULL);
840 client_socket_factory_.set_default_client_socket_type(
841 MockTransportClientSocketFactory::MOCK_DELAYED_FAILING_CLIENT_SOCKET);
842 base::TimeDelta delay = base::TimeDelta::FromMilliseconds(
843 TransportConnectJobHelper::kIPv6FallbackTimerInMs / 3);
844 client_socket_factory_.set_delay(delay);
846 // Resolve an AddressList with 4 IPv6 addresses and 2 IPv4 addresses.
847 host_resolver_->rules()->AddIPLiteralRule("*",
848 "1:abcd::3:4:ff,2:abcd::3:4:ff,"
849 "3:abcd::3:4:ff,4:abcd::3:4:ff,"
850 "1.1.1.1,2.2.2.2",
851 std::string());
853 // Expected order of events:
854 // After 100ms: Connect to 1:abcd::3:4:ff times out
855 // After 200ms: Connect to 2:abcd::3:4:ff times out
856 // After 300ms: Connect to 3:abcd::3:4:ff times out, IPv4 fallback starts
857 // After 400ms: Connect to 4:abcd::3:4:ff and 1.1.1.1 time out
858 // After 500ms: Connect to 2.2.2.2 times out
860 TestCompletionCallback callback;
861 ClientSocketHandle handle;
862 base::Time start(base::Time::NowFromSystemTime());
863 int rv =
864 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
865 EXPECT_EQ(ERR_IO_PENDING, rv);
867 EXPECT_EQ(ERR_CONNECTION_FAILED, callback.WaitForResult());
869 EXPECT_GE(base::Time::NowFromSystemTime() - start, delay * 5);
872 // Global timeout for all connects applies. This test is disabled by default
873 // because it takes 4 minutes. Run with --gtest_also_run_disabled_tests if you
874 // want to run it.
875 TEST_F(WebSocketTransportClientSocketPoolTest, DISABLED_OverallTimeoutApplies) {
876 WebSocketTransportClientSocketPool pool(kMaxSockets,
877 kMaxSocketsPerGroup,
878 histograms_.get(),
879 host_resolver_.get(),
880 &client_socket_factory_,
881 NULL);
882 const base::TimeDelta connect_job_timeout = pool.ConnectionTimeout();
884 client_socket_factory_.set_default_client_socket_type(
885 MockTransportClientSocketFactory::MOCK_DELAYED_FAILING_CLIENT_SOCKET);
886 client_socket_factory_.set_delay(base::TimeDelta::FromSeconds(1) +
887 connect_job_timeout / 6);
889 // Resolve an AddressList with 6 IPv6 addresses and 6 IPv4 addresses.
890 host_resolver_->rules()->AddIPLiteralRule("*",
891 "1:abcd::3:4:ff,2:abcd::3:4:ff,"
892 "3:abcd::3:4:ff,4:abcd::3:4:ff,"
893 "5:abcd::3:4:ff,6:abcd::3:4:ff,"
894 "1.1.1.1,2.2.2.2,3.3.3.3,"
895 "4.4.4.4,5.5.5.5,6.6.6.6",
896 std::string());
898 TestCompletionCallback callback;
899 ClientSocketHandle handle;
901 int rv =
902 handle.Init("a", params_, LOW, callback.callback(), &pool, BoundNetLog());
903 EXPECT_EQ(ERR_IO_PENDING, rv);
905 EXPECT_EQ(ERR_TIMED_OUT, callback.WaitForResult());
908 TEST_F(WebSocketTransportClientSocketPoolTest, MaxSocketsEnforced) {
909 host_resolver_->set_synchronous_mode(true);
910 for (int i = 0; i < kMaxSockets; ++i) {
911 ASSERT_EQ(OK, StartRequest("a", kDefaultPriority));
912 WebSocketTransportClientSocketPool::UnlockEndpoint(request(i)->handle());
913 RunUntilIdle();
915 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
918 TEST_F(WebSocketTransportClientSocketPoolTest, MaxSocketsEnforcedWhenPending) {
919 for (int i = 0; i < kMaxSockets + 1; ++i) {
920 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
922 // Now there are 32 sockets waiting to connect, and one stalled.
923 for (int i = 0; i < kMaxSockets; ++i) {
924 RunUntilIdle();
925 EXPECT_TRUE(request(i)->handle()->is_initialized());
926 EXPECT_TRUE(request(i)->handle()->socket());
927 WebSocketTransportClientSocketPool::UnlockEndpoint(request(i)->handle());
929 // Now there are 32 sockets connected, and one stalled.
930 RunUntilIdle();
931 EXPECT_FALSE(request(kMaxSockets)->handle()->is_initialized());
932 EXPECT_FALSE(request(kMaxSockets)->handle()->socket());
935 TEST_F(WebSocketTransportClientSocketPoolTest, StalledSocketReleased) {
936 host_resolver_->set_synchronous_mode(true);
937 for (int i = 0; i < kMaxSockets; ++i) {
938 ASSERT_EQ(OK, StartRequest("a", kDefaultPriority));
939 WebSocketTransportClientSocketPool::UnlockEndpoint(request(i)->handle());
940 RunUntilIdle();
943 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
944 ReleaseOneConnection(ClientSocketPoolTest::NO_KEEP_ALIVE);
945 EXPECT_TRUE(request(kMaxSockets)->handle()->is_initialized());
946 EXPECT_TRUE(request(kMaxSockets)->handle()->socket());
949 TEST_F(WebSocketTransportClientSocketPoolTest, IsStalledTrueWhenStalled) {
950 for (int i = 0; i < kMaxSockets + 1; ++i) {
951 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
953 EXPECT_EQ(OK, request(0)->WaitForResult());
954 EXPECT_TRUE(pool_.IsStalled());
957 TEST_F(WebSocketTransportClientSocketPoolTest,
958 CancellingPendingSocketUnstallsStalledSocket) {
959 for (int i = 0; i < kMaxSockets + 1; ++i) {
960 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
962 EXPECT_EQ(OK, request(0)->WaitForResult());
963 request(1)->handle()->Reset();
964 RunUntilIdle();
965 EXPECT_FALSE(pool_.IsStalled());
968 TEST_F(WebSocketTransportClientSocketPoolTest,
969 LoadStateOfStalledSocketIsWaitingForAvailableSocket) {
970 for (int i = 0; i < kMaxSockets + 1; ++i) {
971 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
973 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET,
974 pool_.GetLoadState("a", request(kMaxSockets)->handle()));
977 TEST_F(WebSocketTransportClientSocketPoolTest,
978 CancellingStalledSocketUnstallsPool) {
979 for (int i = 0; i < kMaxSockets + 1; ++i) {
980 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
982 request(kMaxSockets)->handle()->Reset();
983 RunUntilIdle();
984 EXPECT_FALSE(pool_.IsStalled());
987 TEST_F(WebSocketTransportClientSocketPoolTest,
988 FlushWithErrorFlushesPendingConnections) {
989 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
990 pool_.FlushWithError(ERR_FAILED);
991 EXPECT_EQ(ERR_FAILED, request(0)->WaitForResult());
994 TEST_F(WebSocketTransportClientSocketPoolTest,
995 FlushWithErrorFlushesStalledConnections) {
996 for (int i = 0; i < kMaxSockets + 1; ++i) {
997 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
999 pool_.FlushWithError(ERR_FAILED);
1000 EXPECT_EQ(ERR_FAILED, request(kMaxSockets)->WaitForResult());
1003 TEST_F(WebSocketTransportClientSocketPoolTest,
1004 AfterFlushWithErrorCanMakeNewConnections) {
1005 for (int i = 0; i < kMaxSockets + 1; ++i) {
1006 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
1008 pool_.FlushWithError(ERR_FAILED);
1009 host_resolver_->set_synchronous_mode(true);
1010 EXPECT_EQ(OK, StartRequest("a", kDefaultPriority));
1013 // Deleting pending connections can release the lock on the endpoint, which can
1014 // in principle lead to other pending connections succeeding. However, when we
1015 // call FlushWithError(), everything should fail.
1016 TEST_F(WebSocketTransportClientSocketPoolTest,
1017 FlushWithErrorDoesNotCauseSuccessfulConnections) {
1018 host_resolver_->set_synchronous_mode(true);
1019 MockTransportClientSocketFactory::ClientSocketType first_type[] = {
1020 // First socket
1021 MockTransportClientSocketFactory::MOCK_PENDING_CLIENT_SOCKET
1023 client_socket_factory_.set_client_socket_types(first_type,
1024 arraysize(first_type));
1025 // The rest of the sockets will connect synchronously.
1026 client_socket_factory_.set_default_client_socket_type(
1027 MockTransportClientSocketFactory::MOCK_CLIENT_SOCKET);
1028 for (int i = 0; i < kMaxSockets; ++i) {
1029 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
1031 // Now we have one socket in STATE_TRANSPORT_CONNECT and the rest in
1032 // STATE_OBTAIN_LOCK. If any of the sockets in STATE_OBTAIN_LOCK is given the
1033 // lock, they will synchronously connect.
1034 pool_.FlushWithError(ERR_FAILED);
1035 for (int i = 0; i < kMaxSockets; ++i) {
1036 EXPECT_EQ(ERR_FAILED, request(i)->WaitForResult());
1040 // This is a regression test for the first attempted fix for
1041 // FlushWithErrorDoesNotCauseSuccessfulConnections. Because a ConnectJob can
1042 // have both IPv4 and IPv6 subjobs, it can be both connecting and waiting for
1043 // the lock at the same time.
1044 TEST_F(WebSocketTransportClientSocketPoolTest,
1045 FlushWithErrorDoesNotCauseSuccessfulConnectionsMultipleAddressTypes) {
1046 host_resolver_->set_synchronous_mode(true);
1047 // The first |kMaxSockets| sockets to connect will be IPv6. Then we will have
1048 // one IPv4.
1049 std::vector<MockTransportClientSocketFactory::ClientSocketType> socket_types(
1050 kMaxSockets + 1,
1051 MockTransportClientSocketFactory::MOCK_STALLED_CLIENT_SOCKET);
1052 client_socket_factory_.set_client_socket_types(&socket_types[0],
1053 socket_types.size());
1054 // The rest of the sockets will connect synchronously.
1055 client_socket_factory_.set_default_client_socket_type(
1056 MockTransportClientSocketFactory::MOCK_CLIENT_SOCKET);
1057 for (int i = 0; i < kMaxSockets; ++i) {
1058 host_resolver_->rules()->ClearRules();
1059 // Each connect job has a different IPv6 address but the same IPv4 address.
1060 // So the IPv6 connections happen in parallel but the IPv4 ones are
1061 // serialised.
1062 host_resolver_->rules()->AddIPLiteralRule("*",
1063 base::StringPrintf(
1064 "%x:abcd::3:4:ff,"
1065 "1.1.1.1",
1066 i + 1),
1067 std::string());
1068 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
1070 // Now we have |kMaxSockets| IPv6 sockets stalled in connect. No IPv4 sockets
1071 // are started yet.
1072 RunLoopForTimePeriod(base::TimeDelta::FromMilliseconds(
1073 TransportConnectJobHelper::kIPv6FallbackTimerInMs));
1074 // Now we have |kMaxSockets| IPv6 sockets and one IPv4 socket stalled in
1075 // connect, and |kMaxSockets - 1| IPv4 sockets waiting for the endpoint lock.
1076 pool_.FlushWithError(ERR_FAILED);
1077 for (int i = 0; i < kMaxSockets; ++i) {
1078 EXPECT_EQ(ERR_FAILED, request(i)->WaitForResult());
1082 // Sockets that have had ownership transferred to a ClientSocketHandle should
1083 // not be affected by FlushWithError.
1084 TEST_F(WebSocketTransportClientSocketPoolTest,
1085 FlushWithErrorDoesNotAffectHandedOutSockets) {
1086 host_resolver_->set_synchronous_mode(true);
1087 MockTransportClientSocketFactory::ClientSocketType socket_types[] = {
1088 MockTransportClientSocketFactory::MOCK_CLIENT_SOCKET,
1089 MockTransportClientSocketFactory::MOCK_STALLED_CLIENT_SOCKET};
1090 client_socket_factory_.set_client_socket_types(socket_types,
1091 arraysize(socket_types));
1092 EXPECT_EQ(OK, StartRequest("a", kDefaultPriority));
1093 // Socket has been "handed out".
1094 EXPECT_TRUE(request(0)->handle()->socket());
1096 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
1097 // Now we have one socket handed out, and one pending.
1098 pool_.FlushWithError(ERR_FAILED);
1099 EXPECT_EQ(ERR_FAILED, request(1)->WaitForResult());
1100 // Socket owned by ClientSocketHandle is unaffected:
1101 EXPECT_TRUE(request(0)->handle()->socket());
1102 // Return it to the pool (which deletes it).
1103 request(0)->handle()->Reset();
1106 // Sockets should not be leaked if CancelRequest() is called in between
1107 // SetSocket() being called on the ClientSocketHandle and InvokeUserCallback().
1108 TEST_F(WebSocketTransportClientSocketPoolTest, CancelRequestReclaimsSockets) {
1109 host_resolver_->set_synchronous_mode(true);
1110 MockTransportClientSocketFactory::ClientSocketType socket_types[] = {
1111 MockTransportClientSocketFactory::MOCK_TRIGGERABLE_CLIENT_SOCKET,
1112 MockTransportClientSocketFactory::MOCK_CLIENT_SOCKET};
1114 client_socket_factory_.set_client_socket_types(socket_types,
1115 arraysize(socket_types));
1117 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
1119 base::Closure connect_trigger =
1120 client_socket_factory_.WaitForTriggerableSocketCreation();
1122 connect_trigger.Run(); // Calls InvokeUserCallbackLater()
1124 request(0)->handle()->Reset(); // calls CancelRequest()
1126 RunUntilIdle();
1127 // We should now be able to create a new connection without blocking on the
1128 // endpoint lock.
1129 EXPECT_EQ(OK, StartRequest("a", kDefaultPriority));
1132 // A handshake completing and then the WebSocket closing should only release one
1133 // Endpoint, not two.
1134 TEST_F(WebSocketTransportClientSocketPoolTest, EndpointLockIsOnlyReleasedOnce) {
1135 host_resolver_->set_synchronous_mode(true);
1136 ASSERT_EQ(OK, StartRequest("a", kDefaultPriority));
1137 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
1138 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", kDefaultPriority));
1139 // First socket completes handshake.
1140 WebSocketTransportClientSocketPool::UnlockEndpoint(request(0)->handle());
1141 RunUntilIdle();
1142 // First socket is closed.
1143 request(0)->handle()->Reset();
1144 // Second socket should have been released.
1145 EXPECT_EQ(OK, request(1)->WaitForResult());
1146 // Third socket should still be waiting for endpoint.
1147 ASSERT_FALSE(request(2)->handle()->is_initialized());
1148 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET,
1149 request(2)->handle()->GetLoadState());
1152 } // namespace
1154 } // namespace net