Include all dupe types (event when value is zero) in scan stats.
[chromium-blink-merge.git] / net / socket / client_socket_pool_base_unittest.cc
blob49300118baf9e10dbeeb35b0e27bea258f96e755
1 // Copyright (c) 2012 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/client_socket_pool_base.h"
7 #include <vector>
9 #include "base/bind.h"
10 #include "base/bind_helpers.h"
11 #include "base/callback.h"
12 #include "base/logging.h"
13 #include "base/memory/ref_counted.h"
14 #include "base/memory/scoped_vector.h"
15 #include "base/memory/weak_ptr.h"
16 #include "base/message_loop/message_loop.h"
17 #include "base/run_loop.h"
18 #include "base/strings/string_number_conversions.h"
19 #include "base/strings/stringprintf.h"
20 #include "base/threading/platform_thread.h"
21 #include "base/values.h"
22 #include "net/base/load_timing_info.h"
23 #include "net/base/load_timing_info_test_util.h"
24 #include "net/base/net_errors.h"
25 #include "net/base/request_priority.h"
26 #include "net/base/test_completion_callback.h"
27 #include "net/http/http_response_headers.h"
28 #include "net/log/net_log.h"
29 #include "net/log/test_net_log.h"
30 #include "net/log/test_net_log_entry.h"
31 #include "net/log/test_net_log_util.h"
32 #include "net/socket/client_socket_factory.h"
33 #include "net/socket/client_socket_handle.h"
34 #include "net/socket/socket_test_util.h"
35 #include "net/socket/ssl_client_socket.h"
36 #include "net/socket/stream_socket.h"
37 #include "net/udp/datagram_client_socket.h"
38 #include "testing/gmock/include/gmock/gmock.h"
39 #include "testing/gtest/include/gtest/gtest.h"
41 using ::testing::Invoke;
42 using ::testing::Return;
44 namespace net {
46 namespace {
48 const int kDefaultMaxSockets = 4;
49 const int kDefaultMaxSocketsPerGroup = 2;
51 // Make sure |handle| sets load times correctly when it has been assigned a
52 // reused socket.
53 void TestLoadTimingInfoConnectedReused(const ClientSocketHandle& handle) {
54 LoadTimingInfo load_timing_info;
55 // Only pass true in as |is_reused|, as in general, HttpStream types should
56 // have stricter concepts of reuse than socket pools.
57 EXPECT_TRUE(handle.GetLoadTimingInfo(true, &load_timing_info));
59 EXPECT_EQ(true, load_timing_info.socket_reused);
60 EXPECT_NE(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
62 ExpectConnectTimingHasNoTimes(load_timing_info.connect_timing);
63 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
66 // Make sure |handle| sets load times correctly when it has been assigned a
67 // fresh socket. Also runs TestLoadTimingInfoConnectedReused, since the owner
68 // of a connection where |is_reused| is false may consider the connection
69 // reused.
70 void TestLoadTimingInfoConnectedNotReused(const ClientSocketHandle& handle) {
71 EXPECT_FALSE(handle.is_reused());
73 LoadTimingInfo load_timing_info;
74 EXPECT_TRUE(handle.GetLoadTimingInfo(false, &load_timing_info));
76 EXPECT_FALSE(load_timing_info.socket_reused);
77 EXPECT_NE(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
79 ExpectConnectTimingHasTimes(load_timing_info.connect_timing,
80 CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
81 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
83 TestLoadTimingInfoConnectedReused(handle);
86 // Make sure |handle| sets load times correctly, in the case that it does not
87 // currently have a socket.
88 void TestLoadTimingInfoNotConnected(const ClientSocketHandle& handle) {
89 // Should only be set to true once a socket is assigned, if at all.
90 EXPECT_FALSE(handle.is_reused());
92 LoadTimingInfo load_timing_info;
93 EXPECT_FALSE(handle.GetLoadTimingInfo(false, &load_timing_info));
95 EXPECT_FALSE(load_timing_info.socket_reused);
96 EXPECT_EQ(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
98 ExpectConnectTimingHasNoTimes(load_timing_info.connect_timing);
99 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
102 class TestSocketParams : public base::RefCounted<TestSocketParams> {
103 public:
104 explicit TestSocketParams(bool ignore_limits)
105 : ignore_limits_(ignore_limits) {}
107 bool ignore_limits() { return ignore_limits_; }
109 private:
110 friend class base::RefCounted<TestSocketParams>;
111 ~TestSocketParams() {}
113 const bool ignore_limits_;
115 typedef ClientSocketPoolBase<TestSocketParams> TestClientSocketPoolBase;
117 class MockClientSocket : public StreamSocket {
118 public:
119 explicit MockClientSocket(net::NetLog* net_log)
120 : connected_(false),
121 has_unread_data_(false),
122 net_log_(BoundNetLog::Make(net_log, NetLog::SOURCE_SOCKET)),
123 was_used_to_convey_data_(false) {}
125 // Sets whether the socket has unread data. If true, the next call to Read()
126 // will return 1 byte and IsConnectedAndIdle() will return false.
127 void set_has_unread_data(bool has_unread_data) {
128 has_unread_data_ = has_unread_data;
131 // Socket implementation.
132 int Read(IOBuffer* /* buf */,
133 int len,
134 const CompletionCallback& /* callback */) override {
135 if (has_unread_data_ && len > 0) {
136 has_unread_data_ = false;
137 was_used_to_convey_data_ = true;
138 return 1;
140 return ERR_UNEXPECTED;
143 int Write(IOBuffer* /* buf */,
144 int len,
145 const CompletionCallback& /* callback */) override {
146 was_used_to_convey_data_ = true;
147 return len;
149 int SetReceiveBufferSize(int32 size) override { return OK; }
150 int SetSendBufferSize(int32 size) override { return OK; }
152 // StreamSocket implementation.
153 int Connect(const CompletionCallback& callback) override {
154 connected_ = true;
155 return OK;
158 void Disconnect() override { connected_ = false; }
159 bool IsConnected() const override { return connected_; }
160 bool IsConnectedAndIdle() const override {
161 return connected_ && !has_unread_data_;
164 int GetPeerAddress(IPEndPoint* /* address */) const override {
165 return ERR_UNEXPECTED;
168 int GetLocalAddress(IPEndPoint* /* address */) const override {
169 return ERR_UNEXPECTED;
172 const BoundNetLog& NetLog() const override { return net_log_; }
174 void SetSubresourceSpeculation() override {}
175 void SetOmniboxSpeculation() override {}
176 bool WasEverUsed() const override { return was_used_to_convey_data_; }
177 bool UsingTCPFastOpen() const override { return false; }
178 bool WasNpnNegotiated() const override { return false; }
179 NextProto GetNegotiatedProtocol() const override { return kProtoUnknown; }
180 bool GetSSLInfo(SSLInfo* ssl_info) override { return false; }
181 void GetConnectionAttempts(ConnectionAttempts* out) const override {
182 out->clear();
184 void ClearConnectionAttempts() override {}
185 void AddConnectionAttempts(const ConnectionAttempts& attempts) override {}
187 private:
188 bool connected_;
189 bool has_unread_data_;
190 BoundNetLog net_log_;
191 bool was_used_to_convey_data_;
193 DISALLOW_COPY_AND_ASSIGN(MockClientSocket);
196 class TestConnectJob;
198 class MockClientSocketFactory : public ClientSocketFactory {
199 public:
200 MockClientSocketFactory() : allocation_count_(0) {}
202 scoped_ptr<DatagramClientSocket> CreateDatagramClientSocket(
203 DatagramSocket::BindType bind_type,
204 const RandIntCallback& rand_int_cb,
205 NetLog* net_log,
206 const NetLog::Source& source) override {
207 NOTREACHED();
208 return scoped_ptr<DatagramClientSocket>();
211 scoped_ptr<StreamSocket> CreateTransportClientSocket(
212 const AddressList& addresses,
213 NetLog* /* net_log */,
214 const NetLog::Source& /*source*/) override {
215 allocation_count_++;
216 return scoped_ptr<StreamSocket>();
219 scoped_ptr<SSLClientSocket> CreateSSLClientSocket(
220 scoped_ptr<ClientSocketHandle> transport_socket,
221 const HostPortPair& host_and_port,
222 const SSLConfig& ssl_config,
223 const SSLClientSocketContext& context) override {
224 NOTIMPLEMENTED();
225 return scoped_ptr<SSLClientSocket>();
228 void ClearSSLSessionCache() override { NOTIMPLEMENTED(); }
230 void WaitForSignal(TestConnectJob* job) { waiting_jobs_.push_back(job); }
232 void SignalJobs();
234 void SignalJob(size_t job);
236 void SetJobLoadState(size_t job, LoadState load_state);
238 int allocation_count() const { return allocation_count_; }
240 private:
241 int allocation_count_;
242 std::vector<TestConnectJob*> waiting_jobs_;
245 class TestConnectJob : public ConnectJob {
246 public:
247 enum JobType {
248 kMockJob,
249 kMockFailingJob,
250 kMockPendingJob,
251 kMockPendingFailingJob,
252 kMockWaitingJob,
253 kMockRecoverableJob,
254 kMockPendingRecoverableJob,
255 kMockAdditionalErrorStateJob,
256 kMockPendingAdditionalErrorStateJob,
257 kMockUnreadDataJob,
260 // The kMockPendingJob uses a slight delay before allowing the connect
261 // to complete.
262 static const int kPendingConnectDelay = 2;
264 TestConnectJob(JobType job_type,
265 const std::string& group_name,
266 const TestClientSocketPoolBase::Request& request,
267 base::TimeDelta timeout_duration,
268 ConnectJob::Delegate* delegate,
269 MockClientSocketFactory* client_socket_factory,
270 NetLog* net_log)
271 : ConnectJob(group_name, timeout_duration, request.priority(), delegate,
272 BoundNetLog::Make(net_log, NetLog::SOURCE_CONNECT_JOB)),
273 job_type_(job_type),
274 client_socket_factory_(client_socket_factory),
275 load_state_(LOAD_STATE_IDLE),
276 store_additional_error_state_(false),
277 weak_factory_(this) {
280 void Signal() {
281 DoConnect(waiting_success_, true /* async */, false /* recoverable */);
284 void set_load_state(LoadState load_state) { load_state_ = load_state; }
286 // From ConnectJob:
288 LoadState GetLoadState() const override { return load_state_; }
290 void GetAdditionalErrorState(ClientSocketHandle* handle) override {
291 if (store_additional_error_state_) {
292 // Set all of the additional error state fields in some way.
293 handle->set_is_ssl_error(true);
294 HttpResponseInfo info;
295 info.headers = new HttpResponseHeaders(std::string());
296 handle->set_ssl_error_response_info(info);
300 private:
301 // From ConnectJob:
303 int ConnectInternal() override {
304 AddressList ignored;
305 client_socket_factory_->CreateTransportClientSocket(ignored, NULL,
306 NetLog::Source());
307 SetSocket(
308 scoped_ptr<StreamSocket>(new MockClientSocket(net_log().net_log())));
309 switch (job_type_) {
310 case kMockJob:
311 return DoConnect(true /* successful */, false /* sync */,
312 false /* recoverable */);
313 case kMockFailingJob:
314 return DoConnect(false /* error */, false /* sync */,
315 false /* recoverable */);
316 case kMockPendingJob:
317 set_load_state(LOAD_STATE_CONNECTING);
319 // Depending on execution timings, posting a delayed task can result
320 // in the task getting executed the at the earliest possible
321 // opportunity or only after returning once from the message loop and
322 // then a second call into the message loop. In order to make behavior
323 // more deterministic, we change the default delay to 2ms. This should
324 // always require us to wait for the second call into the message loop.
326 // N.B. The correct fix for this and similar timing problems is to
327 // abstract time for the purpose of unittests. Unfortunately, we have
328 // a lot of third-party components that directly call the various
329 // time functions, so this change would be rather invasive.
330 base::MessageLoop::current()->PostDelayedTask(
331 FROM_HERE,
332 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
333 weak_factory_.GetWeakPtr(),
334 true /* successful */,
335 true /* async */,
336 false /* recoverable */),
337 base::TimeDelta::FromMilliseconds(kPendingConnectDelay));
338 return ERR_IO_PENDING;
339 case kMockPendingFailingJob:
340 set_load_state(LOAD_STATE_CONNECTING);
341 base::MessageLoop::current()->PostDelayedTask(
342 FROM_HERE,
343 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
344 weak_factory_.GetWeakPtr(),
345 false /* error */,
346 true /* async */,
347 false /* recoverable */),
348 base::TimeDelta::FromMilliseconds(2));
349 return ERR_IO_PENDING;
350 case kMockWaitingJob:
351 set_load_state(LOAD_STATE_CONNECTING);
352 client_socket_factory_->WaitForSignal(this);
353 waiting_success_ = true;
354 return ERR_IO_PENDING;
355 case kMockRecoverableJob:
356 return DoConnect(false /* error */, false /* sync */,
357 true /* recoverable */);
358 case kMockPendingRecoverableJob:
359 set_load_state(LOAD_STATE_CONNECTING);
360 base::MessageLoop::current()->PostDelayedTask(
361 FROM_HERE,
362 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
363 weak_factory_.GetWeakPtr(),
364 false /* error */,
365 true /* async */,
366 true /* recoverable */),
367 base::TimeDelta::FromMilliseconds(2));
368 return ERR_IO_PENDING;
369 case kMockAdditionalErrorStateJob:
370 store_additional_error_state_ = true;
371 return DoConnect(false /* error */, false /* sync */,
372 false /* recoverable */);
373 case kMockPendingAdditionalErrorStateJob:
374 set_load_state(LOAD_STATE_CONNECTING);
375 store_additional_error_state_ = true;
376 base::MessageLoop::current()->PostDelayedTask(
377 FROM_HERE,
378 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
379 weak_factory_.GetWeakPtr(),
380 false /* error */,
381 true /* async */,
382 false /* recoverable */),
383 base::TimeDelta::FromMilliseconds(2));
384 return ERR_IO_PENDING;
385 case kMockUnreadDataJob: {
386 int ret = DoConnect(true /* successful */, false /* sync */,
387 false /* recoverable */);
388 static_cast<MockClientSocket*>(socket())->set_has_unread_data(true);
389 return ret;
391 default:
392 NOTREACHED();
393 SetSocket(scoped_ptr<StreamSocket>());
394 return ERR_FAILED;
398 int DoConnect(bool succeed, bool was_async, bool recoverable) {
399 int result = OK;
400 if (succeed) {
401 socket()->Connect(CompletionCallback());
402 } else if (recoverable) {
403 result = ERR_PROXY_AUTH_REQUESTED;
404 } else {
405 result = ERR_CONNECTION_FAILED;
406 SetSocket(scoped_ptr<StreamSocket>());
409 if (was_async)
410 NotifyDelegateOfCompletion(result);
411 return result;
414 bool waiting_success_;
415 const JobType job_type_;
416 MockClientSocketFactory* const client_socket_factory_;
417 LoadState load_state_;
418 bool store_additional_error_state_;
420 base::WeakPtrFactory<TestConnectJob> weak_factory_;
422 DISALLOW_COPY_AND_ASSIGN(TestConnectJob);
425 class TestConnectJobFactory
426 : public TestClientSocketPoolBase::ConnectJobFactory {
427 public:
428 TestConnectJobFactory(MockClientSocketFactory* client_socket_factory,
429 NetLog* net_log)
430 : job_type_(TestConnectJob::kMockJob),
431 job_types_(NULL),
432 client_socket_factory_(client_socket_factory),
433 net_log_(net_log) {
436 ~TestConnectJobFactory() override {}
438 void set_job_type(TestConnectJob::JobType job_type) { job_type_ = job_type; }
440 void set_job_types(std::list<TestConnectJob::JobType>* job_types) {
441 job_types_ = job_types;
442 CHECK(!job_types_->empty());
445 void set_timeout_duration(base::TimeDelta timeout_duration) {
446 timeout_duration_ = timeout_duration;
449 // ConnectJobFactory implementation.
451 scoped_ptr<ConnectJob> NewConnectJob(
452 const std::string& group_name,
453 const TestClientSocketPoolBase::Request& request,
454 ConnectJob::Delegate* delegate) const override {
455 EXPECT_TRUE(!job_types_ || !job_types_->empty());
456 TestConnectJob::JobType job_type = job_type_;
457 if (job_types_ && !job_types_->empty()) {
458 job_type = job_types_->front();
459 job_types_->pop_front();
461 return scoped_ptr<ConnectJob>(new TestConnectJob(job_type,
462 group_name,
463 request,
464 timeout_duration_,
465 delegate,
466 client_socket_factory_,
467 net_log_));
470 base::TimeDelta ConnectionTimeout() const override {
471 return timeout_duration_;
474 private:
475 TestConnectJob::JobType job_type_;
476 std::list<TestConnectJob::JobType>* job_types_;
477 base::TimeDelta timeout_duration_;
478 MockClientSocketFactory* const client_socket_factory_;
479 NetLog* net_log_;
481 DISALLOW_COPY_AND_ASSIGN(TestConnectJobFactory);
484 class TestClientSocketPool : public ClientSocketPool {
485 public:
486 typedef TestSocketParams SocketParams;
488 TestClientSocketPool(
489 int max_sockets,
490 int max_sockets_per_group,
491 base::TimeDelta unused_idle_socket_timeout,
492 base::TimeDelta used_idle_socket_timeout,
493 TestClientSocketPoolBase::ConnectJobFactory* connect_job_factory)
494 : base_(NULL,
495 max_sockets,
496 max_sockets_per_group,
497 unused_idle_socket_timeout,
498 used_idle_socket_timeout,
499 connect_job_factory) {}
501 ~TestClientSocketPool() override {}
503 int RequestSocket(const std::string& group_name,
504 const void* params,
505 RequestPriority priority,
506 ClientSocketHandle* handle,
507 const CompletionCallback& callback,
508 const BoundNetLog& net_log) override {
509 const scoped_refptr<TestSocketParams>* casted_socket_params =
510 static_cast<const scoped_refptr<TestSocketParams>*>(params);
511 return base_.RequestSocket(group_name, *casted_socket_params, priority,
512 handle, callback, net_log);
515 void RequestSockets(const std::string& group_name,
516 const void* params,
517 int num_sockets,
518 const BoundNetLog& net_log) override {
519 const scoped_refptr<TestSocketParams>* casted_params =
520 static_cast<const scoped_refptr<TestSocketParams>*>(params);
522 base_.RequestSockets(group_name, *casted_params, num_sockets, net_log);
525 void CancelRequest(const std::string& group_name,
526 ClientSocketHandle* handle) override {
527 base_.CancelRequest(group_name, handle);
530 void ReleaseSocket(const std::string& group_name,
531 scoped_ptr<StreamSocket> socket,
532 int id) override {
533 base_.ReleaseSocket(group_name, socket.Pass(), id);
536 void FlushWithError(int error) override { base_.FlushWithError(error); }
538 bool IsStalled() const override { return base_.IsStalled(); }
540 void CloseIdleSockets() override { base_.CloseIdleSockets(); }
542 int IdleSocketCount() const override { return base_.idle_socket_count(); }
544 int IdleSocketCountInGroup(const std::string& group_name) const override {
545 return base_.IdleSocketCountInGroup(group_name);
548 LoadState GetLoadState(const std::string& group_name,
549 const ClientSocketHandle* handle) const override {
550 return base_.GetLoadState(group_name, handle);
553 void AddHigherLayeredPool(HigherLayeredPool* higher_pool) override {
554 base_.AddHigherLayeredPool(higher_pool);
557 void RemoveHigherLayeredPool(HigherLayeredPool* higher_pool) override {
558 base_.RemoveHigherLayeredPool(higher_pool);
561 scoped_ptr<base::DictionaryValue> GetInfoAsValue(
562 const std::string& name,
563 const std::string& type,
564 bool include_nested_pools) const override {
565 return base_.GetInfoAsValue(name, type);
568 base::TimeDelta ConnectionTimeout() const override {
569 return base_.ConnectionTimeout();
572 const TestClientSocketPoolBase* base() const { return &base_; }
574 int NumUnassignedConnectJobsInGroup(const std::string& group_name) const {
575 return base_.NumUnassignedConnectJobsInGroup(group_name);
578 int NumConnectJobsInGroup(const std::string& group_name) const {
579 return base_.NumConnectJobsInGroup(group_name);
582 int NumActiveSocketsInGroup(const std::string& group_name) const {
583 return base_.NumActiveSocketsInGroup(group_name);
586 bool HasGroup(const std::string& group_name) const {
587 return base_.HasGroup(group_name);
590 void CleanupTimedOutIdleSockets() { base_.CleanupIdleSockets(false); }
592 void EnableConnectBackupJobs() { base_.EnableConnectBackupJobs(); }
594 bool CloseOneIdleConnectionInHigherLayeredPool() {
595 return base_.CloseOneIdleConnectionInHigherLayeredPool();
598 private:
599 TestClientSocketPoolBase base_;
601 DISALLOW_COPY_AND_ASSIGN(TestClientSocketPool);
604 } // namespace
606 namespace {
608 void MockClientSocketFactory::SignalJobs() {
609 for (std::vector<TestConnectJob*>::iterator it = waiting_jobs_.begin();
610 it != waiting_jobs_.end(); ++it) {
611 (*it)->Signal();
613 waiting_jobs_.clear();
616 void MockClientSocketFactory::SignalJob(size_t job) {
617 ASSERT_LT(job, waiting_jobs_.size());
618 waiting_jobs_[job]->Signal();
619 waiting_jobs_.erase(waiting_jobs_.begin() + job);
622 void MockClientSocketFactory::SetJobLoadState(size_t job,
623 LoadState load_state) {
624 ASSERT_LT(job, waiting_jobs_.size());
625 waiting_jobs_[job]->set_load_state(load_state);
628 class TestConnectJobDelegate : public ConnectJob::Delegate {
629 public:
630 TestConnectJobDelegate()
631 : have_result_(false), waiting_for_result_(false), result_(OK) {}
632 ~TestConnectJobDelegate() override {}
634 void OnConnectJobComplete(int result, ConnectJob* job) override {
635 result_ = result;
636 scoped_ptr<ConnectJob> owned_job(job);
637 scoped_ptr<StreamSocket> socket = owned_job->PassSocket();
638 // socket.get() should be NULL iff result != OK
639 EXPECT_EQ(socket == NULL, result != OK);
640 have_result_ = true;
641 if (waiting_for_result_)
642 base::MessageLoop::current()->Quit();
645 int WaitForResult() {
646 DCHECK(!waiting_for_result_);
647 while (!have_result_) {
648 waiting_for_result_ = true;
649 base::MessageLoop::current()->Run();
650 waiting_for_result_ = false;
652 have_result_ = false; // auto-reset for next callback
653 return result_;
656 private:
657 bool have_result_;
658 bool waiting_for_result_;
659 int result_;
662 class ClientSocketPoolBaseTest : public testing::Test {
663 protected:
664 ClientSocketPoolBaseTest()
665 : params_(new TestSocketParams(false /* ignore_limits */)) {
666 connect_backup_jobs_enabled_ =
667 internal::ClientSocketPoolBaseHelper::connect_backup_jobs_enabled();
668 internal::ClientSocketPoolBaseHelper::set_connect_backup_jobs_enabled(true);
669 cleanup_timer_enabled_ =
670 internal::ClientSocketPoolBaseHelper::cleanup_timer_enabled();
673 ~ClientSocketPoolBaseTest() override {
674 internal::ClientSocketPoolBaseHelper::set_connect_backup_jobs_enabled(
675 connect_backup_jobs_enabled_);
676 internal::ClientSocketPoolBaseHelper::set_cleanup_timer_enabled(
677 cleanup_timer_enabled_);
680 void CreatePool(int max_sockets, int max_sockets_per_group) {
681 CreatePoolWithIdleTimeouts(
682 max_sockets,
683 max_sockets_per_group,
684 ClientSocketPool::unused_idle_socket_timeout(),
685 ClientSocketPool::used_idle_socket_timeout());
688 void CreatePoolWithIdleTimeouts(
689 int max_sockets, int max_sockets_per_group,
690 base::TimeDelta unused_idle_socket_timeout,
691 base::TimeDelta used_idle_socket_timeout) {
692 DCHECK(!pool_.get());
693 connect_job_factory_ = new TestConnectJobFactory(&client_socket_factory_,
694 &net_log_);
695 pool_.reset(new TestClientSocketPool(max_sockets,
696 max_sockets_per_group,
697 unused_idle_socket_timeout,
698 used_idle_socket_timeout,
699 connect_job_factory_));
702 int StartRequestWithParams(
703 const std::string& group_name,
704 RequestPriority priority,
705 const scoped_refptr<TestSocketParams>& params) {
706 return test_base_.StartRequestUsingPool(
707 pool_.get(), group_name, priority, params);
710 int StartRequest(const std::string& group_name, RequestPriority priority) {
711 return StartRequestWithParams(group_name, priority, params_);
714 int GetOrderOfRequest(size_t index) const {
715 return test_base_.GetOrderOfRequest(index);
718 bool ReleaseOneConnection(ClientSocketPoolTest::KeepAlive keep_alive) {
719 return test_base_.ReleaseOneConnection(keep_alive);
722 void ReleaseAllConnections(ClientSocketPoolTest::KeepAlive keep_alive) {
723 test_base_.ReleaseAllConnections(keep_alive);
726 TestSocketRequest* request(int i) { return test_base_.request(i); }
727 size_t requests_size() const { return test_base_.requests_size(); }
728 ScopedVector<TestSocketRequest>* requests() { return test_base_.requests(); }
729 size_t completion_count() const { return test_base_.completion_count(); }
731 TestNetLog net_log_;
732 bool connect_backup_jobs_enabled_;
733 bool cleanup_timer_enabled_;
734 MockClientSocketFactory client_socket_factory_;
735 TestConnectJobFactory* connect_job_factory_;
736 scoped_refptr<TestSocketParams> params_;
737 scoped_ptr<TestClientSocketPool> pool_;
738 ClientSocketPoolTest test_base_;
741 // Even though a timeout is specified, it doesn't time out on a synchronous
742 // completion.
743 TEST_F(ClientSocketPoolBaseTest, ConnectJob_NoTimeoutOnSynchronousCompletion) {
744 TestConnectJobDelegate delegate;
745 ClientSocketHandle ignored;
746 TestClientSocketPoolBase::Request request(
747 &ignored, CompletionCallback(), DEFAULT_PRIORITY,
748 internal::ClientSocketPoolBaseHelper::NORMAL,
749 false, params_, BoundNetLog());
750 scoped_ptr<TestConnectJob> job(
751 new TestConnectJob(TestConnectJob::kMockJob,
752 "a",
753 request,
754 base::TimeDelta::FromMicroseconds(1),
755 &delegate,
756 &client_socket_factory_,
757 NULL));
758 EXPECT_EQ(OK, job->Connect());
761 TEST_F(ClientSocketPoolBaseTest, ConnectJob_TimedOut) {
762 TestConnectJobDelegate delegate;
763 ClientSocketHandle ignored;
764 TestNetLog log;
766 TestClientSocketPoolBase::Request request(
767 &ignored, CompletionCallback(), DEFAULT_PRIORITY,
768 internal::ClientSocketPoolBaseHelper::NORMAL,
769 false, params_, BoundNetLog());
770 // Deleted by TestConnectJobDelegate.
771 TestConnectJob* job =
772 new TestConnectJob(TestConnectJob::kMockPendingJob,
773 "a",
774 request,
775 base::TimeDelta::FromMicroseconds(1),
776 &delegate,
777 &client_socket_factory_,
778 &log);
779 ASSERT_EQ(ERR_IO_PENDING, job->Connect());
780 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(1));
781 EXPECT_EQ(ERR_TIMED_OUT, delegate.WaitForResult());
783 TestNetLogEntry::List entries;
784 log.GetEntries(&entries);
786 EXPECT_EQ(6u, entries.size());
787 EXPECT_TRUE(LogContainsBeginEvent(
788 entries, 0, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB));
789 EXPECT_TRUE(LogContainsBeginEvent(
790 entries, 1, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB_CONNECT));
791 EXPECT_TRUE(LogContainsEvent(
792 entries, 2, NetLog::TYPE_CONNECT_JOB_SET_SOCKET,
793 NetLog::PHASE_NONE));
794 EXPECT_TRUE(LogContainsEvent(
795 entries, 3, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB_TIMED_OUT,
796 NetLog::PHASE_NONE));
797 EXPECT_TRUE(LogContainsEndEvent(
798 entries, 4, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB_CONNECT));
799 EXPECT_TRUE(LogContainsEndEvent(
800 entries, 5, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB));
803 TEST_F(ClientSocketPoolBaseTest, BasicSynchronous) {
804 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
806 TestCompletionCallback callback;
807 ClientSocketHandle handle;
808 BoundTestNetLog log;
809 TestLoadTimingInfoNotConnected(handle);
811 EXPECT_EQ(OK,
812 handle.Init("a",
813 params_,
814 DEFAULT_PRIORITY,
815 callback.callback(),
816 pool_.get(),
817 log.bound()));
818 EXPECT_TRUE(handle.is_initialized());
819 EXPECT_TRUE(handle.socket());
820 TestLoadTimingInfoConnectedNotReused(handle);
822 handle.Reset();
823 TestLoadTimingInfoNotConnected(handle);
825 TestNetLogEntry::List entries;
826 log.GetEntries(&entries);
828 EXPECT_EQ(4u, entries.size());
829 EXPECT_TRUE(LogContainsBeginEvent(
830 entries, 0, NetLog::TYPE_SOCKET_POOL));
831 EXPECT_TRUE(LogContainsEvent(
832 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
833 NetLog::PHASE_NONE));
834 EXPECT_TRUE(LogContainsEvent(
835 entries, 2, NetLog::TYPE_SOCKET_POOL_BOUND_TO_SOCKET,
836 NetLog::PHASE_NONE));
837 EXPECT_TRUE(LogContainsEndEvent(
838 entries, 3, NetLog::TYPE_SOCKET_POOL));
841 TEST_F(ClientSocketPoolBaseTest, InitConnectionFailure) {
842 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
844 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
845 BoundTestNetLog log;
847 ClientSocketHandle handle;
848 TestCompletionCallback callback;
849 // Set the additional error state members to ensure that they get cleared.
850 handle.set_is_ssl_error(true);
851 HttpResponseInfo info;
852 info.headers = new HttpResponseHeaders(std::string());
853 handle.set_ssl_error_response_info(info);
854 EXPECT_EQ(ERR_CONNECTION_FAILED,
855 handle.Init("a",
856 params_,
857 DEFAULT_PRIORITY,
858 callback.callback(),
859 pool_.get(),
860 log.bound()));
861 EXPECT_FALSE(handle.socket());
862 EXPECT_FALSE(handle.is_ssl_error());
863 EXPECT_TRUE(handle.ssl_error_response_info().headers.get() == NULL);
864 TestLoadTimingInfoNotConnected(handle);
866 TestNetLogEntry::List entries;
867 log.GetEntries(&entries);
869 EXPECT_EQ(3u, entries.size());
870 EXPECT_TRUE(LogContainsBeginEvent(
871 entries, 0, NetLog::TYPE_SOCKET_POOL));
872 EXPECT_TRUE(LogContainsEvent(
873 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
874 NetLog::PHASE_NONE));
875 EXPECT_TRUE(LogContainsEndEvent(
876 entries, 2, NetLog::TYPE_SOCKET_POOL));
879 TEST_F(ClientSocketPoolBaseTest, TotalLimit) {
880 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
882 // TODO(eroman): Check that the NetLog contains this event.
884 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
885 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
886 EXPECT_EQ(OK, StartRequest("c", DEFAULT_PRIORITY));
887 EXPECT_EQ(OK, StartRequest("d", DEFAULT_PRIORITY));
889 EXPECT_EQ(static_cast<int>(requests_size()),
890 client_socket_factory_.allocation_count());
891 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
893 EXPECT_EQ(ERR_IO_PENDING, StartRequest("e", DEFAULT_PRIORITY));
894 EXPECT_EQ(ERR_IO_PENDING, StartRequest("f", DEFAULT_PRIORITY));
895 EXPECT_EQ(ERR_IO_PENDING, StartRequest("g", DEFAULT_PRIORITY));
897 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
899 EXPECT_EQ(static_cast<int>(requests_size()),
900 client_socket_factory_.allocation_count());
901 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
903 EXPECT_EQ(1, GetOrderOfRequest(1));
904 EXPECT_EQ(2, GetOrderOfRequest(2));
905 EXPECT_EQ(3, GetOrderOfRequest(3));
906 EXPECT_EQ(4, GetOrderOfRequest(4));
907 EXPECT_EQ(5, GetOrderOfRequest(5));
908 EXPECT_EQ(6, GetOrderOfRequest(6));
909 EXPECT_EQ(7, GetOrderOfRequest(7));
911 // Make sure we test order of all requests made.
912 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(8));
915 TEST_F(ClientSocketPoolBaseTest, TotalLimitReachedNewGroup) {
916 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
918 // TODO(eroman): Check that the NetLog contains this event.
920 // Reach all limits: max total sockets, and max sockets per group.
921 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
922 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
923 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
924 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
926 EXPECT_EQ(static_cast<int>(requests_size()),
927 client_socket_factory_.allocation_count());
928 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
930 // Now create a new group and verify that we don't starve it.
931 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", DEFAULT_PRIORITY));
933 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
935 EXPECT_EQ(static_cast<int>(requests_size()),
936 client_socket_factory_.allocation_count());
937 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
939 EXPECT_EQ(1, GetOrderOfRequest(1));
940 EXPECT_EQ(2, GetOrderOfRequest(2));
941 EXPECT_EQ(3, GetOrderOfRequest(3));
942 EXPECT_EQ(4, GetOrderOfRequest(4));
943 EXPECT_EQ(5, GetOrderOfRequest(5));
945 // Make sure we test order of all requests made.
946 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(6));
949 TEST_F(ClientSocketPoolBaseTest, TotalLimitRespectsPriority) {
950 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
952 EXPECT_EQ(OK, StartRequest("b", LOWEST));
953 EXPECT_EQ(OK, StartRequest("a", MEDIUM));
954 EXPECT_EQ(OK, StartRequest("b", HIGHEST));
955 EXPECT_EQ(OK, StartRequest("a", LOWEST));
957 EXPECT_EQ(static_cast<int>(requests_size()),
958 client_socket_factory_.allocation_count());
960 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", LOWEST));
961 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
962 EXPECT_EQ(ERR_IO_PENDING, StartRequest("b", HIGHEST));
964 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
966 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
968 // First 4 requests don't have to wait, and finish in order.
969 EXPECT_EQ(1, GetOrderOfRequest(1));
970 EXPECT_EQ(2, GetOrderOfRequest(2));
971 EXPECT_EQ(3, GetOrderOfRequest(3));
972 EXPECT_EQ(4, GetOrderOfRequest(4));
974 // Request ("b", HIGHEST) has the highest priority, then ("a", MEDIUM),
975 // and then ("c", LOWEST).
976 EXPECT_EQ(7, GetOrderOfRequest(5));
977 EXPECT_EQ(6, GetOrderOfRequest(6));
978 EXPECT_EQ(5, GetOrderOfRequest(7));
980 // Make sure we test order of all requests made.
981 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(9));
984 TEST_F(ClientSocketPoolBaseTest, TotalLimitRespectsGroupLimit) {
985 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
987 EXPECT_EQ(OK, StartRequest("a", LOWEST));
988 EXPECT_EQ(OK, StartRequest("a", LOW));
989 EXPECT_EQ(OK, StartRequest("b", HIGHEST));
990 EXPECT_EQ(OK, StartRequest("b", MEDIUM));
992 EXPECT_EQ(static_cast<int>(requests_size()),
993 client_socket_factory_.allocation_count());
995 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", MEDIUM));
996 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
997 EXPECT_EQ(ERR_IO_PENDING, StartRequest("b", HIGHEST));
999 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
1001 EXPECT_EQ(static_cast<int>(requests_size()),
1002 client_socket_factory_.allocation_count());
1003 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
1005 // First 4 requests don't have to wait, and finish in order.
1006 EXPECT_EQ(1, GetOrderOfRequest(1));
1007 EXPECT_EQ(2, GetOrderOfRequest(2));
1008 EXPECT_EQ(3, GetOrderOfRequest(3));
1009 EXPECT_EQ(4, GetOrderOfRequest(4));
1011 // Request ("b", 7) has the highest priority, but we can't make new socket for
1012 // group "b", because it has reached the per-group limit. Then we make
1013 // socket for ("c", 6), because it has higher priority than ("a", 4),
1014 // and we still can't make a socket for group "b".
1015 EXPECT_EQ(5, GetOrderOfRequest(5));
1016 EXPECT_EQ(6, GetOrderOfRequest(6));
1017 EXPECT_EQ(7, GetOrderOfRequest(7));
1019 // Make sure we test order of all requests made.
1020 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(8));
1023 // Make sure that we count connecting sockets against the total limit.
1024 TEST_F(ClientSocketPoolBaseTest, TotalLimitCountsConnectingSockets) {
1025 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1027 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1028 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
1029 EXPECT_EQ(OK, StartRequest("c", DEFAULT_PRIORITY));
1031 // Create one asynchronous request.
1032 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1033 EXPECT_EQ(ERR_IO_PENDING, StartRequest("d", DEFAULT_PRIORITY));
1035 // We post all of our delayed tasks with a 2ms delay. I.e. they don't
1036 // actually become pending until 2ms after they have been created. In order
1037 // to flush all tasks, we need to wait so that we know there are no
1038 // soon-to-be-pending tasks waiting.
1039 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(10));
1040 base::MessageLoop::current()->RunUntilIdle();
1042 // The next synchronous request should wait for its turn.
1043 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1044 EXPECT_EQ(ERR_IO_PENDING, StartRequest("e", DEFAULT_PRIORITY));
1046 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
1048 EXPECT_EQ(static_cast<int>(requests_size()),
1049 client_socket_factory_.allocation_count());
1051 EXPECT_EQ(1, GetOrderOfRequest(1));
1052 EXPECT_EQ(2, GetOrderOfRequest(2));
1053 EXPECT_EQ(3, GetOrderOfRequest(3));
1054 EXPECT_EQ(4, GetOrderOfRequest(4));
1055 EXPECT_EQ(5, GetOrderOfRequest(5));
1057 // Make sure we test order of all requests made.
1058 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(6));
1061 TEST_F(ClientSocketPoolBaseTest, CorrectlyCountStalledGroups) {
1062 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
1063 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1065 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1066 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1067 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1068 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1070 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1072 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1074 EXPECT_EQ(ERR_IO_PENDING, StartRequest("b", DEFAULT_PRIORITY));
1075 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", DEFAULT_PRIORITY));
1077 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1079 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1080 EXPECT_EQ(kDefaultMaxSockets + 1, client_socket_factory_.allocation_count());
1081 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1082 EXPECT_EQ(kDefaultMaxSockets + 2, client_socket_factory_.allocation_count());
1083 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1084 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1085 EXPECT_EQ(kDefaultMaxSockets + 2, client_socket_factory_.allocation_count());
1088 TEST_F(ClientSocketPoolBaseTest, StallAndThenCancelAndTriggerAvailableSocket) {
1089 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
1090 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1092 ClientSocketHandle handle;
1093 TestCompletionCallback callback;
1094 EXPECT_EQ(ERR_IO_PENDING,
1095 handle.Init("a",
1096 params_,
1097 DEFAULT_PRIORITY,
1098 callback.callback(),
1099 pool_.get(),
1100 BoundNetLog()));
1102 ClientSocketHandle handles[4];
1103 for (size_t i = 0; i < arraysize(handles); ++i) {
1104 TestCompletionCallback callback;
1105 EXPECT_EQ(ERR_IO_PENDING,
1106 handles[i].Init("b",
1107 params_,
1108 DEFAULT_PRIORITY,
1109 callback.callback(),
1110 pool_.get(),
1111 BoundNetLog()));
1114 // One will be stalled, cancel all the handles now.
1115 // This should hit the OnAvailableSocketSlot() code where we previously had
1116 // stalled groups, but no longer have any.
1117 for (size_t i = 0; i < arraysize(handles); ++i)
1118 handles[i].Reset();
1121 TEST_F(ClientSocketPoolBaseTest, CancelStalledSocketAtSocketLimit) {
1122 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1123 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1126 ClientSocketHandle handles[kDefaultMaxSockets];
1127 TestCompletionCallback callbacks[kDefaultMaxSockets];
1128 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1129 EXPECT_EQ(OK, handles[i].Init(base::IntToString(i),
1130 params_,
1131 DEFAULT_PRIORITY,
1132 callbacks[i].callback(),
1133 pool_.get(),
1134 BoundNetLog()));
1137 // Force a stalled group.
1138 ClientSocketHandle stalled_handle;
1139 TestCompletionCallback callback;
1140 EXPECT_EQ(ERR_IO_PENDING, stalled_handle.Init("foo",
1141 params_,
1142 DEFAULT_PRIORITY,
1143 callback.callback(),
1144 pool_.get(),
1145 BoundNetLog()));
1147 // Cancel the stalled request.
1148 stalled_handle.Reset();
1150 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1151 EXPECT_EQ(0, pool_->IdleSocketCount());
1153 // Dropping out of scope will close all handles and return them to idle.
1156 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1157 EXPECT_EQ(kDefaultMaxSockets, pool_->IdleSocketCount());
1160 TEST_F(ClientSocketPoolBaseTest, CancelPendingSocketAtSocketLimit) {
1161 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1162 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1165 ClientSocketHandle handles[kDefaultMaxSockets];
1166 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1167 TestCompletionCallback callback;
1168 EXPECT_EQ(ERR_IO_PENDING, handles[i].Init(base::IntToString(i),
1169 params_,
1170 DEFAULT_PRIORITY,
1171 callback.callback(),
1172 pool_.get(),
1173 BoundNetLog()));
1176 // Force a stalled group.
1177 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1178 ClientSocketHandle stalled_handle;
1179 TestCompletionCallback callback;
1180 EXPECT_EQ(ERR_IO_PENDING, stalled_handle.Init("foo",
1181 params_,
1182 DEFAULT_PRIORITY,
1183 callback.callback(),
1184 pool_.get(),
1185 BoundNetLog()));
1187 // Since it is stalled, it should have no connect jobs.
1188 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("foo"));
1189 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("foo"));
1191 // Cancel the stalled request.
1192 handles[0].Reset();
1194 // Now we should have a connect job.
1195 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("foo"));
1196 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("foo"));
1198 // The stalled socket should connect.
1199 EXPECT_EQ(OK, callback.WaitForResult());
1201 EXPECT_EQ(kDefaultMaxSockets + 1,
1202 client_socket_factory_.allocation_count());
1203 EXPECT_EQ(0, pool_->IdleSocketCount());
1204 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("foo"));
1205 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("foo"));
1207 // Dropping out of scope will close all handles and return them to idle.
1210 EXPECT_EQ(1, pool_->IdleSocketCount());
1213 TEST_F(ClientSocketPoolBaseTest, WaitForStalledSocketAtSocketLimit) {
1214 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1215 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1217 ClientSocketHandle stalled_handle;
1218 TestCompletionCallback callback;
1220 EXPECT_FALSE(pool_->IsStalled());
1221 ClientSocketHandle handles[kDefaultMaxSockets];
1222 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1223 TestCompletionCallback callback;
1224 EXPECT_EQ(OK, handles[i].Init(base::StringPrintf(
1225 "Take 2: %d", i),
1226 params_,
1227 DEFAULT_PRIORITY,
1228 callback.callback(),
1229 pool_.get(),
1230 BoundNetLog()));
1233 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1234 EXPECT_EQ(0, pool_->IdleSocketCount());
1235 EXPECT_FALSE(pool_->IsStalled());
1237 // Now we will hit the socket limit.
1238 EXPECT_EQ(ERR_IO_PENDING, stalled_handle.Init("foo",
1239 params_,
1240 DEFAULT_PRIORITY,
1241 callback.callback(),
1242 pool_.get(),
1243 BoundNetLog()));
1244 EXPECT_TRUE(pool_->IsStalled());
1246 // Dropping out of scope will close all handles and return them to idle.
1249 // But if we wait for it, the released idle sockets will be closed in
1250 // preference of the waiting request.
1251 EXPECT_EQ(OK, callback.WaitForResult());
1253 EXPECT_EQ(kDefaultMaxSockets + 1, client_socket_factory_.allocation_count());
1254 EXPECT_EQ(3, pool_->IdleSocketCount());
1257 // Regression test for http://crbug.com/40952.
1258 TEST_F(ClientSocketPoolBaseTest, CloseIdleSocketAtSocketLimitDeleteGroup) {
1259 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1260 pool_->EnableConnectBackupJobs();
1261 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1263 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1264 ClientSocketHandle handle;
1265 TestCompletionCallback callback;
1266 EXPECT_EQ(OK, handle.Init(base::IntToString(i),
1267 params_,
1268 DEFAULT_PRIORITY,
1269 callback.callback(),
1270 pool_.get(),
1271 BoundNetLog()));
1274 // Flush all the DoReleaseSocket tasks.
1275 base::MessageLoop::current()->RunUntilIdle();
1277 // Stall a group. Set a pending job so it'll trigger a backup job if we don't
1278 // reuse a socket.
1279 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1280 ClientSocketHandle handle;
1281 TestCompletionCallback callback;
1283 // "0" is special here, since it should be the first entry in the sorted map,
1284 // which is the one which we would close an idle socket for. We shouldn't
1285 // close an idle socket though, since we should reuse the idle socket.
1286 EXPECT_EQ(OK, handle.Init("0",
1287 params_,
1288 DEFAULT_PRIORITY,
1289 callback.callback(),
1290 pool_.get(),
1291 BoundNetLog()));
1293 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1294 EXPECT_EQ(kDefaultMaxSockets - 1, pool_->IdleSocketCount());
1297 TEST_F(ClientSocketPoolBaseTest, PendingRequests) {
1298 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1300 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1301 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1302 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", IDLE));
1303 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1304 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1305 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1306 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1307 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1309 ReleaseAllConnections(ClientSocketPoolTest::KEEP_ALIVE);
1311 EXPECT_EQ(kDefaultMaxSocketsPerGroup,
1312 client_socket_factory_.allocation_count());
1313 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup,
1314 completion_count());
1316 EXPECT_EQ(1, GetOrderOfRequest(1));
1317 EXPECT_EQ(2, GetOrderOfRequest(2));
1318 EXPECT_EQ(8, GetOrderOfRequest(3));
1319 EXPECT_EQ(6, GetOrderOfRequest(4));
1320 EXPECT_EQ(4, GetOrderOfRequest(5));
1321 EXPECT_EQ(3, GetOrderOfRequest(6));
1322 EXPECT_EQ(5, GetOrderOfRequest(7));
1323 EXPECT_EQ(7, GetOrderOfRequest(8));
1325 // Make sure we test order of all requests made.
1326 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(9));
1329 TEST_F(ClientSocketPoolBaseTest, PendingRequests_NoKeepAlive) {
1330 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1332 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1333 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1334 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1335 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1336 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1337 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1338 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1340 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
1342 for (size_t i = kDefaultMaxSocketsPerGroup; i < requests_size(); ++i)
1343 EXPECT_EQ(OK, request(i)->WaitForResult());
1345 EXPECT_EQ(static_cast<int>(requests_size()),
1346 client_socket_factory_.allocation_count());
1347 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup,
1348 completion_count());
1351 // This test will start up a RequestSocket() and then immediately Cancel() it.
1352 // The pending connect job will be cancelled and should not call back into
1353 // ClientSocketPoolBase.
1354 TEST_F(ClientSocketPoolBaseTest, CancelRequestClearGroup) {
1355 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1357 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1358 ClientSocketHandle handle;
1359 TestCompletionCallback callback;
1360 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
1361 params_,
1362 DEFAULT_PRIORITY,
1363 callback.callback(),
1364 pool_.get(),
1365 BoundNetLog()));
1366 handle.Reset();
1369 TEST_F(ClientSocketPoolBaseTest, ConnectCancelConnect) {
1370 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1372 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1373 ClientSocketHandle handle;
1374 TestCompletionCallback callback;
1376 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
1377 params_,
1378 DEFAULT_PRIORITY,
1379 callback.callback(),
1380 pool_.get(),
1381 BoundNetLog()));
1383 handle.Reset();
1385 TestCompletionCallback callback2;
1386 EXPECT_EQ(ERR_IO_PENDING,
1387 handle.Init("a",
1388 params_,
1389 DEFAULT_PRIORITY,
1390 callback2.callback(),
1391 pool_.get(),
1392 BoundNetLog()));
1394 EXPECT_EQ(OK, callback2.WaitForResult());
1395 EXPECT_FALSE(callback.have_result());
1397 handle.Reset();
1400 TEST_F(ClientSocketPoolBaseTest, CancelRequest) {
1401 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1403 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1404 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1405 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1406 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1407 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1408 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1409 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1411 // Cancel a request.
1412 size_t index_to_cancel = kDefaultMaxSocketsPerGroup + 2;
1413 EXPECT_FALSE((*requests())[index_to_cancel]->handle()->is_initialized());
1414 (*requests())[index_to_cancel]->handle()->Reset();
1416 ReleaseAllConnections(ClientSocketPoolTest::KEEP_ALIVE);
1418 EXPECT_EQ(kDefaultMaxSocketsPerGroup,
1419 client_socket_factory_.allocation_count());
1420 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup - 1,
1421 completion_count());
1423 EXPECT_EQ(1, GetOrderOfRequest(1));
1424 EXPECT_EQ(2, GetOrderOfRequest(2));
1425 EXPECT_EQ(5, GetOrderOfRequest(3));
1426 EXPECT_EQ(3, GetOrderOfRequest(4));
1427 EXPECT_EQ(ClientSocketPoolTest::kRequestNotFound,
1428 GetOrderOfRequest(5)); // Canceled request.
1429 EXPECT_EQ(4, GetOrderOfRequest(6));
1430 EXPECT_EQ(6, GetOrderOfRequest(7));
1432 // Make sure we test order of all requests made.
1433 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(8));
1436 // Function to be used as a callback on socket request completion. It first
1437 // disconnects the successfully connected socket from the first request, and
1438 // then reuses the ClientSocketHandle to request another socket.
1440 // |nested_callback| is called with the result of the second socket request.
1441 void RequestSocketOnComplete(ClientSocketHandle* handle,
1442 TestClientSocketPool* pool,
1443 TestConnectJobFactory* test_connect_job_factory,
1444 TestConnectJob::JobType next_job_type,
1445 const CompletionCallback& nested_callback,
1446 int first_request_result) {
1447 EXPECT_EQ(OK, first_request_result);
1449 test_connect_job_factory->set_job_type(next_job_type);
1451 // Don't allow reuse of the socket. Disconnect it and then release it.
1452 if (handle->socket())
1453 handle->socket()->Disconnect();
1454 handle->Reset();
1456 scoped_refptr<TestSocketParams> params(
1457 new TestSocketParams(false /* ignore_limits */));
1458 TestCompletionCallback callback;
1459 int rv =
1460 handle->Init("a", params, LOWEST, nested_callback, pool, BoundNetLog());
1461 if (rv != ERR_IO_PENDING) {
1462 DCHECK_EQ(TestConnectJob::kMockJob, next_job_type);
1463 nested_callback.Run(rv);
1464 } else {
1465 DCHECK_EQ(TestConnectJob::kMockPendingJob, next_job_type);
1469 // Tests the case where a second socket is requested in a completion callback,
1470 // and the second socket connects asynchronously. Reuses the same
1471 // ClientSocketHandle for the second socket, after disconnecting the first.
1472 TEST_F(ClientSocketPoolBaseTest, RequestPendingJobTwice) {
1473 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1475 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1476 ClientSocketHandle handle;
1477 TestCompletionCallback second_result_callback;
1478 int rv = handle.Init(
1479 "a", params_, DEFAULT_PRIORITY,
1480 base::Bind(&RequestSocketOnComplete, &handle, pool_.get(),
1481 connect_job_factory_, TestConnectJob::kMockPendingJob,
1482 second_result_callback.callback()),
1483 pool_.get(), BoundNetLog());
1484 ASSERT_EQ(ERR_IO_PENDING, rv);
1486 EXPECT_EQ(OK, second_result_callback.WaitForResult());
1489 // Tests the case where a second socket is requested in a completion callback,
1490 // and the second socket connects synchronously. Reuses the same
1491 // ClientSocketHandle for the second socket, after disconnecting the first.
1492 TEST_F(ClientSocketPoolBaseTest, RequestPendingJobThenSynchronous) {
1493 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1495 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1496 ClientSocketHandle handle;
1497 TestCompletionCallback second_result_callback;
1498 int rv = handle.Init(
1499 "a", params_, DEFAULT_PRIORITY,
1500 base::Bind(&RequestSocketOnComplete, &handle, pool_.get(),
1501 connect_job_factory_, TestConnectJob::kMockPendingJob,
1502 second_result_callback.callback()),
1503 pool_.get(), BoundNetLog());
1504 ASSERT_EQ(ERR_IO_PENDING, rv);
1506 EXPECT_EQ(OK, second_result_callback.WaitForResult());
1509 // Make sure that pending requests get serviced after active requests get
1510 // cancelled.
1511 TEST_F(ClientSocketPoolBaseTest, CancelActiveRequestWithPendingRequests) {
1512 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1514 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1516 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1517 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1518 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1519 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1520 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1521 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1522 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1524 // Now, kDefaultMaxSocketsPerGroup requests should be active.
1525 // Let's cancel them.
1526 for (int i = 0; i < kDefaultMaxSocketsPerGroup; ++i) {
1527 ASSERT_FALSE(request(i)->handle()->is_initialized());
1528 request(i)->handle()->Reset();
1531 // Let's wait for the rest to complete now.
1532 for (size_t i = kDefaultMaxSocketsPerGroup; i < requests_size(); ++i) {
1533 EXPECT_EQ(OK, request(i)->WaitForResult());
1534 request(i)->handle()->Reset();
1537 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup,
1538 completion_count());
1541 // Make sure that pending requests get serviced after active requests fail.
1542 TEST_F(ClientSocketPoolBaseTest, FailingActiveRequestWithPendingRequests) {
1543 const size_t kMaxSockets = 5;
1544 CreatePool(kMaxSockets, kDefaultMaxSocketsPerGroup);
1546 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1548 const size_t kNumberOfRequests = 2 * kDefaultMaxSocketsPerGroup + 1;
1549 ASSERT_LE(kNumberOfRequests, kMaxSockets); // Otherwise the test will hang.
1551 // Queue up all the requests
1552 for (size_t i = 0; i < kNumberOfRequests; ++i)
1553 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1555 for (size_t i = 0; i < kNumberOfRequests; ++i)
1556 EXPECT_EQ(ERR_CONNECTION_FAILED, request(i)->WaitForResult());
1559 TEST_F(ClientSocketPoolBaseTest, CancelActiveRequestThenRequestSocket) {
1560 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1562 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1564 ClientSocketHandle handle;
1565 TestCompletionCallback callback;
1566 int rv = handle.Init("a",
1567 params_,
1568 DEFAULT_PRIORITY,
1569 callback.callback(),
1570 pool_.get(),
1571 BoundNetLog());
1572 EXPECT_EQ(ERR_IO_PENDING, rv);
1574 // Cancel the active request.
1575 handle.Reset();
1577 rv = handle.Init("a",
1578 params_,
1579 DEFAULT_PRIORITY,
1580 callback.callback(),
1581 pool_.get(),
1582 BoundNetLog());
1583 EXPECT_EQ(ERR_IO_PENDING, rv);
1584 EXPECT_EQ(OK, callback.WaitForResult());
1586 EXPECT_FALSE(handle.is_reused());
1587 TestLoadTimingInfoConnectedNotReused(handle);
1588 EXPECT_EQ(2, client_socket_factory_.allocation_count());
1591 // Regression test for http://crbug.com/17985.
1592 TEST_F(ClientSocketPoolBaseTest, GroupWithPendingRequestsIsNotEmpty) {
1593 const int kMaxSockets = 3;
1594 const int kMaxSocketsPerGroup = 2;
1595 CreatePool(kMaxSockets, kMaxSocketsPerGroup);
1597 const RequestPriority kHighPriority = HIGHEST;
1599 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1600 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1602 // This is going to be a pending request in an otherwise empty group.
1603 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1605 // Reach the maximum socket limit.
1606 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
1608 // Create a stalled group with high priorities.
1609 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", kHighPriority));
1610 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", kHighPriority));
1612 // Release the first two sockets from "a". Because this is a keepalive,
1613 // the first release will unblock the pending request for "a". The
1614 // second release will unblock a request for "c", becaue it is the next
1615 // high priority socket.
1616 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1617 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1619 // Closing idle sockets should not get us into trouble, but in the bug
1620 // we were hitting a CHECK here.
1621 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
1622 pool_->CloseIdleSockets();
1624 // Run the released socket wakeups.
1625 base::MessageLoop::current()->RunUntilIdle();
1628 TEST_F(ClientSocketPoolBaseTest, BasicAsynchronous) {
1629 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1631 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1632 ClientSocketHandle handle;
1633 TestCompletionCallback callback;
1634 BoundTestNetLog log;
1635 int rv = handle.Init("a",
1636 params_,
1637 LOWEST,
1638 callback.callback(),
1639 pool_.get(),
1640 log.bound());
1641 EXPECT_EQ(ERR_IO_PENDING, rv);
1642 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
1643 TestLoadTimingInfoNotConnected(handle);
1645 EXPECT_EQ(OK, callback.WaitForResult());
1646 EXPECT_TRUE(handle.is_initialized());
1647 EXPECT_TRUE(handle.socket());
1648 TestLoadTimingInfoConnectedNotReused(handle);
1650 handle.Reset();
1651 TestLoadTimingInfoNotConnected(handle);
1653 TestNetLogEntry::List entries;
1654 log.GetEntries(&entries);
1656 EXPECT_EQ(4u, entries.size());
1657 EXPECT_TRUE(LogContainsBeginEvent(
1658 entries, 0, NetLog::TYPE_SOCKET_POOL));
1659 EXPECT_TRUE(LogContainsEvent(
1660 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
1661 NetLog::PHASE_NONE));
1662 EXPECT_TRUE(LogContainsEvent(
1663 entries, 2, NetLog::TYPE_SOCKET_POOL_BOUND_TO_SOCKET,
1664 NetLog::PHASE_NONE));
1665 EXPECT_TRUE(LogContainsEndEvent(
1666 entries, 3, NetLog::TYPE_SOCKET_POOL));
1669 TEST_F(ClientSocketPoolBaseTest,
1670 InitConnectionAsynchronousFailure) {
1671 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1673 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1674 ClientSocketHandle handle;
1675 TestCompletionCallback callback;
1676 BoundTestNetLog log;
1677 // Set the additional error state members to ensure that they get cleared.
1678 handle.set_is_ssl_error(true);
1679 HttpResponseInfo info;
1680 info.headers = new HttpResponseHeaders(std::string());
1681 handle.set_ssl_error_response_info(info);
1682 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
1683 params_,
1684 DEFAULT_PRIORITY,
1685 callback.callback(),
1686 pool_.get(),
1687 log.bound()));
1688 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
1689 EXPECT_EQ(ERR_CONNECTION_FAILED, callback.WaitForResult());
1690 EXPECT_FALSE(handle.is_ssl_error());
1691 EXPECT_TRUE(handle.ssl_error_response_info().headers.get() == NULL);
1693 TestNetLogEntry::List entries;
1694 log.GetEntries(&entries);
1696 EXPECT_EQ(3u, entries.size());
1697 EXPECT_TRUE(LogContainsBeginEvent(
1698 entries, 0, NetLog::TYPE_SOCKET_POOL));
1699 EXPECT_TRUE(LogContainsEvent(
1700 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
1701 NetLog::PHASE_NONE));
1702 EXPECT_TRUE(LogContainsEndEvent(
1703 entries, 2, NetLog::TYPE_SOCKET_POOL));
1706 // Check that an async ConnectJob failure does not result in creation of a new
1707 // ConnectJob when there's another pending request also waiting on its own
1708 // ConnectJob. See http://crbug.com/463960.
1709 TEST_F(ClientSocketPoolBaseTest, AsyncFailureWithPendingRequestWithJob) {
1710 CreatePool(2, 2);
1711 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1713 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1714 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1716 EXPECT_EQ(ERR_CONNECTION_FAILED, request(0)->WaitForResult());
1717 EXPECT_EQ(ERR_CONNECTION_FAILED, request(1)->WaitForResult());
1719 EXPECT_EQ(2, client_socket_factory_.allocation_count());
1722 TEST_F(ClientSocketPoolBaseTest, TwoRequestsCancelOne) {
1723 // TODO(eroman): Add back the log expectations! Removed them because the
1724 // ordering is difficult, and some may fire during destructor.
1725 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1727 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1728 ClientSocketHandle handle;
1729 TestCompletionCallback callback;
1730 ClientSocketHandle handle2;
1731 TestCompletionCallback callback2;
1733 EXPECT_EQ(ERR_IO_PENDING,
1734 handle.Init("a",
1735 params_,
1736 DEFAULT_PRIORITY,
1737 callback.callback(),
1738 pool_.get(),
1739 BoundNetLog()));
1740 BoundTestNetLog log2;
1741 EXPECT_EQ(ERR_IO_PENDING,
1742 handle2.Init("a",
1743 params_,
1744 DEFAULT_PRIORITY,
1745 callback2.callback(),
1746 pool_.get(),
1747 BoundNetLog()));
1749 handle.Reset();
1752 // At this point, request 2 is just waiting for the connect job to finish.
1754 EXPECT_EQ(OK, callback2.WaitForResult());
1755 handle2.Reset();
1757 // Now request 2 has actually finished.
1758 // TODO(eroman): Add back log expectations.
1761 TEST_F(ClientSocketPoolBaseTest, CancelRequestLimitsJobs) {
1762 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1764 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1766 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1767 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1768 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1769 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1771 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1772 (*requests())[2]->handle()->Reset();
1773 (*requests())[3]->handle()->Reset();
1774 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1776 (*requests())[1]->handle()->Reset();
1777 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1779 (*requests())[0]->handle()->Reset();
1780 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1783 // When requests and ConnectJobs are not coupled, the request will get serviced
1784 // by whatever comes first.
1785 TEST_F(ClientSocketPoolBaseTest, ReleaseSockets) {
1786 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1788 // Start job 1 (async OK)
1789 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1791 std::vector<TestSocketRequest*> request_order;
1792 size_t completion_count; // unused
1793 TestSocketRequest req1(&request_order, &completion_count);
1794 int rv = req1.handle()->Init("a",
1795 params_,
1796 DEFAULT_PRIORITY,
1797 req1.callback(), pool_.get(),
1798 BoundNetLog());
1799 EXPECT_EQ(ERR_IO_PENDING, rv);
1800 EXPECT_EQ(OK, req1.WaitForResult());
1802 // Job 1 finished OK. Start job 2 (also async OK). Request 3 is pending
1803 // without a job.
1804 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1806 TestSocketRequest req2(&request_order, &completion_count);
1807 rv = req2.handle()->Init("a",
1808 params_,
1809 DEFAULT_PRIORITY,
1810 req2.callback(),
1811 pool_.get(),
1812 BoundNetLog());
1813 EXPECT_EQ(ERR_IO_PENDING, rv);
1814 TestSocketRequest req3(&request_order, &completion_count);
1815 rv = req3.handle()->Init("a",
1816 params_,
1817 DEFAULT_PRIORITY,
1818 req3.callback(),
1819 pool_.get(),
1820 BoundNetLog());
1821 EXPECT_EQ(ERR_IO_PENDING, rv);
1823 // Both Requests 2 and 3 are pending. We release socket 1 which should
1824 // service request 2. Request 3 should still be waiting.
1825 req1.handle()->Reset();
1826 // Run the released socket wakeups.
1827 base::MessageLoop::current()->RunUntilIdle();
1828 ASSERT_TRUE(req2.handle()->socket());
1829 EXPECT_EQ(OK, req2.WaitForResult());
1830 EXPECT_FALSE(req3.handle()->socket());
1832 // Signal job 2, which should service request 3.
1834 client_socket_factory_.SignalJobs();
1835 EXPECT_EQ(OK, req3.WaitForResult());
1837 ASSERT_EQ(3U, request_order.size());
1838 EXPECT_EQ(&req1, request_order[0]);
1839 EXPECT_EQ(&req2, request_order[1]);
1840 EXPECT_EQ(&req3, request_order[2]);
1841 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
1844 // The requests are not coupled to the jobs. So, the requests should finish in
1845 // their priority / insertion order.
1846 TEST_F(ClientSocketPoolBaseTest, PendingJobCompletionOrder) {
1847 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1848 // First two jobs are async.
1849 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1851 std::vector<TestSocketRequest*> request_order;
1852 size_t completion_count; // unused
1853 TestSocketRequest req1(&request_order, &completion_count);
1854 int rv = req1.handle()->Init("a",
1855 params_,
1856 DEFAULT_PRIORITY,
1857 req1.callback(),
1858 pool_.get(),
1859 BoundNetLog());
1860 EXPECT_EQ(ERR_IO_PENDING, rv);
1862 TestSocketRequest req2(&request_order, &completion_count);
1863 rv = req2.handle()->Init("a",
1864 params_,
1865 DEFAULT_PRIORITY,
1866 req2.callback(),
1867 pool_.get(),
1868 BoundNetLog());
1869 EXPECT_EQ(ERR_IO_PENDING, rv);
1871 // The pending job is sync.
1872 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1874 TestSocketRequest req3(&request_order, &completion_count);
1875 rv = req3.handle()->Init("a",
1876 params_,
1877 DEFAULT_PRIORITY,
1878 req3.callback(),
1879 pool_.get(),
1880 BoundNetLog());
1881 EXPECT_EQ(ERR_IO_PENDING, rv);
1883 EXPECT_EQ(ERR_CONNECTION_FAILED, req1.WaitForResult());
1884 EXPECT_EQ(OK, req2.WaitForResult());
1885 EXPECT_EQ(ERR_CONNECTION_FAILED, req3.WaitForResult());
1887 ASSERT_EQ(3U, request_order.size());
1888 EXPECT_EQ(&req1, request_order[0]);
1889 EXPECT_EQ(&req2, request_order[1]);
1890 EXPECT_EQ(&req3, request_order[2]);
1893 // Test GetLoadState in the case there's only one socket request.
1894 TEST_F(ClientSocketPoolBaseTest, LoadStateOneRequest) {
1895 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1896 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1898 ClientSocketHandle handle;
1899 TestCompletionCallback callback;
1900 int rv = handle.Init("a",
1901 params_,
1902 DEFAULT_PRIORITY,
1903 callback.callback(),
1904 pool_.get(),
1905 BoundNetLog());
1906 EXPECT_EQ(ERR_IO_PENDING, rv);
1907 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1909 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_SSL_HANDSHAKE);
1910 EXPECT_EQ(LOAD_STATE_SSL_HANDSHAKE, handle.GetLoadState());
1912 // No point in completing the connection, since ClientSocketHandles only
1913 // expect the LoadState to be checked while connecting.
1916 // Test GetLoadState in the case there are two socket requests.
1917 // Only the first connection in the pool should affect the pool's load status.
1918 TEST_F(ClientSocketPoolBaseTest, LoadStateTwoRequests) {
1919 CreatePool(2, 2);
1920 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1922 ClientSocketHandle handle;
1923 TestCompletionCallback callback;
1924 int rv = handle.Init("a", params_, DEFAULT_PRIORITY, callback.callback(),
1925 pool_.get(), BoundNetLog());
1926 EXPECT_EQ(ERR_IO_PENDING, rv);
1927 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_RESOLVING_HOST);
1929 ClientSocketHandle handle2;
1930 TestCompletionCallback callback2;
1931 rv = handle2.Init("a", params_, DEFAULT_PRIORITY, callback2.callback(),
1932 pool_.get(), BoundNetLog());
1933 EXPECT_EQ(ERR_IO_PENDING, rv);
1934 client_socket_factory_.SetJobLoadState(1, LOAD_STATE_RESOLVING_HOST);
1936 // Check that both handles report the state of the first job.
1937 EXPECT_EQ(LOAD_STATE_RESOLVING_HOST, handle.GetLoadState());
1938 EXPECT_EQ(LOAD_STATE_RESOLVING_HOST, handle2.GetLoadState());
1940 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_CONNECTING);
1942 // Check that both handles change to LOAD_STATE_CONNECTING.
1943 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1944 EXPECT_EQ(LOAD_STATE_CONNECTING, handle2.GetLoadState());
1947 // Test that the second connection request does not affect the pool's load
1948 // status.
1949 TEST_F(ClientSocketPoolBaseTest, LoadStateTwoRequestsChangeSecondRequestState) {
1950 CreatePool(2, 2);
1951 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1953 ClientSocketHandle handle;
1954 TestCompletionCallback callback;
1955 int rv = handle.Init("a", params_, DEFAULT_PRIORITY, callback.callback(),
1956 pool_.get(), BoundNetLog());
1957 EXPECT_EQ(ERR_IO_PENDING, rv);
1959 ClientSocketHandle handle2;
1960 TestCompletionCallback callback2;
1961 rv = handle2.Init("a", params_, DEFAULT_PRIORITY, callback2.callback(),
1962 pool_.get(), BoundNetLog());
1963 EXPECT_EQ(ERR_IO_PENDING, rv);
1964 client_socket_factory_.SetJobLoadState(1, LOAD_STATE_RESOLVING_HOST);
1966 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1967 EXPECT_EQ(LOAD_STATE_CONNECTING, handle2.GetLoadState());
1969 // First job connects and the first request gets the socket. The
1970 // second handle switches to the state of the remaining ConnectJob.
1971 client_socket_factory_.SignalJob(0);
1972 EXPECT_EQ(OK, callback.WaitForResult());
1973 EXPECT_EQ(LOAD_STATE_RESOLVING_HOST, handle2.GetLoadState());
1976 // Test GetLoadState in the case the per-group limit is reached.
1977 TEST_F(ClientSocketPoolBaseTest, LoadStateGroupLimit) {
1978 CreatePool(2, 1);
1979 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1981 ClientSocketHandle handle;
1982 TestCompletionCallback callback;
1983 int rv = handle.Init("a",
1984 params_,
1985 MEDIUM,
1986 callback.callback(),
1987 pool_.get(),
1988 BoundNetLog());
1989 EXPECT_EQ(ERR_IO_PENDING, rv);
1990 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1992 // Request another socket from the same pool, buth with a higher priority.
1993 // The first request should now be stalled at the socket group limit.
1994 ClientSocketHandle handle2;
1995 TestCompletionCallback callback2;
1996 rv = handle2.Init("a",
1997 params_,
1998 HIGHEST,
1999 callback2.callback(),
2000 pool_.get(),
2001 BoundNetLog());
2002 EXPECT_EQ(ERR_IO_PENDING, rv);
2003 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET, handle.GetLoadState());
2004 EXPECT_EQ(LOAD_STATE_CONNECTING, handle2.GetLoadState());
2006 // The first handle should remain stalled as the other socket goes through
2007 // the connect process.
2009 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_SSL_HANDSHAKE);
2010 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET, handle.GetLoadState());
2011 EXPECT_EQ(LOAD_STATE_SSL_HANDSHAKE, handle2.GetLoadState());
2013 client_socket_factory_.SignalJob(0);
2014 EXPECT_EQ(OK, callback2.WaitForResult());
2015 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET, handle.GetLoadState());
2017 // Closing the second socket should cause the stalled handle to finally get a
2018 // ConnectJob.
2019 handle2.socket()->Disconnect();
2020 handle2.Reset();
2021 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
2024 // Test GetLoadState in the case the per-pool limit is reached.
2025 TEST_F(ClientSocketPoolBaseTest, LoadStatePoolLimit) {
2026 CreatePool(2, 2);
2027 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2029 ClientSocketHandle handle;
2030 TestCompletionCallback callback;
2031 int rv = handle.Init("a",
2032 params_,
2033 DEFAULT_PRIORITY,
2034 callback.callback(),
2035 pool_.get(),
2036 BoundNetLog());
2037 EXPECT_EQ(ERR_IO_PENDING, rv);
2039 // Request for socket from another pool.
2040 ClientSocketHandle handle2;
2041 TestCompletionCallback callback2;
2042 rv = handle2.Init("b",
2043 params_,
2044 DEFAULT_PRIORITY,
2045 callback2.callback(),
2046 pool_.get(),
2047 BoundNetLog());
2048 EXPECT_EQ(ERR_IO_PENDING, rv);
2050 // Request another socket from the first pool. Request should stall at the
2051 // socket pool limit.
2052 ClientSocketHandle handle3;
2053 TestCompletionCallback callback3;
2054 rv = handle3.Init("a",
2055 params_,
2056 DEFAULT_PRIORITY,
2057 callback2.callback(),
2058 pool_.get(),
2059 BoundNetLog());
2060 EXPECT_EQ(ERR_IO_PENDING, rv);
2062 // The third handle should remain stalled as the other sockets in its group
2063 // goes through the connect process.
2065 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
2066 EXPECT_EQ(LOAD_STATE_WAITING_FOR_STALLED_SOCKET_POOL, handle3.GetLoadState());
2068 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_SSL_HANDSHAKE);
2069 EXPECT_EQ(LOAD_STATE_SSL_HANDSHAKE, handle.GetLoadState());
2070 EXPECT_EQ(LOAD_STATE_WAITING_FOR_STALLED_SOCKET_POOL, handle3.GetLoadState());
2072 client_socket_factory_.SignalJob(0);
2073 EXPECT_EQ(OK, callback.WaitForResult());
2074 EXPECT_EQ(LOAD_STATE_WAITING_FOR_STALLED_SOCKET_POOL, handle3.GetLoadState());
2076 // Closing a socket should allow the stalled handle to finally get a new
2077 // ConnectJob.
2078 handle.socket()->Disconnect();
2079 handle.Reset();
2080 EXPECT_EQ(LOAD_STATE_CONNECTING, handle3.GetLoadState());
2083 TEST_F(ClientSocketPoolBaseTest, Recoverable) {
2084 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2085 connect_job_factory_->set_job_type(TestConnectJob::kMockRecoverableJob);
2087 ClientSocketHandle handle;
2088 TestCompletionCallback callback;
2089 EXPECT_EQ(ERR_PROXY_AUTH_REQUESTED,
2090 handle.Init("a", params_, DEFAULT_PRIORITY, callback.callback(),
2091 pool_.get(), BoundNetLog()));
2092 EXPECT_TRUE(handle.is_initialized());
2093 EXPECT_TRUE(handle.socket());
2096 TEST_F(ClientSocketPoolBaseTest, AsyncRecoverable) {
2097 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2099 connect_job_factory_->set_job_type(
2100 TestConnectJob::kMockPendingRecoverableJob);
2101 ClientSocketHandle handle;
2102 TestCompletionCallback callback;
2103 EXPECT_EQ(ERR_IO_PENDING,
2104 handle.Init("a",
2105 params_,
2106 DEFAULT_PRIORITY,
2107 callback.callback(),
2108 pool_.get(),
2109 BoundNetLog()));
2110 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2111 EXPECT_EQ(ERR_PROXY_AUTH_REQUESTED, callback.WaitForResult());
2112 EXPECT_TRUE(handle.is_initialized());
2113 EXPECT_TRUE(handle.socket());
2116 TEST_F(ClientSocketPoolBaseTest, AdditionalErrorStateSynchronous) {
2117 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2118 connect_job_factory_->set_job_type(
2119 TestConnectJob::kMockAdditionalErrorStateJob);
2121 ClientSocketHandle handle;
2122 TestCompletionCallback callback;
2123 EXPECT_EQ(ERR_CONNECTION_FAILED,
2124 handle.Init("a",
2125 params_,
2126 DEFAULT_PRIORITY,
2127 callback.callback(),
2128 pool_.get(),
2129 BoundNetLog()));
2130 EXPECT_FALSE(handle.is_initialized());
2131 EXPECT_FALSE(handle.socket());
2132 EXPECT_TRUE(handle.is_ssl_error());
2133 EXPECT_FALSE(handle.ssl_error_response_info().headers.get() == NULL);
2136 TEST_F(ClientSocketPoolBaseTest, AdditionalErrorStateAsynchronous) {
2137 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2139 connect_job_factory_->set_job_type(
2140 TestConnectJob::kMockPendingAdditionalErrorStateJob);
2141 ClientSocketHandle handle;
2142 TestCompletionCallback callback;
2143 EXPECT_EQ(ERR_IO_PENDING,
2144 handle.Init("a",
2145 params_,
2146 DEFAULT_PRIORITY,
2147 callback.callback(),
2148 pool_.get(),
2149 BoundNetLog()));
2150 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2151 EXPECT_EQ(ERR_CONNECTION_FAILED, callback.WaitForResult());
2152 EXPECT_FALSE(handle.is_initialized());
2153 EXPECT_FALSE(handle.socket());
2154 EXPECT_TRUE(handle.is_ssl_error());
2155 EXPECT_FALSE(handle.ssl_error_response_info().headers.get() == NULL);
2158 // Make sure we can reuse sockets when the cleanup timer is disabled.
2159 TEST_F(ClientSocketPoolBaseTest, DisableCleanupTimerReuse) {
2160 // Disable cleanup timer.
2161 internal::ClientSocketPoolBaseHelper::set_cleanup_timer_enabled(false);
2163 CreatePoolWithIdleTimeouts(
2164 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2165 base::TimeDelta(), // Time out unused sockets immediately.
2166 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2168 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2170 ClientSocketHandle handle;
2171 TestCompletionCallback callback;
2172 int rv = handle.Init("a",
2173 params_,
2174 LOWEST,
2175 callback.callback(),
2176 pool_.get(),
2177 BoundNetLog());
2178 ASSERT_EQ(ERR_IO_PENDING, rv);
2179 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2180 ASSERT_EQ(OK, callback.WaitForResult());
2182 // Use and release the socket.
2183 EXPECT_EQ(1, handle.socket()->Write(NULL, 1, CompletionCallback()));
2184 TestLoadTimingInfoConnectedNotReused(handle);
2185 handle.Reset();
2187 // Should now have one idle socket.
2188 ASSERT_EQ(1, pool_->IdleSocketCount());
2190 // Request a new socket. This should reuse the old socket and complete
2191 // synchronously.
2192 BoundTestNetLog log;
2193 rv = handle.Init("a",
2194 params_,
2195 LOWEST,
2196 CompletionCallback(),
2197 pool_.get(),
2198 log.bound());
2199 ASSERT_EQ(OK, rv);
2200 EXPECT_TRUE(handle.is_reused());
2201 TestLoadTimingInfoConnectedReused(handle);
2203 ASSERT_TRUE(pool_->HasGroup("a"));
2204 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
2205 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
2207 TestNetLogEntry::List entries;
2208 log.GetEntries(&entries);
2209 EXPECT_TRUE(LogContainsEntryWithType(
2210 entries, 1, NetLog::TYPE_SOCKET_POOL_REUSED_AN_EXISTING_SOCKET));
2213 // Make sure we cleanup old unused sockets when the cleanup timer is disabled.
2214 TEST_F(ClientSocketPoolBaseTest, DisableCleanupTimerNoReuse) {
2215 // Disable cleanup timer.
2216 internal::ClientSocketPoolBaseHelper::set_cleanup_timer_enabled(false);
2218 CreatePoolWithIdleTimeouts(
2219 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2220 base::TimeDelta(), // Time out unused sockets immediately
2221 base::TimeDelta()); // Time out used sockets immediately
2223 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2225 // Startup two mock pending connect jobs, which will sit in the MessageLoop.
2227 ClientSocketHandle handle;
2228 TestCompletionCallback callback;
2229 int rv = handle.Init("a",
2230 params_,
2231 LOWEST,
2232 callback.callback(),
2233 pool_.get(),
2234 BoundNetLog());
2235 ASSERT_EQ(ERR_IO_PENDING, rv);
2236 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2238 ClientSocketHandle handle2;
2239 TestCompletionCallback callback2;
2240 rv = handle2.Init("a",
2241 params_,
2242 LOWEST,
2243 callback2.callback(),
2244 pool_.get(),
2245 BoundNetLog());
2246 ASSERT_EQ(ERR_IO_PENDING, rv);
2247 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle2));
2249 // Cancel one of the requests. Wait for the other, which will get the first
2250 // job. Release the socket. Run the loop again to make sure the second
2251 // socket is sitting idle and the first one is released (since ReleaseSocket()
2252 // just posts a DoReleaseSocket() task).
2254 handle.Reset();
2255 ASSERT_EQ(OK, callback2.WaitForResult());
2256 // Use the socket.
2257 EXPECT_EQ(1, handle2.socket()->Write(NULL, 1, CompletionCallback()));
2258 handle2.Reset();
2260 // We post all of our delayed tasks with a 2ms delay. I.e. they don't
2261 // actually become pending until 2ms after they have been created. In order
2262 // to flush all tasks, we need to wait so that we know there are no
2263 // soon-to-be-pending tasks waiting.
2264 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(10));
2265 base::MessageLoop::current()->RunUntilIdle();
2267 // Both sockets should now be idle.
2268 ASSERT_EQ(2, pool_->IdleSocketCount());
2270 // Request a new socket. This should cleanup the unused and timed out ones.
2271 // A new socket will be created rather than reusing the idle one.
2272 BoundTestNetLog log;
2273 TestCompletionCallback callback3;
2274 rv = handle.Init("a",
2275 params_,
2276 LOWEST,
2277 callback3.callback(),
2278 pool_.get(),
2279 log.bound());
2280 ASSERT_EQ(ERR_IO_PENDING, rv);
2281 ASSERT_EQ(OK, callback3.WaitForResult());
2282 EXPECT_FALSE(handle.is_reused());
2284 // Make sure the idle socket is closed.
2285 ASSERT_TRUE(pool_->HasGroup("a"));
2286 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
2287 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
2289 TestNetLogEntry::List entries;
2290 log.GetEntries(&entries);
2291 EXPECT_FALSE(LogContainsEntryWithType(
2292 entries, 1, NetLog::TYPE_SOCKET_POOL_REUSED_AN_EXISTING_SOCKET));
2295 TEST_F(ClientSocketPoolBaseTest, CleanupTimedOutIdleSockets) {
2296 CreatePoolWithIdleTimeouts(
2297 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2298 base::TimeDelta(), // Time out unused sockets immediately.
2299 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2301 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2303 // Startup two mock pending connect jobs, which will sit in the MessageLoop.
2305 ClientSocketHandle handle;
2306 TestCompletionCallback callback;
2307 int rv = handle.Init("a",
2308 params_,
2309 LOWEST,
2310 callback.callback(),
2311 pool_.get(),
2312 BoundNetLog());
2313 EXPECT_EQ(ERR_IO_PENDING, rv);
2314 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2316 ClientSocketHandle handle2;
2317 TestCompletionCallback callback2;
2318 rv = handle2.Init("a",
2319 params_,
2320 LOWEST,
2321 callback2.callback(),
2322 pool_.get(),
2323 BoundNetLog());
2324 EXPECT_EQ(ERR_IO_PENDING, rv);
2325 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle2));
2327 // Cancel one of the requests. Wait for the other, which will get the first
2328 // job. Release the socket. Run the loop again to make sure the second
2329 // socket is sitting idle and the first one is released (since ReleaseSocket()
2330 // just posts a DoReleaseSocket() task).
2332 handle.Reset();
2333 EXPECT_EQ(OK, callback2.WaitForResult());
2334 // Use the socket.
2335 EXPECT_EQ(1, handle2.socket()->Write(NULL, 1, CompletionCallback()));
2336 handle2.Reset();
2338 // We post all of our delayed tasks with a 2ms delay. I.e. they don't
2339 // actually become pending until 2ms after they have been created. In order
2340 // to flush all tasks, we need to wait so that we know there are no
2341 // soon-to-be-pending tasks waiting.
2342 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(10));
2343 base::MessageLoop::current()->RunUntilIdle();
2345 ASSERT_EQ(2, pool_->IdleSocketCount());
2347 // Invoke the idle socket cleanup check. Only one socket should be left, the
2348 // used socket. Request it to make sure that it's used.
2350 pool_->CleanupTimedOutIdleSockets();
2351 BoundTestNetLog log;
2352 rv = handle.Init("a",
2353 params_,
2354 LOWEST,
2355 callback.callback(),
2356 pool_.get(),
2357 log.bound());
2358 EXPECT_EQ(OK, rv);
2359 EXPECT_TRUE(handle.is_reused());
2361 TestNetLogEntry::List entries;
2362 log.GetEntries(&entries);
2363 EXPECT_TRUE(LogContainsEntryWithType(
2364 entries, 1, NetLog::TYPE_SOCKET_POOL_REUSED_AN_EXISTING_SOCKET));
2367 // Make sure that we process all pending requests even when we're stalling
2368 // because of multiple releasing disconnected sockets.
2369 TEST_F(ClientSocketPoolBaseTest, MultipleReleasingDisconnectedSockets) {
2370 CreatePoolWithIdleTimeouts(
2371 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2372 base::TimeDelta(), // Time out unused sockets immediately.
2373 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2375 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2377 // Startup 4 connect jobs. Two of them will be pending.
2379 ClientSocketHandle handle;
2380 TestCompletionCallback callback;
2381 int rv = handle.Init("a",
2382 params_,
2383 LOWEST,
2384 callback.callback(),
2385 pool_.get(),
2386 BoundNetLog());
2387 EXPECT_EQ(OK, rv);
2389 ClientSocketHandle handle2;
2390 TestCompletionCallback callback2;
2391 rv = handle2.Init("a",
2392 params_,
2393 LOWEST,
2394 callback2.callback(),
2395 pool_.get(),
2396 BoundNetLog());
2397 EXPECT_EQ(OK, rv);
2399 ClientSocketHandle handle3;
2400 TestCompletionCallback callback3;
2401 rv = handle3.Init("a",
2402 params_,
2403 LOWEST,
2404 callback3.callback(),
2405 pool_.get(),
2406 BoundNetLog());
2407 EXPECT_EQ(ERR_IO_PENDING, rv);
2409 ClientSocketHandle handle4;
2410 TestCompletionCallback callback4;
2411 rv = handle4.Init("a",
2412 params_,
2413 LOWEST,
2414 callback4.callback(),
2415 pool_.get(),
2416 BoundNetLog());
2417 EXPECT_EQ(ERR_IO_PENDING, rv);
2419 // Release two disconnected sockets.
2421 handle.socket()->Disconnect();
2422 handle.Reset();
2423 handle2.socket()->Disconnect();
2424 handle2.Reset();
2426 EXPECT_EQ(OK, callback3.WaitForResult());
2427 EXPECT_FALSE(handle3.is_reused());
2428 EXPECT_EQ(OK, callback4.WaitForResult());
2429 EXPECT_FALSE(handle4.is_reused());
2432 // Regression test for http://crbug.com/42267.
2433 // When DoReleaseSocket() is processed for one socket, it is blocked because the
2434 // other stalled groups all have releasing sockets, so no progress can be made.
2435 TEST_F(ClientSocketPoolBaseTest, SocketLimitReleasingSockets) {
2436 CreatePoolWithIdleTimeouts(
2437 4 /* socket limit */, 4 /* socket limit per group */,
2438 base::TimeDelta(), // Time out unused sockets immediately.
2439 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2441 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2443 // Max out the socket limit with 2 per group.
2445 ClientSocketHandle handle_a[4];
2446 TestCompletionCallback callback_a[4];
2447 ClientSocketHandle handle_b[4];
2448 TestCompletionCallback callback_b[4];
2450 for (int i = 0; i < 2; ++i) {
2451 EXPECT_EQ(OK, handle_a[i].Init("a",
2452 params_,
2453 LOWEST,
2454 callback_a[i].callback(),
2455 pool_.get(),
2456 BoundNetLog()));
2457 EXPECT_EQ(OK, handle_b[i].Init("b",
2458 params_,
2459 LOWEST,
2460 callback_b[i].callback(),
2461 pool_.get(),
2462 BoundNetLog()));
2465 // Make 4 pending requests, 2 per group.
2467 for (int i = 2; i < 4; ++i) {
2468 EXPECT_EQ(ERR_IO_PENDING,
2469 handle_a[i].Init("a",
2470 params_,
2471 LOWEST,
2472 callback_a[i].callback(),
2473 pool_.get(),
2474 BoundNetLog()));
2475 EXPECT_EQ(ERR_IO_PENDING,
2476 handle_b[i].Init("b",
2477 params_,
2478 LOWEST,
2479 callback_b[i].callback(),
2480 pool_.get(),
2481 BoundNetLog()));
2484 // Release b's socket first. The order is important, because in
2485 // DoReleaseSocket(), we'll process b's released socket, and since both b and
2486 // a are stalled, but 'a' is lower lexicographically, we'll process group 'a'
2487 // first, which has a releasing socket, so it refuses to start up another
2488 // ConnectJob. So, we used to infinite loop on this.
2489 handle_b[0].socket()->Disconnect();
2490 handle_b[0].Reset();
2491 handle_a[0].socket()->Disconnect();
2492 handle_a[0].Reset();
2494 // Used to get stuck here.
2495 base::MessageLoop::current()->RunUntilIdle();
2497 handle_b[1].socket()->Disconnect();
2498 handle_b[1].Reset();
2499 handle_a[1].socket()->Disconnect();
2500 handle_a[1].Reset();
2502 for (int i = 2; i < 4; ++i) {
2503 EXPECT_EQ(OK, callback_b[i].WaitForResult());
2504 EXPECT_EQ(OK, callback_a[i].WaitForResult());
2508 TEST_F(ClientSocketPoolBaseTest,
2509 ReleasingDisconnectedSocketsMaintainsPriorityOrder) {
2510 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2512 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2514 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2515 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2516 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2517 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2519 EXPECT_EQ(OK, (*requests())[0]->WaitForResult());
2520 EXPECT_EQ(OK, (*requests())[1]->WaitForResult());
2521 EXPECT_EQ(2u, completion_count());
2523 // Releases one connection.
2524 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::NO_KEEP_ALIVE));
2525 EXPECT_EQ(OK, (*requests())[2]->WaitForResult());
2527 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::NO_KEEP_ALIVE));
2528 EXPECT_EQ(OK, (*requests())[3]->WaitForResult());
2529 EXPECT_EQ(4u, completion_count());
2531 EXPECT_EQ(1, GetOrderOfRequest(1));
2532 EXPECT_EQ(2, GetOrderOfRequest(2));
2533 EXPECT_EQ(3, GetOrderOfRequest(3));
2534 EXPECT_EQ(4, GetOrderOfRequest(4));
2536 // Make sure we test order of all requests made.
2537 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(5));
2540 class TestReleasingSocketRequest : public TestCompletionCallbackBase {
2541 public:
2542 TestReleasingSocketRequest(TestClientSocketPool* pool,
2543 int expected_result,
2544 bool reset_releasing_handle)
2545 : pool_(pool),
2546 expected_result_(expected_result),
2547 reset_releasing_handle_(reset_releasing_handle),
2548 callback_(base::Bind(&TestReleasingSocketRequest::OnComplete,
2549 base::Unretained(this))) {
2552 ~TestReleasingSocketRequest() override {}
2554 ClientSocketHandle* handle() { return &handle_; }
2556 const CompletionCallback& callback() const { return callback_; }
2558 private:
2559 void OnComplete(int result) {
2560 SetResult(result);
2561 if (reset_releasing_handle_)
2562 handle_.Reset();
2564 scoped_refptr<TestSocketParams> con_params(
2565 new TestSocketParams(false /* ignore_limits */));
2566 EXPECT_EQ(expected_result_,
2567 handle2_.Init("a", con_params, DEFAULT_PRIORITY,
2568 callback2_.callback(), pool_, BoundNetLog()));
2571 TestClientSocketPool* const pool_;
2572 int expected_result_;
2573 bool reset_releasing_handle_;
2574 ClientSocketHandle handle_;
2575 ClientSocketHandle handle2_;
2576 CompletionCallback callback_;
2577 TestCompletionCallback callback2_;
2581 TEST_F(ClientSocketPoolBaseTest, AdditionalErrorSocketsDontUseSlot) {
2582 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2584 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
2585 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
2586 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
2588 EXPECT_EQ(static_cast<int>(requests_size()),
2589 client_socket_factory_.allocation_count());
2591 connect_job_factory_->set_job_type(
2592 TestConnectJob::kMockPendingAdditionalErrorStateJob);
2593 TestReleasingSocketRequest req(pool_.get(), OK, false);
2594 EXPECT_EQ(ERR_IO_PENDING,
2595 req.handle()->Init("a", params_, DEFAULT_PRIORITY, req.callback(),
2596 pool_.get(), BoundNetLog()));
2597 // The next job should complete synchronously
2598 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2600 EXPECT_EQ(ERR_CONNECTION_FAILED, req.WaitForResult());
2601 EXPECT_FALSE(req.handle()->is_initialized());
2602 EXPECT_FALSE(req.handle()->socket());
2603 EXPECT_TRUE(req.handle()->is_ssl_error());
2604 EXPECT_FALSE(req.handle()->ssl_error_response_info().headers.get() == NULL);
2607 // http://crbug.com/44724 regression test.
2608 // We start releasing the pool when we flush on network change. When that
2609 // happens, the only active references are in the ClientSocketHandles. When a
2610 // ConnectJob completes and calls back into the last ClientSocketHandle, that
2611 // callback can release the last reference and delete the pool. After the
2612 // callback finishes, we go back to the stack frame within the now-deleted pool.
2613 // Executing any code that refers to members of the now-deleted pool can cause
2614 // crashes.
2615 TEST_F(ClientSocketPoolBaseTest, CallbackThatReleasesPool) {
2616 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2617 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
2619 ClientSocketHandle handle;
2620 TestCompletionCallback callback;
2621 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2622 params_,
2623 DEFAULT_PRIORITY,
2624 callback.callback(),
2625 pool_.get(),
2626 BoundNetLog()));
2628 pool_->FlushWithError(ERR_NETWORK_CHANGED);
2630 // We'll call back into this now.
2631 callback.WaitForResult();
2634 TEST_F(ClientSocketPoolBaseTest, DoNotReuseSocketAfterFlush) {
2635 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2636 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2638 ClientSocketHandle handle;
2639 TestCompletionCallback callback;
2640 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2641 params_,
2642 DEFAULT_PRIORITY,
2643 callback.callback(),
2644 pool_.get(),
2645 BoundNetLog()));
2646 EXPECT_EQ(OK, callback.WaitForResult());
2647 EXPECT_EQ(ClientSocketHandle::UNUSED, handle.reuse_type());
2649 pool_->FlushWithError(ERR_NETWORK_CHANGED);
2651 handle.Reset();
2652 base::MessageLoop::current()->RunUntilIdle();
2654 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2655 params_,
2656 DEFAULT_PRIORITY,
2657 callback.callback(),
2658 pool_.get(),
2659 BoundNetLog()));
2660 EXPECT_EQ(OK, callback.WaitForResult());
2661 EXPECT_EQ(ClientSocketHandle::UNUSED, handle.reuse_type());
2664 class ConnectWithinCallback : public TestCompletionCallbackBase {
2665 public:
2666 ConnectWithinCallback(
2667 const std::string& group_name,
2668 const scoped_refptr<TestSocketParams>& params,
2669 TestClientSocketPool* pool)
2670 : group_name_(group_name),
2671 params_(params),
2672 pool_(pool),
2673 callback_(base::Bind(&ConnectWithinCallback::OnComplete,
2674 base::Unretained(this))) {
2677 ~ConnectWithinCallback() override {}
2679 int WaitForNestedResult() {
2680 return nested_callback_.WaitForResult();
2683 const CompletionCallback& callback() const { return callback_; }
2685 private:
2686 void OnComplete(int result) {
2687 SetResult(result);
2688 EXPECT_EQ(ERR_IO_PENDING,
2689 handle_.Init(group_name_,
2690 params_,
2691 DEFAULT_PRIORITY,
2692 nested_callback_.callback(),
2693 pool_,
2694 BoundNetLog()));
2697 const std::string group_name_;
2698 const scoped_refptr<TestSocketParams> params_;
2699 TestClientSocketPool* const pool_;
2700 ClientSocketHandle handle_;
2701 CompletionCallback callback_;
2702 TestCompletionCallback nested_callback_;
2704 DISALLOW_COPY_AND_ASSIGN(ConnectWithinCallback);
2707 TEST_F(ClientSocketPoolBaseTest, AbortAllRequestsOnFlush) {
2708 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2710 // First job will be waiting until it gets aborted.
2711 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2713 ClientSocketHandle handle;
2714 ConnectWithinCallback callback("a", params_, pool_.get());
2715 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2716 params_,
2717 DEFAULT_PRIORITY,
2718 callback.callback(),
2719 pool_.get(),
2720 BoundNetLog()));
2722 // Second job will be started during the first callback, and will
2723 // asynchronously complete with OK.
2724 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2725 pool_->FlushWithError(ERR_NETWORK_CHANGED);
2726 EXPECT_EQ(ERR_NETWORK_CHANGED, callback.WaitForResult());
2727 EXPECT_EQ(OK, callback.WaitForNestedResult());
2730 // Cancel a pending socket request while we're at max sockets,
2731 // and verify that the backup socket firing doesn't cause a crash.
2732 TEST_F(ClientSocketPoolBaseTest, BackupSocketCancelAtMaxSockets) {
2733 // Max 4 sockets globally, max 4 sockets per group.
2734 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
2735 pool_->EnableConnectBackupJobs();
2737 // Create the first socket and set to ERR_IO_PENDING. This starts the backup
2738 // timer.
2739 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2740 ClientSocketHandle handle;
2741 TestCompletionCallback callback;
2742 EXPECT_EQ(ERR_IO_PENDING, handle.Init("bar",
2743 params_,
2744 DEFAULT_PRIORITY,
2745 callback.callback(),
2746 pool_.get(),
2747 BoundNetLog()));
2749 // Start (MaxSockets - 1) connected sockets to reach max sockets.
2750 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2751 ClientSocketHandle handles[kDefaultMaxSockets];
2752 for (int i = 1; i < kDefaultMaxSockets; ++i) {
2753 TestCompletionCallback callback;
2754 EXPECT_EQ(OK, handles[i].Init("bar",
2755 params_,
2756 DEFAULT_PRIORITY,
2757 callback.callback(),
2758 pool_.get(),
2759 BoundNetLog()));
2762 base::MessageLoop::current()->RunUntilIdle();
2764 // Cancel the pending request.
2765 handle.Reset();
2767 // Wait for the backup timer to fire (add some slop to ensure it fires)
2768 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(
2769 ClientSocketPool::kMaxConnectRetryIntervalMs / 2 * 3));
2771 base::MessageLoop::current()->RunUntilIdle();
2772 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
2775 TEST_F(ClientSocketPoolBaseTest, CancelBackupSocketAfterCancelingAllRequests) {
2776 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
2777 pool_->EnableConnectBackupJobs();
2779 // Create the first socket and set to ERR_IO_PENDING. This starts the backup
2780 // timer.
2781 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2782 ClientSocketHandle handle;
2783 TestCompletionCallback callback;
2784 EXPECT_EQ(ERR_IO_PENDING, handle.Init("bar",
2785 params_,
2786 DEFAULT_PRIORITY,
2787 callback.callback(),
2788 pool_.get(),
2789 BoundNetLog()));
2790 ASSERT_TRUE(pool_->HasGroup("bar"));
2791 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("bar"));
2792 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("bar"));
2794 // Cancel the socket request. This should cancel the backup timer. Wait for
2795 // the backup time to see if it indeed got canceled.
2796 handle.Reset();
2797 // Wait for the backup timer to fire (add some slop to ensure it fires)
2798 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(
2799 ClientSocketPool::kMaxConnectRetryIntervalMs / 2 * 3));
2800 base::MessageLoop::current()->RunUntilIdle();
2801 ASSERT_TRUE(pool_->HasGroup("bar"));
2802 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("bar"));
2805 TEST_F(ClientSocketPoolBaseTest, CancelBackupSocketAfterFinishingAllRequests) {
2806 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
2807 pool_->EnableConnectBackupJobs();
2809 // Create the first socket and set to ERR_IO_PENDING. This starts the backup
2810 // timer.
2811 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2812 ClientSocketHandle handle;
2813 TestCompletionCallback callback;
2814 EXPECT_EQ(ERR_IO_PENDING, handle.Init("bar",
2815 params_,
2816 DEFAULT_PRIORITY,
2817 callback.callback(),
2818 pool_.get(),
2819 BoundNetLog()));
2820 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2821 ClientSocketHandle handle2;
2822 TestCompletionCallback callback2;
2823 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("bar",
2824 params_,
2825 DEFAULT_PRIORITY,
2826 callback2.callback(),
2827 pool_.get(),
2828 BoundNetLog()));
2829 ASSERT_TRUE(pool_->HasGroup("bar"));
2830 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("bar"));
2832 // Cancel request 1 and then complete request 2. With the requests finished,
2833 // the backup timer should be cancelled.
2834 handle.Reset();
2835 EXPECT_EQ(OK, callback2.WaitForResult());
2836 // Wait for the backup timer to fire (add some slop to ensure it fires)
2837 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(
2838 ClientSocketPool::kMaxConnectRetryIntervalMs / 2 * 3));
2839 base::MessageLoop::current()->RunUntilIdle();
2842 // Test delayed socket binding for the case where we have two connects,
2843 // and while one is waiting on a connect, the other frees up.
2844 // The socket waiting on a connect should switch immediately to the freed
2845 // up socket.
2846 TEST_F(ClientSocketPoolBaseTest, DelayedSocketBindingWaitingForConnect) {
2847 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2848 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2850 ClientSocketHandle handle1;
2851 TestCompletionCallback callback;
2852 EXPECT_EQ(ERR_IO_PENDING,
2853 handle1.Init("a",
2854 params_,
2855 DEFAULT_PRIORITY,
2856 callback.callback(),
2857 pool_.get(),
2858 BoundNetLog()));
2859 EXPECT_EQ(OK, callback.WaitForResult());
2861 // No idle sockets, no pending jobs.
2862 EXPECT_EQ(0, pool_->IdleSocketCount());
2863 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2865 // Create a second socket to the same host, but this one will wait.
2866 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2867 ClientSocketHandle handle2;
2868 EXPECT_EQ(ERR_IO_PENDING,
2869 handle2.Init("a",
2870 params_,
2871 DEFAULT_PRIORITY,
2872 callback.callback(),
2873 pool_.get(),
2874 BoundNetLog()));
2875 // No idle sockets, and one connecting job.
2876 EXPECT_EQ(0, pool_->IdleSocketCount());
2877 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2879 // Return the first handle to the pool. This will initiate the delayed
2880 // binding.
2881 handle1.Reset();
2883 base::MessageLoop::current()->RunUntilIdle();
2885 // Still no idle sockets, still one pending connect job.
2886 EXPECT_EQ(0, pool_->IdleSocketCount());
2887 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2889 // The second socket connected, even though it was a Waiting Job.
2890 EXPECT_EQ(OK, callback.WaitForResult());
2892 // And we can see there is still one job waiting.
2893 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2895 // Finally, signal the waiting Connect.
2896 client_socket_factory_.SignalJobs();
2897 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2899 base::MessageLoop::current()->RunUntilIdle();
2902 // Test delayed socket binding when a group is at capacity and one
2903 // of the group's sockets frees up.
2904 TEST_F(ClientSocketPoolBaseTest, DelayedSocketBindingAtGroupCapacity) {
2905 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2906 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2908 ClientSocketHandle handle1;
2909 TestCompletionCallback callback;
2910 EXPECT_EQ(ERR_IO_PENDING,
2911 handle1.Init("a",
2912 params_,
2913 DEFAULT_PRIORITY,
2914 callback.callback(),
2915 pool_.get(),
2916 BoundNetLog()));
2917 EXPECT_EQ(OK, callback.WaitForResult());
2919 // No idle sockets, no pending jobs.
2920 EXPECT_EQ(0, pool_->IdleSocketCount());
2921 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2923 // Create a second socket to the same host, but this one will wait.
2924 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2925 ClientSocketHandle handle2;
2926 EXPECT_EQ(ERR_IO_PENDING,
2927 handle2.Init("a",
2928 params_,
2929 DEFAULT_PRIORITY,
2930 callback.callback(),
2931 pool_.get(),
2932 BoundNetLog()));
2933 // No idle sockets, and one connecting job.
2934 EXPECT_EQ(0, pool_->IdleSocketCount());
2935 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2937 // Return the first handle to the pool. This will initiate the delayed
2938 // binding.
2939 handle1.Reset();
2941 base::MessageLoop::current()->RunUntilIdle();
2943 // Still no idle sockets, still one pending connect job.
2944 EXPECT_EQ(0, pool_->IdleSocketCount());
2945 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2947 // The second socket connected, even though it was a Waiting Job.
2948 EXPECT_EQ(OK, callback.WaitForResult());
2950 // And we can see there is still one job waiting.
2951 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2953 // Finally, signal the waiting Connect.
2954 client_socket_factory_.SignalJobs();
2955 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2957 base::MessageLoop::current()->RunUntilIdle();
2960 // Test out the case where we have one socket connected, one
2961 // connecting, when the first socket finishes and goes idle.
2962 // Although the second connection is pending, the second request
2963 // should complete, by taking the first socket's idle socket.
2964 TEST_F(ClientSocketPoolBaseTest, DelayedSocketBindingAtStall) {
2965 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2966 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2968 ClientSocketHandle handle1;
2969 TestCompletionCallback callback;
2970 EXPECT_EQ(ERR_IO_PENDING,
2971 handle1.Init("a",
2972 params_,
2973 DEFAULT_PRIORITY,
2974 callback.callback(),
2975 pool_.get(),
2976 BoundNetLog()));
2977 EXPECT_EQ(OK, callback.WaitForResult());
2979 // No idle sockets, no pending jobs.
2980 EXPECT_EQ(0, pool_->IdleSocketCount());
2981 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2983 // Create a second socket to the same host, but this one will wait.
2984 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2985 ClientSocketHandle handle2;
2986 EXPECT_EQ(ERR_IO_PENDING,
2987 handle2.Init("a",
2988 params_,
2989 DEFAULT_PRIORITY,
2990 callback.callback(),
2991 pool_.get(),
2992 BoundNetLog()));
2993 // No idle sockets, and one connecting job.
2994 EXPECT_EQ(0, pool_->IdleSocketCount());
2995 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2997 // Return the first handle to the pool. This will initiate the delayed
2998 // binding.
2999 handle1.Reset();
3001 base::MessageLoop::current()->RunUntilIdle();
3003 // Still no idle sockets, still one pending connect job.
3004 EXPECT_EQ(0, pool_->IdleSocketCount());
3005 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3007 // The second socket connected, even though it was a Waiting Job.
3008 EXPECT_EQ(OK, callback.WaitForResult());
3010 // And we can see there is still one job waiting.
3011 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3013 // Finally, signal the waiting Connect.
3014 client_socket_factory_.SignalJobs();
3015 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3017 base::MessageLoop::current()->RunUntilIdle();
3020 // Cover the case where on an available socket slot, we have one pending
3021 // request that completes synchronously, thereby making the Group empty.
3022 TEST_F(ClientSocketPoolBaseTest, SynchronouslyProcessOnePendingRequest) {
3023 const int kUnlimitedSockets = 100;
3024 const int kOneSocketPerGroup = 1;
3025 CreatePool(kUnlimitedSockets, kOneSocketPerGroup);
3027 // Make the first request asynchronous fail.
3028 // This will free up a socket slot later.
3029 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
3031 ClientSocketHandle handle1;
3032 TestCompletionCallback callback1;
3033 EXPECT_EQ(ERR_IO_PENDING,
3034 handle1.Init("a",
3035 params_,
3036 DEFAULT_PRIORITY,
3037 callback1.callback(),
3038 pool_.get(),
3039 BoundNetLog()));
3040 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3042 // Make the second request synchronously fail. This should make the Group
3043 // empty.
3044 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
3045 ClientSocketHandle handle2;
3046 TestCompletionCallback callback2;
3047 // It'll be ERR_IO_PENDING now, but the TestConnectJob will synchronously fail
3048 // when created.
3049 EXPECT_EQ(ERR_IO_PENDING,
3050 handle2.Init("a",
3051 params_,
3052 DEFAULT_PRIORITY,
3053 callback2.callback(),
3054 pool_.get(),
3055 BoundNetLog()));
3057 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3059 EXPECT_EQ(ERR_CONNECTION_FAILED, callback1.WaitForResult());
3060 EXPECT_EQ(ERR_CONNECTION_FAILED, callback2.WaitForResult());
3061 EXPECT_FALSE(pool_->HasGroup("a"));
3064 TEST_F(ClientSocketPoolBaseTest, PreferUsedSocketToUnusedSocket) {
3065 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
3067 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3069 ClientSocketHandle handle1;
3070 TestCompletionCallback callback1;
3071 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3072 params_,
3073 DEFAULT_PRIORITY,
3074 callback1.callback(),
3075 pool_.get(),
3076 BoundNetLog()));
3078 ClientSocketHandle handle2;
3079 TestCompletionCallback callback2;
3080 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3081 params_,
3082 DEFAULT_PRIORITY,
3083 callback2.callback(),
3084 pool_.get(),
3085 BoundNetLog()));
3086 ClientSocketHandle handle3;
3087 TestCompletionCallback callback3;
3088 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("a",
3089 params_,
3090 DEFAULT_PRIORITY,
3091 callback3.callback(),
3092 pool_.get(),
3093 BoundNetLog()));
3095 EXPECT_EQ(OK, callback1.WaitForResult());
3096 EXPECT_EQ(OK, callback2.WaitForResult());
3097 EXPECT_EQ(OK, callback3.WaitForResult());
3099 // Use the socket.
3100 EXPECT_EQ(1, handle1.socket()->Write(NULL, 1, CompletionCallback()));
3101 EXPECT_EQ(1, handle3.socket()->Write(NULL, 1, CompletionCallback()));
3103 handle1.Reset();
3104 handle2.Reset();
3105 handle3.Reset();
3107 EXPECT_EQ(OK, handle1.Init("a",
3108 params_,
3109 DEFAULT_PRIORITY,
3110 callback1.callback(),
3111 pool_.get(),
3112 BoundNetLog()));
3113 EXPECT_EQ(OK, handle2.Init("a",
3114 params_,
3115 DEFAULT_PRIORITY,
3116 callback2.callback(),
3117 pool_.get(),
3118 BoundNetLog()));
3119 EXPECT_EQ(OK, handle3.Init("a",
3120 params_,
3121 DEFAULT_PRIORITY,
3122 callback3.callback(),
3123 pool_.get(),
3124 BoundNetLog()));
3126 EXPECT_TRUE(handle1.socket()->WasEverUsed());
3127 EXPECT_TRUE(handle2.socket()->WasEverUsed());
3128 EXPECT_FALSE(handle3.socket()->WasEverUsed());
3131 TEST_F(ClientSocketPoolBaseTest, RequestSockets) {
3132 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3133 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3135 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3137 ASSERT_TRUE(pool_->HasGroup("a"));
3138 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3139 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3140 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3142 ClientSocketHandle handle1;
3143 TestCompletionCallback callback1;
3144 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3145 params_,
3146 DEFAULT_PRIORITY,
3147 callback1.callback(),
3148 pool_.get(),
3149 BoundNetLog()));
3151 ClientSocketHandle handle2;
3152 TestCompletionCallback callback2;
3153 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3154 params_,
3155 DEFAULT_PRIORITY,
3156 callback2.callback(),
3157 pool_.get(),
3158 BoundNetLog()));
3160 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3161 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3162 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3164 EXPECT_EQ(OK, callback1.WaitForResult());
3165 EXPECT_EQ(OK, callback2.WaitForResult());
3166 handle1.Reset();
3167 handle2.Reset();
3169 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3170 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3171 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3174 TEST_F(ClientSocketPoolBaseTest, RequestSocketsWhenAlreadyHaveAConnectJob) {
3175 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3176 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3178 ClientSocketHandle handle1;
3179 TestCompletionCallback callback1;
3180 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3181 params_,
3182 DEFAULT_PRIORITY,
3183 callback1.callback(),
3184 pool_.get(),
3185 BoundNetLog()));
3187 ASSERT_TRUE(pool_->HasGroup("a"));
3188 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3189 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3190 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3192 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3194 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3195 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3196 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3198 ClientSocketHandle handle2;
3199 TestCompletionCallback callback2;
3200 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3201 params_,
3202 DEFAULT_PRIORITY,
3203 callback2.callback(),
3204 pool_.get(),
3205 BoundNetLog()));
3207 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3208 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3209 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3211 EXPECT_EQ(OK, callback1.WaitForResult());
3212 EXPECT_EQ(OK, callback2.WaitForResult());
3213 handle1.Reset();
3214 handle2.Reset();
3216 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3217 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3218 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3221 TEST_F(ClientSocketPoolBaseTest,
3222 RequestSocketsWhenAlreadyHaveMultipleConnectJob) {
3223 CreatePool(4, 4);
3224 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3226 ClientSocketHandle handle1;
3227 TestCompletionCallback callback1;
3228 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3229 params_,
3230 DEFAULT_PRIORITY,
3231 callback1.callback(),
3232 pool_.get(),
3233 BoundNetLog()));
3235 ClientSocketHandle handle2;
3236 TestCompletionCallback callback2;
3237 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3238 params_,
3239 DEFAULT_PRIORITY,
3240 callback2.callback(),
3241 pool_.get(),
3242 BoundNetLog()));
3244 ClientSocketHandle handle3;
3245 TestCompletionCallback callback3;
3246 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("a",
3247 params_,
3248 DEFAULT_PRIORITY,
3249 callback3.callback(),
3250 pool_.get(),
3251 BoundNetLog()));
3253 ASSERT_TRUE(pool_->HasGroup("a"));
3254 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3255 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3256 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3258 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3260 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3261 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3262 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3264 EXPECT_EQ(OK, callback1.WaitForResult());
3265 EXPECT_EQ(OK, callback2.WaitForResult());
3266 EXPECT_EQ(OK, callback3.WaitForResult());
3267 handle1.Reset();
3268 handle2.Reset();
3269 handle3.Reset();
3271 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3272 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3273 EXPECT_EQ(3, pool_->IdleSocketCountInGroup("a"));
3276 TEST_F(ClientSocketPoolBaseTest, RequestSocketsAtMaxSocketLimit) {
3277 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
3278 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3280 ASSERT_FALSE(pool_->HasGroup("a"));
3282 pool_->RequestSockets("a", &params_, kDefaultMaxSockets,
3283 BoundNetLog());
3285 ASSERT_TRUE(pool_->HasGroup("a"));
3286 EXPECT_EQ(kDefaultMaxSockets, pool_->NumConnectJobsInGroup("a"));
3287 EXPECT_EQ(kDefaultMaxSockets, pool_->NumUnassignedConnectJobsInGroup("a"));
3289 ASSERT_FALSE(pool_->HasGroup("b"));
3291 pool_->RequestSockets("b", &params_, kDefaultMaxSockets,
3292 BoundNetLog());
3294 ASSERT_FALSE(pool_->HasGroup("b"));
3297 TEST_F(ClientSocketPoolBaseTest, RequestSocketsHitMaxSocketLimit) {
3298 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
3299 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3301 ASSERT_FALSE(pool_->HasGroup("a"));
3303 pool_->RequestSockets("a", &params_, kDefaultMaxSockets - 1,
3304 BoundNetLog());
3306 ASSERT_TRUE(pool_->HasGroup("a"));
3307 EXPECT_EQ(kDefaultMaxSockets - 1, pool_->NumConnectJobsInGroup("a"));
3308 EXPECT_EQ(kDefaultMaxSockets - 1,
3309 pool_->NumUnassignedConnectJobsInGroup("a"));
3310 EXPECT_FALSE(pool_->IsStalled());
3312 ASSERT_FALSE(pool_->HasGroup("b"));
3314 pool_->RequestSockets("b", &params_, kDefaultMaxSockets,
3315 BoundNetLog());
3317 ASSERT_TRUE(pool_->HasGroup("b"));
3318 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("b"));
3319 EXPECT_FALSE(pool_->IsStalled());
3322 TEST_F(ClientSocketPoolBaseTest, RequestSocketsCountIdleSockets) {
3323 CreatePool(4, 4);
3324 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3326 ClientSocketHandle handle1;
3327 TestCompletionCallback callback1;
3328 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3329 params_,
3330 DEFAULT_PRIORITY,
3331 callback1.callback(),
3332 pool_.get(),
3333 BoundNetLog()));
3334 ASSERT_EQ(OK, callback1.WaitForResult());
3335 handle1.Reset();
3337 ASSERT_TRUE(pool_->HasGroup("a"));
3338 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3339 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3340 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3342 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3344 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3345 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3346 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3349 TEST_F(ClientSocketPoolBaseTest, RequestSocketsCountActiveSockets) {
3350 CreatePool(4, 4);
3351 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3353 ClientSocketHandle handle1;
3354 TestCompletionCallback callback1;
3355 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3356 params_,
3357 DEFAULT_PRIORITY,
3358 callback1.callback(),
3359 pool_.get(),
3360 BoundNetLog()));
3361 ASSERT_EQ(OK, callback1.WaitForResult());
3363 ASSERT_TRUE(pool_->HasGroup("a"));
3364 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3365 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3366 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3367 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
3369 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3371 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3372 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3373 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3374 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
3377 TEST_F(ClientSocketPoolBaseTest, RequestSocketsSynchronous) {
3378 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3379 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3381 pool_->RequestSockets("a", &params_, kDefaultMaxSocketsPerGroup,
3382 BoundNetLog());
3384 ASSERT_TRUE(pool_->HasGroup("a"));
3385 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3386 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3387 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->IdleSocketCountInGroup("a"));
3389 pool_->RequestSockets("b", &params_, kDefaultMaxSocketsPerGroup,
3390 BoundNetLog());
3392 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("b"));
3393 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3394 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->IdleSocketCountInGroup("b"));
3397 TEST_F(ClientSocketPoolBaseTest, RequestSocketsSynchronousError) {
3398 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3399 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
3401 pool_->RequestSockets("a", &params_, kDefaultMaxSocketsPerGroup,
3402 BoundNetLog());
3404 ASSERT_FALSE(pool_->HasGroup("a"));
3406 connect_job_factory_->set_job_type(
3407 TestConnectJob::kMockAdditionalErrorStateJob);
3408 pool_->RequestSockets("a", &params_, kDefaultMaxSocketsPerGroup,
3409 BoundNetLog());
3411 ASSERT_FALSE(pool_->HasGroup("a"));
3414 TEST_F(ClientSocketPoolBaseTest, RequestSocketsMultipleTimesDoesNothing) {
3415 CreatePool(4, 4);
3416 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3418 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3420 ASSERT_TRUE(pool_->HasGroup("a"));
3421 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3422 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3423 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3425 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3426 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3427 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3428 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3430 ClientSocketHandle handle1;
3431 TestCompletionCallback callback1;
3432 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3433 params_,
3434 DEFAULT_PRIORITY,
3435 callback1.callback(),
3436 pool_.get(),
3437 BoundNetLog()));
3438 ASSERT_EQ(OK, callback1.WaitForResult());
3440 ClientSocketHandle handle2;
3441 TestCompletionCallback callback2;
3442 int rv = handle2.Init("a",
3443 params_,
3444 DEFAULT_PRIORITY,
3445 callback2.callback(),
3446 pool_.get(),
3447 BoundNetLog());
3448 if (rv != OK) {
3449 EXPECT_EQ(ERR_IO_PENDING, rv);
3450 EXPECT_EQ(OK, callback2.WaitForResult());
3453 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3454 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3455 EXPECT_EQ(2, pool_->NumActiveSocketsInGroup("a"));
3456 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3458 handle1.Reset();
3459 handle2.Reset();
3461 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3462 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3463 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3465 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3466 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3467 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3468 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3471 TEST_F(ClientSocketPoolBaseTest, RequestSocketsDifferentNumSockets) {
3472 CreatePool(4, 4);
3473 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3475 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3477 ASSERT_TRUE(pool_->HasGroup("a"));
3478 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3479 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3480 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3482 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3483 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3484 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3485 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3487 pool_->RequestSockets("a", &params_, 3, BoundNetLog());
3488 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3489 EXPECT_EQ(3, pool_->NumUnassignedConnectJobsInGroup("a"));
3490 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3492 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3493 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3494 EXPECT_EQ(3, pool_->NumUnassignedConnectJobsInGroup("a"));
3495 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3498 TEST_F(ClientSocketPoolBaseTest, PreconnectJobsTakenByNormalRequests) {
3499 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3500 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3502 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3504 ASSERT_TRUE(pool_->HasGroup("a"));
3505 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3506 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3507 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3509 ClientSocketHandle handle1;
3510 TestCompletionCallback callback1;
3511 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3512 params_,
3513 DEFAULT_PRIORITY,
3514 callback1.callback(),
3515 pool_.get(),
3516 BoundNetLog()));
3518 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3519 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3520 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3522 ASSERT_EQ(OK, callback1.WaitForResult());
3524 // Make sure if a preconnected socket is not fully connected when a request
3525 // starts, it has a connect start time.
3526 TestLoadTimingInfoConnectedNotReused(handle1);
3527 handle1.Reset();
3529 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3532 // Checks that fully connected preconnect jobs have no connect times, and are
3533 // marked as reused.
3534 TEST_F(ClientSocketPoolBaseTest, ConnectedPreconnectJobsHaveNoConnectTimes) {
3535 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3536 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3537 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3539 ASSERT_TRUE(pool_->HasGroup("a"));
3540 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3541 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3542 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3544 ClientSocketHandle handle;
3545 TestCompletionCallback callback;
3546 EXPECT_EQ(OK, handle.Init("a",
3547 params_,
3548 DEFAULT_PRIORITY,
3549 callback.callback(),
3550 pool_.get(),
3551 BoundNetLog()));
3553 // Make sure the idle socket was used.
3554 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3556 TestLoadTimingInfoConnectedReused(handle);
3557 handle.Reset();
3558 TestLoadTimingInfoNotConnected(handle);
3561 // http://crbug.com/64940 regression test.
3562 TEST_F(ClientSocketPoolBaseTest, PreconnectClosesIdleSocketRemovesGroup) {
3563 const int kMaxTotalSockets = 3;
3564 const int kMaxSocketsPerGroup = 2;
3565 CreatePool(kMaxTotalSockets, kMaxSocketsPerGroup);
3566 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3568 // Note that group name ordering matters here. "a" comes before "b", so
3569 // CloseOneIdleSocket() will try to close "a"'s idle socket.
3571 // Set up one idle socket in "a".
3572 ClientSocketHandle handle1;
3573 TestCompletionCallback callback1;
3574 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3575 params_,
3576 DEFAULT_PRIORITY,
3577 callback1.callback(),
3578 pool_.get(),
3579 BoundNetLog()));
3581 ASSERT_EQ(OK, callback1.WaitForResult());
3582 handle1.Reset();
3583 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3585 // Set up two active sockets in "b".
3586 ClientSocketHandle handle2;
3587 TestCompletionCallback callback2;
3588 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("b",
3589 params_,
3590 DEFAULT_PRIORITY,
3591 callback1.callback(),
3592 pool_.get(),
3593 BoundNetLog()));
3594 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("b",
3595 params_,
3596 DEFAULT_PRIORITY,
3597 callback2.callback(),
3598 pool_.get(),
3599 BoundNetLog()));
3601 ASSERT_EQ(OK, callback1.WaitForResult());
3602 ASSERT_EQ(OK, callback2.WaitForResult());
3603 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("b"));
3604 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3605 EXPECT_EQ(2, pool_->NumActiveSocketsInGroup("b"));
3607 // Now we have 1 idle socket in "a" and 2 active sockets in "b". This means
3608 // we've maxed out on sockets, since we set |kMaxTotalSockets| to 3.
3609 // Requesting 2 preconnected sockets for "a" should fail to allocate any more
3610 // sockets for "a", and "b" should still have 2 active sockets.
3612 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3613 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3614 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3615 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3616 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("a"));
3617 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("b"));
3618 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3619 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("b"));
3620 EXPECT_EQ(2, pool_->NumActiveSocketsInGroup("b"));
3622 // Now release the 2 active sockets for "b". This will give us 1 idle socket
3623 // in "a" and 2 idle sockets in "b". Requesting 2 preconnected sockets for
3624 // "a" should result in closing 1 for "b".
3625 handle1.Reset();
3626 handle2.Reset();
3627 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("b"));
3628 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("b"));
3630 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3631 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3632 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3633 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3634 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("a"));
3635 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("b"));
3636 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3637 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("b"));
3638 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("b"));
3641 TEST_F(ClientSocketPoolBaseTest, PreconnectWithoutBackupJob) {
3642 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3643 pool_->EnableConnectBackupJobs();
3645 // Make the ConnectJob hang until it times out, shorten the timeout.
3646 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
3647 connect_job_factory_->set_timeout_duration(
3648 base::TimeDelta::FromMilliseconds(500));
3649 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3650 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3651 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3652 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3654 // Verify the backup timer doesn't create a backup job, by making
3655 // the backup job a pending job instead of a waiting job, so it
3656 // *would* complete if it were created.
3657 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3658 base::MessageLoop::current()->PostDelayedTask(
3659 FROM_HERE,
3660 base::MessageLoop::QuitClosure(),
3661 base::TimeDelta::FromSeconds(1));
3662 base::MessageLoop::current()->Run();
3663 EXPECT_FALSE(pool_->HasGroup("a"));
3666 TEST_F(ClientSocketPoolBaseTest, PreconnectWithBackupJob) {
3667 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3668 pool_->EnableConnectBackupJobs();
3670 // Make the ConnectJob hang forever.
3671 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
3672 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3673 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3674 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3675 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3676 base::MessageLoop::current()->RunUntilIdle();
3678 // Make the backup job be a pending job, so it completes normally.
3679 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3680 ClientSocketHandle handle;
3681 TestCompletionCallback callback;
3682 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
3683 params_,
3684 DEFAULT_PRIORITY,
3685 callback.callback(),
3686 pool_.get(),
3687 BoundNetLog()));
3688 // Timer has started, but the backup connect job shouldn't be created yet.
3689 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3690 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3691 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3692 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("a"));
3693 ASSERT_EQ(OK, callback.WaitForResult());
3695 // The hung connect job should still be there, but everything else should be
3696 // complete.
3697 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3698 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3699 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3700 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
3703 // Tests that a preconnect that starts out with unread data can still be used.
3704 // http://crbug.com/334467
3705 TEST_F(ClientSocketPoolBaseTest, PreconnectWithUnreadData) {
3706 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3707 connect_job_factory_->set_job_type(TestConnectJob::kMockUnreadDataJob);
3709 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3711 ASSERT_TRUE(pool_->HasGroup("a"));
3712 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3713 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3714 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3716 // Fail future jobs to be sure that handle receives the preconnected socket
3717 // rather than closing it and making a new one.
3718 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
3719 ClientSocketHandle handle;
3720 TestCompletionCallback callback;
3721 EXPECT_EQ(OK, handle.Init("a",
3722 params_,
3723 DEFAULT_PRIORITY,
3724 callback.callback(),
3725 pool_.get(),
3726 BoundNetLog()));
3728 ASSERT_TRUE(pool_->HasGroup("a"));
3729 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3730 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3731 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3733 // Drain the pending read.
3734 EXPECT_EQ(1, handle.socket()->Read(NULL, 1, CompletionCallback()));
3736 TestLoadTimingInfoConnectedReused(handle);
3737 handle.Reset();
3739 // The socket should be usable now that it's idle again.
3740 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3743 class MockLayeredPool : public HigherLayeredPool {
3744 public:
3745 MockLayeredPool(TestClientSocketPool* pool,
3746 const std::string& group_name)
3747 : pool_(pool),
3748 group_name_(group_name),
3749 can_release_connection_(true) {
3750 pool_->AddHigherLayeredPool(this);
3753 ~MockLayeredPool() {
3754 pool_->RemoveHigherLayeredPool(this);
3757 int RequestSocket(TestClientSocketPool* pool) {
3758 scoped_refptr<TestSocketParams> params(
3759 new TestSocketParams(false /* ignore_limits */));
3760 return handle_.Init(group_name_, params, DEFAULT_PRIORITY,
3761 callback_.callback(), pool, BoundNetLog());
3764 int RequestSocketWithoutLimits(TestClientSocketPool* pool) {
3765 scoped_refptr<TestSocketParams> params(
3766 new TestSocketParams(true /* ignore_limits */));
3767 return handle_.Init(group_name_, params, MAXIMUM_PRIORITY,
3768 callback_.callback(), pool, BoundNetLog());
3771 bool ReleaseOneConnection() {
3772 if (!handle_.is_initialized() || !can_release_connection_) {
3773 return false;
3775 handle_.socket()->Disconnect();
3776 handle_.Reset();
3777 return true;
3780 void set_can_release_connection(bool can_release_connection) {
3781 can_release_connection_ = can_release_connection;
3784 MOCK_METHOD0(CloseOneIdleConnection, bool());
3786 private:
3787 TestClientSocketPool* const pool_;
3788 ClientSocketHandle handle_;
3789 TestCompletionCallback callback_;
3790 const std::string group_name_;
3791 bool can_release_connection_;
3794 TEST_F(ClientSocketPoolBaseTest, FailToCloseIdleSocketsNotHeldByLayeredPool) {
3795 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3796 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3798 MockLayeredPool mock_layered_pool(pool_.get(), "foo");
3799 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3800 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3801 .WillOnce(Return(false));
3802 EXPECT_FALSE(pool_->CloseOneIdleConnectionInHigherLayeredPool());
3805 TEST_F(ClientSocketPoolBaseTest, ForciblyCloseIdleSocketsHeldByLayeredPool) {
3806 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3807 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3809 MockLayeredPool mock_layered_pool(pool_.get(), "foo");
3810 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3811 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3812 .WillOnce(Invoke(&mock_layered_pool,
3813 &MockLayeredPool::ReleaseOneConnection));
3814 EXPECT_TRUE(pool_->CloseOneIdleConnectionInHigherLayeredPool());
3817 // Tests the basic case of closing an idle socket in a higher layered pool when
3818 // a new request is issued and the lower layer pool is stalled.
3819 TEST_F(ClientSocketPoolBaseTest, CloseIdleSocketsHeldByLayeredPoolWhenNeeded) {
3820 CreatePool(1, 1);
3821 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3823 MockLayeredPool mock_layered_pool(pool_.get(), "foo");
3824 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3825 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3826 .WillOnce(Invoke(&mock_layered_pool,
3827 &MockLayeredPool::ReleaseOneConnection));
3828 ClientSocketHandle handle;
3829 TestCompletionCallback callback;
3830 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
3831 params_,
3832 DEFAULT_PRIORITY,
3833 callback.callback(),
3834 pool_.get(),
3835 BoundNetLog()));
3836 EXPECT_EQ(OK, callback.WaitForResult());
3839 // Same as above, but the idle socket is in the same group as the stalled
3840 // socket, and closes the only other request in its group when closing requests
3841 // in higher layered pools. This generally shouldn't happen, but it may be
3842 // possible if a higher level pool issues a request and the request is
3843 // subsequently cancelled. Even if it's not possible, best not to crash.
3844 TEST_F(ClientSocketPoolBaseTest,
3845 CloseIdleSocketsHeldByLayeredPoolWhenNeededSameGroup) {
3846 CreatePool(2, 2);
3847 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3849 // Need a socket in another group for the pool to be stalled (If a group
3850 // has the maximum number of connections already, it's not stalled).
3851 ClientSocketHandle handle1;
3852 TestCompletionCallback callback1;
3853 EXPECT_EQ(OK, handle1.Init("group1",
3854 params_,
3855 DEFAULT_PRIORITY,
3856 callback1.callback(),
3857 pool_.get(),
3858 BoundNetLog()));
3860 MockLayeredPool mock_layered_pool(pool_.get(), "group2");
3861 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3862 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3863 .WillOnce(Invoke(&mock_layered_pool,
3864 &MockLayeredPool::ReleaseOneConnection));
3865 ClientSocketHandle handle;
3866 TestCompletionCallback callback2;
3867 EXPECT_EQ(ERR_IO_PENDING, handle.Init("group2",
3868 params_,
3869 DEFAULT_PRIORITY,
3870 callback2.callback(),
3871 pool_.get(),
3872 BoundNetLog()));
3873 EXPECT_EQ(OK, callback2.WaitForResult());
3876 // Tests the case when an idle socket can be closed when a new request is
3877 // issued, and the new request belongs to a group that was previously stalled.
3878 TEST_F(ClientSocketPoolBaseTest,
3879 CloseIdleSocketsHeldByLayeredPoolInSameGroupWhenNeeded) {
3880 CreatePool(2, 2);
3881 std::list<TestConnectJob::JobType> job_types;
3882 job_types.push_back(TestConnectJob::kMockJob);
3883 job_types.push_back(TestConnectJob::kMockJob);
3884 job_types.push_back(TestConnectJob::kMockJob);
3885 job_types.push_back(TestConnectJob::kMockJob);
3886 connect_job_factory_->set_job_types(&job_types);
3888 ClientSocketHandle handle1;
3889 TestCompletionCallback callback1;
3890 EXPECT_EQ(OK, handle1.Init("group1",
3891 params_,
3892 DEFAULT_PRIORITY,
3893 callback1.callback(),
3894 pool_.get(),
3895 BoundNetLog()));
3897 MockLayeredPool mock_layered_pool(pool_.get(), "group2");
3898 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3899 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3900 .WillRepeatedly(Invoke(&mock_layered_pool,
3901 &MockLayeredPool::ReleaseOneConnection));
3902 mock_layered_pool.set_can_release_connection(false);
3904 // The third request is made when the socket pool is in a stalled state.
3905 ClientSocketHandle handle3;
3906 TestCompletionCallback callback3;
3907 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("group3",
3908 params_,
3909 DEFAULT_PRIORITY,
3910 callback3.callback(),
3911 pool_.get(),
3912 BoundNetLog()));
3914 base::RunLoop().RunUntilIdle();
3915 EXPECT_FALSE(callback3.have_result());
3917 // The fourth request is made when the pool is no longer stalled. The third
3918 // request should be serviced first, since it was issued first and has the
3919 // same priority.
3920 mock_layered_pool.set_can_release_connection(true);
3921 ClientSocketHandle handle4;
3922 TestCompletionCallback callback4;
3923 EXPECT_EQ(ERR_IO_PENDING, handle4.Init("group3",
3924 params_,
3925 DEFAULT_PRIORITY,
3926 callback4.callback(),
3927 pool_.get(),
3928 BoundNetLog()));
3929 EXPECT_EQ(OK, callback3.WaitForResult());
3930 EXPECT_FALSE(callback4.have_result());
3932 // Closing a handle should free up another socket slot.
3933 handle1.Reset();
3934 EXPECT_EQ(OK, callback4.WaitForResult());
3937 // Tests the case when an idle socket can be closed when a new request is
3938 // issued, and the new request belongs to a group that was previously stalled.
3940 // The two differences from the above test are that the stalled requests are not
3941 // in the same group as the layered pool's request, and the the fourth request
3942 // has a higher priority than the third one, so gets a socket first.
3943 TEST_F(ClientSocketPoolBaseTest,
3944 CloseIdleSocketsHeldByLayeredPoolInSameGroupWhenNeeded2) {
3945 CreatePool(2, 2);
3946 std::list<TestConnectJob::JobType> job_types;
3947 job_types.push_back(TestConnectJob::kMockJob);
3948 job_types.push_back(TestConnectJob::kMockJob);
3949 job_types.push_back(TestConnectJob::kMockJob);
3950 job_types.push_back(TestConnectJob::kMockJob);
3951 connect_job_factory_->set_job_types(&job_types);
3953 ClientSocketHandle handle1;
3954 TestCompletionCallback callback1;
3955 EXPECT_EQ(OK, handle1.Init("group1",
3956 params_,
3957 DEFAULT_PRIORITY,
3958 callback1.callback(),
3959 pool_.get(),
3960 BoundNetLog()));
3962 MockLayeredPool mock_layered_pool(pool_.get(), "group2");
3963 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3964 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3965 .WillRepeatedly(Invoke(&mock_layered_pool,
3966 &MockLayeredPool::ReleaseOneConnection));
3967 mock_layered_pool.set_can_release_connection(false);
3969 // The third request is made when the socket pool is in a stalled state.
3970 ClientSocketHandle handle3;
3971 TestCompletionCallback callback3;
3972 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("group3",
3973 params_,
3974 MEDIUM,
3975 callback3.callback(),
3976 pool_.get(),
3977 BoundNetLog()));
3979 base::RunLoop().RunUntilIdle();
3980 EXPECT_FALSE(callback3.have_result());
3982 // The fourth request is made when the pool is no longer stalled. This
3983 // request has a higher priority than the third request, so is serviced first.
3984 mock_layered_pool.set_can_release_connection(true);
3985 ClientSocketHandle handle4;
3986 TestCompletionCallback callback4;
3987 EXPECT_EQ(ERR_IO_PENDING, handle4.Init("group3",
3988 params_,
3989 HIGHEST,
3990 callback4.callback(),
3991 pool_.get(),
3992 BoundNetLog()));
3993 EXPECT_EQ(OK, callback4.WaitForResult());
3994 EXPECT_FALSE(callback3.have_result());
3996 // Closing a handle should free up another socket slot.
3997 handle1.Reset();
3998 EXPECT_EQ(OK, callback3.WaitForResult());
4001 TEST_F(ClientSocketPoolBaseTest,
4002 CloseMultipleIdleSocketsHeldByLayeredPoolWhenNeeded) {
4003 CreatePool(1, 1);
4004 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
4006 MockLayeredPool mock_layered_pool1(pool_.get(), "foo");
4007 EXPECT_EQ(OK, mock_layered_pool1.RequestSocket(pool_.get()));
4008 EXPECT_CALL(mock_layered_pool1, CloseOneIdleConnection())
4009 .WillRepeatedly(Invoke(&mock_layered_pool1,
4010 &MockLayeredPool::ReleaseOneConnection));
4011 MockLayeredPool mock_layered_pool2(pool_.get(), "bar");
4012 EXPECT_EQ(OK, mock_layered_pool2.RequestSocketWithoutLimits(pool_.get()));
4013 EXPECT_CALL(mock_layered_pool2, CloseOneIdleConnection())
4014 .WillRepeatedly(Invoke(&mock_layered_pool2,
4015 &MockLayeredPool::ReleaseOneConnection));
4016 ClientSocketHandle handle;
4017 TestCompletionCallback callback;
4018 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
4019 params_,
4020 DEFAULT_PRIORITY,
4021 callback.callback(),
4022 pool_.get(),
4023 BoundNetLog()));
4024 EXPECT_EQ(OK, callback.WaitForResult());
4027 // Test that when a socket pool and group are at their limits, a request
4028 // with |ignore_limits| triggers creation of a new socket, and gets the socket
4029 // instead of a request with the same priority that was issued earlier, but
4030 // that does not have |ignore_limits| set.
4031 TEST_F(ClientSocketPoolBaseTest, IgnoreLimits) {
4032 scoped_refptr<TestSocketParams> params_ignore_limits(
4033 new TestSocketParams(true /* ignore_limits */));
4034 CreatePool(1, 1);
4036 // Issue a request to reach the socket pool limit.
4037 EXPECT_EQ(OK, StartRequestWithParams("a", MAXIMUM_PRIORITY, params_));
4038 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4040 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
4042 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4043 params_));
4044 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4046 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4047 params_ignore_limits));
4048 ASSERT_EQ(1, pool_->NumConnectJobsInGroup("a"));
4050 EXPECT_EQ(OK, request(2)->WaitForResult());
4051 EXPECT_FALSE(request(1)->have_result());
4054 // Test that when a socket pool and group are at their limits, a ConnectJob
4055 // issued for a request with |ignore_limits| set is not cancelled when a request
4056 // without |ignore_limits| issued to the same group is cancelled.
4057 TEST_F(ClientSocketPoolBaseTest, IgnoreLimitsCancelOtherJob) {
4058 scoped_refptr<TestSocketParams> params_ignore_limits(
4059 new TestSocketParams(true /* ignore_limits */));
4060 CreatePool(1, 1);
4062 // Issue a request to reach the socket pool limit.
4063 EXPECT_EQ(OK, StartRequestWithParams("a", MAXIMUM_PRIORITY, params_));
4064 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4066 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
4068 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4069 params_));
4070 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4072 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4073 params_ignore_limits));
4074 ASSERT_EQ(1, pool_->NumConnectJobsInGroup("a"));
4076 // Cancel the pending request without ignore_limits set. The ConnectJob
4077 // should not be cancelled.
4078 request(1)->handle()->Reset();
4079 ASSERT_EQ(1, pool_->NumConnectJobsInGroup("a"));
4081 EXPECT_EQ(OK, request(2)->WaitForResult());
4082 EXPECT_FALSE(request(1)->have_result());
4085 } // namespace
4087 } // namespace net