OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 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/socket/ssl_server_socket_nss.h" | 5 #include "net/socket/ssl_server_socket_nss.h" |
6 | 6 |
7 #if defined(OS_WIN) | 7 #if defined(OS_WIN) |
8 #include <winsock2.h> | 8 #include <winsock2.h> |
9 #endif | 9 #endif |
10 | 10 |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
74 g_nss_ssl_server_init_singleton = LAZY_INSTANCE_INITIALIZER; | 74 g_nss_ssl_server_init_singleton = LAZY_INSTANCE_INITIALIZER; |
75 | 75 |
76 } // namespace | 76 } // namespace |
77 | 77 |
78 void EnableSSLServerSockets() { | 78 void EnableSSLServerSockets() { |
79 g_nss_ssl_server_init_singleton.Get(); | 79 g_nss_ssl_server_init_singleton.Get(); |
80 } | 80 } |
81 | 81 |
82 scoped_ptr<SSLServerSocket> CreateSSLServerSocket( | 82 scoped_ptr<SSLServerSocket> CreateSSLServerSocket( |
83 scoped_ptr<StreamSocket> socket, | 83 scoped_ptr<StreamSocket> socket, |
84 X509Certificate* cert, | 84 X509Certificate* certificate, |
85 crypto::RSAPrivateKey* key, | 85 crypto::RSAPrivateKey* key, |
86 const SSLServerConfig& ssl_config) { | 86 const SSLServerConfig& ssl_server_config) { |
87 DCHECK(g_nss_server_sockets_init) << "EnableSSLServerSockets() has not been" | 87 DCHECK(g_nss_server_sockets_init) << "EnableSSLServerSockets() has not been" |
88 << " called yet!"; | 88 << " called yet!"; |
89 | 89 |
90 return scoped_ptr<SSLServerSocket>( | 90 return scoped_ptr<SSLServerSocket>(new SSLServerSocketNSS( |
91 new SSLServerSocketNSS(socket.Pass(), cert, key, ssl_config)); | 91 socket.Pass(), certificate, key, ssl_server_config)); |
92 } | 92 } |
93 | 93 |
94 SSLServerSocketNSS::SSLServerSocketNSS( | 94 SSLServerSocketNSS::SSLServerSocketNSS( |
95 scoped_ptr<StreamSocket> transport_socket, | 95 scoped_ptr<StreamSocket> transport_socket, |
96 scoped_refptr<X509Certificate> cert, | 96 scoped_refptr<X509Certificate> cert, |
97 crypto::RSAPrivateKey* key, | 97 crypto::RSAPrivateKey* key, |
98 const SSLServerConfig& ssl_config) | 98 const SSLServerConfig& ssl_server_config) |
99 : transport_send_busy_(false), | 99 : transport_send_busy_(false), |
100 transport_recv_busy_(false), | 100 transport_recv_busy_(false), |
101 user_read_buf_len_(0), | 101 user_read_buf_len_(0), |
102 user_write_buf_len_(0), | 102 user_write_buf_len_(0), |
103 nss_fd_(NULL), | 103 nss_fd_(NULL), |
104 nss_bufs_(NULL), | 104 nss_bufs_(NULL), |
105 transport_socket_(transport_socket.Pass()), | 105 transport_socket_(transport_socket.Pass()), |
106 ssl_config_(ssl_config), | 106 ssl_server_config_(ssl_server_config), |
107 cert_(cert), | 107 cert_(cert), |
108 next_handshake_state_(STATE_NONE), | 108 next_handshake_state_(STATE_NONE), |
109 completed_handshake_(false) { | 109 completed_handshake_(false) { |
110 // TODO(hclam): Need a better way to clone a key. | 110 // TODO(hclam): Need a better way to clone a key. |
111 std::vector<uint8> key_bytes; | 111 std::vector<uint8> key_bytes; |
112 CHECK(key->ExportPrivateKey(&key_bytes)); | 112 CHECK(key->ExportPrivateKey(&key_bytes)); |
113 key_.reset(crypto::RSAPrivateKey::CreateFromPrivateKeyInfo(key_bytes)); | 113 key_.reset(crypto::RSAPrivateKey::CreateFromPrivateKeyInfo(key_bytes)); |
114 CHECK(key_.get()); | 114 CHECK(key_.get()); |
115 } | 115 } |
116 | 116 |
(...skipping 214 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
331 /* Push SSL onto our fake I/O socket */ | 331 /* Push SSL onto our fake I/O socket */ |
332 nss_fd_ = SSL_ImportFD(NULL, nss_fd_); | 332 nss_fd_ = SSL_ImportFD(NULL, nss_fd_); |
333 if (nss_fd_ == NULL) { | 333 if (nss_fd_ == NULL) { |
334 LogFailedNSSFunction(net_log_, "SSL_ImportFD", ""); | 334 LogFailedNSSFunction(net_log_, "SSL_ImportFD", ""); |
335 return ERR_OUT_OF_MEMORY; // TODO(port): map NSPR/NSS error code. | 335 return ERR_OUT_OF_MEMORY; // TODO(port): map NSPR/NSS error code. |
336 } | 336 } |
337 // TODO(port): set more ssl options! Check errors! | 337 // TODO(port): set more ssl options! Check errors! |
338 | 338 |
339 int rv; | 339 int rv; |
340 | 340 |
341 if (ssl_config_.require_client_cert) { | 341 if (ssl_server_config_.require_client_cert) { |
342 rv = SSL_OptionSet(nss_fd_, SSL_REQUEST_CERTIFICATE, PR_TRUE); | 342 rv = SSL_OptionSet(nss_fd_, SSL_REQUEST_CERTIFICATE, PR_TRUE); |
343 if (rv != SECSuccess) { | 343 if (rv != SECSuccess) { |
344 LogFailedNSSFunction(net_log_, "SSL_OptionSet", | 344 LogFailedNSSFunction(net_log_, "SSL_OptionSet", |
345 "SSL_REQUEST_CERTIFICATE"); | 345 "SSL_REQUEST_CERTIFICATE"); |
346 return ERR_UNEXPECTED; | 346 return ERR_UNEXPECTED; |
347 } | 347 } |
348 } | 348 } |
349 | 349 |
350 rv = SSL_OptionSet(nss_fd_, SSL_SECURITY, PR_TRUE); | 350 rv = SSL_OptionSet(nss_fd_, SSL_SECURITY, PR_TRUE); |
351 if (rv != SECSuccess) { | 351 if (rv != SECSuccess) { |
352 LogFailedNSSFunction(net_log_, "SSL_OptionSet", "SSL_SECURITY"); | 352 LogFailedNSSFunction(net_log_, "SSL_OptionSet", "SSL_SECURITY"); |
353 return ERR_UNEXPECTED; | 353 return ERR_UNEXPECTED; |
354 } | 354 } |
355 | 355 |
356 rv = SSL_OptionSet(nss_fd_, SSL_ENABLE_SSL2, PR_FALSE); | 356 rv = SSL_OptionSet(nss_fd_, SSL_ENABLE_SSL2, PR_FALSE); |
357 if (rv != SECSuccess) { | 357 if (rv != SECSuccess) { |
358 LogFailedNSSFunction(net_log_, "SSL_OptionSet", "SSL_ENABLE_SSL2"); | 358 LogFailedNSSFunction(net_log_, "SSL_OptionSet", "SSL_ENABLE_SSL2"); |
359 return ERR_UNEXPECTED; | 359 return ERR_UNEXPECTED; |
360 } | 360 } |
361 | 361 |
362 SSLVersionRange version_range; | 362 SSLVersionRange version_range; |
363 version_range.min = ssl_config_.version_min; | 363 version_range.min = ssl_server_config_.version_min; |
364 version_range.max = ssl_config_.version_max; | 364 version_range.max = ssl_server_config_.version_max; |
365 rv = SSL_VersionRangeSet(nss_fd_, &version_range); | 365 rv = SSL_VersionRangeSet(nss_fd_, &version_range); |
366 if (rv != SECSuccess) { | 366 if (rv != SECSuccess) { |
367 LogFailedNSSFunction(net_log_, "SSL_VersionRangeSet", ""); | 367 LogFailedNSSFunction(net_log_, "SSL_VersionRangeSet", ""); |
368 return ERR_NO_SSL_VERSIONS_ENABLED; | 368 return ERR_NO_SSL_VERSIONS_ENABLED; |
369 } | 369 } |
370 | 370 |
371 if (ssl_config_.require_ecdhe) { | 371 if (ssl_server_config_.require_ecdhe) { |
372 const PRUint16* const ssl_ciphers = SSL_GetImplementedCiphers(); | 372 const PRUint16* const ssl_ciphers = SSL_GetImplementedCiphers(); |
373 const PRUint16 num_ciphers = SSL_GetNumImplementedCiphers(); | 373 const PRUint16 num_ciphers = SSL_GetNumImplementedCiphers(); |
374 | 374 |
375 // Iterate over the cipher suites and disable those that don't use ECDHE. | 375 // Iterate over the cipher suites and disable those that don't use ECDHE. |
376 for (unsigned i = 0; i < num_ciphers; i++) { | 376 for (unsigned i = 0; i < num_ciphers; i++) { |
377 SSLCipherSuiteInfo info; | 377 SSLCipherSuiteInfo info; |
378 if (SSL_GetCipherSuiteInfo(ssl_ciphers[i], &info, sizeof(info)) == | 378 if (SSL_GetCipherSuiteInfo(ssl_ciphers[i], &info, sizeof(info)) == |
379 SECSuccess) { | 379 SECSuccess) { |
380 if (strcmp(info.keaTypeName, "ECDHE") != 0) { | 380 if (strcmp(info.keaTypeName, "ECDHE") != 0) { |
381 SSL_CipherPrefSet(nss_fd_, ssl_ciphers[i], PR_FALSE); | 381 SSL_CipherPrefSet(nss_fd_, ssl_ciphers[i], PR_FALSE); |
382 } | 382 } |
383 } | 383 } |
384 } | 384 } |
385 } | 385 } |
386 | 386 |
387 for (std::vector<uint16>::const_iterator it = | 387 for (std::vector<uint16>::const_iterator it = |
388 ssl_config_.disabled_cipher_suites.begin(); | 388 ssl_server_config_.disabled_cipher_suites.begin(); |
389 it != ssl_config_.disabled_cipher_suites.end(); ++it) { | 389 it != ssl_server_config_.disabled_cipher_suites.end(); ++it) { |
390 // This will fail if the specified cipher is not implemented by NSS, but | 390 // This will fail if the specified cipher is not implemented by NSS, but |
391 // the failure is harmless. | 391 // the failure is harmless. |
392 SSL_CipherPrefSet(nss_fd_, *it, PR_FALSE); | 392 SSL_CipherPrefSet(nss_fd_, *it, PR_FALSE); |
393 } | 393 } |
394 | 394 |
395 // Server socket doesn't need session tickets. | 395 // Server socket doesn't need session tickets. |
396 rv = SSL_OptionSet(nss_fd_, SSL_ENABLE_SESSION_TICKETS, PR_FALSE); | 396 rv = SSL_OptionSet(nss_fd_, SSL_ENABLE_SESSION_TICKETS, PR_FALSE); |
397 if (rv != SECSuccess) { | 397 if (rv != SECSuccess) { |
398 LogFailedNSSFunction( | 398 LogFailedNSSFunction( |
399 net_log_, "SSL_OptionSet", "SSL_ENABLE_SESSION_TICKETS"); | 399 net_log_, "SSL_OptionSet", "SSL_ENABLE_SESSION_TICKETS"); |
(...skipping 448 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
848 // initializes the NSS base library. | 848 // initializes the NSS base library. |
849 EnsureNSSSSLInit(); | 849 EnsureNSSSSLInit(); |
850 if (!NSS_IsInitialized()) | 850 if (!NSS_IsInitialized()) |
851 return ERR_UNEXPECTED; | 851 return ERR_UNEXPECTED; |
852 | 852 |
853 EnableSSLServerSockets(); | 853 EnableSSLServerSockets(); |
854 return OK; | 854 return OK; |
855 } | 855 } |
856 | 856 |
857 } // namespace net | 857 } // namespace net |
OLD | NEW |