OLD | NEW |
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "net/http/http_network_transaction.h" | 5 #include "net/http/http_network_transaction.h" |
6 | 6 |
7 #include <math.h> // ceil | 7 #include <math.h> // ceil |
8 #include <vector> | 8 #include <vector> |
9 | 9 |
10 #include "base/basictypes.h" | 10 #include "base/basictypes.h" |
11 #include "base/compiler_specific.h" | 11 #include "base/compiler_specific.h" |
12 #include "base/file_path.h" | 12 #include "base/file_path.h" |
13 #include "base/file_util.h" | 13 #include "base/file_util.h" |
14 #include "base/scoped_ptr.h" | 14 #include "base/scoped_ptr.h" |
15 #include "base/utf_string_conversions.h" | 15 #include "base/utf_string_conversions.h" |
16 #include "net/base/auth.h" | 16 #include "net/base/auth.h" |
17 #include "net/base/capturing_net_log.h" | 17 #include "net/base/capturing_net_log.h" |
18 #include "net/base/completion_callback.h" | 18 #include "net/base/completion_callback.h" |
19 #include "net/base/mock_host_resolver.h" | 19 #include "net/base/mock_host_resolver.h" |
20 #include "net/base/net_log.h" | 20 #include "net/base/net_log.h" |
21 #include "net/base/net_log_unittest.h" | 21 #include "net/base/net_log_unittest.h" |
22 #include "net/base/request_priority.h" | 22 #include "net/base/request_priority.h" |
| 23 #include "net/base/ssl_cert_request_info.h" |
23 #include "net/base/ssl_config_service_defaults.h" | 24 #include "net/base/ssl_config_service_defaults.h" |
24 #include "net/base/ssl_info.h" | 25 #include "net/base/ssl_info.h" |
25 #include "net/base/test_completion_callback.h" | 26 #include "net/base/test_completion_callback.h" |
26 #include "net/base/upload_data.h" | 27 #include "net/base/upload_data.h" |
27 #include "net/http/http_auth_handler_digest.h" | 28 #include "net/http/http_auth_handler_digest.h" |
28 #include "net/http/http_auth_handler_mock.h" | 29 #include "net/http/http_auth_handler_mock.h" |
29 #include "net/http/http_auth_handler_ntlm.h" | 30 #include "net/http/http_auth_handler_ntlm.h" |
30 #include "net/http/http_basic_stream.h" | 31 #include "net/http/http_basic_stream.h" |
31 #include "net/http/http_net_log_params.h" | 32 #include "net/http/http_net_log_params.h" |
32 #include "net/http/http_network_session.h" | 33 #include "net/http/http_network_session.h" |
(...skipping 8167 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
8200 if (rv == net::ERR_IO_PENDING) | 8201 if (rv == net::ERR_IO_PENDING) |
8201 rv = callback.WaitForResult(); | 8202 rv = callback.WaitForResult(); |
8202 ASSERT_EQ(OK, rv); | 8203 ASSERT_EQ(OK, rv); |
8203 | 8204 |
8204 std::string contents; | 8205 std::string contents; |
8205 rv = ReadTransaction(trans.get(), &contents); | 8206 rv = ReadTransaction(trans.get(), &contents); |
8206 EXPECT_EQ(net::OK, rv); | 8207 EXPECT_EQ(net::OK, rv); |
8207 EXPECT_EQ("hello world", contents); | 8208 EXPECT_EQ("hello world", contents); |
8208 } | 8209 } |
8209 | 8210 |
| 8211 // Ensure that a client certificate is removed from the SSL client auth |
| 8212 // cache when: |
| 8213 // 1) No proxy is involved. |
| 8214 // 2) TLS False Start is disabled. |
| 8215 // 3) The initial TLS handshake requests a client certificate. |
| 8216 // 4) The client supplies an invalid/unacceptable certificate. |
| 8217 TEST_F(HttpNetworkTransactionTest, ClientAuthCertCache_Direct_NoFalseStart) { |
| 8218 SessionDependencies session_deps; |
| 8219 |
| 8220 scoped_refptr<SSLCertRequestInfo> cert_request(new SSLCertRequestInfo()); |
| 8221 cert_request->host_and_port = "www.example.com:443"; |
| 8222 |
| 8223 // [ssl_]data1 contains the data for the first SSL handshake. When a |
| 8224 // CertificateRequest is received for the first time, the handshake will |
| 8225 // be aborted to allow the caller to provide a certificate. |
| 8226 SSLSocketDataProvider ssl_data1(true /* async */, |
| 8227 net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED); |
| 8228 ssl_data1.cert_request_info = cert_request.get(); |
| 8229 session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_data1); |
| 8230 net::StaticSocketDataProvider data1(NULL, 0, NULL, 0); |
| 8231 session_deps.socket_factory.AddSocketDataProvider(&data1); |
| 8232 |
| 8233 // [ssl_]data2 contains the data for the second SSL handshake. When TLS |
| 8234 // False Start is not being used, the result of the SSL handshake will be |
| 8235 // returned as part of the SSLClientSocket::Connect() call. This test |
| 8236 // matches the result of a server sending a handshake_failure alert, |
| 8237 // rather than a Finished message, because it requires a client |
| 8238 // certificate and none was supplied. |
| 8239 SSLSocketDataProvider ssl_data2(true /* async */, |
| 8240 net::ERR_SSL_PROTOCOL_ERROR); |
| 8241 ssl_data2.cert_request_info = cert_request.get(); |
| 8242 session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_data2); |
| 8243 net::StaticSocketDataProvider data2(NULL, 0, NULL, 0); |
| 8244 session_deps.socket_factory.AddSocketDataProvider(&data2); |
| 8245 |
| 8246 // [ssl_]data3 contains the data for the third SSL handshake. When a |
| 8247 // connection to a server fails during an SSL handshake, |
| 8248 // HttpNetworkTransaction will attempt to fallback to SSLv3 if the initial |
| 8249 // connection was attempted with TLSv1. This is transparent to the caller |
| 8250 // of the HttpNetworkTransaction. Because this test failure is due to |
| 8251 // requiring a client certificate, this fallback handshake should also |
| 8252 // fail. |
| 8253 SSLSocketDataProvider ssl_data3(true /* async */, |
| 8254 net::ERR_SSL_PROTOCOL_ERROR); |
| 8255 ssl_data3.cert_request_info = cert_request.get(); |
| 8256 session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_data3); |
| 8257 net::StaticSocketDataProvider data3(NULL, 0, NULL, 0); |
| 8258 session_deps.socket_factory.AddSocketDataProvider(&data3); |
| 8259 |
| 8260 scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
| 8261 scoped_ptr<HttpNetworkTransaction> trans(new HttpNetworkTransaction(session)); |
| 8262 |
| 8263 net::HttpRequestInfo request_info; |
| 8264 request_info.url = GURL("https://www.example.com/"); |
| 8265 request_info.method = "GET"; |
| 8266 request_info.load_flags = net::LOAD_NORMAL; |
| 8267 |
| 8268 // Begin the SSL handshake with the peer. This consumes ssl_data1. |
| 8269 TestCompletionCallback callback; |
| 8270 int rv = trans->Start(&request_info, &callback, net::BoundNetLog()); |
| 8271 ASSERT_EQ(net::ERR_IO_PENDING, rv); |
| 8272 |
| 8273 // Complete the SSL handshake, which should abort due to requiring a |
| 8274 // client certificate. |
| 8275 rv = callback.WaitForResult(); |
| 8276 ASSERT_EQ(net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED, rv); |
| 8277 |
| 8278 // Indicate that no certificate should be supplied. From the perspective |
| 8279 // of SSLClientCertCache, NULL is just as meaningful as a real |
| 8280 // certificate, so this is the same as supply a |
| 8281 // legitimate-but-unacceptable certificate. |
| 8282 rv = trans->RestartWithCertificate(NULL, &callback); |
| 8283 ASSERT_EQ(net::ERR_IO_PENDING, rv); |
| 8284 |
| 8285 // Ensure the certificate was added to the client auth cache before |
| 8286 // allowing the connection to continue restarting. |
| 8287 scoped_refptr<X509Certificate> client_cert; |
| 8288 ASSERT_TRUE(session->ssl_client_auth_cache()->Lookup("www.example.com:443", |
| 8289 &client_cert)); |
| 8290 ASSERT_EQ(NULL, client_cert.get()); |
| 8291 |
| 8292 // Restart the handshake. This will consume ssl_data2, which fails, and |
| 8293 // then consume ssl_data3, which should also fail. The result code is |
| 8294 // checked against what ssl_data3 should return. |
| 8295 rv = callback.WaitForResult(); |
| 8296 ASSERT_EQ(net::ERR_SSL_PROTOCOL_ERROR, rv); |
| 8297 |
| 8298 // Ensure that the client certificate is removed from the cache on a |
| 8299 // handshake failure. |
| 8300 ASSERT_FALSE(session->ssl_client_auth_cache()->Lookup("www.example.com:443", |
| 8301 &client_cert)); |
| 8302 } |
| 8303 |
| 8304 // Ensure that a client certificate is removed from the SSL client auth |
| 8305 // cache when: |
| 8306 // 1) No proxy is involved. |
| 8307 // 2) TLS False Start is enabled. |
| 8308 // 3) The initial TLS handshake requests a client certificate. |
| 8309 // 4) The client supplies an invalid/unacceptable certificate. |
| 8310 TEST_F(HttpNetworkTransactionTest, ClientAuthCertCache_Direct_FalseStart) { |
| 8311 SessionDependencies session_deps; |
| 8312 |
| 8313 scoped_refptr<SSLCertRequestInfo> cert_request(new SSLCertRequestInfo()); |
| 8314 cert_request->host_and_port = "www.example.com:443"; |
| 8315 |
| 8316 // When TLS False Start is used, SSLClientSocket::Connect() calls will |
| 8317 // return successfully after reading up to the peer's Certificate message. |
| 8318 // This is to allow the caller to call SSLClientSocket::Write(), which can |
| 8319 // enqueue application data to be sent in the same packet as the |
| 8320 // ChangeCipherSpec and Finished messages. |
| 8321 // The actual handshake will be finished when SSLClientSocket::Read() is |
| 8322 // called, which expects to process the peer's ChangeCipherSpec and |
| 8323 // Finished messages. If there was an error negotiating with the peer, |
| 8324 // such as due to the peer requiring a client certificate when none was |
| 8325 // supplied, the alert sent by the peer won't be processed until Read() is |
| 8326 // called. |
| 8327 |
| 8328 // Like the non-False Start case, when a client certificate is requested by |
| 8329 // the peer, the handshake is aborted during the Connect() call. |
| 8330 // [ssl_]data1 represents the initial SSL handshake with the peer. |
| 8331 SSLSocketDataProvider ssl_data1(true /* async */, |
| 8332 net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED); |
| 8333 ssl_data1.cert_request_info = cert_request.get(); |
| 8334 session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_data1); |
| 8335 net::StaticSocketDataProvider data1(NULL, 0, NULL, 0); |
| 8336 session_deps.socket_factory.AddSocketDataProvider(&data1); |
| 8337 |
| 8338 // When a client certificate is supplied, Connect() will not be aborted |
| 8339 // when the peer requests the certificate. Instead, the handshake will |
| 8340 // artificially succeed, allowing the caller to write the HTTP request to |
| 8341 // the socket. The handshake messages are not processed until Read() is |
| 8342 // called, which then detects that the handshake was aborted, due to the |
| 8343 // peer sending a handshake_failure because it requires a client |
| 8344 // certificate. |
| 8345 SSLSocketDataProvider ssl_data2(true /* async */, net::OK); |
| 8346 ssl_data2.cert_request_info = cert_request.get(); |
| 8347 session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_data2); |
| 8348 net::MockRead data2_reads[] = { |
| 8349 net::MockRead(true /* async */, net::ERR_SSL_PROTOCOL_ERROR), |
| 8350 }; |
| 8351 net::StaticSocketDataProvider data2( |
| 8352 data2_reads, arraysize(data2_reads), NULL, 0); |
| 8353 session_deps.socket_factory.AddSocketDataProvider(&data2); |
| 8354 |
| 8355 // As described in ClientAuthCertCache_Direct_NoFalseStart, [ssl_]data3 is |
| 8356 // the data for the SSL handshake once the TLSv1 connection falls back to |
| 8357 // SSLv3. It has the same behaviour as [ssl_]data2. |
| 8358 SSLSocketDataProvider ssl_data3(true /* async */, net::OK); |
| 8359 ssl_data3.cert_request_info = cert_request.get(); |
| 8360 session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_data3); |
| 8361 net::StaticSocketDataProvider data3( |
| 8362 data2_reads, arraysize(data2_reads), NULL, 0); |
| 8363 session_deps.socket_factory.AddSocketDataProvider(&data3); |
| 8364 |
| 8365 scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
| 8366 scoped_ptr<HttpNetworkTransaction> trans(new HttpNetworkTransaction(session)); |
| 8367 |
| 8368 net::HttpRequestInfo request_info; |
| 8369 request_info.url = GURL("https://www.example.com/"); |
| 8370 request_info.method = "GET"; |
| 8371 request_info.load_flags = net::LOAD_NORMAL; |
| 8372 |
| 8373 // Begin the initial SSL handshake. |
| 8374 TestCompletionCallback callback; |
| 8375 int rv = trans->Start(&request_info, &callback, net::BoundNetLog()); |
| 8376 ASSERT_EQ(net::ERR_IO_PENDING, rv); |
| 8377 |
| 8378 // Complete the SSL handshake, which should abort due to requiring a |
| 8379 // client certificate. |
| 8380 rv = callback.WaitForResult(); |
| 8381 ASSERT_EQ(net::ERR_SSL_CLIENT_AUTH_CERT_NEEDED, rv); |
| 8382 |
| 8383 // Indicate that no certificate should be supplied. From the perspective |
| 8384 // of SSLClientCertCache, NULL is just as meaningful as a real |
| 8385 // certificate, so this is the same as supply a |
| 8386 // legitimate-but-unacceptable certificate. |
| 8387 rv = trans->RestartWithCertificate(NULL, &callback); |
| 8388 ASSERT_EQ(net::ERR_IO_PENDING, rv); |
| 8389 |
| 8390 // Ensure the certificate was added to the client auth cache before |
| 8391 // allowing the connection to continue restarting. |
| 8392 scoped_refptr<X509Certificate> client_cert; |
| 8393 ASSERT_TRUE(session->ssl_client_auth_cache()->Lookup("www.example.com:443", |
| 8394 &client_cert)); |
| 8395 ASSERT_EQ(NULL, client_cert.get()); |
| 8396 |
| 8397 |
| 8398 // Restart the handshake. This will consume ssl_data2, which fails, and |
| 8399 // then consume ssl_data3, which should also fail. The result code is |
| 8400 // checked against what ssl_data3 should return. |
| 8401 rv = callback.WaitForResult(); |
| 8402 ASSERT_EQ(net::ERR_SSL_PROTOCOL_ERROR, rv); |
| 8403 |
| 8404 // Ensure that the client certificate is removed from the cache on a |
| 8405 // handshake failure. |
| 8406 ASSERT_FALSE(session->ssl_client_auth_cache()->Lookup("www.example.com:443", |
| 8407 &client_cert)); |
| 8408 } |
| 8409 |
8210 } // namespace net | 8410 } // namespace net |
OLD | NEW |