Update V8 to version 4.6.48.
[chromium-blink-merge.git] / net / socket / client_socket_pool_base_unittest.cc
blob2ac188159a7dd470f4cdbbff449d9b4bcd2f391b
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/location.h"
13 #include "base/logging.h"
14 #include "base/memory/ref_counted.h"
15 #include "base/memory/scoped_vector.h"
16 #include "base/memory/weak_ptr.h"
17 #include "base/message_loop/message_loop.h"
18 #include "base/run_loop.h"
19 #include "base/single_thread_task_runner.h"
20 #include "base/strings/string_number_conversions.h"
21 #include "base/strings/stringprintf.h"
22 #include "base/thread_task_runner_handle.h"
23 #include "base/threading/platform_thread.h"
24 #include "base/values.h"
25 #include "net/base/load_timing_info.h"
26 #include "net/base/load_timing_info_test_util.h"
27 #include "net/base/net_errors.h"
28 #include "net/base/request_priority.h"
29 #include "net/base/test_completion_callback.h"
30 #include "net/http/http_response_headers.h"
31 #include "net/log/net_log.h"
32 #include "net/log/test_net_log.h"
33 #include "net/log/test_net_log_entry.h"
34 #include "net/log/test_net_log_util.h"
35 #include "net/socket/client_socket_factory.h"
36 #include "net/socket/client_socket_handle.h"
37 #include "net/socket/socket_test_util.h"
38 #include "net/socket/ssl_client_socket.h"
39 #include "net/socket/stream_socket.h"
40 #include "net/udp/datagram_client_socket.h"
41 #include "testing/gmock/include/gmock/gmock.h"
42 #include "testing/gtest/include/gtest/gtest.h"
44 using ::testing::Invoke;
45 using ::testing::Return;
47 namespace net {
49 namespace {
51 const int kDefaultMaxSockets = 4;
52 const int kDefaultMaxSocketsPerGroup = 2;
54 // Make sure |handle| sets load times correctly when it has been assigned a
55 // reused socket.
56 void TestLoadTimingInfoConnectedReused(const ClientSocketHandle& handle) {
57 LoadTimingInfo load_timing_info;
58 // Only pass true in as |is_reused|, as in general, HttpStream types should
59 // have stricter concepts of reuse than socket pools.
60 EXPECT_TRUE(handle.GetLoadTimingInfo(true, &load_timing_info));
62 EXPECT_EQ(true, load_timing_info.socket_reused);
63 EXPECT_NE(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
65 ExpectConnectTimingHasNoTimes(load_timing_info.connect_timing);
66 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
69 // Make sure |handle| sets load times correctly when it has been assigned a
70 // fresh socket. Also runs TestLoadTimingInfoConnectedReused, since the owner
71 // of a connection where |is_reused| is false may consider the connection
72 // reused.
73 void TestLoadTimingInfoConnectedNotReused(const ClientSocketHandle& handle) {
74 EXPECT_FALSE(handle.is_reused());
76 LoadTimingInfo load_timing_info;
77 EXPECT_TRUE(handle.GetLoadTimingInfo(false, &load_timing_info));
79 EXPECT_FALSE(load_timing_info.socket_reused);
80 EXPECT_NE(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
82 ExpectConnectTimingHasTimes(load_timing_info.connect_timing,
83 CONNECT_TIMING_HAS_CONNECT_TIMES_ONLY);
84 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
86 TestLoadTimingInfoConnectedReused(handle);
89 // Make sure |handle| sets load times correctly, in the case that it does not
90 // currently have a socket.
91 void TestLoadTimingInfoNotConnected(const ClientSocketHandle& handle) {
92 // Should only be set to true once a socket is assigned, if at all.
93 EXPECT_FALSE(handle.is_reused());
95 LoadTimingInfo load_timing_info;
96 EXPECT_FALSE(handle.GetLoadTimingInfo(false, &load_timing_info));
98 EXPECT_FALSE(load_timing_info.socket_reused);
99 EXPECT_EQ(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
101 ExpectConnectTimingHasNoTimes(load_timing_info.connect_timing);
102 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
105 class TestSocketParams : public base::RefCounted<TestSocketParams> {
106 public:
107 explicit TestSocketParams(bool ignore_limits)
108 : ignore_limits_(ignore_limits) {}
110 bool ignore_limits() { return ignore_limits_; }
112 private:
113 friend class base::RefCounted<TestSocketParams>;
114 ~TestSocketParams() {}
116 const bool ignore_limits_;
118 typedef ClientSocketPoolBase<TestSocketParams> TestClientSocketPoolBase;
120 class MockClientSocket : public StreamSocket {
121 public:
122 explicit MockClientSocket(net::NetLog* net_log)
123 : connected_(false),
124 has_unread_data_(false),
125 net_log_(BoundNetLog::Make(net_log, NetLog::SOURCE_SOCKET)),
126 was_used_to_convey_data_(false) {}
128 // Sets whether the socket has unread data. If true, the next call to Read()
129 // will return 1 byte and IsConnectedAndIdle() will return false.
130 void set_has_unread_data(bool has_unread_data) {
131 has_unread_data_ = has_unread_data;
134 // Socket implementation.
135 int Read(IOBuffer* /* buf */,
136 int len,
137 const CompletionCallback& /* callback */) override {
138 if (has_unread_data_ && len > 0) {
139 has_unread_data_ = false;
140 was_used_to_convey_data_ = true;
141 return 1;
143 return ERR_UNEXPECTED;
146 int Write(IOBuffer* /* buf */,
147 int len,
148 const CompletionCallback& /* callback */) override {
149 was_used_to_convey_data_ = true;
150 return len;
152 int SetReceiveBufferSize(int32 size) override { return OK; }
153 int SetSendBufferSize(int32 size) override { return OK; }
155 // StreamSocket implementation.
156 int Connect(const CompletionCallback& callback) override {
157 connected_ = true;
158 return OK;
161 void Disconnect() override { connected_ = false; }
162 bool IsConnected() const override { return connected_; }
163 bool IsConnectedAndIdle() const override {
164 return connected_ && !has_unread_data_;
167 int GetPeerAddress(IPEndPoint* /* address */) const override {
168 return ERR_UNEXPECTED;
171 int GetLocalAddress(IPEndPoint* /* address */) const override {
172 return ERR_UNEXPECTED;
175 const BoundNetLog& NetLog() const override { return net_log_; }
177 void SetSubresourceSpeculation() override {}
178 void SetOmniboxSpeculation() override {}
179 bool WasEverUsed() const override { return was_used_to_convey_data_; }
180 bool UsingTCPFastOpen() const override { return false; }
181 bool WasNpnNegotiated() const override { return false; }
182 NextProto GetNegotiatedProtocol() const override { return kProtoUnknown; }
183 bool GetSSLInfo(SSLInfo* ssl_info) override { return false; }
184 void GetConnectionAttempts(ConnectionAttempts* out) const override {
185 out->clear();
187 void ClearConnectionAttempts() override {}
188 void AddConnectionAttempts(const ConnectionAttempts& attempts) override {}
190 private:
191 bool connected_;
192 bool has_unread_data_;
193 BoundNetLog net_log_;
194 bool was_used_to_convey_data_;
196 DISALLOW_COPY_AND_ASSIGN(MockClientSocket);
199 class TestConnectJob;
201 class MockClientSocketFactory : public ClientSocketFactory {
202 public:
203 MockClientSocketFactory() : allocation_count_(0) {}
205 scoped_ptr<DatagramClientSocket> CreateDatagramClientSocket(
206 DatagramSocket::BindType bind_type,
207 const RandIntCallback& rand_int_cb,
208 NetLog* net_log,
209 const NetLog::Source& source) override {
210 NOTREACHED();
211 return scoped_ptr<DatagramClientSocket>();
214 scoped_ptr<StreamSocket> CreateTransportClientSocket(
215 const AddressList& addresses,
216 NetLog* /* net_log */,
217 const NetLog::Source& /*source*/) override {
218 allocation_count_++;
219 return scoped_ptr<StreamSocket>();
222 scoped_ptr<SSLClientSocket> CreateSSLClientSocket(
223 scoped_ptr<ClientSocketHandle> transport_socket,
224 const HostPortPair& host_and_port,
225 const SSLConfig& ssl_config,
226 const SSLClientSocketContext& context) override {
227 NOTIMPLEMENTED();
228 return scoped_ptr<SSLClientSocket>();
231 void ClearSSLSessionCache() override { NOTIMPLEMENTED(); }
233 void WaitForSignal(TestConnectJob* job) { waiting_jobs_.push_back(job); }
235 void SignalJobs();
237 void SignalJob(size_t job);
239 void SetJobLoadState(size_t job, LoadState load_state);
241 int allocation_count() const { return allocation_count_; }
243 private:
244 int allocation_count_;
245 std::vector<TestConnectJob*> waiting_jobs_;
248 class TestConnectJob : public ConnectJob {
249 public:
250 enum JobType {
251 kMockJob,
252 kMockFailingJob,
253 kMockPendingJob,
254 kMockPendingFailingJob,
255 kMockWaitingJob,
256 kMockRecoverableJob,
257 kMockPendingRecoverableJob,
258 kMockAdditionalErrorStateJob,
259 kMockPendingAdditionalErrorStateJob,
260 kMockUnreadDataJob,
263 // The kMockPendingJob uses a slight delay before allowing the connect
264 // to complete.
265 static const int kPendingConnectDelay = 2;
267 TestConnectJob(JobType job_type,
268 const std::string& group_name,
269 const TestClientSocketPoolBase::Request& request,
270 base::TimeDelta timeout_duration,
271 ConnectJob::Delegate* delegate,
272 MockClientSocketFactory* client_socket_factory,
273 NetLog* net_log)
274 : ConnectJob(group_name, timeout_duration, request.priority(), delegate,
275 BoundNetLog::Make(net_log, NetLog::SOURCE_CONNECT_JOB)),
276 job_type_(job_type),
277 client_socket_factory_(client_socket_factory),
278 load_state_(LOAD_STATE_IDLE),
279 store_additional_error_state_(false),
280 weak_factory_(this) {
283 void Signal() {
284 DoConnect(waiting_success_, true /* async */, false /* recoverable */);
287 void set_load_state(LoadState load_state) { load_state_ = load_state; }
289 // From ConnectJob:
291 LoadState GetLoadState() const override { return load_state_; }
293 void GetAdditionalErrorState(ClientSocketHandle* handle) override {
294 if (store_additional_error_state_) {
295 // Set all of the additional error state fields in some way.
296 handle->set_is_ssl_error(true);
297 HttpResponseInfo info;
298 info.headers = new HttpResponseHeaders(std::string());
299 handle->set_ssl_error_response_info(info);
303 private:
304 // From ConnectJob:
306 int ConnectInternal() override {
307 AddressList ignored;
308 client_socket_factory_->CreateTransportClientSocket(ignored, NULL,
309 NetLog::Source());
310 SetSocket(
311 scoped_ptr<StreamSocket>(new MockClientSocket(net_log().net_log())));
312 switch (job_type_) {
313 case kMockJob:
314 return DoConnect(true /* successful */, false /* sync */,
315 false /* recoverable */);
316 case kMockFailingJob:
317 return DoConnect(false /* error */, false /* sync */,
318 false /* recoverable */);
319 case kMockPendingJob:
320 set_load_state(LOAD_STATE_CONNECTING);
322 // Depending on execution timings, posting a delayed task can result
323 // in the task getting executed the at the earliest possible
324 // opportunity or only after returning once from the message loop and
325 // then a second call into the message loop. In order to make behavior
326 // more deterministic, we change the default delay to 2ms. This should
327 // always require us to wait for the second call into the message loop.
329 // N.B. The correct fix for this and similar timing problems is to
330 // abstract time for the purpose of unittests. Unfortunately, we have
331 // a lot of third-party components that directly call the various
332 // time functions, so this change would be rather invasive.
333 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
334 FROM_HERE,
335 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
336 weak_factory_.GetWeakPtr(), true /* successful */,
337 true /* async */, false /* recoverable */),
338 base::TimeDelta::FromMilliseconds(kPendingConnectDelay));
339 return ERR_IO_PENDING;
340 case kMockPendingFailingJob:
341 set_load_state(LOAD_STATE_CONNECTING);
342 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
343 FROM_HERE,
344 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
345 weak_factory_.GetWeakPtr(), false /* error */,
346 true /* async */, false /* recoverable */),
347 base::TimeDelta::FromMilliseconds(2));
348 return ERR_IO_PENDING;
349 case kMockWaitingJob:
350 set_load_state(LOAD_STATE_CONNECTING);
351 client_socket_factory_->WaitForSignal(this);
352 waiting_success_ = true;
353 return ERR_IO_PENDING;
354 case kMockRecoverableJob:
355 return DoConnect(false /* error */, false /* sync */,
356 true /* recoverable */);
357 case kMockPendingRecoverableJob:
358 set_load_state(LOAD_STATE_CONNECTING);
359 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
360 FROM_HERE,
361 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
362 weak_factory_.GetWeakPtr(), false /* error */,
363 true /* async */, true /* recoverable */),
364 base::TimeDelta::FromMilliseconds(2));
365 return ERR_IO_PENDING;
366 case kMockAdditionalErrorStateJob:
367 store_additional_error_state_ = true;
368 return DoConnect(false /* error */, false /* sync */,
369 false /* recoverable */);
370 case kMockPendingAdditionalErrorStateJob:
371 set_load_state(LOAD_STATE_CONNECTING);
372 store_additional_error_state_ = true;
373 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
374 FROM_HERE,
375 base::Bind(base::IgnoreResult(&TestConnectJob::DoConnect),
376 weak_factory_.GetWeakPtr(), false /* error */,
377 true /* async */, false /* recoverable */),
378 base::TimeDelta::FromMilliseconds(2));
379 return ERR_IO_PENDING;
380 case kMockUnreadDataJob: {
381 int ret = DoConnect(true /* successful */, false /* sync */,
382 false /* recoverable */);
383 static_cast<MockClientSocket*>(socket())->set_has_unread_data(true);
384 return ret;
386 default:
387 NOTREACHED();
388 SetSocket(scoped_ptr<StreamSocket>());
389 return ERR_FAILED;
393 int DoConnect(bool succeed, bool was_async, bool recoverable) {
394 int result = OK;
395 if (succeed) {
396 socket()->Connect(CompletionCallback());
397 } else if (recoverable) {
398 result = ERR_PROXY_AUTH_REQUESTED;
399 } else {
400 result = ERR_CONNECTION_FAILED;
401 SetSocket(scoped_ptr<StreamSocket>());
404 if (was_async)
405 NotifyDelegateOfCompletion(result);
406 return result;
409 bool waiting_success_;
410 const JobType job_type_;
411 MockClientSocketFactory* const client_socket_factory_;
412 LoadState load_state_;
413 bool store_additional_error_state_;
415 base::WeakPtrFactory<TestConnectJob> weak_factory_;
417 DISALLOW_COPY_AND_ASSIGN(TestConnectJob);
420 class TestConnectJobFactory
421 : public TestClientSocketPoolBase::ConnectJobFactory {
422 public:
423 TestConnectJobFactory(MockClientSocketFactory* client_socket_factory,
424 NetLog* net_log)
425 : job_type_(TestConnectJob::kMockJob),
426 job_types_(NULL),
427 client_socket_factory_(client_socket_factory),
428 net_log_(net_log) {
431 ~TestConnectJobFactory() override {}
433 void set_job_type(TestConnectJob::JobType job_type) { job_type_ = job_type; }
435 void set_job_types(std::list<TestConnectJob::JobType>* job_types) {
436 job_types_ = job_types;
437 CHECK(!job_types_->empty());
440 void set_timeout_duration(base::TimeDelta timeout_duration) {
441 timeout_duration_ = timeout_duration;
444 // ConnectJobFactory implementation.
446 scoped_ptr<ConnectJob> NewConnectJob(
447 const std::string& group_name,
448 const TestClientSocketPoolBase::Request& request,
449 ConnectJob::Delegate* delegate) const override {
450 EXPECT_TRUE(!job_types_ || !job_types_->empty());
451 TestConnectJob::JobType job_type = job_type_;
452 if (job_types_ && !job_types_->empty()) {
453 job_type = job_types_->front();
454 job_types_->pop_front();
456 return scoped_ptr<ConnectJob>(new TestConnectJob(job_type,
457 group_name,
458 request,
459 timeout_duration_,
460 delegate,
461 client_socket_factory_,
462 net_log_));
465 base::TimeDelta ConnectionTimeout() const override {
466 return timeout_duration_;
469 private:
470 TestConnectJob::JobType job_type_;
471 std::list<TestConnectJob::JobType>* job_types_;
472 base::TimeDelta timeout_duration_;
473 MockClientSocketFactory* const client_socket_factory_;
474 NetLog* net_log_;
476 DISALLOW_COPY_AND_ASSIGN(TestConnectJobFactory);
479 class TestClientSocketPool : public ClientSocketPool {
480 public:
481 typedef TestSocketParams SocketParams;
483 TestClientSocketPool(
484 int max_sockets,
485 int max_sockets_per_group,
486 base::TimeDelta unused_idle_socket_timeout,
487 base::TimeDelta used_idle_socket_timeout,
488 TestClientSocketPoolBase::ConnectJobFactory* connect_job_factory)
489 : base_(NULL,
490 max_sockets,
491 max_sockets_per_group,
492 unused_idle_socket_timeout,
493 used_idle_socket_timeout,
494 connect_job_factory) {}
496 ~TestClientSocketPool() override {}
498 int RequestSocket(const std::string& group_name,
499 const void* params,
500 RequestPriority priority,
501 ClientSocketHandle* handle,
502 const CompletionCallback& callback,
503 const BoundNetLog& net_log) override {
504 const scoped_refptr<TestSocketParams>* casted_socket_params =
505 static_cast<const scoped_refptr<TestSocketParams>*>(params);
506 return base_.RequestSocket(group_name, *casted_socket_params, priority,
507 handle, callback, net_log);
510 void RequestSockets(const std::string& group_name,
511 const void* params,
512 int num_sockets,
513 const BoundNetLog& net_log) override {
514 const scoped_refptr<TestSocketParams>* casted_params =
515 static_cast<const scoped_refptr<TestSocketParams>*>(params);
517 base_.RequestSockets(group_name, *casted_params, num_sockets, net_log);
520 void CancelRequest(const std::string& group_name,
521 ClientSocketHandle* handle) override {
522 base_.CancelRequest(group_name, handle);
525 void ReleaseSocket(const std::string& group_name,
526 scoped_ptr<StreamSocket> socket,
527 int id) override {
528 base_.ReleaseSocket(group_name, socket.Pass(), id);
531 void FlushWithError(int error) override { base_.FlushWithError(error); }
533 bool IsStalled() const override { return base_.IsStalled(); }
535 void CloseIdleSockets() override { base_.CloseIdleSockets(); }
537 int IdleSocketCount() const override { return base_.idle_socket_count(); }
539 int IdleSocketCountInGroup(const std::string& group_name) const override {
540 return base_.IdleSocketCountInGroup(group_name);
543 LoadState GetLoadState(const std::string& group_name,
544 const ClientSocketHandle* handle) const override {
545 return base_.GetLoadState(group_name, handle);
548 void AddHigherLayeredPool(HigherLayeredPool* higher_pool) override {
549 base_.AddHigherLayeredPool(higher_pool);
552 void RemoveHigherLayeredPool(HigherLayeredPool* higher_pool) override {
553 base_.RemoveHigherLayeredPool(higher_pool);
556 scoped_ptr<base::DictionaryValue> GetInfoAsValue(
557 const std::string& name,
558 const std::string& type,
559 bool include_nested_pools) const override {
560 return base_.GetInfoAsValue(name, type);
563 base::TimeDelta ConnectionTimeout() const override {
564 return base_.ConnectionTimeout();
567 const TestClientSocketPoolBase* base() const { return &base_; }
569 int NumUnassignedConnectJobsInGroup(const std::string& group_name) const {
570 return base_.NumUnassignedConnectJobsInGroup(group_name);
573 int NumConnectJobsInGroup(const std::string& group_name) const {
574 return base_.NumConnectJobsInGroup(group_name);
577 int NumActiveSocketsInGroup(const std::string& group_name) const {
578 return base_.NumActiveSocketsInGroup(group_name);
581 bool HasGroup(const std::string& group_name) const {
582 return base_.HasGroup(group_name);
585 void CleanupTimedOutIdleSockets() { base_.CleanupIdleSockets(false); }
587 void EnableConnectBackupJobs() { base_.EnableConnectBackupJobs(); }
589 bool CloseOneIdleConnectionInHigherLayeredPool() {
590 return base_.CloseOneIdleConnectionInHigherLayeredPool();
593 private:
594 TestClientSocketPoolBase base_;
596 DISALLOW_COPY_AND_ASSIGN(TestClientSocketPool);
599 } // namespace
601 namespace {
603 void MockClientSocketFactory::SignalJobs() {
604 for (std::vector<TestConnectJob*>::iterator it = waiting_jobs_.begin();
605 it != waiting_jobs_.end(); ++it) {
606 (*it)->Signal();
608 waiting_jobs_.clear();
611 void MockClientSocketFactory::SignalJob(size_t job) {
612 ASSERT_LT(job, waiting_jobs_.size());
613 waiting_jobs_[job]->Signal();
614 waiting_jobs_.erase(waiting_jobs_.begin() + job);
617 void MockClientSocketFactory::SetJobLoadState(size_t job,
618 LoadState load_state) {
619 ASSERT_LT(job, waiting_jobs_.size());
620 waiting_jobs_[job]->set_load_state(load_state);
623 class TestConnectJobDelegate : public ConnectJob::Delegate {
624 public:
625 TestConnectJobDelegate()
626 : have_result_(false), waiting_for_result_(false), result_(OK) {}
627 ~TestConnectJobDelegate() override {}
629 void OnConnectJobComplete(int result, ConnectJob* job) override {
630 result_ = result;
631 scoped_ptr<ConnectJob> owned_job(job);
632 scoped_ptr<StreamSocket> socket = owned_job->PassSocket();
633 // socket.get() should be NULL iff result != OK
634 EXPECT_EQ(socket == NULL, result != OK);
635 have_result_ = true;
636 if (waiting_for_result_)
637 base::MessageLoop::current()->Quit();
640 int WaitForResult() {
641 DCHECK(!waiting_for_result_);
642 while (!have_result_) {
643 waiting_for_result_ = true;
644 base::MessageLoop::current()->Run();
645 waiting_for_result_ = false;
647 have_result_ = false; // auto-reset for next callback
648 return result_;
651 private:
652 bool have_result_;
653 bool waiting_for_result_;
654 int result_;
657 class ClientSocketPoolBaseTest : public testing::Test {
658 protected:
659 ClientSocketPoolBaseTest()
660 : params_(new TestSocketParams(false /* ignore_limits */)) {
661 connect_backup_jobs_enabled_ =
662 internal::ClientSocketPoolBaseHelper::connect_backup_jobs_enabled();
663 internal::ClientSocketPoolBaseHelper::set_connect_backup_jobs_enabled(true);
664 cleanup_timer_enabled_ =
665 internal::ClientSocketPoolBaseHelper::cleanup_timer_enabled();
668 ~ClientSocketPoolBaseTest() override {
669 internal::ClientSocketPoolBaseHelper::set_connect_backup_jobs_enabled(
670 connect_backup_jobs_enabled_);
671 internal::ClientSocketPoolBaseHelper::set_cleanup_timer_enabled(
672 cleanup_timer_enabled_);
675 void CreatePool(int max_sockets, int max_sockets_per_group) {
676 CreatePoolWithIdleTimeouts(
677 max_sockets,
678 max_sockets_per_group,
679 ClientSocketPool::unused_idle_socket_timeout(),
680 ClientSocketPool::used_idle_socket_timeout());
683 void CreatePoolWithIdleTimeouts(
684 int max_sockets, int max_sockets_per_group,
685 base::TimeDelta unused_idle_socket_timeout,
686 base::TimeDelta used_idle_socket_timeout) {
687 DCHECK(!pool_.get());
688 connect_job_factory_ = new TestConnectJobFactory(&client_socket_factory_,
689 &net_log_);
690 pool_.reset(new TestClientSocketPool(max_sockets,
691 max_sockets_per_group,
692 unused_idle_socket_timeout,
693 used_idle_socket_timeout,
694 connect_job_factory_));
697 int StartRequestWithParams(
698 const std::string& group_name,
699 RequestPriority priority,
700 const scoped_refptr<TestSocketParams>& params) {
701 return test_base_.StartRequestUsingPool(
702 pool_.get(), group_name, priority, params);
705 int StartRequest(const std::string& group_name, RequestPriority priority) {
706 return StartRequestWithParams(group_name, priority, params_);
709 int GetOrderOfRequest(size_t index) const {
710 return test_base_.GetOrderOfRequest(index);
713 bool ReleaseOneConnection(ClientSocketPoolTest::KeepAlive keep_alive) {
714 return test_base_.ReleaseOneConnection(keep_alive);
717 void ReleaseAllConnections(ClientSocketPoolTest::KeepAlive keep_alive) {
718 test_base_.ReleaseAllConnections(keep_alive);
721 TestSocketRequest* request(int i) { return test_base_.request(i); }
722 size_t requests_size() const { return test_base_.requests_size(); }
723 ScopedVector<TestSocketRequest>* requests() { return test_base_.requests(); }
724 size_t completion_count() const { return test_base_.completion_count(); }
726 TestNetLog net_log_;
727 bool connect_backup_jobs_enabled_;
728 bool cleanup_timer_enabled_;
729 MockClientSocketFactory client_socket_factory_;
730 TestConnectJobFactory* connect_job_factory_;
731 scoped_refptr<TestSocketParams> params_;
732 scoped_ptr<TestClientSocketPool> pool_;
733 ClientSocketPoolTest test_base_;
736 // Even though a timeout is specified, it doesn't time out on a synchronous
737 // completion.
738 TEST_F(ClientSocketPoolBaseTest, ConnectJob_NoTimeoutOnSynchronousCompletion) {
739 TestConnectJobDelegate delegate;
740 ClientSocketHandle ignored;
741 TestClientSocketPoolBase::Request request(
742 &ignored, CompletionCallback(), DEFAULT_PRIORITY,
743 internal::ClientSocketPoolBaseHelper::NORMAL,
744 false, params_, BoundNetLog());
745 scoped_ptr<TestConnectJob> job(
746 new TestConnectJob(TestConnectJob::kMockJob,
747 "a",
748 request,
749 base::TimeDelta::FromMicroseconds(1),
750 &delegate,
751 &client_socket_factory_,
752 NULL));
753 EXPECT_EQ(OK, job->Connect());
756 TEST_F(ClientSocketPoolBaseTest, ConnectJob_TimedOut) {
757 TestConnectJobDelegate delegate;
758 ClientSocketHandle ignored;
759 TestNetLog log;
761 TestClientSocketPoolBase::Request request(
762 &ignored, CompletionCallback(), DEFAULT_PRIORITY,
763 internal::ClientSocketPoolBaseHelper::NORMAL,
764 false, params_, BoundNetLog());
765 // Deleted by TestConnectJobDelegate.
766 TestConnectJob* job =
767 new TestConnectJob(TestConnectJob::kMockPendingJob,
768 "a",
769 request,
770 base::TimeDelta::FromMicroseconds(1),
771 &delegate,
772 &client_socket_factory_,
773 &log);
774 ASSERT_EQ(ERR_IO_PENDING, job->Connect());
775 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(1));
776 EXPECT_EQ(ERR_TIMED_OUT, delegate.WaitForResult());
778 TestNetLogEntry::List entries;
779 log.GetEntries(&entries);
781 EXPECT_EQ(6u, entries.size());
782 EXPECT_TRUE(LogContainsBeginEvent(
783 entries, 0, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB));
784 EXPECT_TRUE(LogContainsBeginEvent(
785 entries, 1, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB_CONNECT));
786 EXPECT_TRUE(LogContainsEvent(
787 entries, 2, NetLog::TYPE_CONNECT_JOB_SET_SOCKET,
788 NetLog::PHASE_NONE));
789 EXPECT_TRUE(LogContainsEvent(
790 entries, 3, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB_TIMED_OUT,
791 NetLog::PHASE_NONE));
792 EXPECT_TRUE(LogContainsEndEvent(
793 entries, 4, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB_CONNECT));
794 EXPECT_TRUE(LogContainsEndEvent(
795 entries, 5, NetLog::TYPE_SOCKET_POOL_CONNECT_JOB));
798 TEST_F(ClientSocketPoolBaseTest, BasicSynchronous) {
799 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
801 TestCompletionCallback callback;
802 ClientSocketHandle handle;
803 BoundTestNetLog log;
804 TestLoadTimingInfoNotConnected(handle);
806 EXPECT_EQ(OK,
807 handle.Init("a",
808 params_,
809 DEFAULT_PRIORITY,
810 callback.callback(),
811 pool_.get(),
812 log.bound()));
813 EXPECT_TRUE(handle.is_initialized());
814 EXPECT_TRUE(handle.socket());
815 TestLoadTimingInfoConnectedNotReused(handle);
817 handle.Reset();
818 TestLoadTimingInfoNotConnected(handle);
820 TestNetLogEntry::List entries;
821 log.GetEntries(&entries);
823 EXPECT_EQ(4u, entries.size());
824 EXPECT_TRUE(LogContainsBeginEvent(
825 entries, 0, NetLog::TYPE_SOCKET_POOL));
826 EXPECT_TRUE(LogContainsEvent(
827 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
828 NetLog::PHASE_NONE));
829 EXPECT_TRUE(LogContainsEvent(
830 entries, 2, NetLog::TYPE_SOCKET_POOL_BOUND_TO_SOCKET,
831 NetLog::PHASE_NONE));
832 EXPECT_TRUE(LogContainsEndEvent(
833 entries, 3, NetLog::TYPE_SOCKET_POOL));
836 TEST_F(ClientSocketPoolBaseTest, InitConnectionFailure) {
837 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
839 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
840 BoundTestNetLog log;
842 ClientSocketHandle handle;
843 TestCompletionCallback callback;
844 // Set the additional error state members to ensure that they get cleared.
845 handle.set_is_ssl_error(true);
846 HttpResponseInfo info;
847 info.headers = new HttpResponseHeaders(std::string());
848 handle.set_ssl_error_response_info(info);
849 EXPECT_EQ(ERR_CONNECTION_FAILED,
850 handle.Init("a",
851 params_,
852 DEFAULT_PRIORITY,
853 callback.callback(),
854 pool_.get(),
855 log.bound()));
856 EXPECT_FALSE(handle.socket());
857 EXPECT_FALSE(handle.is_ssl_error());
858 EXPECT_TRUE(handle.ssl_error_response_info().headers.get() == NULL);
859 TestLoadTimingInfoNotConnected(handle);
861 TestNetLogEntry::List entries;
862 log.GetEntries(&entries);
864 EXPECT_EQ(3u, entries.size());
865 EXPECT_TRUE(LogContainsBeginEvent(
866 entries, 0, NetLog::TYPE_SOCKET_POOL));
867 EXPECT_TRUE(LogContainsEvent(
868 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
869 NetLog::PHASE_NONE));
870 EXPECT_TRUE(LogContainsEndEvent(
871 entries, 2, NetLog::TYPE_SOCKET_POOL));
874 TEST_F(ClientSocketPoolBaseTest, TotalLimit) {
875 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
877 // TODO(eroman): Check that the NetLog contains this event.
879 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
880 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
881 EXPECT_EQ(OK, StartRequest("c", DEFAULT_PRIORITY));
882 EXPECT_EQ(OK, StartRequest("d", DEFAULT_PRIORITY));
884 EXPECT_EQ(static_cast<int>(requests_size()),
885 client_socket_factory_.allocation_count());
886 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
888 EXPECT_EQ(ERR_IO_PENDING, StartRequest("e", DEFAULT_PRIORITY));
889 EXPECT_EQ(ERR_IO_PENDING, StartRequest("f", DEFAULT_PRIORITY));
890 EXPECT_EQ(ERR_IO_PENDING, StartRequest("g", DEFAULT_PRIORITY));
892 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
894 EXPECT_EQ(static_cast<int>(requests_size()),
895 client_socket_factory_.allocation_count());
896 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
898 EXPECT_EQ(1, GetOrderOfRequest(1));
899 EXPECT_EQ(2, GetOrderOfRequest(2));
900 EXPECT_EQ(3, GetOrderOfRequest(3));
901 EXPECT_EQ(4, GetOrderOfRequest(4));
902 EXPECT_EQ(5, GetOrderOfRequest(5));
903 EXPECT_EQ(6, GetOrderOfRequest(6));
904 EXPECT_EQ(7, GetOrderOfRequest(7));
906 // Make sure we test order of all requests made.
907 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(8));
910 TEST_F(ClientSocketPoolBaseTest, TotalLimitReachedNewGroup) {
911 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
913 // TODO(eroman): Check that the NetLog contains this event.
915 // Reach all limits: max total sockets, and max sockets per group.
916 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
917 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
918 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
919 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
921 EXPECT_EQ(static_cast<int>(requests_size()),
922 client_socket_factory_.allocation_count());
923 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
925 // Now create a new group and verify that we don't starve it.
926 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", DEFAULT_PRIORITY));
928 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
930 EXPECT_EQ(static_cast<int>(requests_size()),
931 client_socket_factory_.allocation_count());
932 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
934 EXPECT_EQ(1, GetOrderOfRequest(1));
935 EXPECT_EQ(2, GetOrderOfRequest(2));
936 EXPECT_EQ(3, GetOrderOfRequest(3));
937 EXPECT_EQ(4, GetOrderOfRequest(4));
938 EXPECT_EQ(5, GetOrderOfRequest(5));
940 // Make sure we test order of all requests made.
941 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(6));
944 TEST_F(ClientSocketPoolBaseTest, TotalLimitRespectsPriority) {
945 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
947 EXPECT_EQ(OK, StartRequest("b", LOWEST));
948 EXPECT_EQ(OK, StartRequest("a", MEDIUM));
949 EXPECT_EQ(OK, StartRequest("b", HIGHEST));
950 EXPECT_EQ(OK, StartRequest("a", LOWEST));
952 EXPECT_EQ(static_cast<int>(requests_size()),
953 client_socket_factory_.allocation_count());
955 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", LOWEST));
956 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
957 EXPECT_EQ(ERR_IO_PENDING, StartRequest("b", HIGHEST));
959 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
961 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
963 // First 4 requests don't have to wait, and finish in order.
964 EXPECT_EQ(1, GetOrderOfRequest(1));
965 EXPECT_EQ(2, GetOrderOfRequest(2));
966 EXPECT_EQ(3, GetOrderOfRequest(3));
967 EXPECT_EQ(4, GetOrderOfRequest(4));
969 // Request ("b", HIGHEST) has the highest priority, then ("a", MEDIUM),
970 // and then ("c", LOWEST).
971 EXPECT_EQ(7, GetOrderOfRequest(5));
972 EXPECT_EQ(6, GetOrderOfRequest(6));
973 EXPECT_EQ(5, GetOrderOfRequest(7));
975 // Make sure we test order of all requests made.
976 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(9));
979 TEST_F(ClientSocketPoolBaseTest, TotalLimitRespectsGroupLimit) {
980 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
982 EXPECT_EQ(OK, StartRequest("a", LOWEST));
983 EXPECT_EQ(OK, StartRequest("a", LOW));
984 EXPECT_EQ(OK, StartRequest("b", HIGHEST));
985 EXPECT_EQ(OK, StartRequest("b", MEDIUM));
987 EXPECT_EQ(static_cast<int>(requests_size()),
988 client_socket_factory_.allocation_count());
990 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", MEDIUM));
991 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
992 EXPECT_EQ(ERR_IO_PENDING, StartRequest("b", HIGHEST));
994 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
996 EXPECT_EQ(static_cast<int>(requests_size()),
997 client_socket_factory_.allocation_count());
998 EXPECT_EQ(requests_size() - kDefaultMaxSockets, completion_count());
1000 // First 4 requests don't have to wait, and finish in order.
1001 EXPECT_EQ(1, GetOrderOfRequest(1));
1002 EXPECT_EQ(2, GetOrderOfRequest(2));
1003 EXPECT_EQ(3, GetOrderOfRequest(3));
1004 EXPECT_EQ(4, GetOrderOfRequest(4));
1006 // Request ("b", 7) has the highest priority, but we can't make new socket for
1007 // group "b", because it has reached the per-group limit. Then we make
1008 // socket for ("c", 6), because it has higher priority than ("a", 4),
1009 // and we still can't make a socket for group "b".
1010 EXPECT_EQ(5, GetOrderOfRequest(5));
1011 EXPECT_EQ(6, GetOrderOfRequest(6));
1012 EXPECT_EQ(7, GetOrderOfRequest(7));
1014 // Make sure we test order of all requests made.
1015 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(8));
1018 // Make sure that we count connecting sockets against the total limit.
1019 TEST_F(ClientSocketPoolBaseTest, TotalLimitCountsConnectingSockets) {
1020 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1022 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1023 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
1024 EXPECT_EQ(OK, StartRequest("c", DEFAULT_PRIORITY));
1026 // Create one asynchronous request.
1027 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1028 EXPECT_EQ(ERR_IO_PENDING, StartRequest("d", DEFAULT_PRIORITY));
1030 // We post all of our delayed tasks with a 2ms delay. I.e. they don't
1031 // actually become pending until 2ms after they have been created. In order
1032 // to flush all tasks, we need to wait so that we know there are no
1033 // soon-to-be-pending tasks waiting.
1034 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(10));
1035 base::MessageLoop::current()->RunUntilIdle();
1037 // The next synchronous request should wait for its turn.
1038 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1039 EXPECT_EQ(ERR_IO_PENDING, StartRequest("e", DEFAULT_PRIORITY));
1041 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
1043 EXPECT_EQ(static_cast<int>(requests_size()),
1044 client_socket_factory_.allocation_count());
1046 EXPECT_EQ(1, GetOrderOfRequest(1));
1047 EXPECT_EQ(2, GetOrderOfRequest(2));
1048 EXPECT_EQ(3, GetOrderOfRequest(3));
1049 EXPECT_EQ(4, GetOrderOfRequest(4));
1050 EXPECT_EQ(5, GetOrderOfRequest(5));
1052 // Make sure we test order of all requests made.
1053 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(6));
1056 TEST_F(ClientSocketPoolBaseTest, CorrectlyCountStalledGroups) {
1057 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
1058 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1060 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1061 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1062 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1063 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1065 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1067 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1069 EXPECT_EQ(ERR_IO_PENDING, StartRequest("b", DEFAULT_PRIORITY));
1070 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", DEFAULT_PRIORITY));
1072 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1074 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1075 EXPECT_EQ(kDefaultMaxSockets + 1, client_socket_factory_.allocation_count());
1076 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1077 EXPECT_EQ(kDefaultMaxSockets + 2, client_socket_factory_.allocation_count());
1078 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1079 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1080 EXPECT_EQ(kDefaultMaxSockets + 2, client_socket_factory_.allocation_count());
1083 TEST_F(ClientSocketPoolBaseTest, StallAndThenCancelAndTriggerAvailableSocket) {
1084 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
1085 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1087 ClientSocketHandle handle;
1088 TestCompletionCallback callback;
1089 EXPECT_EQ(ERR_IO_PENDING,
1090 handle.Init("a",
1091 params_,
1092 DEFAULT_PRIORITY,
1093 callback.callback(),
1094 pool_.get(),
1095 BoundNetLog()));
1097 ClientSocketHandle handles[4];
1098 for (size_t i = 0; i < arraysize(handles); ++i) {
1099 TestCompletionCallback callback;
1100 EXPECT_EQ(ERR_IO_PENDING,
1101 handles[i].Init("b",
1102 params_,
1103 DEFAULT_PRIORITY,
1104 callback.callback(),
1105 pool_.get(),
1106 BoundNetLog()));
1109 // One will be stalled, cancel all the handles now.
1110 // This should hit the OnAvailableSocketSlot() code where we previously had
1111 // stalled groups, but no longer have any.
1112 for (size_t i = 0; i < arraysize(handles); ++i)
1113 handles[i].Reset();
1116 TEST_F(ClientSocketPoolBaseTest, CancelStalledSocketAtSocketLimit) {
1117 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1118 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1121 ClientSocketHandle handles[kDefaultMaxSockets];
1122 TestCompletionCallback callbacks[kDefaultMaxSockets];
1123 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1124 EXPECT_EQ(OK, handles[i].Init(base::IntToString(i),
1125 params_,
1126 DEFAULT_PRIORITY,
1127 callbacks[i].callback(),
1128 pool_.get(),
1129 BoundNetLog()));
1132 // Force a stalled group.
1133 ClientSocketHandle stalled_handle;
1134 TestCompletionCallback callback;
1135 EXPECT_EQ(ERR_IO_PENDING, stalled_handle.Init("foo",
1136 params_,
1137 DEFAULT_PRIORITY,
1138 callback.callback(),
1139 pool_.get(),
1140 BoundNetLog()));
1142 // Cancel the stalled request.
1143 stalled_handle.Reset();
1145 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1146 EXPECT_EQ(0, pool_->IdleSocketCount());
1148 // Dropping out of scope will close all handles and return them to idle.
1151 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1152 EXPECT_EQ(kDefaultMaxSockets, pool_->IdleSocketCount());
1155 TEST_F(ClientSocketPoolBaseTest, CancelPendingSocketAtSocketLimit) {
1156 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1157 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1160 ClientSocketHandle handles[kDefaultMaxSockets];
1161 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1162 TestCompletionCallback callback;
1163 EXPECT_EQ(ERR_IO_PENDING, handles[i].Init(base::IntToString(i),
1164 params_,
1165 DEFAULT_PRIORITY,
1166 callback.callback(),
1167 pool_.get(),
1168 BoundNetLog()));
1171 // Force a stalled group.
1172 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1173 ClientSocketHandle stalled_handle;
1174 TestCompletionCallback callback;
1175 EXPECT_EQ(ERR_IO_PENDING, stalled_handle.Init("foo",
1176 params_,
1177 DEFAULT_PRIORITY,
1178 callback.callback(),
1179 pool_.get(),
1180 BoundNetLog()));
1182 // Since it is stalled, it should have no connect jobs.
1183 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("foo"));
1184 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("foo"));
1186 // Cancel the stalled request.
1187 handles[0].Reset();
1189 // Now we should have a connect job.
1190 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("foo"));
1191 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("foo"));
1193 // The stalled socket should connect.
1194 EXPECT_EQ(OK, callback.WaitForResult());
1196 EXPECT_EQ(kDefaultMaxSockets + 1,
1197 client_socket_factory_.allocation_count());
1198 EXPECT_EQ(0, pool_->IdleSocketCount());
1199 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("foo"));
1200 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("foo"));
1202 // Dropping out of scope will close all handles and return them to idle.
1205 EXPECT_EQ(1, pool_->IdleSocketCount());
1208 TEST_F(ClientSocketPoolBaseTest, WaitForStalledSocketAtSocketLimit) {
1209 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1210 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1212 ClientSocketHandle stalled_handle;
1213 TestCompletionCallback callback;
1215 EXPECT_FALSE(pool_->IsStalled());
1216 ClientSocketHandle handles[kDefaultMaxSockets];
1217 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1218 TestCompletionCallback callback;
1219 EXPECT_EQ(OK, handles[i].Init(base::StringPrintf(
1220 "Take 2: %d", i),
1221 params_,
1222 DEFAULT_PRIORITY,
1223 callback.callback(),
1224 pool_.get(),
1225 BoundNetLog()));
1228 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1229 EXPECT_EQ(0, pool_->IdleSocketCount());
1230 EXPECT_FALSE(pool_->IsStalled());
1232 // Now we will hit the socket limit.
1233 EXPECT_EQ(ERR_IO_PENDING, stalled_handle.Init("foo",
1234 params_,
1235 DEFAULT_PRIORITY,
1236 callback.callback(),
1237 pool_.get(),
1238 BoundNetLog()));
1239 EXPECT_TRUE(pool_->IsStalled());
1241 // Dropping out of scope will close all handles and return them to idle.
1244 // But if we wait for it, the released idle sockets will be closed in
1245 // preference of the waiting request.
1246 EXPECT_EQ(OK, callback.WaitForResult());
1248 EXPECT_EQ(kDefaultMaxSockets + 1, client_socket_factory_.allocation_count());
1249 EXPECT_EQ(3, pool_->IdleSocketCount());
1252 // Regression test for http://crbug.com/40952.
1253 TEST_F(ClientSocketPoolBaseTest, CloseIdleSocketAtSocketLimitDeleteGroup) {
1254 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1255 pool_->EnableConnectBackupJobs();
1256 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1258 for (int i = 0; i < kDefaultMaxSockets; ++i) {
1259 ClientSocketHandle handle;
1260 TestCompletionCallback callback;
1261 EXPECT_EQ(OK, handle.Init(base::IntToString(i),
1262 params_,
1263 DEFAULT_PRIORITY,
1264 callback.callback(),
1265 pool_.get(),
1266 BoundNetLog()));
1269 // Flush all the DoReleaseSocket tasks.
1270 base::MessageLoop::current()->RunUntilIdle();
1272 // Stall a group. Set a pending job so it'll trigger a backup job if we don't
1273 // reuse a socket.
1274 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1275 ClientSocketHandle handle;
1276 TestCompletionCallback callback;
1278 // "0" is special here, since it should be the first entry in the sorted map,
1279 // which is the one which we would close an idle socket for. We shouldn't
1280 // close an idle socket though, since we should reuse the idle socket.
1281 EXPECT_EQ(OK, handle.Init("0",
1282 params_,
1283 DEFAULT_PRIORITY,
1284 callback.callback(),
1285 pool_.get(),
1286 BoundNetLog()));
1288 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
1289 EXPECT_EQ(kDefaultMaxSockets - 1, pool_->IdleSocketCount());
1292 TEST_F(ClientSocketPoolBaseTest, PendingRequests) {
1293 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1295 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1296 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1297 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", IDLE));
1298 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1299 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1300 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1301 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1302 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1304 ReleaseAllConnections(ClientSocketPoolTest::KEEP_ALIVE);
1306 EXPECT_EQ(kDefaultMaxSocketsPerGroup,
1307 client_socket_factory_.allocation_count());
1308 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup,
1309 completion_count());
1311 EXPECT_EQ(1, GetOrderOfRequest(1));
1312 EXPECT_EQ(2, GetOrderOfRequest(2));
1313 EXPECT_EQ(8, GetOrderOfRequest(3));
1314 EXPECT_EQ(6, GetOrderOfRequest(4));
1315 EXPECT_EQ(4, GetOrderOfRequest(5));
1316 EXPECT_EQ(3, GetOrderOfRequest(6));
1317 EXPECT_EQ(5, GetOrderOfRequest(7));
1318 EXPECT_EQ(7, GetOrderOfRequest(8));
1320 // Make sure we test order of all requests made.
1321 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(9));
1324 TEST_F(ClientSocketPoolBaseTest, PendingRequests_NoKeepAlive) {
1325 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1327 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1328 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1329 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1330 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1331 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1332 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1333 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1335 ReleaseAllConnections(ClientSocketPoolTest::NO_KEEP_ALIVE);
1337 for (size_t i = kDefaultMaxSocketsPerGroup; i < requests_size(); ++i)
1338 EXPECT_EQ(OK, request(i)->WaitForResult());
1340 EXPECT_EQ(static_cast<int>(requests_size()),
1341 client_socket_factory_.allocation_count());
1342 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup,
1343 completion_count());
1346 // This test will start up a RequestSocket() and then immediately Cancel() it.
1347 // The pending connect job will be cancelled and should not call back into
1348 // ClientSocketPoolBase.
1349 TEST_F(ClientSocketPoolBaseTest, CancelRequestClearGroup) {
1350 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1352 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1353 ClientSocketHandle handle;
1354 TestCompletionCallback callback;
1355 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
1356 params_,
1357 DEFAULT_PRIORITY,
1358 callback.callback(),
1359 pool_.get(),
1360 BoundNetLog()));
1361 handle.Reset();
1364 TEST_F(ClientSocketPoolBaseTest, ConnectCancelConnect) {
1365 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1367 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1368 ClientSocketHandle handle;
1369 TestCompletionCallback callback;
1371 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
1372 params_,
1373 DEFAULT_PRIORITY,
1374 callback.callback(),
1375 pool_.get(),
1376 BoundNetLog()));
1378 handle.Reset();
1380 TestCompletionCallback callback2;
1381 EXPECT_EQ(ERR_IO_PENDING,
1382 handle.Init("a",
1383 params_,
1384 DEFAULT_PRIORITY,
1385 callback2.callback(),
1386 pool_.get(),
1387 BoundNetLog()));
1389 EXPECT_EQ(OK, callback2.WaitForResult());
1390 EXPECT_FALSE(callback.have_result());
1392 handle.Reset();
1395 TEST_F(ClientSocketPoolBaseTest, CancelRequest) {
1396 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1398 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1399 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1400 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1401 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1402 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1403 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1404 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1406 // Cancel a request.
1407 size_t index_to_cancel = kDefaultMaxSocketsPerGroup + 2;
1408 EXPECT_FALSE((*requests())[index_to_cancel]->handle()->is_initialized());
1409 (*requests())[index_to_cancel]->handle()->Reset();
1411 ReleaseAllConnections(ClientSocketPoolTest::KEEP_ALIVE);
1413 EXPECT_EQ(kDefaultMaxSocketsPerGroup,
1414 client_socket_factory_.allocation_count());
1415 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup - 1,
1416 completion_count());
1418 EXPECT_EQ(1, GetOrderOfRequest(1));
1419 EXPECT_EQ(2, GetOrderOfRequest(2));
1420 EXPECT_EQ(5, GetOrderOfRequest(3));
1421 EXPECT_EQ(3, GetOrderOfRequest(4));
1422 EXPECT_EQ(ClientSocketPoolTest::kRequestNotFound,
1423 GetOrderOfRequest(5)); // Canceled request.
1424 EXPECT_EQ(4, GetOrderOfRequest(6));
1425 EXPECT_EQ(6, GetOrderOfRequest(7));
1427 // Make sure we test order of all requests made.
1428 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(8));
1431 // Function to be used as a callback on socket request completion. It first
1432 // disconnects the successfully connected socket from the first request, and
1433 // then reuses the ClientSocketHandle to request another socket.
1435 // |nested_callback| is called with the result of the second socket request.
1436 void RequestSocketOnComplete(ClientSocketHandle* handle,
1437 TestClientSocketPool* pool,
1438 TestConnectJobFactory* test_connect_job_factory,
1439 TestConnectJob::JobType next_job_type,
1440 const CompletionCallback& nested_callback,
1441 int first_request_result) {
1442 EXPECT_EQ(OK, first_request_result);
1444 test_connect_job_factory->set_job_type(next_job_type);
1446 // Don't allow reuse of the socket. Disconnect it and then release it.
1447 if (handle->socket())
1448 handle->socket()->Disconnect();
1449 handle->Reset();
1451 scoped_refptr<TestSocketParams> params(
1452 new TestSocketParams(false /* ignore_limits */));
1453 TestCompletionCallback callback;
1454 int rv =
1455 handle->Init("a", params, LOWEST, nested_callback, pool, BoundNetLog());
1456 if (rv != ERR_IO_PENDING) {
1457 DCHECK_EQ(TestConnectJob::kMockJob, next_job_type);
1458 nested_callback.Run(rv);
1459 } else {
1460 DCHECK_EQ(TestConnectJob::kMockPendingJob, next_job_type);
1464 // Tests the case where a second socket is requested in a completion callback,
1465 // and the second socket connects asynchronously. Reuses the same
1466 // ClientSocketHandle for the second socket, after disconnecting the first.
1467 TEST_F(ClientSocketPoolBaseTest, RequestPendingJobTwice) {
1468 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1470 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1471 ClientSocketHandle handle;
1472 TestCompletionCallback second_result_callback;
1473 int rv = handle.Init(
1474 "a", params_, DEFAULT_PRIORITY,
1475 base::Bind(&RequestSocketOnComplete, &handle, pool_.get(),
1476 connect_job_factory_, TestConnectJob::kMockPendingJob,
1477 second_result_callback.callback()),
1478 pool_.get(), BoundNetLog());
1479 ASSERT_EQ(ERR_IO_PENDING, rv);
1481 EXPECT_EQ(OK, second_result_callback.WaitForResult());
1484 // Tests the case where a second socket is requested in a completion callback,
1485 // and the second socket connects synchronously. Reuses the same
1486 // ClientSocketHandle for the second socket, after disconnecting the first.
1487 TEST_F(ClientSocketPoolBaseTest, RequestPendingJobThenSynchronous) {
1488 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1490 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1491 ClientSocketHandle handle;
1492 TestCompletionCallback second_result_callback;
1493 int rv = handle.Init(
1494 "a", params_, DEFAULT_PRIORITY,
1495 base::Bind(&RequestSocketOnComplete, &handle, pool_.get(),
1496 connect_job_factory_, TestConnectJob::kMockPendingJob,
1497 second_result_callback.callback()),
1498 pool_.get(), BoundNetLog());
1499 ASSERT_EQ(ERR_IO_PENDING, rv);
1501 EXPECT_EQ(OK, second_result_callback.WaitForResult());
1504 // Make sure that pending requests get serviced after active requests get
1505 // cancelled.
1506 TEST_F(ClientSocketPoolBaseTest, CancelActiveRequestWithPendingRequests) {
1507 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1509 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1511 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1512 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1513 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1514 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1515 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1516 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1517 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1519 // Now, kDefaultMaxSocketsPerGroup requests should be active.
1520 // Let's cancel them.
1521 for (int i = 0; i < kDefaultMaxSocketsPerGroup; ++i) {
1522 ASSERT_FALSE(request(i)->handle()->is_initialized());
1523 request(i)->handle()->Reset();
1526 // Let's wait for the rest to complete now.
1527 for (size_t i = kDefaultMaxSocketsPerGroup; i < requests_size(); ++i) {
1528 EXPECT_EQ(OK, request(i)->WaitForResult());
1529 request(i)->handle()->Reset();
1532 EXPECT_EQ(requests_size() - kDefaultMaxSocketsPerGroup,
1533 completion_count());
1536 // Make sure that pending requests get serviced after active requests fail.
1537 TEST_F(ClientSocketPoolBaseTest, FailingActiveRequestWithPendingRequests) {
1538 const size_t kMaxSockets = 5;
1539 CreatePool(kMaxSockets, kDefaultMaxSocketsPerGroup);
1541 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1543 const size_t kNumberOfRequests = 2 * kDefaultMaxSocketsPerGroup + 1;
1544 ASSERT_LE(kNumberOfRequests, kMaxSockets); // Otherwise the test will hang.
1546 // Queue up all the requests
1547 for (size_t i = 0; i < kNumberOfRequests; ++i)
1548 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1550 for (size_t i = 0; i < kNumberOfRequests; ++i)
1551 EXPECT_EQ(ERR_CONNECTION_FAILED, request(i)->WaitForResult());
1554 TEST_F(ClientSocketPoolBaseTest, CancelActiveRequestThenRequestSocket) {
1555 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1557 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1559 ClientSocketHandle handle;
1560 TestCompletionCallback callback;
1561 int rv = handle.Init("a",
1562 params_,
1563 DEFAULT_PRIORITY,
1564 callback.callback(),
1565 pool_.get(),
1566 BoundNetLog());
1567 EXPECT_EQ(ERR_IO_PENDING, rv);
1569 // Cancel the active request.
1570 handle.Reset();
1572 rv = handle.Init("a",
1573 params_,
1574 DEFAULT_PRIORITY,
1575 callback.callback(),
1576 pool_.get(),
1577 BoundNetLog());
1578 EXPECT_EQ(ERR_IO_PENDING, rv);
1579 EXPECT_EQ(OK, callback.WaitForResult());
1581 EXPECT_FALSE(handle.is_reused());
1582 TestLoadTimingInfoConnectedNotReused(handle);
1583 EXPECT_EQ(2, client_socket_factory_.allocation_count());
1586 // Regression test for http://crbug.com/17985.
1587 TEST_F(ClientSocketPoolBaseTest, GroupWithPendingRequestsIsNotEmpty) {
1588 const int kMaxSockets = 3;
1589 const int kMaxSocketsPerGroup = 2;
1590 CreatePool(kMaxSockets, kMaxSocketsPerGroup);
1592 const RequestPriority kHighPriority = HIGHEST;
1594 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1595 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
1597 // This is going to be a pending request in an otherwise empty group.
1598 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1600 // Reach the maximum socket limit.
1601 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
1603 // Create a stalled group with high priorities.
1604 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", kHighPriority));
1605 EXPECT_EQ(ERR_IO_PENDING, StartRequest("c", kHighPriority));
1607 // Release the first two sockets from "a". Because this is a keepalive,
1608 // the first release will unblock the pending request for "a". The
1609 // second release will unblock a request for "c", becaue it is the next
1610 // high priority socket.
1611 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1612 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::KEEP_ALIVE));
1614 // Closing idle sockets should not get us into trouble, but in the bug
1615 // we were hitting a CHECK here.
1616 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
1617 pool_->CloseIdleSockets();
1619 // Run the released socket wakeups.
1620 base::MessageLoop::current()->RunUntilIdle();
1623 TEST_F(ClientSocketPoolBaseTest, BasicAsynchronous) {
1624 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1626 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1627 ClientSocketHandle handle;
1628 TestCompletionCallback callback;
1629 BoundTestNetLog log;
1630 int rv = handle.Init("a",
1631 params_,
1632 LOWEST,
1633 callback.callback(),
1634 pool_.get(),
1635 log.bound());
1636 EXPECT_EQ(ERR_IO_PENDING, rv);
1637 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
1638 TestLoadTimingInfoNotConnected(handle);
1640 EXPECT_EQ(OK, callback.WaitForResult());
1641 EXPECT_TRUE(handle.is_initialized());
1642 EXPECT_TRUE(handle.socket());
1643 TestLoadTimingInfoConnectedNotReused(handle);
1645 handle.Reset();
1646 TestLoadTimingInfoNotConnected(handle);
1648 TestNetLogEntry::List entries;
1649 log.GetEntries(&entries);
1651 EXPECT_EQ(4u, entries.size());
1652 EXPECT_TRUE(LogContainsBeginEvent(
1653 entries, 0, NetLog::TYPE_SOCKET_POOL));
1654 EXPECT_TRUE(LogContainsEvent(
1655 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
1656 NetLog::PHASE_NONE));
1657 EXPECT_TRUE(LogContainsEvent(
1658 entries, 2, NetLog::TYPE_SOCKET_POOL_BOUND_TO_SOCKET,
1659 NetLog::PHASE_NONE));
1660 EXPECT_TRUE(LogContainsEndEvent(
1661 entries, 3, NetLog::TYPE_SOCKET_POOL));
1664 TEST_F(ClientSocketPoolBaseTest,
1665 InitConnectionAsynchronousFailure) {
1666 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1668 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1669 ClientSocketHandle handle;
1670 TestCompletionCallback callback;
1671 BoundTestNetLog log;
1672 // Set the additional error state members to ensure that they get cleared.
1673 handle.set_is_ssl_error(true);
1674 HttpResponseInfo info;
1675 info.headers = new HttpResponseHeaders(std::string());
1676 handle.set_ssl_error_response_info(info);
1677 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
1678 params_,
1679 DEFAULT_PRIORITY,
1680 callback.callback(),
1681 pool_.get(),
1682 log.bound()));
1683 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
1684 EXPECT_EQ(ERR_CONNECTION_FAILED, callback.WaitForResult());
1685 EXPECT_FALSE(handle.is_ssl_error());
1686 EXPECT_TRUE(handle.ssl_error_response_info().headers.get() == NULL);
1688 TestNetLogEntry::List entries;
1689 log.GetEntries(&entries);
1691 EXPECT_EQ(3u, entries.size());
1692 EXPECT_TRUE(LogContainsBeginEvent(
1693 entries, 0, NetLog::TYPE_SOCKET_POOL));
1694 EXPECT_TRUE(LogContainsEvent(
1695 entries, 1, NetLog::TYPE_SOCKET_POOL_BOUND_TO_CONNECT_JOB,
1696 NetLog::PHASE_NONE));
1697 EXPECT_TRUE(LogContainsEndEvent(
1698 entries, 2, NetLog::TYPE_SOCKET_POOL));
1701 // Check that an async ConnectJob failure does not result in creation of a new
1702 // ConnectJob when there's another pending request also waiting on its own
1703 // ConnectJob. See http://crbug.com/463960.
1704 TEST_F(ClientSocketPoolBaseTest, AsyncFailureWithPendingRequestWithJob) {
1705 CreatePool(2, 2);
1706 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1708 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1709 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
1711 EXPECT_EQ(ERR_CONNECTION_FAILED, request(0)->WaitForResult());
1712 EXPECT_EQ(ERR_CONNECTION_FAILED, request(1)->WaitForResult());
1714 EXPECT_EQ(2, client_socket_factory_.allocation_count());
1717 TEST_F(ClientSocketPoolBaseTest, TwoRequestsCancelOne) {
1718 // TODO(eroman): Add back the log expectations! Removed them because the
1719 // ordering is difficult, and some may fire during destructor.
1720 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1722 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1723 ClientSocketHandle handle;
1724 TestCompletionCallback callback;
1725 ClientSocketHandle handle2;
1726 TestCompletionCallback callback2;
1728 EXPECT_EQ(ERR_IO_PENDING,
1729 handle.Init("a",
1730 params_,
1731 DEFAULT_PRIORITY,
1732 callback.callback(),
1733 pool_.get(),
1734 BoundNetLog()));
1735 BoundTestNetLog log2;
1736 EXPECT_EQ(ERR_IO_PENDING,
1737 handle2.Init("a",
1738 params_,
1739 DEFAULT_PRIORITY,
1740 callback2.callback(),
1741 pool_.get(),
1742 BoundNetLog()));
1744 handle.Reset();
1747 // At this point, request 2 is just waiting for the connect job to finish.
1749 EXPECT_EQ(OK, callback2.WaitForResult());
1750 handle2.Reset();
1752 // Now request 2 has actually finished.
1753 // TODO(eroman): Add back log expectations.
1756 TEST_F(ClientSocketPoolBaseTest, CancelRequestLimitsJobs) {
1757 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1759 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1761 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOWEST));
1762 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", LOW));
1763 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", MEDIUM));
1764 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", HIGHEST));
1766 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1767 (*requests())[2]->handle()->Reset();
1768 (*requests())[3]->handle()->Reset();
1769 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1771 (*requests())[1]->handle()->Reset();
1772 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1774 (*requests())[0]->handle()->Reset();
1775 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->NumConnectJobsInGroup("a"));
1778 // When requests and ConnectJobs are not coupled, the request will get serviced
1779 // by whatever comes first.
1780 TEST_F(ClientSocketPoolBaseTest, ReleaseSockets) {
1781 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1783 // Start job 1 (async OK)
1784 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
1786 std::vector<TestSocketRequest*> request_order;
1787 size_t completion_count; // unused
1788 TestSocketRequest req1(&request_order, &completion_count);
1789 int rv = req1.handle()->Init("a",
1790 params_,
1791 DEFAULT_PRIORITY,
1792 req1.callback(), pool_.get(),
1793 BoundNetLog());
1794 EXPECT_EQ(ERR_IO_PENDING, rv);
1795 EXPECT_EQ(OK, req1.WaitForResult());
1797 // Job 1 finished OK. Start job 2 (also async OK). Request 3 is pending
1798 // without a job.
1799 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1801 TestSocketRequest req2(&request_order, &completion_count);
1802 rv = req2.handle()->Init("a",
1803 params_,
1804 DEFAULT_PRIORITY,
1805 req2.callback(),
1806 pool_.get(),
1807 BoundNetLog());
1808 EXPECT_EQ(ERR_IO_PENDING, rv);
1809 TestSocketRequest req3(&request_order, &completion_count);
1810 rv = req3.handle()->Init("a",
1811 params_,
1812 DEFAULT_PRIORITY,
1813 req3.callback(),
1814 pool_.get(),
1815 BoundNetLog());
1816 EXPECT_EQ(ERR_IO_PENDING, rv);
1818 // Both Requests 2 and 3 are pending. We release socket 1 which should
1819 // service request 2. Request 3 should still be waiting.
1820 req1.handle()->Reset();
1821 // Run the released socket wakeups.
1822 base::MessageLoop::current()->RunUntilIdle();
1823 ASSERT_TRUE(req2.handle()->socket());
1824 EXPECT_EQ(OK, req2.WaitForResult());
1825 EXPECT_FALSE(req3.handle()->socket());
1827 // Signal job 2, which should service request 3.
1829 client_socket_factory_.SignalJobs();
1830 EXPECT_EQ(OK, req3.WaitForResult());
1832 ASSERT_EQ(3U, request_order.size());
1833 EXPECT_EQ(&req1, request_order[0]);
1834 EXPECT_EQ(&req2, request_order[1]);
1835 EXPECT_EQ(&req3, request_order[2]);
1836 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
1839 // The requests are not coupled to the jobs. So, the requests should finish in
1840 // their priority / insertion order.
1841 TEST_F(ClientSocketPoolBaseTest, PendingJobCompletionOrder) {
1842 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1843 // First two jobs are async.
1844 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
1846 std::vector<TestSocketRequest*> request_order;
1847 size_t completion_count; // unused
1848 TestSocketRequest req1(&request_order, &completion_count);
1849 int rv = req1.handle()->Init("a",
1850 params_,
1851 DEFAULT_PRIORITY,
1852 req1.callback(),
1853 pool_.get(),
1854 BoundNetLog());
1855 EXPECT_EQ(ERR_IO_PENDING, rv);
1857 TestSocketRequest req2(&request_order, &completion_count);
1858 rv = req2.handle()->Init("a",
1859 params_,
1860 DEFAULT_PRIORITY,
1861 req2.callback(),
1862 pool_.get(),
1863 BoundNetLog());
1864 EXPECT_EQ(ERR_IO_PENDING, rv);
1866 // The pending job is sync.
1867 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
1869 TestSocketRequest req3(&request_order, &completion_count);
1870 rv = req3.handle()->Init("a",
1871 params_,
1872 DEFAULT_PRIORITY,
1873 req3.callback(),
1874 pool_.get(),
1875 BoundNetLog());
1876 EXPECT_EQ(ERR_IO_PENDING, rv);
1878 EXPECT_EQ(ERR_CONNECTION_FAILED, req1.WaitForResult());
1879 EXPECT_EQ(OK, req2.WaitForResult());
1880 EXPECT_EQ(ERR_CONNECTION_FAILED, req3.WaitForResult());
1882 ASSERT_EQ(3U, request_order.size());
1883 EXPECT_EQ(&req1, request_order[0]);
1884 EXPECT_EQ(&req2, request_order[1]);
1885 EXPECT_EQ(&req3, request_order[2]);
1888 // Test GetLoadState in the case there's only one socket request.
1889 TEST_F(ClientSocketPoolBaseTest, LoadStateOneRequest) {
1890 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
1891 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1893 ClientSocketHandle handle;
1894 TestCompletionCallback callback;
1895 int rv = handle.Init("a",
1896 params_,
1897 DEFAULT_PRIORITY,
1898 callback.callback(),
1899 pool_.get(),
1900 BoundNetLog());
1901 EXPECT_EQ(ERR_IO_PENDING, rv);
1902 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1904 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_SSL_HANDSHAKE);
1905 EXPECT_EQ(LOAD_STATE_SSL_HANDSHAKE, handle.GetLoadState());
1907 // No point in completing the connection, since ClientSocketHandles only
1908 // expect the LoadState to be checked while connecting.
1911 // Test GetLoadState in the case there are two socket requests.
1912 // Only the first connection in the pool should affect the pool's load status.
1913 TEST_F(ClientSocketPoolBaseTest, LoadStateTwoRequests) {
1914 CreatePool(2, 2);
1915 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1917 ClientSocketHandle handle;
1918 TestCompletionCallback callback;
1919 int rv = handle.Init("a", params_, DEFAULT_PRIORITY, callback.callback(),
1920 pool_.get(), BoundNetLog());
1921 EXPECT_EQ(ERR_IO_PENDING, rv);
1922 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_RESOLVING_HOST);
1924 ClientSocketHandle handle2;
1925 TestCompletionCallback callback2;
1926 rv = handle2.Init("a", params_, DEFAULT_PRIORITY, callback2.callback(),
1927 pool_.get(), BoundNetLog());
1928 EXPECT_EQ(ERR_IO_PENDING, rv);
1929 client_socket_factory_.SetJobLoadState(1, LOAD_STATE_RESOLVING_HOST);
1931 // Check that both handles report the state of the first job.
1932 EXPECT_EQ(LOAD_STATE_RESOLVING_HOST, handle.GetLoadState());
1933 EXPECT_EQ(LOAD_STATE_RESOLVING_HOST, handle2.GetLoadState());
1935 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_CONNECTING);
1937 // Check that both handles change to LOAD_STATE_CONNECTING.
1938 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1939 EXPECT_EQ(LOAD_STATE_CONNECTING, handle2.GetLoadState());
1942 // Test that the second connection request does not affect the pool's load
1943 // status.
1944 TEST_F(ClientSocketPoolBaseTest, LoadStateTwoRequestsChangeSecondRequestState) {
1945 CreatePool(2, 2);
1946 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1948 ClientSocketHandle handle;
1949 TestCompletionCallback callback;
1950 int rv = handle.Init("a", params_, DEFAULT_PRIORITY, callback.callback(),
1951 pool_.get(), BoundNetLog());
1952 EXPECT_EQ(ERR_IO_PENDING, rv);
1954 ClientSocketHandle handle2;
1955 TestCompletionCallback callback2;
1956 rv = handle2.Init("a", params_, DEFAULT_PRIORITY, callback2.callback(),
1957 pool_.get(), BoundNetLog());
1958 EXPECT_EQ(ERR_IO_PENDING, rv);
1959 client_socket_factory_.SetJobLoadState(1, LOAD_STATE_RESOLVING_HOST);
1961 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1962 EXPECT_EQ(LOAD_STATE_CONNECTING, handle2.GetLoadState());
1964 // First job connects and the first request gets the socket. The
1965 // second handle switches to the state of the remaining ConnectJob.
1966 client_socket_factory_.SignalJob(0);
1967 EXPECT_EQ(OK, callback.WaitForResult());
1968 EXPECT_EQ(LOAD_STATE_RESOLVING_HOST, handle2.GetLoadState());
1971 // Test GetLoadState in the case the per-group limit is reached.
1972 TEST_F(ClientSocketPoolBaseTest, LoadStateGroupLimit) {
1973 CreatePool(2, 1);
1974 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
1976 ClientSocketHandle handle;
1977 TestCompletionCallback callback;
1978 int rv = handle.Init("a",
1979 params_,
1980 MEDIUM,
1981 callback.callback(),
1982 pool_.get(),
1983 BoundNetLog());
1984 EXPECT_EQ(ERR_IO_PENDING, rv);
1985 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
1987 // Request another socket from the same pool, buth with a higher priority.
1988 // The first request should now be stalled at the socket group limit.
1989 ClientSocketHandle handle2;
1990 TestCompletionCallback callback2;
1991 rv = handle2.Init("a",
1992 params_,
1993 HIGHEST,
1994 callback2.callback(),
1995 pool_.get(),
1996 BoundNetLog());
1997 EXPECT_EQ(ERR_IO_PENDING, rv);
1998 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET, handle.GetLoadState());
1999 EXPECT_EQ(LOAD_STATE_CONNECTING, handle2.GetLoadState());
2001 // The first handle should remain stalled as the other socket goes through
2002 // the connect process.
2004 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_SSL_HANDSHAKE);
2005 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET, handle.GetLoadState());
2006 EXPECT_EQ(LOAD_STATE_SSL_HANDSHAKE, handle2.GetLoadState());
2008 client_socket_factory_.SignalJob(0);
2009 EXPECT_EQ(OK, callback2.WaitForResult());
2010 EXPECT_EQ(LOAD_STATE_WAITING_FOR_AVAILABLE_SOCKET, handle.GetLoadState());
2012 // Closing the second socket should cause the stalled handle to finally get a
2013 // ConnectJob.
2014 handle2.socket()->Disconnect();
2015 handle2.Reset();
2016 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
2019 // Test GetLoadState in the case the per-pool limit is reached.
2020 TEST_F(ClientSocketPoolBaseTest, LoadStatePoolLimit) {
2021 CreatePool(2, 2);
2022 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2024 ClientSocketHandle handle;
2025 TestCompletionCallback callback;
2026 int rv = handle.Init("a",
2027 params_,
2028 DEFAULT_PRIORITY,
2029 callback.callback(),
2030 pool_.get(),
2031 BoundNetLog());
2032 EXPECT_EQ(ERR_IO_PENDING, rv);
2034 // Request for socket from another pool.
2035 ClientSocketHandle handle2;
2036 TestCompletionCallback callback2;
2037 rv = handle2.Init("b",
2038 params_,
2039 DEFAULT_PRIORITY,
2040 callback2.callback(),
2041 pool_.get(),
2042 BoundNetLog());
2043 EXPECT_EQ(ERR_IO_PENDING, rv);
2045 // Request another socket from the first pool. Request should stall at the
2046 // socket pool limit.
2047 ClientSocketHandle handle3;
2048 TestCompletionCallback callback3;
2049 rv = handle3.Init("a",
2050 params_,
2051 DEFAULT_PRIORITY,
2052 callback2.callback(),
2053 pool_.get(),
2054 BoundNetLog());
2055 EXPECT_EQ(ERR_IO_PENDING, rv);
2057 // The third handle should remain stalled as the other sockets in its group
2058 // goes through the connect process.
2060 EXPECT_EQ(LOAD_STATE_CONNECTING, handle.GetLoadState());
2061 EXPECT_EQ(LOAD_STATE_WAITING_FOR_STALLED_SOCKET_POOL, handle3.GetLoadState());
2063 client_socket_factory_.SetJobLoadState(0, LOAD_STATE_SSL_HANDSHAKE);
2064 EXPECT_EQ(LOAD_STATE_SSL_HANDSHAKE, handle.GetLoadState());
2065 EXPECT_EQ(LOAD_STATE_WAITING_FOR_STALLED_SOCKET_POOL, handle3.GetLoadState());
2067 client_socket_factory_.SignalJob(0);
2068 EXPECT_EQ(OK, callback.WaitForResult());
2069 EXPECT_EQ(LOAD_STATE_WAITING_FOR_STALLED_SOCKET_POOL, handle3.GetLoadState());
2071 // Closing a socket should allow the stalled handle to finally get a new
2072 // ConnectJob.
2073 handle.socket()->Disconnect();
2074 handle.Reset();
2075 EXPECT_EQ(LOAD_STATE_CONNECTING, handle3.GetLoadState());
2078 TEST_F(ClientSocketPoolBaseTest, Recoverable) {
2079 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2080 connect_job_factory_->set_job_type(TestConnectJob::kMockRecoverableJob);
2082 ClientSocketHandle handle;
2083 TestCompletionCallback callback;
2084 EXPECT_EQ(ERR_PROXY_AUTH_REQUESTED,
2085 handle.Init("a", params_, DEFAULT_PRIORITY, callback.callback(),
2086 pool_.get(), BoundNetLog()));
2087 EXPECT_TRUE(handle.is_initialized());
2088 EXPECT_TRUE(handle.socket());
2091 TEST_F(ClientSocketPoolBaseTest, AsyncRecoverable) {
2092 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2094 connect_job_factory_->set_job_type(
2095 TestConnectJob::kMockPendingRecoverableJob);
2096 ClientSocketHandle handle;
2097 TestCompletionCallback callback;
2098 EXPECT_EQ(ERR_IO_PENDING,
2099 handle.Init("a",
2100 params_,
2101 DEFAULT_PRIORITY,
2102 callback.callback(),
2103 pool_.get(),
2104 BoundNetLog()));
2105 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2106 EXPECT_EQ(ERR_PROXY_AUTH_REQUESTED, callback.WaitForResult());
2107 EXPECT_TRUE(handle.is_initialized());
2108 EXPECT_TRUE(handle.socket());
2111 TEST_F(ClientSocketPoolBaseTest, AdditionalErrorStateSynchronous) {
2112 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2113 connect_job_factory_->set_job_type(
2114 TestConnectJob::kMockAdditionalErrorStateJob);
2116 ClientSocketHandle handle;
2117 TestCompletionCallback callback;
2118 EXPECT_EQ(ERR_CONNECTION_FAILED,
2119 handle.Init("a",
2120 params_,
2121 DEFAULT_PRIORITY,
2122 callback.callback(),
2123 pool_.get(),
2124 BoundNetLog()));
2125 EXPECT_FALSE(handle.is_initialized());
2126 EXPECT_FALSE(handle.socket());
2127 EXPECT_TRUE(handle.is_ssl_error());
2128 EXPECT_FALSE(handle.ssl_error_response_info().headers.get() == NULL);
2131 TEST_F(ClientSocketPoolBaseTest, AdditionalErrorStateAsynchronous) {
2132 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2134 connect_job_factory_->set_job_type(
2135 TestConnectJob::kMockPendingAdditionalErrorStateJob);
2136 ClientSocketHandle handle;
2137 TestCompletionCallback callback;
2138 EXPECT_EQ(ERR_IO_PENDING,
2139 handle.Init("a",
2140 params_,
2141 DEFAULT_PRIORITY,
2142 callback.callback(),
2143 pool_.get(),
2144 BoundNetLog()));
2145 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2146 EXPECT_EQ(ERR_CONNECTION_FAILED, callback.WaitForResult());
2147 EXPECT_FALSE(handle.is_initialized());
2148 EXPECT_FALSE(handle.socket());
2149 EXPECT_TRUE(handle.is_ssl_error());
2150 EXPECT_FALSE(handle.ssl_error_response_info().headers.get() == NULL);
2153 // Make sure we can reuse sockets when the cleanup timer is disabled.
2154 TEST_F(ClientSocketPoolBaseTest, DisableCleanupTimerReuse) {
2155 // Disable cleanup timer.
2156 internal::ClientSocketPoolBaseHelper::set_cleanup_timer_enabled(false);
2158 CreatePoolWithIdleTimeouts(
2159 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2160 base::TimeDelta(), // Time out unused sockets immediately.
2161 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2163 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2165 ClientSocketHandle handle;
2166 TestCompletionCallback callback;
2167 int rv = handle.Init("a",
2168 params_,
2169 LOWEST,
2170 callback.callback(),
2171 pool_.get(),
2172 BoundNetLog());
2173 ASSERT_EQ(ERR_IO_PENDING, rv);
2174 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2175 ASSERT_EQ(OK, callback.WaitForResult());
2177 // Use and release the socket.
2178 EXPECT_EQ(1, handle.socket()->Write(NULL, 1, CompletionCallback()));
2179 TestLoadTimingInfoConnectedNotReused(handle);
2180 handle.Reset();
2182 // Should now have one idle socket.
2183 ASSERT_EQ(1, pool_->IdleSocketCount());
2185 // Request a new socket. This should reuse the old socket and complete
2186 // synchronously.
2187 BoundTestNetLog log;
2188 rv = handle.Init("a",
2189 params_,
2190 LOWEST,
2191 CompletionCallback(),
2192 pool_.get(),
2193 log.bound());
2194 ASSERT_EQ(OK, rv);
2195 EXPECT_TRUE(handle.is_reused());
2196 TestLoadTimingInfoConnectedReused(handle);
2198 ASSERT_TRUE(pool_->HasGroup("a"));
2199 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
2200 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
2202 TestNetLogEntry::List entries;
2203 log.GetEntries(&entries);
2204 EXPECT_TRUE(LogContainsEntryWithType(
2205 entries, 1, NetLog::TYPE_SOCKET_POOL_REUSED_AN_EXISTING_SOCKET));
2208 // Make sure we cleanup old unused sockets when the cleanup timer is disabled.
2209 TEST_F(ClientSocketPoolBaseTest, DisableCleanupTimerNoReuse) {
2210 // Disable cleanup timer.
2211 internal::ClientSocketPoolBaseHelper::set_cleanup_timer_enabled(false);
2213 CreatePoolWithIdleTimeouts(
2214 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2215 base::TimeDelta(), // Time out unused sockets immediately
2216 base::TimeDelta()); // Time out used sockets immediately
2218 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2220 // Startup two mock pending connect jobs, which will sit in the MessageLoop.
2222 ClientSocketHandle handle;
2223 TestCompletionCallback callback;
2224 int rv = handle.Init("a",
2225 params_,
2226 LOWEST,
2227 callback.callback(),
2228 pool_.get(),
2229 BoundNetLog());
2230 ASSERT_EQ(ERR_IO_PENDING, rv);
2231 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2233 ClientSocketHandle handle2;
2234 TestCompletionCallback callback2;
2235 rv = handle2.Init("a",
2236 params_,
2237 LOWEST,
2238 callback2.callback(),
2239 pool_.get(),
2240 BoundNetLog());
2241 ASSERT_EQ(ERR_IO_PENDING, rv);
2242 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle2));
2244 // Cancel one of the requests. Wait for the other, which will get the first
2245 // job. Release the socket. Run the loop again to make sure the second
2246 // socket is sitting idle and the first one is released (since ReleaseSocket()
2247 // just posts a DoReleaseSocket() task).
2249 handle.Reset();
2250 ASSERT_EQ(OK, callback2.WaitForResult());
2251 // Use the socket.
2252 EXPECT_EQ(1, handle2.socket()->Write(NULL, 1, CompletionCallback()));
2253 handle2.Reset();
2255 // We post all of our delayed tasks with a 2ms delay. I.e. they don't
2256 // actually become pending until 2ms after they have been created. In order
2257 // to flush all tasks, we need to wait so that we know there are no
2258 // soon-to-be-pending tasks waiting.
2259 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(10));
2260 base::MessageLoop::current()->RunUntilIdle();
2262 // Both sockets should now be idle.
2263 ASSERT_EQ(2, pool_->IdleSocketCount());
2265 // Request a new socket. This should cleanup the unused and timed out ones.
2266 // A new socket will be created rather than reusing the idle one.
2267 BoundTestNetLog log;
2268 TestCompletionCallback callback3;
2269 rv = handle.Init("a",
2270 params_,
2271 LOWEST,
2272 callback3.callback(),
2273 pool_.get(),
2274 log.bound());
2275 ASSERT_EQ(ERR_IO_PENDING, rv);
2276 ASSERT_EQ(OK, callback3.WaitForResult());
2277 EXPECT_FALSE(handle.is_reused());
2279 // Make sure the idle socket is closed.
2280 ASSERT_TRUE(pool_->HasGroup("a"));
2281 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
2282 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
2284 TestNetLogEntry::List entries;
2285 log.GetEntries(&entries);
2286 EXPECT_FALSE(LogContainsEntryWithType(
2287 entries, 1, NetLog::TYPE_SOCKET_POOL_REUSED_AN_EXISTING_SOCKET));
2290 TEST_F(ClientSocketPoolBaseTest, CleanupTimedOutIdleSockets) {
2291 CreatePoolWithIdleTimeouts(
2292 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2293 base::TimeDelta(), // Time out unused sockets immediately.
2294 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2296 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2298 // Startup two mock pending connect jobs, which will sit in the MessageLoop.
2300 ClientSocketHandle handle;
2301 TestCompletionCallback callback;
2302 int rv = handle.Init("a",
2303 params_,
2304 LOWEST,
2305 callback.callback(),
2306 pool_.get(),
2307 BoundNetLog());
2308 EXPECT_EQ(ERR_IO_PENDING, rv);
2309 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle));
2311 ClientSocketHandle handle2;
2312 TestCompletionCallback callback2;
2313 rv = handle2.Init("a",
2314 params_,
2315 LOWEST,
2316 callback2.callback(),
2317 pool_.get(),
2318 BoundNetLog());
2319 EXPECT_EQ(ERR_IO_PENDING, rv);
2320 EXPECT_EQ(LOAD_STATE_CONNECTING, pool_->GetLoadState("a", &handle2));
2322 // Cancel one of the requests. Wait for the other, which will get the first
2323 // job. Release the socket. Run the loop again to make sure the second
2324 // socket is sitting idle and the first one is released (since ReleaseSocket()
2325 // just posts a DoReleaseSocket() task).
2327 handle.Reset();
2328 EXPECT_EQ(OK, callback2.WaitForResult());
2329 // Use the socket.
2330 EXPECT_EQ(1, handle2.socket()->Write(NULL, 1, CompletionCallback()));
2331 handle2.Reset();
2333 // We post all of our delayed tasks with a 2ms delay. I.e. they don't
2334 // actually become pending until 2ms after they have been created. In order
2335 // to flush all tasks, we need to wait so that we know there are no
2336 // soon-to-be-pending tasks waiting.
2337 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(10));
2338 base::MessageLoop::current()->RunUntilIdle();
2340 ASSERT_EQ(2, pool_->IdleSocketCount());
2342 // Invoke the idle socket cleanup check. Only one socket should be left, the
2343 // used socket. Request it to make sure that it's used.
2345 pool_->CleanupTimedOutIdleSockets();
2346 BoundTestNetLog log;
2347 rv = handle.Init("a",
2348 params_,
2349 LOWEST,
2350 callback.callback(),
2351 pool_.get(),
2352 log.bound());
2353 EXPECT_EQ(OK, rv);
2354 EXPECT_TRUE(handle.is_reused());
2356 TestNetLogEntry::List entries;
2357 log.GetEntries(&entries);
2358 EXPECT_TRUE(LogContainsEntryWithType(
2359 entries, 1, NetLog::TYPE_SOCKET_POOL_REUSED_AN_EXISTING_SOCKET));
2362 // Make sure that we process all pending requests even when we're stalling
2363 // because of multiple releasing disconnected sockets.
2364 TEST_F(ClientSocketPoolBaseTest, MultipleReleasingDisconnectedSockets) {
2365 CreatePoolWithIdleTimeouts(
2366 kDefaultMaxSockets, kDefaultMaxSocketsPerGroup,
2367 base::TimeDelta(), // Time out unused sockets immediately.
2368 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2370 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2372 // Startup 4 connect jobs. Two of them will be pending.
2374 ClientSocketHandle handle;
2375 TestCompletionCallback callback;
2376 int rv = handle.Init("a",
2377 params_,
2378 LOWEST,
2379 callback.callback(),
2380 pool_.get(),
2381 BoundNetLog());
2382 EXPECT_EQ(OK, rv);
2384 ClientSocketHandle handle2;
2385 TestCompletionCallback callback2;
2386 rv = handle2.Init("a",
2387 params_,
2388 LOWEST,
2389 callback2.callback(),
2390 pool_.get(),
2391 BoundNetLog());
2392 EXPECT_EQ(OK, rv);
2394 ClientSocketHandle handle3;
2395 TestCompletionCallback callback3;
2396 rv = handle3.Init("a",
2397 params_,
2398 LOWEST,
2399 callback3.callback(),
2400 pool_.get(),
2401 BoundNetLog());
2402 EXPECT_EQ(ERR_IO_PENDING, rv);
2404 ClientSocketHandle handle4;
2405 TestCompletionCallback callback4;
2406 rv = handle4.Init("a",
2407 params_,
2408 LOWEST,
2409 callback4.callback(),
2410 pool_.get(),
2411 BoundNetLog());
2412 EXPECT_EQ(ERR_IO_PENDING, rv);
2414 // Release two disconnected sockets.
2416 handle.socket()->Disconnect();
2417 handle.Reset();
2418 handle2.socket()->Disconnect();
2419 handle2.Reset();
2421 EXPECT_EQ(OK, callback3.WaitForResult());
2422 EXPECT_FALSE(handle3.is_reused());
2423 EXPECT_EQ(OK, callback4.WaitForResult());
2424 EXPECT_FALSE(handle4.is_reused());
2427 // Regression test for http://crbug.com/42267.
2428 // When DoReleaseSocket() is processed for one socket, it is blocked because the
2429 // other stalled groups all have releasing sockets, so no progress can be made.
2430 TEST_F(ClientSocketPoolBaseTest, SocketLimitReleasingSockets) {
2431 CreatePoolWithIdleTimeouts(
2432 4 /* socket limit */, 4 /* socket limit per group */,
2433 base::TimeDelta(), // Time out unused sockets immediately.
2434 base::TimeDelta::FromDays(1)); // Don't time out used sockets.
2436 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2438 // Max out the socket limit with 2 per group.
2440 ClientSocketHandle handle_a[4];
2441 TestCompletionCallback callback_a[4];
2442 ClientSocketHandle handle_b[4];
2443 TestCompletionCallback callback_b[4];
2445 for (int i = 0; i < 2; ++i) {
2446 EXPECT_EQ(OK, handle_a[i].Init("a",
2447 params_,
2448 LOWEST,
2449 callback_a[i].callback(),
2450 pool_.get(),
2451 BoundNetLog()));
2452 EXPECT_EQ(OK, handle_b[i].Init("b",
2453 params_,
2454 LOWEST,
2455 callback_b[i].callback(),
2456 pool_.get(),
2457 BoundNetLog()));
2460 // Make 4 pending requests, 2 per group.
2462 for (int i = 2; i < 4; ++i) {
2463 EXPECT_EQ(ERR_IO_PENDING,
2464 handle_a[i].Init("a",
2465 params_,
2466 LOWEST,
2467 callback_a[i].callback(),
2468 pool_.get(),
2469 BoundNetLog()));
2470 EXPECT_EQ(ERR_IO_PENDING,
2471 handle_b[i].Init("b",
2472 params_,
2473 LOWEST,
2474 callback_b[i].callback(),
2475 pool_.get(),
2476 BoundNetLog()));
2479 // Release b's socket first. The order is important, because in
2480 // DoReleaseSocket(), we'll process b's released socket, and since both b and
2481 // a are stalled, but 'a' is lower lexicographically, we'll process group 'a'
2482 // first, which has a releasing socket, so it refuses to start up another
2483 // ConnectJob. So, we used to infinite loop on this.
2484 handle_b[0].socket()->Disconnect();
2485 handle_b[0].Reset();
2486 handle_a[0].socket()->Disconnect();
2487 handle_a[0].Reset();
2489 // Used to get stuck here.
2490 base::MessageLoop::current()->RunUntilIdle();
2492 handle_b[1].socket()->Disconnect();
2493 handle_b[1].Reset();
2494 handle_a[1].socket()->Disconnect();
2495 handle_a[1].Reset();
2497 for (int i = 2; i < 4; ++i) {
2498 EXPECT_EQ(OK, callback_b[i].WaitForResult());
2499 EXPECT_EQ(OK, callback_a[i].WaitForResult());
2503 TEST_F(ClientSocketPoolBaseTest,
2504 ReleasingDisconnectedSocketsMaintainsPriorityOrder) {
2505 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2507 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2509 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2510 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2511 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2512 EXPECT_EQ(ERR_IO_PENDING, StartRequest("a", DEFAULT_PRIORITY));
2514 EXPECT_EQ(OK, (*requests())[0]->WaitForResult());
2515 EXPECT_EQ(OK, (*requests())[1]->WaitForResult());
2516 EXPECT_EQ(2u, completion_count());
2518 // Releases one connection.
2519 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::NO_KEEP_ALIVE));
2520 EXPECT_EQ(OK, (*requests())[2]->WaitForResult());
2522 EXPECT_TRUE(ReleaseOneConnection(ClientSocketPoolTest::NO_KEEP_ALIVE));
2523 EXPECT_EQ(OK, (*requests())[3]->WaitForResult());
2524 EXPECT_EQ(4u, completion_count());
2526 EXPECT_EQ(1, GetOrderOfRequest(1));
2527 EXPECT_EQ(2, GetOrderOfRequest(2));
2528 EXPECT_EQ(3, GetOrderOfRequest(3));
2529 EXPECT_EQ(4, GetOrderOfRequest(4));
2531 // Make sure we test order of all requests made.
2532 EXPECT_EQ(ClientSocketPoolTest::kIndexOutOfBounds, GetOrderOfRequest(5));
2535 class TestReleasingSocketRequest : public TestCompletionCallbackBase {
2536 public:
2537 TestReleasingSocketRequest(TestClientSocketPool* pool,
2538 int expected_result,
2539 bool reset_releasing_handle)
2540 : pool_(pool),
2541 expected_result_(expected_result),
2542 reset_releasing_handle_(reset_releasing_handle),
2543 callback_(base::Bind(&TestReleasingSocketRequest::OnComplete,
2544 base::Unretained(this))) {
2547 ~TestReleasingSocketRequest() override {}
2549 ClientSocketHandle* handle() { return &handle_; }
2551 const CompletionCallback& callback() const { return callback_; }
2553 private:
2554 void OnComplete(int result) {
2555 SetResult(result);
2556 if (reset_releasing_handle_)
2557 handle_.Reset();
2559 scoped_refptr<TestSocketParams> con_params(
2560 new TestSocketParams(false /* ignore_limits */));
2561 EXPECT_EQ(expected_result_,
2562 handle2_.Init("a", con_params, DEFAULT_PRIORITY,
2563 callback2_.callback(), pool_, BoundNetLog()));
2566 TestClientSocketPool* const pool_;
2567 int expected_result_;
2568 bool reset_releasing_handle_;
2569 ClientSocketHandle handle_;
2570 ClientSocketHandle handle2_;
2571 CompletionCallback callback_;
2572 TestCompletionCallback callback2_;
2576 TEST_F(ClientSocketPoolBaseTest, AdditionalErrorSocketsDontUseSlot) {
2577 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2579 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
2580 EXPECT_EQ(OK, StartRequest("a", DEFAULT_PRIORITY));
2581 EXPECT_EQ(OK, StartRequest("b", DEFAULT_PRIORITY));
2583 EXPECT_EQ(static_cast<int>(requests_size()),
2584 client_socket_factory_.allocation_count());
2586 connect_job_factory_->set_job_type(
2587 TestConnectJob::kMockPendingAdditionalErrorStateJob);
2588 TestReleasingSocketRequest req(pool_.get(), OK, false);
2589 EXPECT_EQ(ERR_IO_PENDING,
2590 req.handle()->Init("a", params_, DEFAULT_PRIORITY, req.callback(),
2591 pool_.get(), BoundNetLog()));
2592 // The next job should complete synchronously
2593 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2595 EXPECT_EQ(ERR_CONNECTION_FAILED, req.WaitForResult());
2596 EXPECT_FALSE(req.handle()->is_initialized());
2597 EXPECT_FALSE(req.handle()->socket());
2598 EXPECT_TRUE(req.handle()->is_ssl_error());
2599 EXPECT_FALSE(req.handle()->ssl_error_response_info().headers.get() == NULL);
2602 // http://crbug.com/44724 regression test.
2603 // We start releasing the pool when we flush on network change. When that
2604 // happens, the only active references are in the ClientSocketHandles. When a
2605 // ConnectJob completes and calls back into the last ClientSocketHandle, that
2606 // callback can release the last reference and delete the pool. After the
2607 // callback finishes, we go back to the stack frame within the now-deleted pool.
2608 // Executing any code that refers to members of the now-deleted pool can cause
2609 // crashes.
2610 TEST_F(ClientSocketPoolBaseTest, CallbackThatReleasesPool) {
2611 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2612 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
2614 ClientSocketHandle handle;
2615 TestCompletionCallback callback;
2616 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2617 params_,
2618 DEFAULT_PRIORITY,
2619 callback.callback(),
2620 pool_.get(),
2621 BoundNetLog()));
2623 pool_->FlushWithError(ERR_NETWORK_CHANGED);
2625 // We'll call back into this now.
2626 callback.WaitForResult();
2629 TEST_F(ClientSocketPoolBaseTest, DoNotReuseSocketAfterFlush) {
2630 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2631 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2633 ClientSocketHandle handle;
2634 TestCompletionCallback callback;
2635 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2636 params_,
2637 DEFAULT_PRIORITY,
2638 callback.callback(),
2639 pool_.get(),
2640 BoundNetLog()));
2641 EXPECT_EQ(OK, callback.WaitForResult());
2642 EXPECT_EQ(ClientSocketHandle::UNUSED, handle.reuse_type());
2644 pool_->FlushWithError(ERR_NETWORK_CHANGED);
2646 handle.Reset();
2647 base::MessageLoop::current()->RunUntilIdle();
2649 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2650 params_,
2651 DEFAULT_PRIORITY,
2652 callback.callback(),
2653 pool_.get(),
2654 BoundNetLog()));
2655 EXPECT_EQ(OK, callback.WaitForResult());
2656 EXPECT_EQ(ClientSocketHandle::UNUSED, handle.reuse_type());
2659 class ConnectWithinCallback : public TestCompletionCallbackBase {
2660 public:
2661 ConnectWithinCallback(
2662 const std::string& group_name,
2663 const scoped_refptr<TestSocketParams>& params,
2664 TestClientSocketPool* pool)
2665 : group_name_(group_name),
2666 params_(params),
2667 pool_(pool),
2668 callback_(base::Bind(&ConnectWithinCallback::OnComplete,
2669 base::Unretained(this))) {
2672 ~ConnectWithinCallback() override {}
2674 int WaitForNestedResult() {
2675 return nested_callback_.WaitForResult();
2678 const CompletionCallback& callback() const { return callback_; }
2680 private:
2681 void OnComplete(int result) {
2682 SetResult(result);
2683 EXPECT_EQ(ERR_IO_PENDING,
2684 handle_.Init(group_name_,
2685 params_,
2686 DEFAULT_PRIORITY,
2687 nested_callback_.callback(),
2688 pool_,
2689 BoundNetLog()));
2692 const std::string group_name_;
2693 const scoped_refptr<TestSocketParams> params_;
2694 TestClientSocketPool* const pool_;
2695 ClientSocketHandle handle_;
2696 CompletionCallback callback_;
2697 TestCompletionCallback nested_callback_;
2699 DISALLOW_COPY_AND_ASSIGN(ConnectWithinCallback);
2702 TEST_F(ClientSocketPoolBaseTest, AbortAllRequestsOnFlush) {
2703 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2705 // First job will be waiting until it gets aborted.
2706 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2708 ClientSocketHandle handle;
2709 ConnectWithinCallback callback("a", params_, pool_.get());
2710 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
2711 params_,
2712 DEFAULT_PRIORITY,
2713 callback.callback(),
2714 pool_.get(),
2715 BoundNetLog()));
2717 // Second job will be started during the first callback, and will
2718 // asynchronously complete with OK.
2719 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2720 pool_->FlushWithError(ERR_NETWORK_CHANGED);
2721 EXPECT_EQ(ERR_NETWORK_CHANGED, callback.WaitForResult());
2722 EXPECT_EQ(OK, callback.WaitForNestedResult());
2725 // Cancel a pending socket request while we're at max sockets,
2726 // and verify that the backup socket firing doesn't cause a crash.
2727 TEST_F(ClientSocketPoolBaseTest, BackupSocketCancelAtMaxSockets) {
2728 // Max 4 sockets globally, max 4 sockets per group.
2729 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
2730 pool_->EnableConnectBackupJobs();
2732 // Create the first socket and set to ERR_IO_PENDING. This starts the backup
2733 // timer.
2734 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2735 ClientSocketHandle handle;
2736 TestCompletionCallback callback;
2737 EXPECT_EQ(ERR_IO_PENDING, handle.Init("bar",
2738 params_,
2739 DEFAULT_PRIORITY,
2740 callback.callback(),
2741 pool_.get(),
2742 BoundNetLog()));
2744 // Start (MaxSockets - 1) connected sockets to reach max sockets.
2745 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
2746 ClientSocketHandle handles[kDefaultMaxSockets];
2747 for (int i = 1; i < kDefaultMaxSockets; ++i) {
2748 TestCompletionCallback callback;
2749 EXPECT_EQ(OK, handles[i].Init("bar",
2750 params_,
2751 DEFAULT_PRIORITY,
2752 callback.callback(),
2753 pool_.get(),
2754 BoundNetLog()));
2757 base::MessageLoop::current()->RunUntilIdle();
2759 // Cancel the pending request.
2760 handle.Reset();
2762 // Wait for the backup timer to fire (add some slop to ensure it fires)
2763 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(
2764 ClientSocketPool::kMaxConnectRetryIntervalMs / 2 * 3));
2766 base::MessageLoop::current()->RunUntilIdle();
2767 EXPECT_EQ(kDefaultMaxSockets, client_socket_factory_.allocation_count());
2770 TEST_F(ClientSocketPoolBaseTest, CancelBackupSocketAfterCancelingAllRequests) {
2771 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
2772 pool_->EnableConnectBackupJobs();
2774 // Create the first socket and set to ERR_IO_PENDING. This starts the backup
2775 // timer.
2776 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2777 ClientSocketHandle handle;
2778 TestCompletionCallback callback;
2779 EXPECT_EQ(ERR_IO_PENDING, handle.Init("bar",
2780 params_,
2781 DEFAULT_PRIORITY,
2782 callback.callback(),
2783 pool_.get(),
2784 BoundNetLog()));
2785 ASSERT_TRUE(pool_->HasGroup("bar"));
2786 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("bar"));
2787 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("bar"));
2789 // Cancel the socket request. This should cancel the backup timer. Wait for
2790 // the backup time to see if it indeed got canceled.
2791 handle.Reset();
2792 // Wait for the backup timer to fire (add some slop to ensure it fires)
2793 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(
2794 ClientSocketPool::kMaxConnectRetryIntervalMs / 2 * 3));
2795 base::MessageLoop::current()->RunUntilIdle();
2796 ASSERT_TRUE(pool_->HasGroup("bar"));
2797 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("bar"));
2800 TEST_F(ClientSocketPoolBaseTest, CancelBackupSocketAfterFinishingAllRequests) {
2801 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
2802 pool_->EnableConnectBackupJobs();
2804 // Create the first socket and set to ERR_IO_PENDING. This starts the backup
2805 // timer.
2806 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2807 ClientSocketHandle handle;
2808 TestCompletionCallback callback;
2809 EXPECT_EQ(ERR_IO_PENDING, handle.Init("bar",
2810 params_,
2811 DEFAULT_PRIORITY,
2812 callback.callback(),
2813 pool_.get(),
2814 BoundNetLog()));
2815 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2816 ClientSocketHandle handle2;
2817 TestCompletionCallback callback2;
2818 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("bar",
2819 params_,
2820 DEFAULT_PRIORITY,
2821 callback2.callback(),
2822 pool_.get(),
2823 BoundNetLog()));
2824 ASSERT_TRUE(pool_->HasGroup("bar"));
2825 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("bar"));
2827 // Cancel request 1 and then complete request 2. With the requests finished,
2828 // the backup timer should be cancelled.
2829 handle.Reset();
2830 EXPECT_EQ(OK, callback2.WaitForResult());
2831 // Wait for the backup timer to fire (add some slop to ensure it fires)
2832 base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(
2833 ClientSocketPool::kMaxConnectRetryIntervalMs / 2 * 3));
2834 base::MessageLoop::current()->RunUntilIdle();
2837 // Test delayed socket binding for the case where we have two connects,
2838 // and while one is waiting on a connect, the other frees up.
2839 // The socket waiting on a connect should switch immediately to the freed
2840 // up socket.
2841 TEST_F(ClientSocketPoolBaseTest, DelayedSocketBindingWaitingForConnect) {
2842 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2843 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2845 ClientSocketHandle handle1;
2846 TestCompletionCallback callback;
2847 EXPECT_EQ(ERR_IO_PENDING,
2848 handle1.Init("a",
2849 params_,
2850 DEFAULT_PRIORITY,
2851 callback.callback(),
2852 pool_.get(),
2853 BoundNetLog()));
2854 EXPECT_EQ(OK, callback.WaitForResult());
2856 // No idle sockets, no pending jobs.
2857 EXPECT_EQ(0, pool_->IdleSocketCount());
2858 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2860 // Create a second socket to the same host, but this one will wait.
2861 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2862 ClientSocketHandle handle2;
2863 EXPECT_EQ(ERR_IO_PENDING,
2864 handle2.Init("a",
2865 params_,
2866 DEFAULT_PRIORITY,
2867 callback.callback(),
2868 pool_.get(),
2869 BoundNetLog()));
2870 // No idle sockets, and one connecting job.
2871 EXPECT_EQ(0, pool_->IdleSocketCount());
2872 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2874 // Return the first handle to the pool. This will initiate the delayed
2875 // binding.
2876 handle1.Reset();
2878 base::MessageLoop::current()->RunUntilIdle();
2880 // Still no idle sockets, still one pending connect job.
2881 EXPECT_EQ(0, pool_->IdleSocketCount());
2882 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2884 // The second socket connected, even though it was a Waiting Job.
2885 EXPECT_EQ(OK, callback.WaitForResult());
2887 // And we can see there is still one job waiting.
2888 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2890 // Finally, signal the waiting Connect.
2891 client_socket_factory_.SignalJobs();
2892 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2894 base::MessageLoop::current()->RunUntilIdle();
2897 // Test delayed socket binding when a group is at capacity and one
2898 // of the group's sockets frees up.
2899 TEST_F(ClientSocketPoolBaseTest, DelayedSocketBindingAtGroupCapacity) {
2900 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2901 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2903 ClientSocketHandle handle1;
2904 TestCompletionCallback callback;
2905 EXPECT_EQ(ERR_IO_PENDING,
2906 handle1.Init("a",
2907 params_,
2908 DEFAULT_PRIORITY,
2909 callback.callback(),
2910 pool_.get(),
2911 BoundNetLog()));
2912 EXPECT_EQ(OK, callback.WaitForResult());
2914 // No idle sockets, no pending jobs.
2915 EXPECT_EQ(0, pool_->IdleSocketCount());
2916 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2918 // Create a second socket to the same host, but this one will wait.
2919 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2920 ClientSocketHandle handle2;
2921 EXPECT_EQ(ERR_IO_PENDING,
2922 handle2.Init("a",
2923 params_,
2924 DEFAULT_PRIORITY,
2925 callback.callback(),
2926 pool_.get(),
2927 BoundNetLog()));
2928 // No idle sockets, and one connecting job.
2929 EXPECT_EQ(0, pool_->IdleSocketCount());
2930 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2932 // Return the first handle to the pool. This will initiate the delayed
2933 // binding.
2934 handle1.Reset();
2936 base::MessageLoop::current()->RunUntilIdle();
2938 // Still no idle sockets, still one pending connect job.
2939 EXPECT_EQ(0, pool_->IdleSocketCount());
2940 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2942 // The second socket connected, even though it was a Waiting Job.
2943 EXPECT_EQ(OK, callback.WaitForResult());
2945 // And we can see there is still one job waiting.
2946 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2948 // Finally, signal the waiting Connect.
2949 client_socket_factory_.SignalJobs();
2950 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2952 base::MessageLoop::current()->RunUntilIdle();
2955 // Test out the case where we have one socket connected, one
2956 // connecting, when the first socket finishes and goes idle.
2957 // Although the second connection is pending, the second request
2958 // should complete, by taking the first socket's idle socket.
2959 TEST_F(ClientSocketPoolBaseTest, DelayedSocketBindingAtStall) {
2960 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
2961 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
2963 ClientSocketHandle handle1;
2964 TestCompletionCallback callback;
2965 EXPECT_EQ(ERR_IO_PENDING,
2966 handle1.Init("a",
2967 params_,
2968 DEFAULT_PRIORITY,
2969 callback.callback(),
2970 pool_.get(),
2971 BoundNetLog()));
2972 EXPECT_EQ(OK, callback.WaitForResult());
2974 // No idle sockets, no pending jobs.
2975 EXPECT_EQ(0, pool_->IdleSocketCount());
2976 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
2978 // Create a second socket to the same host, but this one will wait.
2979 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
2980 ClientSocketHandle handle2;
2981 EXPECT_EQ(ERR_IO_PENDING,
2982 handle2.Init("a",
2983 params_,
2984 DEFAULT_PRIORITY,
2985 callback.callback(),
2986 pool_.get(),
2987 BoundNetLog()));
2988 // No idle sockets, and one connecting job.
2989 EXPECT_EQ(0, pool_->IdleSocketCount());
2990 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
2992 // Return the first handle to the pool. This will initiate the delayed
2993 // binding.
2994 handle1.Reset();
2996 base::MessageLoop::current()->RunUntilIdle();
2998 // Still no idle sockets, still one pending connect job.
2999 EXPECT_EQ(0, pool_->IdleSocketCount());
3000 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3002 // The second socket connected, even though it was a Waiting Job.
3003 EXPECT_EQ(OK, callback.WaitForResult());
3005 // And we can see there is still one job waiting.
3006 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3008 // Finally, signal the waiting Connect.
3009 client_socket_factory_.SignalJobs();
3010 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3012 base::MessageLoop::current()->RunUntilIdle();
3015 // Cover the case where on an available socket slot, we have one pending
3016 // request that completes synchronously, thereby making the Group empty.
3017 TEST_F(ClientSocketPoolBaseTest, SynchronouslyProcessOnePendingRequest) {
3018 const int kUnlimitedSockets = 100;
3019 const int kOneSocketPerGroup = 1;
3020 CreatePool(kUnlimitedSockets, kOneSocketPerGroup);
3022 // Make the first request asynchronous fail.
3023 // This will free up a socket slot later.
3024 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingFailingJob);
3026 ClientSocketHandle handle1;
3027 TestCompletionCallback callback1;
3028 EXPECT_EQ(ERR_IO_PENDING,
3029 handle1.Init("a",
3030 params_,
3031 DEFAULT_PRIORITY,
3032 callback1.callback(),
3033 pool_.get(),
3034 BoundNetLog()));
3035 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3037 // Make the second request synchronously fail. This should make the Group
3038 // empty.
3039 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
3040 ClientSocketHandle handle2;
3041 TestCompletionCallback callback2;
3042 // It'll be ERR_IO_PENDING now, but the TestConnectJob will synchronously fail
3043 // when created.
3044 EXPECT_EQ(ERR_IO_PENDING,
3045 handle2.Init("a",
3046 params_,
3047 DEFAULT_PRIORITY,
3048 callback2.callback(),
3049 pool_.get(),
3050 BoundNetLog()));
3052 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3054 EXPECT_EQ(ERR_CONNECTION_FAILED, callback1.WaitForResult());
3055 EXPECT_EQ(ERR_CONNECTION_FAILED, callback2.WaitForResult());
3056 EXPECT_FALSE(pool_->HasGroup("a"));
3059 TEST_F(ClientSocketPoolBaseTest, PreferUsedSocketToUnusedSocket) {
3060 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
3062 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3064 ClientSocketHandle handle1;
3065 TestCompletionCallback callback1;
3066 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3067 params_,
3068 DEFAULT_PRIORITY,
3069 callback1.callback(),
3070 pool_.get(),
3071 BoundNetLog()));
3073 ClientSocketHandle handle2;
3074 TestCompletionCallback callback2;
3075 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3076 params_,
3077 DEFAULT_PRIORITY,
3078 callback2.callback(),
3079 pool_.get(),
3080 BoundNetLog()));
3081 ClientSocketHandle handle3;
3082 TestCompletionCallback callback3;
3083 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("a",
3084 params_,
3085 DEFAULT_PRIORITY,
3086 callback3.callback(),
3087 pool_.get(),
3088 BoundNetLog()));
3090 EXPECT_EQ(OK, callback1.WaitForResult());
3091 EXPECT_EQ(OK, callback2.WaitForResult());
3092 EXPECT_EQ(OK, callback3.WaitForResult());
3094 // Use the socket.
3095 EXPECT_EQ(1, handle1.socket()->Write(NULL, 1, CompletionCallback()));
3096 EXPECT_EQ(1, handle3.socket()->Write(NULL, 1, CompletionCallback()));
3098 handle1.Reset();
3099 handle2.Reset();
3100 handle3.Reset();
3102 EXPECT_EQ(OK, handle1.Init("a",
3103 params_,
3104 DEFAULT_PRIORITY,
3105 callback1.callback(),
3106 pool_.get(),
3107 BoundNetLog()));
3108 EXPECT_EQ(OK, handle2.Init("a",
3109 params_,
3110 DEFAULT_PRIORITY,
3111 callback2.callback(),
3112 pool_.get(),
3113 BoundNetLog()));
3114 EXPECT_EQ(OK, handle3.Init("a",
3115 params_,
3116 DEFAULT_PRIORITY,
3117 callback3.callback(),
3118 pool_.get(),
3119 BoundNetLog()));
3121 EXPECT_TRUE(handle1.socket()->WasEverUsed());
3122 EXPECT_TRUE(handle2.socket()->WasEverUsed());
3123 EXPECT_FALSE(handle3.socket()->WasEverUsed());
3126 TEST_F(ClientSocketPoolBaseTest, RequestSockets) {
3127 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3128 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3130 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3132 ASSERT_TRUE(pool_->HasGroup("a"));
3133 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3134 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3135 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3137 ClientSocketHandle handle1;
3138 TestCompletionCallback callback1;
3139 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3140 params_,
3141 DEFAULT_PRIORITY,
3142 callback1.callback(),
3143 pool_.get(),
3144 BoundNetLog()));
3146 ClientSocketHandle handle2;
3147 TestCompletionCallback callback2;
3148 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3149 params_,
3150 DEFAULT_PRIORITY,
3151 callback2.callback(),
3152 pool_.get(),
3153 BoundNetLog()));
3155 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3156 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3157 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3159 EXPECT_EQ(OK, callback1.WaitForResult());
3160 EXPECT_EQ(OK, callback2.WaitForResult());
3161 handle1.Reset();
3162 handle2.Reset();
3164 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3165 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3166 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3169 TEST_F(ClientSocketPoolBaseTest, RequestSocketsWhenAlreadyHaveAConnectJob) {
3170 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3171 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3173 ClientSocketHandle handle1;
3174 TestCompletionCallback callback1;
3175 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3176 params_,
3177 DEFAULT_PRIORITY,
3178 callback1.callback(),
3179 pool_.get(),
3180 BoundNetLog()));
3182 ASSERT_TRUE(pool_->HasGroup("a"));
3183 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3184 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3185 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3187 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3189 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3190 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3191 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3193 ClientSocketHandle handle2;
3194 TestCompletionCallback callback2;
3195 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3196 params_,
3197 DEFAULT_PRIORITY,
3198 callback2.callback(),
3199 pool_.get(),
3200 BoundNetLog()));
3202 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3203 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3204 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3206 EXPECT_EQ(OK, callback1.WaitForResult());
3207 EXPECT_EQ(OK, callback2.WaitForResult());
3208 handle1.Reset();
3209 handle2.Reset();
3211 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3212 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3213 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3216 TEST_F(ClientSocketPoolBaseTest,
3217 RequestSocketsWhenAlreadyHaveMultipleConnectJob) {
3218 CreatePool(4, 4);
3219 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3221 ClientSocketHandle handle1;
3222 TestCompletionCallback callback1;
3223 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3224 params_,
3225 DEFAULT_PRIORITY,
3226 callback1.callback(),
3227 pool_.get(),
3228 BoundNetLog()));
3230 ClientSocketHandle handle2;
3231 TestCompletionCallback callback2;
3232 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("a",
3233 params_,
3234 DEFAULT_PRIORITY,
3235 callback2.callback(),
3236 pool_.get(),
3237 BoundNetLog()));
3239 ClientSocketHandle handle3;
3240 TestCompletionCallback callback3;
3241 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("a",
3242 params_,
3243 DEFAULT_PRIORITY,
3244 callback3.callback(),
3245 pool_.get(),
3246 BoundNetLog()));
3248 ASSERT_TRUE(pool_->HasGroup("a"));
3249 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3250 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3251 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3253 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3255 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3256 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3257 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3259 EXPECT_EQ(OK, callback1.WaitForResult());
3260 EXPECT_EQ(OK, callback2.WaitForResult());
3261 EXPECT_EQ(OK, callback3.WaitForResult());
3262 handle1.Reset();
3263 handle2.Reset();
3264 handle3.Reset();
3266 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3267 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3268 EXPECT_EQ(3, pool_->IdleSocketCountInGroup("a"));
3271 TEST_F(ClientSocketPoolBaseTest, RequestSocketsAtMaxSocketLimit) {
3272 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
3273 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3275 ASSERT_FALSE(pool_->HasGroup("a"));
3277 pool_->RequestSockets("a", &params_, kDefaultMaxSockets,
3278 BoundNetLog());
3280 ASSERT_TRUE(pool_->HasGroup("a"));
3281 EXPECT_EQ(kDefaultMaxSockets, pool_->NumConnectJobsInGroup("a"));
3282 EXPECT_EQ(kDefaultMaxSockets, pool_->NumUnassignedConnectJobsInGroup("a"));
3284 ASSERT_FALSE(pool_->HasGroup("b"));
3286 pool_->RequestSockets("b", &params_, kDefaultMaxSockets,
3287 BoundNetLog());
3289 ASSERT_FALSE(pool_->HasGroup("b"));
3292 TEST_F(ClientSocketPoolBaseTest, RequestSocketsHitMaxSocketLimit) {
3293 CreatePool(kDefaultMaxSockets, kDefaultMaxSockets);
3294 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3296 ASSERT_FALSE(pool_->HasGroup("a"));
3298 pool_->RequestSockets("a", &params_, kDefaultMaxSockets - 1,
3299 BoundNetLog());
3301 ASSERT_TRUE(pool_->HasGroup("a"));
3302 EXPECT_EQ(kDefaultMaxSockets - 1, pool_->NumConnectJobsInGroup("a"));
3303 EXPECT_EQ(kDefaultMaxSockets - 1,
3304 pool_->NumUnassignedConnectJobsInGroup("a"));
3305 EXPECT_FALSE(pool_->IsStalled());
3307 ASSERT_FALSE(pool_->HasGroup("b"));
3309 pool_->RequestSockets("b", &params_, kDefaultMaxSockets,
3310 BoundNetLog());
3312 ASSERT_TRUE(pool_->HasGroup("b"));
3313 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("b"));
3314 EXPECT_FALSE(pool_->IsStalled());
3317 TEST_F(ClientSocketPoolBaseTest, RequestSocketsCountIdleSockets) {
3318 CreatePool(4, 4);
3319 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3321 ClientSocketHandle handle1;
3322 TestCompletionCallback callback1;
3323 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3324 params_,
3325 DEFAULT_PRIORITY,
3326 callback1.callback(),
3327 pool_.get(),
3328 BoundNetLog()));
3329 ASSERT_EQ(OK, callback1.WaitForResult());
3330 handle1.Reset();
3332 ASSERT_TRUE(pool_->HasGroup("a"));
3333 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3334 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3335 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3337 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3339 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3340 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3341 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3344 TEST_F(ClientSocketPoolBaseTest, RequestSocketsCountActiveSockets) {
3345 CreatePool(4, 4);
3346 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3348 ClientSocketHandle handle1;
3349 TestCompletionCallback callback1;
3350 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3351 params_,
3352 DEFAULT_PRIORITY,
3353 callback1.callback(),
3354 pool_.get(),
3355 BoundNetLog()));
3356 ASSERT_EQ(OK, callback1.WaitForResult());
3358 ASSERT_TRUE(pool_->HasGroup("a"));
3359 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3360 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3361 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3362 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
3364 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3366 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3367 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3368 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3369 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
3372 TEST_F(ClientSocketPoolBaseTest, RequestSocketsSynchronous) {
3373 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3374 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3376 pool_->RequestSockets("a", &params_, kDefaultMaxSocketsPerGroup,
3377 BoundNetLog());
3379 ASSERT_TRUE(pool_->HasGroup("a"));
3380 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3381 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3382 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->IdleSocketCountInGroup("a"));
3384 pool_->RequestSockets("b", &params_, kDefaultMaxSocketsPerGroup,
3385 BoundNetLog());
3387 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("b"));
3388 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3389 EXPECT_EQ(kDefaultMaxSocketsPerGroup, pool_->IdleSocketCountInGroup("b"));
3392 TEST_F(ClientSocketPoolBaseTest, RequestSocketsSynchronousError) {
3393 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3394 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
3396 pool_->RequestSockets("a", &params_, kDefaultMaxSocketsPerGroup,
3397 BoundNetLog());
3399 ASSERT_FALSE(pool_->HasGroup("a"));
3401 connect_job_factory_->set_job_type(
3402 TestConnectJob::kMockAdditionalErrorStateJob);
3403 pool_->RequestSockets("a", &params_, kDefaultMaxSocketsPerGroup,
3404 BoundNetLog());
3406 ASSERT_FALSE(pool_->HasGroup("a"));
3409 TEST_F(ClientSocketPoolBaseTest, RequestSocketsMultipleTimesDoesNothing) {
3410 CreatePool(4, 4);
3411 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3413 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3415 ASSERT_TRUE(pool_->HasGroup("a"));
3416 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3417 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3418 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3420 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3421 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3422 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3423 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3425 ClientSocketHandle handle1;
3426 TestCompletionCallback callback1;
3427 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3428 params_,
3429 DEFAULT_PRIORITY,
3430 callback1.callback(),
3431 pool_.get(),
3432 BoundNetLog()));
3433 ASSERT_EQ(OK, callback1.WaitForResult());
3435 ClientSocketHandle handle2;
3436 TestCompletionCallback callback2;
3437 int rv = handle2.Init("a",
3438 params_,
3439 DEFAULT_PRIORITY,
3440 callback2.callback(),
3441 pool_.get(),
3442 BoundNetLog());
3443 if (rv != OK) {
3444 EXPECT_EQ(ERR_IO_PENDING, rv);
3445 EXPECT_EQ(OK, callback2.WaitForResult());
3448 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3449 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3450 EXPECT_EQ(2, pool_->NumActiveSocketsInGroup("a"));
3451 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3453 handle1.Reset();
3454 handle2.Reset();
3456 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3457 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3458 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3460 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3461 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3462 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3463 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("a"));
3466 TEST_F(ClientSocketPoolBaseTest, RequestSocketsDifferentNumSockets) {
3467 CreatePool(4, 4);
3468 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3470 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3472 ASSERT_TRUE(pool_->HasGroup("a"));
3473 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3474 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3475 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3477 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3478 EXPECT_EQ(2, pool_->NumConnectJobsInGroup("a"));
3479 EXPECT_EQ(2, pool_->NumUnassignedConnectJobsInGroup("a"));
3480 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3482 pool_->RequestSockets("a", &params_, 3, BoundNetLog());
3483 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3484 EXPECT_EQ(3, pool_->NumUnassignedConnectJobsInGroup("a"));
3485 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3487 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3488 EXPECT_EQ(3, pool_->NumConnectJobsInGroup("a"));
3489 EXPECT_EQ(3, pool_->NumUnassignedConnectJobsInGroup("a"));
3490 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3493 TEST_F(ClientSocketPoolBaseTest, PreconnectJobsTakenByNormalRequests) {
3494 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3495 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3497 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3499 ASSERT_TRUE(pool_->HasGroup("a"));
3500 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3501 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3502 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3504 ClientSocketHandle handle1;
3505 TestCompletionCallback callback1;
3506 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3507 params_,
3508 DEFAULT_PRIORITY,
3509 callback1.callback(),
3510 pool_.get(),
3511 BoundNetLog()));
3513 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3514 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3515 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3517 ASSERT_EQ(OK, callback1.WaitForResult());
3519 // Make sure if a preconnected socket is not fully connected when a request
3520 // starts, it has a connect start time.
3521 TestLoadTimingInfoConnectedNotReused(handle1);
3522 handle1.Reset();
3524 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3527 // Checks that fully connected preconnect jobs have no connect times, and are
3528 // marked as reused.
3529 TEST_F(ClientSocketPoolBaseTest, ConnectedPreconnectJobsHaveNoConnectTimes) {
3530 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3531 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3532 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3534 ASSERT_TRUE(pool_->HasGroup("a"));
3535 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3536 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3537 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3539 ClientSocketHandle handle;
3540 TestCompletionCallback callback;
3541 EXPECT_EQ(OK, handle.Init("a",
3542 params_,
3543 DEFAULT_PRIORITY,
3544 callback.callback(),
3545 pool_.get(),
3546 BoundNetLog()));
3548 // Make sure the idle socket was used.
3549 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3551 TestLoadTimingInfoConnectedReused(handle);
3552 handle.Reset();
3553 TestLoadTimingInfoNotConnected(handle);
3556 // http://crbug.com/64940 regression test.
3557 TEST_F(ClientSocketPoolBaseTest, PreconnectClosesIdleSocketRemovesGroup) {
3558 const int kMaxTotalSockets = 3;
3559 const int kMaxSocketsPerGroup = 2;
3560 CreatePool(kMaxTotalSockets, kMaxSocketsPerGroup);
3561 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3563 // Note that group name ordering matters here. "a" comes before "b", so
3564 // CloseOneIdleSocket() will try to close "a"'s idle socket.
3566 // Set up one idle socket in "a".
3567 ClientSocketHandle handle1;
3568 TestCompletionCallback callback1;
3569 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("a",
3570 params_,
3571 DEFAULT_PRIORITY,
3572 callback1.callback(),
3573 pool_.get(),
3574 BoundNetLog()));
3576 ASSERT_EQ(OK, callback1.WaitForResult());
3577 handle1.Reset();
3578 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3580 // Set up two active sockets in "b".
3581 ClientSocketHandle handle2;
3582 TestCompletionCallback callback2;
3583 EXPECT_EQ(ERR_IO_PENDING, handle1.Init("b",
3584 params_,
3585 DEFAULT_PRIORITY,
3586 callback1.callback(),
3587 pool_.get(),
3588 BoundNetLog()));
3589 EXPECT_EQ(ERR_IO_PENDING, handle2.Init("b",
3590 params_,
3591 DEFAULT_PRIORITY,
3592 callback2.callback(),
3593 pool_.get(),
3594 BoundNetLog()));
3596 ASSERT_EQ(OK, callback1.WaitForResult());
3597 ASSERT_EQ(OK, callback2.WaitForResult());
3598 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("b"));
3599 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3600 EXPECT_EQ(2, pool_->NumActiveSocketsInGroup("b"));
3602 // Now we have 1 idle socket in "a" and 2 active sockets in "b". This means
3603 // we've maxed out on sockets, since we set |kMaxTotalSockets| to 3.
3604 // Requesting 2 preconnected sockets for "a" should fail to allocate any more
3605 // sockets for "a", and "b" should still have 2 active sockets.
3607 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3608 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3609 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3610 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3611 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("a"));
3612 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("b"));
3613 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3614 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("b"));
3615 EXPECT_EQ(2, pool_->NumActiveSocketsInGroup("b"));
3617 // Now release the 2 active sockets for "b". This will give us 1 idle socket
3618 // in "a" and 2 idle sockets in "b". Requesting 2 preconnected sockets for
3619 // "a" should result in closing 1 for "b".
3620 handle1.Reset();
3621 handle2.Reset();
3622 EXPECT_EQ(2, pool_->IdleSocketCountInGroup("b"));
3623 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("b"));
3625 pool_->RequestSockets("a", &params_, 2, BoundNetLog());
3626 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3627 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3628 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3629 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("a"));
3630 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("b"));
3631 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("b"));
3632 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("b"));
3633 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("b"));
3636 TEST_F(ClientSocketPoolBaseTest, PreconnectWithoutBackupJob) {
3637 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3638 pool_->EnableConnectBackupJobs();
3640 // Make the ConnectJob hang until it times out, shorten the timeout.
3641 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
3642 connect_job_factory_->set_timeout_duration(
3643 base::TimeDelta::FromMilliseconds(500));
3644 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3645 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3646 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3647 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3649 // Verify the backup timer doesn't create a backup job, by making
3650 // the backup job a pending job instead of a waiting job, so it
3651 // *would* complete if it were created.
3652 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3653 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
3654 FROM_HERE, base::MessageLoop::QuitClosure(),
3655 base::TimeDelta::FromSeconds(1));
3656 base::MessageLoop::current()->Run();
3657 EXPECT_FALSE(pool_->HasGroup("a"));
3660 TEST_F(ClientSocketPoolBaseTest, PreconnectWithBackupJob) {
3661 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3662 pool_->EnableConnectBackupJobs();
3664 // Make the ConnectJob hang forever.
3665 connect_job_factory_->set_job_type(TestConnectJob::kMockWaitingJob);
3666 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3667 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3668 EXPECT_EQ(1, pool_->NumUnassignedConnectJobsInGroup("a"));
3669 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3670 base::MessageLoop::current()->RunUntilIdle();
3672 // Make the backup job be a pending job, so it completes normally.
3673 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
3674 ClientSocketHandle handle;
3675 TestCompletionCallback callback;
3676 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
3677 params_,
3678 DEFAULT_PRIORITY,
3679 callback.callback(),
3680 pool_.get(),
3681 BoundNetLog()));
3682 // Timer has started, but the backup connect job shouldn't be created yet.
3683 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3684 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3685 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3686 EXPECT_EQ(0, pool_->NumActiveSocketsInGroup("a"));
3687 ASSERT_EQ(OK, callback.WaitForResult());
3689 // The hung connect job should still be there, but everything else should be
3690 // complete.
3691 EXPECT_EQ(1, pool_->NumConnectJobsInGroup("a"));
3692 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3693 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3694 EXPECT_EQ(1, pool_->NumActiveSocketsInGroup("a"));
3697 // Tests that a preconnect that starts out with unread data can still be used.
3698 // http://crbug.com/334467
3699 TEST_F(ClientSocketPoolBaseTest, PreconnectWithUnreadData) {
3700 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3701 connect_job_factory_->set_job_type(TestConnectJob::kMockUnreadDataJob);
3703 pool_->RequestSockets("a", &params_, 1, BoundNetLog());
3705 ASSERT_TRUE(pool_->HasGroup("a"));
3706 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3707 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3708 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3710 // Fail future jobs to be sure that handle receives the preconnected socket
3711 // rather than closing it and making a new one.
3712 connect_job_factory_->set_job_type(TestConnectJob::kMockFailingJob);
3713 ClientSocketHandle handle;
3714 TestCompletionCallback callback;
3715 EXPECT_EQ(OK, handle.Init("a",
3716 params_,
3717 DEFAULT_PRIORITY,
3718 callback.callback(),
3719 pool_.get(),
3720 BoundNetLog()));
3722 ASSERT_TRUE(pool_->HasGroup("a"));
3723 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
3724 EXPECT_EQ(0, pool_->NumUnassignedConnectJobsInGroup("a"));
3725 EXPECT_EQ(0, pool_->IdleSocketCountInGroup("a"));
3727 // Drain the pending read.
3728 EXPECT_EQ(1, handle.socket()->Read(NULL, 1, CompletionCallback()));
3730 TestLoadTimingInfoConnectedReused(handle);
3731 handle.Reset();
3733 // The socket should be usable now that it's idle again.
3734 EXPECT_EQ(1, pool_->IdleSocketCountInGroup("a"));
3737 class MockLayeredPool : public HigherLayeredPool {
3738 public:
3739 MockLayeredPool(TestClientSocketPool* pool,
3740 const std::string& group_name)
3741 : pool_(pool),
3742 group_name_(group_name),
3743 can_release_connection_(true) {
3744 pool_->AddHigherLayeredPool(this);
3747 ~MockLayeredPool() {
3748 pool_->RemoveHigherLayeredPool(this);
3751 int RequestSocket(TestClientSocketPool* pool) {
3752 scoped_refptr<TestSocketParams> params(
3753 new TestSocketParams(false /* ignore_limits */));
3754 return handle_.Init(group_name_, params, DEFAULT_PRIORITY,
3755 callback_.callback(), pool, BoundNetLog());
3758 int RequestSocketWithoutLimits(TestClientSocketPool* pool) {
3759 scoped_refptr<TestSocketParams> params(
3760 new TestSocketParams(true /* ignore_limits */));
3761 return handle_.Init(group_name_, params, MAXIMUM_PRIORITY,
3762 callback_.callback(), pool, BoundNetLog());
3765 bool ReleaseOneConnection() {
3766 if (!handle_.is_initialized() || !can_release_connection_) {
3767 return false;
3769 handle_.socket()->Disconnect();
3770 handle_.Reset();
3771 return true;
3774 void set_can_release_connection(bool can_release_connection) {
3775 can_release_connection_ = can_release_connection;
3778 MOCK_METHOD0(CloseOneIdleConnection, bool());
3780 private:
3781 TestClientSocketPool* const pool_;
3782 ClientSocketHandle handle_;
3783 TestCompletionCallback callback_;
3784 const std::string group_name_;
3785 bool can_release_connection_;
3788 TEST_F(ClientSocketPoolBaseTest, FailToCloseIdleSocketsNotHeldByLayeredPool) {
3789 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3790 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3792 MockLayeredPool mock_layered_pool(pool_.get(), "foo");
3793 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3794 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3795 .WillOnce(Return(false));
3796 EXPECT_FALSE(pool_->CloseOneIdleConnectionInHigherLayeredPool());
3799 TEST_F(ClientSocketPoolBaseTest, ForciblyCloseIdleSocketsHeldByLayeredPool) {
3800 CreatePool(kDefaultMaxSockets, kDefaultMaxSocketsPerGroup);
3801 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3803 MockLayeredPool mock_layered_pool(pool_.get(), "foo");
3804 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3805 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3806 .WillOnce(Invoke(&mock_layered_pool,
3807 &MockLayeredPool::ReleaseOneConnection));
3808 EXPECT_TRUE(pool_->CloseOneIdleConnectionInHigherLayeredPool());
3811 // Tests the basic case of closing an idle socket in a higher layered pool when
3812 // a new request is issued and the lower layer pool is stalled.
3813 TEST_F(ClientSocketPoolBaseTest, CloseIdleSocketsHeldByLayeredPoolWhenNeeded) {
3814 CreatePool(1, 1);
3815 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3817 MockLayeredPool mock_layered_pool(pool_.get(), "foo");
3818 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3819 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3820 .WillOnce(Invoke(&mock_layered_pool,
3821 &MockLayeredPool::ReleaseOneConnection));
3822 ClientSocketHandle handle;
3823 TestCompletionCallback callback;
3824 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
3825 params_,
3826 DEFAULT_PRIORITY,
3827 callback.callback(),
3828 pool_.get(),
3829 BoundNetLog()));
3830 EXPECT_EQ(OK, callback.WaitForResult());
3833 // Same as above, but the idle socket is in the same group as the stalled
3834 // socket, and closes the only other request in its group when closing requests
3835 // in higher layered pools. This generally shouldn't happen, but it may be
3836 // possible if a higher level pool issues a request and the request is
3837 // subsequently cancelled. Even if it's not possible, best not to crash.
3838 TEST_F(ClientSocketPoolBaseTest,
3839 CloseIdleSocketsHeldByLayeredPoolWhenNeededSameGroup) {
3840 CreatePool(2, 2);
3841 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
3843 // Need a socket in another group for the pool to be stalled (If a group
3844 // has the maximum number of connections already, it's not stalled).
3845 ClientSocketHandle handle1;
3846 TestCompletionCallback callback1;
3847 EXPECT_EQ(OK, handle1.Init("group1",
3848 params_,
3849 DEFAULT_PRIORITY,
3850 callback1.callback(),
3851 pool_.get(),
3852 BoundNetLog()));
3854 MockLayeredPool mock_layered_pool(pool_.get(), "group2");
3855 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3856 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3857 .WillOnce(Invoke(&mock_layered_pool,
3858 &MockLayeredPool::ReleaseOneConnection));
3859 ClientSocketHandle handle;
3860 TestCompletionCallback callback2;
3861 EXPECT_EQ(ERR_IO_PENDING, handle.Init("group2",
3862 params_,
3863 DEFAULT_PRIORITY,
3864 callback2.callback(),
3865 pool_.get(),
3866 BoundNetLog()));
3867 EXPECT_EQ(OK, callback2.WaitForResult());
3870 // Tests the case when an idle socket can be closed when a new request is
3871 // issued, and the new request belongs to a group that was previously stalled.
3872 TEST_F(ClientSocketPoolBaseTest,
3873 CloseIdleSocketsHeldByLayeredPoolInSameGroupWhenNeeded) {
3874 CreatePool(2, 2);
3875 std::list<TestConnectJob::JobType> job_types;
3876 job_types.push_back(TestConnectJob::kMockJob);
3877 job_types.push_back(TestConnectJob::kMockJob);
3878 job_types.push_back(TestConnectJob::kMockJob);
3879 job_types.push_back(TestConnectJob::kMockJob);
3880 connect_job_factory_->set_job_types(&job_types);
3882 ClientSocketHandle handle1;
3883 TestCompletionCallback callback1;
3884 EXPECT_EQ(OK, handle1.Init("group1",
3885 params_,
3886 DEFAULT_PRIORITY,
3887 callback1.callback(),
3888 pool_.get(),
3889 BoundNetLog()));
3891 MockLayeredPool mock_layered_pool(pool_.get(), "group2");
3892 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3893 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3894 .WillRepeatedly(Invoke(&mock_layered_pool,
3895 &MockLayeredPool::ReleaseOneConnection));
3896 mock_layered_pool.set_can_release_connection(false);
3898 // The third request is made when the socket pool is in a stalled state.
3899 ClientSocketHandle handle3;
3900 TestCompletionCallback callback3;
3901 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("group3",
3902 params_,
3903 DEFAULT_PRIORITY,
3904 callback3.callback(),
3905 pool_.get(),
3906 BoundNetLog()));
3908 base::RunLoop().RunUntilIdle();
3909 EXPECT_FALSE(callback3.have_result());
3911 // The fourth request is made when the pool is no longer stalled. The third
3912 // request should be serviced first, since it was issued first and has the
3913 // same priority.
3914 mock_layered_pool.set_can_release_connection(true);
3915 ClientSocketHandle handle4;
3916 TestCompletionCallback callback4;
3917 EXPECT_EQ(ERR_IO_PENDING, handle4.Init("group3",
3918 params_,
3919 DEFAULT_PRIORITY,
3920 callback4.callback(),
3921 pool_.get(),
3922 BoundNetLog()));
3923 EXPECT_EQ(OK, callback3.WaitForResult());
3924 EXPECT_FALSE(callback4.have_result());
3926 // Closing a handle should free up another socket slot.
3927 handle1.Reset();
3928 EXPECT_EQ(OK, callback4.WaitForResult());
3931 // Tests the case when an idle socket can be closed when a new request is
3932 // issued, and the new request belongs to a group that was previously stalled.
3934 // The two differences from the above test are that the stalled requests are not
3935 // in the same group as the layered pool's request, and the the fourth request
3936 // has a higher priority than the third one, so gets a socket first.
3937 TEST_F(ClientSocketPoolBaseTest,
3938 CloseIdleSocketsHeldByLayeredPoolInSameGroupWhenNeeded2) {
3939 CreatePool(2, 2);
3940 std::list<TestConnectJob::JobType> job_types;
3941 job_types.push_back(TestConnectJob::kMockJob);
3942 job_types.push_back(TestConnectJob::kMockJob);
3943 job_types.push_back(TestConnectJob::kMockJob);
3944 job_types.push_back(TestConnectJob::kMockJob);
3945 connect_job_factory_->set_job_types(&job_types);
3947 ClientSocketHandle handle1;
3948 TestCompletionCallback callback1;
3949 EXPECT_EQ(OK, handle1.Init("group1",
3950 params_,
3951 DEFAULT_PRIORITY,
3952 callback1.callback(),
3953 pool_.get(),
3954 BoundNetLog()));
3956 MockLayeredPool mock_layered_pool(pool_.get(), "group2");
3957 EXPECT_EQ(OK, mock_layered_pool.RequestSocket(pool_.get()));
3958 EXPECT_CALL(mock_layered_pool, CloseOneIdleConnection())
3959 .WillRepeatedly(Invoke(&mock_layered_pool,
3960 &MockLayeredPool::ReleaseOneConnection));
3961 mock_layered_pool.set_can_release_connection(false);
3963 // The third request is made when the socket pool is in a stalled state.
3964 ClientSocketHandle handle3;
3965 TestCompletionCallback callback3;
3966 EXPECT_EQ(ERR_IO_PENDING, handle3.Init("group3",
3967 params_,
3968 MEDIUM,
3969 callback3.callback(),
3970 pool_.get(),
3971 BoundNetLog()));
3973 base::RunLoop().RunUntilIdle();
3974 EXPECT_FALSE(callback3.have_result());
3976 // The fourth request is made when the pool is no longer stalled. This
3977 // request has a higher priority than the third request, so is serviced first.
3978 mock_layered_pool.set_can_release_connection(true);
3979 ClientSocketHandle handle4;
3980 TestCompletionCallback callback4;
3981 EXPECT_EQ(ERR_IO_PENDING, handle4.Init("group3",
3982 params_,
3983 HIGHEST,
3984 callback4.callback(),
3985 pool_.get(),
3986 BoundNetLog()));
3987 EXPECT_EQ(OK, callback4.WaitForResult());
3988 EXPECT_FALSE(callback3.have_result());
3990 // Closing a handle should free up another socket slot.
3991 handle1.Reset();
3992 EXPECT_EQ(OK, callback3.WaitForResult());
3995 TEST_F(ClientSocketPoolBaseTest,
3996 CloseMultipleIdleSocketsHeldByLayeredPoolWhenNeeded) {
3997 CreatePool(1, 1);
3998 connect_job_factory_->set_job_type(TestConnectJob::kMockJob);
4000 MockLayeredPool mock_layered_pool1(pool_.get(), "foo");
4001 EXPECT_EQ(OK, mock_layered_pool1.RequestSocket(pool_.get()));
4002 EXPECT_CALL(mock_layered_pool1, CloseOneIdleConnection())
4003 .WillRepeatedly(Invoke(&mock_layered_pool1,
4004 &MockLayeredPool::ReleaseOneConnection));
4005 MockLayeredPool mock_layered_pool2(pool_.get(), "bar");
4006 EXPECT_EQ(OK, mock_layered_pool2.RequestSocketWithoutLimits(pool_.get()));
4007 EXPECT_CALL(mock_layered_pool2, CloseOneIdleConnection())
4008 .WillRepeatedly(Invoke(&mock_layered_pool2,
4009 &MockLayeredPool::ReleaseOneConnection));
4010 ClientSocketHandle handle;
4011 TestCompletionCallback callback;
4012 EXPECT_EQ(ERR_IO_PENDING, handle.Init("a",
4013 params_,
4014 DEFAULT_PRIORITY,
4015 callback.callback(),
4016 pool_.get(),
4017 BoundNetLog()));
4018 EXPECT_EQ(OK, callback.WaitForResult());
4021 // Test that when a socket pool and group are at their limits, a request
4022 // with |ignore_limits| triggers creation of a new socket, and gets the socket
4023 // instead of a request with the same priority that was issued earlier, but
4024 // that does not have |ignore_limits| set.
4025 TEST_F(ClientSocketPoolBaseTest, IgnoreLimits) {
4026 scoped_refptr<TestSocketParams> params_ignore_limits(
4027 new TestSocketParams(true /* ignore_limits */));
4028 CreatePool(1, 1);
4030 // Issue a request to reach the socket pool limit.
4031 EXPECT_EQ(OK, StartRequestWithParams("a", MAXIMUM_PRIORITY, params_));
4032 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4034 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
4036 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4037 params_));
4038 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4040 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4041 params_ignore_limits));
4042 ASSERT_EQ(1, pool_->NumConnectJobsInGroup("a"));
4044 EXPECT_EQ(OK, request(2)->WaitForResult());
4045 EXPECT_FALSE(request(1)->have_result());
4048 // Test that when a socket pool and group are at their limits, a ConnectJob
4049 // issued for a request with |ignore_limits| set is not cancelled when a request
4050 // without |ignore_limits| issued to the same group is cancelled.
4051 TEST_F(ClientSocketPoolBaseTest, IgnoreLimitsCancelOtherJob) {
4052 scoped_refptr<TestSocketParams> params_ignore_limits(
4053 new TestSocketParams(true /* ignore_limits */));
4054 CreatePool(1, 1);
4056 // Issue a request to reach the socket pool limit.
4057 EXPECT_EQ(OK, StartRequestWithParams("a", MAXIMUM_PRIORITY, params_));
4058 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4060 connect_job_factory_->set_job_type(TestConnectJob::kMockPendingJob);
4062 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4063 params_));
4064 EXPECT_EQ(0, pool_->NumConnectJobsInGroup("a"));
4066 EXPECT_EQ(ERR_IO_PENDING, StartRequestWithParams("a", MAXIMUM_PRIORITY,
4067 params_ignore_limits));
4068 ASSERT_EQ(1, pool_->NumConnectJobsInGroup("a"));
4070 // Cancel the pending request without ignore_limits set. The ConnectJob
4071 // should not be cancelled.
4072 request(1)->handle()->Reset();
4073 ASSERT_EQ(1, pool_->NumConnectJobsInGroup("a"));
4075 EXPECT_EQ(OK, request(2)->WaitForResult());
4076 EXPECT_FALSE(request(1)->have_result());
4079 } // namespace
4081 } // namespace net