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/http/http_proxy_client_socket_pool.h"
7 #include "base/callback.h"
8 #include "base/compiler_specific.h"
9 #include "base/strings/string_util.h"
10 #include "base/strings/utf_string_conversions.h"
11 #include "base/time.h"
12 #include "net/base/auth.h"
13 #include "net/base/load_timing_info.h"
14 #include "net/base/load_timing_info_test_util.h"
15 #include "net/base/net_errors.h"
16 #include "net/base/test_completion_callback.h"
17 #include "net/cert/cert_verifier.h"
18 #include "net/dns/mock_host_resolver.h"
19 #include "net/http/http_auth_handler_factory.h"
20 #include "net/http/http_network_session.h"
21 #include "net/http/http_request_headers.h"
22 #include "net/http/http_response_headers.h"
23 #include "net/http/http_server_properties_impl.h"
24 #include "net/proxy/proxy_service.h"
25 #include "net/socket/client_socket_handle.h"
26 #include "net/socket/client_socket_pool_histograms.h"
27 #include "net/socket/socket_test_util.h"
28 #include "net/spdy/spdy_session.h"
29 #include "net/spdy/spdy_session_pool.h"
30 #include "net/spdy/spdy_test_util_spdy2.h"
31 #include "net/ssl/ssl_config_service_defaults.h"
32 #include "net/test/test_certificate_data.h"
33 #include "testing/gtest/include/gtest/gtest.h"
35 using namespace net::test_spdy2
;
41 const int kMaxSockets
= 32;
42 const int kMaxSocketsPerGroup
= 6;
44 // Make sure |handle|'s load times are set correctly. DNS and connect start
45 // times comes from mock client sockets in these tests, so primarily serves to
46 // check those times were copied, and ssl times / connect end are set correctly.
47 void TestLoadTimingInfo(const ClientSocketHandle
& handle
) {
48 LoadTimingInfo load_timing_info
;
49 EXPECT_TRUE(handle
.GetLoadTimingInfo(false, &load_timing_info
));
51 EXPECT_FALSE(load_timing_info
.socket_reused
);
52 // None of these tests use a NetLog.
53 EXPECT_EQ(NetLog::Source::kInvalidId
, load_timing_info
.socket_log_id
);
55 ExpectConnectTimingHasTimes(
56 load_timing_info
.connect_timing
,
57 CONNECT_TIMING_HAS_SSL_TIMES
| CONNECT_TIMING_HAS_DNS_TIMES
);
58 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info
);
61 // Just like TestLoadTimingInfo, except DNS times are expected to be null, for
62 // tests over proxies that do DNS lookups themselves.
63 void TestLoadTimingInfoNoDns(const ClientSocketHandle
& handle
) {
64 LoadTimingInfo load_timing_info
;
65 EXPECT_TRUE(handle
.GetLoadTimingInfo(false, &load_timing_info
));
67 // None of these tests use a NetLog.
68 EXPECT_EQ(NetLog::Source::kInvalidId
, load_timing_info
.socket_log_id
);
70 EXPECT_FALSE(load_timing_info
.socket_reused
);
72 ExpectConnectTimingHasTimes(load_timing_info
.connect_timing
,
73 CONNECT_TIMING_HAS_SSL_TIMES
);
74 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info
);
77 class SSLClientSocketPoolTest
: public testing::Test
{
79 SSLClientSocketPoolTest()
80 : proxy_service_(ProxyService::CreateDirect()),
81 ssl_config_service_(new SSLConfigServiceDefaults
),
82 http_auth_handler_factory_(
83 HttpAuthHandlerFactory::CreateDefault(&host_resolver_
)),
84 session_(CreateNetworkSession()),
85 direct_transport_socket_params_(
86 new TransportSocketParams(HostPortPair("host", 443),
90 OnHostResolutionCallback())),
91 transport_histograms_("MockTCP"),
92 transport_socket_pool_(kMaxSockets
,
94 &transport_histograms_
,
96 proxy_transport_socket_params_(
97 new TransportSocketParams(HostPortPair("proxy", 443),
101 OnHostResolutionCallback())),
102 socks_socket_params_(
103 new SOCKSSocketParams(proxy_transport_socket_params_
,
105 HostPortPair("sockshost", 443),
107 socks_histograms_("MockSOCKS"),
108 socks_socket_pool_(kMaxSockets
,
111 &transport_socket_pool_
),
112 http_proxy_socket_params_(
113 new HttpProxySocketParams(proxy_transport_socket_params_
,
117 HostPortPair("host", 80),
118 session_
->http_auth_cache(),
119 session_
->http_auth_handler_factory(),
120 session_
->spdy_session_pool(),
122 http_proxy_histograms_("MockHttpProxy"),
123 http_proxy_socket_pool_(kMaxSockets
,
125 &http_proxy_histograms_
,
127 &transport_socket_pool_
,
130 scoped_refptr
<SSLConfigService
> ssl_config_service(
131 new SSLConfigServiceDefaults
);
132 ssl_config_service
->GetSSLConfig(&ssl_config_
);
135 void CreatePool(bool transport_pool
, bool http_proxy_pool
, bool socks_pool
) {
136 ssl_histograms_
.reset(new ClientSocketPoolHistograms("SSLUnitTest"));
137 pool_
.reset(new SSLClientSocketPool(
140 ssl_histograms_
.get(),
141 NULL
/* host_resolver */,
142 NULL
/* cert_verifier */,
143 NULL
/* server_bound_cert_service */,
144 NULL
/* transport_security_state */,
145 std::string() /* ssl_session_cache_shard */,
147 transport_pool
? &transport_socket_pool_
: NULL
,
148 socks_pool
? &socks_socket_pool_
: NULL
,
149 http_proxy_pool
? &http_proxy_socket_pool_
: NULL
,
154 scoped_refptr
<SSLSocketParams
> SSLParams(ProxyServer::Scheme proxy
,
155 bool want_spdy_over_npn
) {
156 return make_scoped_refptr(new SSLSocketParams(
157 proxy
== ProxyServer::SCHEME_DIRECT
?
158 direct_transport_socket_params_
: NULL
,
159 proxy
== ProxyServer::SCHEME_SOCKS5
? socks_socket_params_
: NULL
,
160 proxy
== ProxyServer::SCHEME_HTTP
? http_proxy_socket_params_
: NULL
,
162 HostPortPair("host", 443),
166 want_spdy_over_npn
));
169 void AddAuthToCache() {
170 const base::string16
kFoo(ASCIIToUTF16("foo"));
171 const base::string16
kBar(ASCIIToUTF16("bar"));
172 session_
->http_auth_cache()->Add(GURL("http://proxy:443/"),
174 HttpAuth::AUTH_SCHEME_BASIC
,
175 "Basic realm=MyRealm1",
176 AuthCredentials(kFoo
, kBar
),
180 HttpNetworkSession
* CreateNetworkSession() {
181 HttpNetworkSession::Params params
;
182 params
.host_resolver
= &host_resolver_
;
183 params
.cert_verifier
= cert_verifier_
.get();
184 params
.transport_security_state
= transport_security_state_
.get();
185 params
.proxy_service
= proxy_service_
.get();
186 params
.client_socket_factory
= &socket_factory_
;
187 params
.ssl_config_service
= ssl_config_service_
.get();
188 params
.http_auth_handler_factory
= http_auth_handler_factory_
.get();
189 params
.http_server_properties
= &http_server_properties_
;
190 params
.enable_spdy_compression
= false;
191 return new HttpNetworkSession(params
);
194 void TestIPPoolingDisabled(SSLSocketDataProvider
* ssl
);
196 MockClientSocketFactory socket_factory_
;
197 MockCachingHostResolver host_resolver_
;
198 scoped_ptr
<CertVerifier
> cert_verifier_
;
199 scoped_ptr
<TransportSecurityState
> transport_security_state_
;
200 const scoped_ptr
<ProxyService
> proxy_service_
;
201 const scoped_refptr
<SSLConfigService
> ssl_config_service_
;
202 const scoped_ptr
<HttpAuthHandlerFactory
> http_auth_handler_factory_
;
203 HttpServerPropertiesImpl http_server_properties_
;
204 const scoped_refptr
<HttpNetworkSession
> session_
;
206 scoped_refptr
<TransportSocketParams
> direct_transport_socket_params_
;
207 ClientSocketPoolHistograms transport_histograms_
;
208 MockTransportClientSocketPool transport_socket_pool_
;
210 scoped_refptr
<TransportSocketParams
> proxy_transport_socket_params_
;
212 scoped_refptr
<SOCKSSocketParams
> socks_socket_params_
;
213 ClientSocketPoolHistograms socks_histograms_
;
214 MockSOCKSClientSocketPool socks_socket_pool_
;
216 scoped_refptr
<HttpProxySocketParams
> http_proxy_socket_params_
;
217 ClientSocketPoolHistograms http_proxy_histograms_
;
218 HttpProxyClientSocketPool http_proxy_socket_pool_
;
220 SSLConfig ssl_config_
;
221 scoped_ptr
<ClientSocketPoolHistograms
> ssl_histograms_
;
222 scoped_ptr
<SSLClientSocketPool
> pool_
;
225 TEST_F(SSLClientSocketPoolTest
, TCPFail
) {
226 StaticSocketDataProvider data
;
227 data
.set_connect_data(MockConnect(SYNCHRONOUS
, ERR_CONNECTION_FAILED
));
228 socket_factory_
.AddSocketDataProvider(&data
);
230 CreatePool(true /* tcp pool */, false, false);
231 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
234 ClientSocketHandle handle
;
235 int rv
= handle
.Init("a", params
, MEDIUM
, CompletionCallback(), pool_
.get(),
237 EXPECT_EQ(ERR_CONNECTION_FAILED
, rv
);
238 EXPECT_FALSE(handle
.is_initialized());
239 EXPECT_FALSE(handle
.socket());
240 EXPECT_FALSE(handle
.is_ssl_error());
243 TEST_F(SSLClientSocketPoolTest
, TCPFailAsync
) {
244 StaticSocketDataProvider data
;
245 data
.set_connect_data(MockConnect(ASYNC
, ERR_CONNECTION_FAILED
));
246 socket_factory_
.AddSocketDataProvider(&data
);
248 CreatePool(true /* tcp pool */, false, false);
249 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
252 ClientSocketHandle handle
;
253 TestCompletionCallback callback
;
254 int rv
= handle
.Init(
255 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
256 EXPECT_EQ(ERR_IO_PENDING
, rv
);
257 EXPECT_FALSE(handle
.is_initialized());
258 EXPECT_FALSE(handle
.socket());
260 EXPECT_EQ(ERR_CONNECTION_FAILED
, callback
.WaitForResult());
261 EXPECT_FALSE(handle
.is_initialized());
262 EXPECT_FALSE(handle
.socket());
263 EXPECT_FALSE(handle
.is_ssl_error());
266 TEST_F(SSLClientSocketPoolTest
, BasicDirect
) {
267 StaticSocketDataProvider data
;
268 data
.set_connect_data(MockConnect(SYNCHRONOUS
, OK
));
269 socket_factory_
.AddSocketDataProvider(&data
);
270 SSLSocketDataProvider
ssl(SYNCHRONOUS
, OK
);
271 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
273 CreatePool(true /* tcp pool */, false, false);
274 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
277 ClientSocketHandle handle
;
278 TestCompletionCallback callback
;
279 int rv
= handle
.Init(
280 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
282 EXPECT_TRUE(handle
.is_initialized());
283 EXPECT_TRUE(handle
.socket());
284 TestLoadTimingInfo(handle
);
287 TEST_F(SSLClientSocketPoolTest
, BasicDirectAsync
) {
288 StaticSocketDataProvider data
;
289 socket_factory_
.AddSocketDataProvider(&data
);
290 SSLSocketDataProvider
ssl(ASYNC
, OK
);
291 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
293 CreatePool(true /* tcp pool */, false, false);
294 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
297 ClientSocketHandle handle
;
298 TestCompletionCallback callback
;
299 int rv
= handle
.Init(
300 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
301 EXPECT_EQ(ERR_IO_PENDING
, rv
);
302 EXPECT_FALSE(handle
.is_initialized());
303 EXPECT_FALSE(handle
.socket());
305 EXPECT_EQ(OK
, callback
.WaitForResult());
306 EXPECT_TRUE(handle
.is_initialized());
307 EXPECT_TRUE(handle
.socket());
308 TestLoadTimingInfo(handle
);
311 TEST_F(SSLClientSocketPoolTest
, DirectCertError
) {
312 StaticSocketDataProvider data
;
313 socket_factory_
.AddSocketDataProvider(&data
);
314 SSLSocketDataProvider
ssl(ASYNC
, ERR_CERT_COMMON_NAME_INVALID
);
315 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
317 CreatePool(true /* tcp pool */, false, false);
318 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
321 ClientSocketHandle handle
;
322 TestCompletionCallback callback
;
323 int rv
= handle
.Init(
324 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
325 EXPECT_EQ(ERR_IO_PENDING
, rv
);
326 EXPECT_FALSE(handle
.is_initialized());
327 EXPECT_FALSE(handle
.socket());
329 EXPECT_EQ(ERR_CERT_COMMON_NAME_INVALID
, callback
.WaitForResult());
330 EXPECT_TRUE(handle
.is_initialized());
331 EXPECT_TRUE(handle
.socket());
332 TestLoadTimingInfo(handle
);
335 TEST_F(SSLClientSocketPoolTest
, DirectSSLError
) {
336 StaticSocketDataProvider data
;
337 socket_factory_
.AddSocketDataProvider(&data
);
338 SSLSocketDataProvider
ssl(ASYNC
, ERR_SSL_PROTOCOL_ERROR
);
339 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
341 CreatePool(true /* tcp pool */, false, false);
342 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
345 ClientSocketHandle handle
;
346 TestCompletionCallback callback
;
347 int rv
= handle
.Init(
348 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
349 EXPECT_EQ(ERR_IO_PENDING
, rv
);
350 EXPECT_FALSE(handle
.is_initialized());
351 EXPECT_FALSE(handle
.socket());
353 EXPECT_EQ(ERR_SSL_PROTOCOL_ERROR
, callback
.WaitForResult());
354 EXPECT_FALSE(handle
.is_initialized());
355 EXPECT_FALSE(handle
.socket());
356 EXPECT_TRUE(handle
.is_ssl_error());
359 TEST_F(SSLClientSocketPoolTest
, DirectWithNPN
) {
360 StaticSocketDataProvider data
;
361 socket_factory_
.AddSocketDataProvider(&data
);
362 SSLSocketDataProvider
ssl(ASYNC
, OK
);
363 ssl
.SetNextProto(kProtoHTTP11
);
364 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
366 CreatePool(true /* tcp pool */, false, false);
367 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
370 ClientSocketHandle handle
;
371 TestCompletionCallback callback
;
372 int rv
= handle
.Init(
373 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
374 EXPECT_EQ(ERR_IO_PENDING
, rv
);
375 EXPECT_FALSE(handle
.is_initialized());
376 EXPECT_FALSE(handle
.socket());
378 EXPECT_EQ(OK
, callback
.WaitForResult());
379 EXPECT_TRUE(handle
.is_initialized());
380 EXPECT_TRUE(handle
.socket());
381 TestLoadTimingInfo(handle
);
382 SSLClientSocket
* ssl_socket
= static_cast<SSLClientSocket
*>(handle
.socket());
383 EXPECT_TRUE(ssl_socket
->WasNpnNegotiated());
386 TEST_F(SSLClientSocketPoolTest
, DirectNoSPDY
) {
387 StaticSocketDataProvider data
;
388 socket_factory_
.AddSocketDataProvider(&data
);
389 SSLSocketDataProvider
ssl(ASYNC
, OK
);
390 ssl
.SetNextProto(kProtoHTTP11
);
391 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
393 CreatePool(true /* tcp pool */, false, false);
394 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
397 ClientSocketHandle handle
;
398 TestCompletionCallback callback
;
399 int rv
= handle
.Init(
400 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
401 EXPECT_EQ(ERR_IO_PENDING
, rv
);
402 EXPECT_FALSE(handle
.is_initialized());
403 EXPECT_FALSE(handle
.socket());
405 EXPECT_EQ(ERR_NPN_NEGOTIATION_FAILED
, callback
.WaitForResult());
406 EXPECT_FALSE(handle
.is_initialized());
407 EXPECT_FALSE(handle
.socket());
408 EXPECT_TRUE(handle
.is_ssl_error());
411 TEST_F(SSLClientSocketPoolTest
, DirectGotSPDY
) {
412 StaticSocketDataProvider data
;
413 socket_factory_
.AddSocketDataProvider(&data
);
414 SSLSocketDataProvider
ssl(ASYNC
, OK
);
415 ssl
.SetNextProto(kProtoSPDY2
);
416 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
418 CreatePool(true /* tcp pool */, false, false);
419 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
422 ClientSocketHandle handle
;
423 TestCompletionCallback callback
;
424 int rv
= handle
.Init(
425 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
426 EXPECT_EQ(ERR_IO_PENDING
, rv
);
427 EXPECT_FALSE(handle
.is_initialized());
428 EXPECT_FALSE(handle
.socket());
430 EXPECT_EQ(OK
, callback
.WaitForResult());
431 EXPECT_TRUE(handle
.is_initialized());
432 EXPECT_TRUE(handle
.socket());
433 TestLoadTimingInfo(handle
);
435 SSLClientSocket
* ssl_socket
= static_cast<SSLClientSocket
*>(handle
.socket());
436 EXPECT_TRUE(ssl_socket
->WasNpnNegotiated());
438 std::string server_protos
;
439 ssl_socket
->GetNextProto(&proto
, &server_protos
);
440 EXPECT_EQ(SSLClientSocket::NextProtoFromString(proto
),
444 TEST_F(SSLClientSocketPoolTest
, DirectGotBonusSPDY
) {
445 StaticSocketDataProvider data
;
446 socket_factory_
.AddSocketDataProvider(&data
);
447 SSLSocketDataProvider
ssl(ASYNC
, OK
);
448 ssl
.SetNextProto(kProtoSPDY2
);
449 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
451 CreatePool(true /* tcp pool */, false, false);
452 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
455 ClientSocketHandle handle
;
456 TestCompletionCallback callback
;
457 int rv
= handle
.Init(
458 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
459 EXPECT_EQ(ERR_IO_PENDING
, rv
);
460 EXPECT_FALSE(handle
.is_initialized());
461 EXPECT_FALSE(handle
.socket());
463 EXPECT_EQ(OK
, callback
.WaitForResult());
464 EXPECT_TRUE(handle
.is_initialized());
465 EXPECT_TRUE(handle
.socket());
466 TestLoadTimingInfo(handle
);
468 SSLClientSocket
* ssl_socket
= static_cast<SSLClientSocket
*>(handle
.socket());
469 EXPECT_TRUE(ssl_socket
->WasNpnNegotiated());
471 std::string server_protos
;
472 ssl_socket
->GetNextProto(&proto
, &server_protos
);
473 EXPECT_EQ(SSLClientSocket::NextProtoFromString(proto
),
477 TEST_F(SSLClientSocketPoolTest
, SOCKSFail
) {
478 StaticSocketDataProvider data
;
479 data
.set_connect_data(MockConnect(SYNCHRONOUS
, ERR_CONNECTION_FAILED
));
480 socket_factory_
.AddSocketDataProvider(&data
);
482 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
483 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_SOCKS5
,
486 ClientSocketHandle handle
;
487 TestCompletionCallback callback
;
488 int rv
= handle
.Init(
489 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
490 EXPECT_EQ(ERR_CONNECTION_FAILED
, rv
);
491 EXPECT_FALSE(handle
.is_initialized());
492 EXPECT_FALSE(handle
.socket());
493 EXPECT_FALSE(handle
.is_ssl_error());
496 TEST_F(SSLClientSocketPoolTest
, SOCKSFailAsync
) {
497 StaticSocketDataProvider data
;
498 data
.set_connect_data(MockConnect(ASYNC
, ERR_CONNECTION_FAILED
));
499 socket_factory_
.AddSocketDataProvider(&data
);
501 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
502 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_SOCKS5
,
505 ClientSocketHandle handle
;
506 TestCompletionCallback callback
;
507 int rv
= handle
.Init(
508 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
509 EXPECT_EQ(ERR_IO_PENDING
, rv
);
510 EXPECT_FALSE(handle
.is_initialized());
511 EXPECT_FALSE(handle
.socket());
513 EXPECT_EQ(ERR_CONNECTION_FAILED
, callback
.WaitForResult());
514 EXPECT_FALSE(handle
.is_initialized());
515 EXPECT_FALSE(handle
.socket());
516 EXPECT_FALSE(handle
.is_ssl_error());
519 TEST_F(SSLClientSocketPoolTest
, SOCKSBasic
) {
520 StaticSocketDataProvider data
;
521 data
.set_connect_data(MockConnect(SYNCHRONOUS
, OK
));
522 socket_factory_
.AddSocketDataProvider(&data
);
523 SSLSocketDataProvider
ssl(SYNCHRONOUS
, OK
);
524 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
526 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
527 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_SOCKS5
,
530 ClientSocketHandle handle
;
531 TestCompletionCallback callback
;
532 int rv
= handle
.Init(
533 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
535 EXPECT_TRUE(handle
.is_initialized());
536 EXPECT_TRUE(handle
.socket());
537 // SOCKS5 generally has no DNS times, but the mock SOCKS5 sockets used here
538 // don't go through the real logic, unlike in the HTTP proxy tests.
539 TestLoadTimingInfo(handle
);
542 TEST_F(SSLClientSocketPoolTest
, SOCKSBasicAsync
) {
543 StaticSocketDataProvider data
;
544 socket_factory_
.AddSocketDataProvider(&data
);
545 SSLSocketDataProvider
ssl(ASYNC
, OK
);
546 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
548 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
549 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_SOCKS5
,
552 ClientSocketHandle handle
;
553 TestCompletionCallback callback
;
554 int rv
= handle
.Init(
555 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
556 EXPECT_EQ(ERR_IO_PENDING
, rv
);
557 EXPECT_FALSE(handle
.is_initialized());
558 EXPECT_FALSE(handle
.socket());
560 EXPECT_EQ(OK
, callback
.WaitForResult());
561 EXPECT_TRUE(handle
.is_initialized());
562 EXPECT_TRUE(handle
.socket());
563 // SOCKS5 generally has no DNS times, but the mock SOCKS5 sockets used here
564 // don't go through the real logic, unlike in the HTTP proxy tests.
565 TestLoadTimingInfo(handle
);
568 TEST_F(SSLClientSocketPoolTest
, HttpProxyFail
) {
569 StaticSocketDataProvider data
;
570 data
.set_connect_data(MockConnect(SYNCHRONOUS
, ERR_CONNECTION_FAILED
));
571 socket_factory_
.AddSocketDataProvider(&data
);
573 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
574 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_HTTP
,
577 ClientSocketHandle handle
;
578 TestCompletionCallback callback
;
579 int rv
= handle
.Init(
580 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
581 EXPECT_EQ(ERR_PROXY_CONNECTION_FAILED
, rv
);
582 EXPECT_FALSE(handle
.is_initialized());
583 EXPECT_FALSE(handle
.socket());
584 EXPECT_FALSE(handle
.is_ssl_error());
587 TEST_F(SSLClientSocketPoolTest
, HttpProxyFailAsync
) {
588 StaticSocketDataProvider data
;
589 data
.set_connect_data(MockConnect(ASYNC
, ERR_CONNECTION_FAILED
));
590 socket_factory_
.AddSocketDataProvider(&data
);
592 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
593 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_HTTP
,
596 ClientSocketHandle handle
;
597 TestCompletionCallback callback
;
598 int rv
= handle
.Init(
599 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
600 EXPECT_EQ(ERR_IO_PENDING
, rv
);
601 EXPECT_FALSE(handle
.is_initialized());
602 EXPECT_FALSE(handle
.socket());
604 EXPECT_EQ(ERR_PROXY_CONNECTION_FAILED
, callback
.WaitForResult());
605 EXPECT_FALSE(handle
.is_initialized());
606 EXPECT_FALSE(handle
.socket());
607 EXPECT_FALSE(handle
.is_ssl_error());
610 TEST_F(SSLClientSocketPoolTest
, HttpProxyBasic
) {
611 MockWrite writes
[] = {
612 MockWrite(SYNCHRONOUS
,
613 "CONNECT host:80 HTTP/1.1\r\n"
615 "Proxy-Connection: keep-alive\r\n"
616 "Proxy-Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
619 MockRead(SYNCHRONOUS
, "HTTP/1.1 200 Connection Established\r\n\r\n"),
621 StaticSocketDataProvider
data(reads
, arraysize(reads
), writes
,
623 data
.set_connect_data(MockConnect(SYNCHRONOUS
, OK
));
624 socket_factory_
.AddSocketDataProvider(&data
);
626 SSLSocketDataProvider
ssl(SYNCHRONOUS
, OK
);
627 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
629 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
630 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_HTTP
,
633 ClientSocketHandle handle
;
634 TestCompletionCallback callback
;
635 int rv
= handle
.Init(
636 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
638 EXPECT_TRUE(handle
.is_initialized());
639 EXPECT_TRUE(handle
.socket());
640 TestLoadTimingInfoNoDns(handle
);
643 TEST_F(SSLClientSocketPoolTest
, HttpProxyBasicAsync
) {
644 MockWrite writes
[] = {
645 MockWrite("CONNECT host:80 HTTP/1.1\r\n"
647 "Proxy-Connection: keep-alive\r\n"
648 "Proxy-Authorization: Basic Zm9vOmJhcg==\r\n\r\n"),
651 MockRead("HTTP/1.1 200 Connection Established\r\n\r\n"),
653 StaticSocketDataProvider
data(reads
, arraysize(reads
), writes
,
655 socket_factory_
.AddSocketDataProvider(&data
);
657 SSLSocketDataProvider
ssl(ASYNC
, OK
);
658 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
660 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
661 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_HTTP
,
664 ClientSocketHandle handle
;
665 TestCompletionCallback callback
;
666 int rv
= handle
.Init(
667 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
668 EXPECT_EQ(ERR_IO_PENDING
, rv
);
669 EXPECT_FALSE(handle
.is_initialized());
670 EXPECT_FALSE(handle
.socket());
672 EXPECT_EQ(OK
, callback
.WaitForResult());
673 EXPECT_TRUE(handle
.is_initialized());
674 EXPECT_TRUE(handle
.socket());
675 TestLoadTimingInfoNoDns(handle
);
678 TEST_F(SSLClientSocketPoolTest
, NeedProxyAuth
) {
679 MockWrite writes
[] = {
680 MockWrite("CONNECT host:80 HTTP/1.1\r\n"
682 "Proxy-Connection: keep-alive\r\n\r\n"),
685 MockRead("HTTP/1.1 407 Proxy Authentication Required\r\n"),
686 MockRead("Proxy-Authenticate: Basic realm=\"MyRealm1\"\r\n"),
687 MockRead("Content-Length: 10\r\n\r\n"),
688 MockRead("0123456789"),
690 StaticSocketDataProvider
data(reads
, arraysize(reads
), writes
,
692 socket_factory_
.AddSocketDataProvider(&data
);
693 SSLSocketDataProvider
ssl(ASYNC
, OK
);
694 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
696 CreatePool(false, true /* http proxy pool */, true /* socks pool */);
697 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_HTTP
,
700 ClientSocketHandle handle
;
701 TestCompletionCallback callback
;
702 int rv
= handle
.Init(
703 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
704 EXPECT_EQ(ERR_IO_PENDING
, rv
);
705 EXPECT_FALSE(handle
.is_initialized());
706 EXPECT_FALSE(handle
.socket());
708 EXPECT_EQ(ERR_PROXY_AUTH_REQUESTED
, callback
.WaitForResult());
709 EXPECT_FALSE(handle
.is_initialized());
710 EXPECT_FALSE(handle
.socket());
711 EXPECT_FALSE(handle
.is_ssl_error());
712 const HttpResponseInfo
& tunnel_info
= handle
.ssl_error_response_info();
713 EXPECT_EQ(tunnel_info
.headers
->response_code(), 407);
714 scoped_ptr
<ClientSocketHandle
> tunnel_handle(
715 handle
.release_pending_http_proxy_connection());
716 EXPECT_TRUE(tunnel_handle
->socket());
717 EXPECT_FALSE(tunnel_handle
->socket()->IsConnected());
720 TEST_F(SSLClientSocketPoolTest
, IPPooling
) {
721 const int kTestPort
= 80;
726 AddressList addresses
;
728 { "www.webkit.org", "192.0.2.33,192.168.0.1,192.168.0.5" },
729 { "code.google.com", "192.168.0.2,192.168.0.3,192.168.0.5" },
730 { "js.webkit.org", "192.168.0.4,192.168.0.1,192.0.2.33" },
733 host_resolver_
.set_synchronous_mode(true);
734 for (size_t i
= 0; i
< ARRAYSIZE_UNSAFE(test_hosts
); i
++) {
735 host_resolver_
.rules()->AddIPLiteralRule(
736 test_hosts
[i
].name
, test_hosts
[i
].iplist
, std::string());
738 // This test requires that the HostResolver cache be populated. Normal
739 // code would have done this already, but we do it manually.
740 HostResolver::RequestInfo
info(HostPortPair(test_hosts
[i
].name
, kTestPort
));
741 host_resolver_
.Resolve(info
, &test_hosts
[i
].addresses
, CompletionCallback(),
742 NULL
, BoundNetLog());
744 // Setup a SpdySessionKey
745 test_hosts
[i
].key
= SpdySessionKey(
746 HostPortPair(test_hosts
[i
].name
, kTestPort
), ProxyServer::Direct(),
747 kPrivacyModeDisabled
);
751 MockRead(ASYNC
, ERR_IO_PENDING
),
753 StaticSocketDataProvider
data(reads
, arraysize(reads
), NULL
, 0);
754 socket_factory_
.AddSocketDataProvider(&data
);
755 SSLSocketDataProvider
ssl(ASYNC
, OK
);
756 ssl
.cert
= X509Certificate::CreateFromBytes(
757 reinterpret_cast<const char*>(webkit_der
), sizeof(webkit_der
));
758 ssl
.SetNextProto(kProtoSPDY2
);
759 socket_factory_
.AddSSLSocketDataProvider(&ssl
);
761 CreatePool(true /* tcp pool */, false, false);
762 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
765 scoped_ptr
<ClientSocketHandle
> handle(new ClientSocketHandle());
766 TestCompletionCallback callback
;
767 int rv
= handle
->Init(
768 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
769 EXPECT_EQ(ERR_IO_PENDING
, rv
);
770 EXPECT_FALSE(handle
->is_initialized());
771 EXPECT_FALSE(handle
->socket());
773 EXPECT_EQ(OK
, callback
.WaitForResult());
774 EXPECT_TRUE(handle
->is_initialized());
775 EXPECT_TRUE(handle
->socket());
777 SSLClientSocket
* ssl_socket
= static_cast<SSLClientSocket
*>(handle
->socket());
778 EXPECT_TRUE(ssl_socket
->WasNpnNegotiated());
780 std::string server_protos
;
781 ssl_socket
->GetNextProto(&proto
, &server_protos
);
782 EXPECT_EQ(SSLClientSocket::NextProtoFromString(proto
),
785 // TODO(rtenneti): MockClientSocket::GetPeerAddress returns 0 as the port
786 // number. Fix it to return port 80 and then use GetPeerAddress to AddAlias.
787 SpdySessionPoolPeer
pool_peer(session_
->spdy_session_pool());
788 pool_peer
.AddAlias(test_hosts
[0].addresses
.front(), test_hosts
[0].key
);
790 scoped_refptr
<SpdySession
> spdy_session
;
791 rv
= session_
->spdy_session_pool()->GetSpdySessionFromSocket(
792 test_hosts
[0].key
, handle
.release(), BoundNetLog(), 0,
793 &spdy_session
, true);
796 EXPECT_TRUE(session_
->spdy_session_pool()->HasSession(test_hosts
[0].key
));
797 EXPECT_FALSE(session_
->spdy_session_pool()->HasSession(test_hosts
[1].key
));
798 EXPECT_TRUE(session_
->spdy_session_pool()->HasSession(test_hosts
[2].key
));
800 session_
->spdy_session_pool()->CloseAllSessions();
803 void SSLClientSocketPoolTest::TestIPPoolingDisabled(
804 SSLSocketDataProvider
* ssl
) {
805 const int kTestPort
= 80;
810 AddressList addresses
;
812 { "www.webkit.org", "192.0.2.33,192.168.0.1,192.168.0.5" },
813 { "js.webkit.com", "192.168.0.4,192.168.0.1,192.0.2.33" },
816 TestCompletionCallback callback
;
818 for (size_t i
= 0; i
< ARRAYSIZE_UNSAFE(test_hosts
); i
++) {
819 host_resolver_
.rules()->AddIPLiteralRule(
820 test_hosts
[i
].name
, test_hosts
[i
].iplist
, std::string());
822 // This test requires that the HostResolver cache be populated. Normal
823 // code would have done this already, but we do it manually.
824 HostResolver::RequestInfo
info(HostPortPair(test_hosts
[i
].name
, kTestPort
));
825 rv
= host_resolver_
.Resolve(info
, &test_hosts
[i
].addresses
,
826 callback
.callback(), NULL
, BoundNetLog());
827 EXPECT_EQ(OK
, callback
.GetResult(rv
));
829 // Setup a SpdySessionKey
830 test_hosts
[i
].key
= SpdySessionKey(
831 HostPortPair(test_hosts
[i
].name
, kTestPort
), ProxyServer::Direct(),
832 kPrivacyModeDisabled
);
836 MockRead(ASYNC
, ERR_IO_PENDING
),
838 StaticSocketDataProvider
data(reads
, arraysize(reads
), NULL
, 0);
839 socket_factory_
.AddSocketDataProvider(&data
);
840 socket_factory_
.AddSSLSocketDataProvider(ssl
);
842 CreatePool(true /* tcp pool */, false, false);
843 scoped_refptr
<SSLSocketParams
> params
= SSLParams(ProxyServer::SCHEME_DIRECT
,
846 scoped_ptr
<ClientSocketHandle
> handle(new ClientSocketHandle());
848 "a", params
, MEDIUM
, callback
.callback(), pool_
.get(), BoundNetLog());
849 EXPECT_EQ(ERR_IO_PENDING
, rv
);
850 EXPECT_FALSE(handle
->is_initialized());
851 EXPECT_FALSE(handle
->socket());
853 EXPECT_EQ(OK
, callback
.WaitForResult());
854 EXPECT_TRUE(handle
->is_initialized());
855 EXPECT_TRUE(handle
->socket());
857 SSLClientSocket
* ssl_socket
= static_cast<SSLClientSocket
*>(handle
->socket());
858 EXPECT_TRUE(ssl_socket
->WasNpnNegotiated());
860 std::string server_protos
;
861 ssl_socket
->GetNextProto(&proto
, &server_protos
);
862 EXPECT_EQ(SSLClientSocket::NextProtoFromString(proto
),
865 // TODO(rtenneti): MockClientSocket::GetPeerAddress returns 0 as the port
866 // number. Fix it to return port 80 and then use GetPeerAddress to AddAlias.
867 SpdySessionPoolPeer
pool_peer(session_
->spdy_session_pool());
868 pool_peer
.AddAlias(test_hosts
[0].addresses
.front(), test_hosts
[0].key
);
870 scoped_refptr
<SpdySession
> spdy_session
;
871 rv
= session_
->spdy_session_pool()->GetSpdySessionFromSocket(
872 test_hosts
[0].key
, handle
.release(), BoundNetLog(), 0,
873 &spdy_session
, true);
876 EXPECT_TRUE(session_
->spdy_session_pool()->HasSession(test_hosts
[0].key
));
877 EXPECT_FALSE(session_
->spdy_session_pool()->HasSession(test_hosts
[1].key
));
879 session_
->spdy_session_pool()->CloseAllSessions();
882 // Verifies that an SSL connection with client authentication disables SPDY IP
884 TEST_F(SSLClientSocketPoolTest
, IPPoolingClientCert
) {
885 SSLSocketDataProvider
ssl(ASYNC
, OK
);
886 ssl
.cert
= X509Certificate::CreateFromBytes(
887 reinterpret_cast<const char*>(webkit_der
), sizeof(webkit_der
));
888 ssl
.client_cert_sent
= true;
889 ssl
.SetNextProto(kProtoSPDY2
);
890 TestIPPoolingDisabled(&ssl
);
893 // Verifies that an SSL connection with channel ID disables SPDY IP pooling.
894 TEST_F(SSLClientSocketPoolTest
, IPPoolingChannelID
) {
895 SSLSocketDataProvider
ssl(ASYNC
, OK
);
896 ssl
.channel_id_sent
= true;
897 ssl
.SetNextProto(kProtoSPDY2
);
898 TestIPPoolingDisabled(&ssl
);
901 // It would be nice to also test the timeouts in SSLClientSocketPool.