Chromium Code Reviews| Index: net/socket/ssl_client_socket_openssl.cc |
| diff --git a/net/socket/ssl_client_socket_openssl.cc b/net/socket/ssl_client_socket_openssl.cc |
| index 88965f5688d2bbe129f8a34e483e92d5df49bfe4..24c5a55beee076afa6f0cf53f39d61a084f0809e 100644 |
| --- a/net/socket/ssl_client_socket_openssl.cc |
| +++ b/net/socket/ssl_client_socket_openssl.cc |
| @@ -358,7 +358,6 @@ SSLClientSocketOpenSSL::SSLClientSocketOpenSSL( |
| server_cert_chain_(new PeerCertificateChain(NULL)), |
| completed_connect_(false), |
| was_ever_used_(false), |
| - client_auth_cert_needed_(false), |
| cert_verifier_(context.cert_verifier), |
| cert_transparency_verifier_(context.cert_transparency_verifier), |
| channel_id_service_(context.channel_id_service), |
| @@ -499,7 +498,6 @@ void SSLClientSocketOpenSSL::Disconnect() { |
| cert_authorities_.clear(); |
| cert_key_types_.clear(); |
| - client_auth_cert_needed_ = false; |
| start_cert_verification_time_ = base::TimeTicks(); |
| @@ -960,17 +958,17 @@ int SSLClientSocketOpenSSL::DoHandshake() { |
| UpdateServerCert(); |
| GotoState(STATE_VERIFY_CERT); |
| } else { |
| - if (client_auth_cert_needed_) |
| - return ERR_SSL_CLIENT_AUTH_CERT_NEEDED; |
| - |
| int ssl_error = SSL_get_error(ssl_, rv); |
| - |
| if (ssl_error == SSL_ERROR_WANT_CHANNEL_ID_LOOKUP) { |
| // The server supports channel ID. Stop to look one up before returning to |
| // the handshake. |
| GotoState(STATE_CHANNEL_ID_LOOKUP); |
| return OK; |
| } |
| + if (ssl_error == SSL_ERROR_WANT_X509_LOOKUP && |
| + !ssl_config_.send_client_cert) { |
| + return ERR_SSL_CLIENT_AUTH_CERT_NEEDED; |
| + } |
| OpenSSLErrorInfo error_info; |
| net_error = MapOpenSSLErrorWithDetails(ssl_error, err_tracer, &error_info); |
| @@ -1389,9 +1387,7 @@ int SSLClientSocketOpenSSL::DoPayloadRead() { |
| // Although only the final SSL_read call may have failed, the failure needs to |
| // processed immediately, while the information still available in OpenSSL's |
| // error queue. |
| - if (client_auth_cert_needed_) { |
| - pending_read_error_ = ERR_SSL_CLIENT_AUTH_CERT_NEEDED; |
| - } else if (ssl_ret <= 0) { |
| + if (ssl_ret <= 0) { |
| // A zero return from SSL_read may mean any of: |
| // - The underlying BIO_read returned 0. |
| // - The peer sent a close_notify. |
| @@ -1403,6 +1399,9 @@ int SSLClientSocketOpenSSL::DoPayloadRead() { |
| pending_read_ssl_error_ = SSL_get_error(ssl_, ssl_ret); |
| if (pending_read_ssl_error_ == SSL_ERROR_ZERO_RETURN) { |
| pending_read_error_ = 0; |
| + } else if (pending_read_ssl_error_ == SSL_ERROR_WANT_X509_LOOKUP && |
| + !ssl_config_.send_client_cert) { |
|
davidben
2015/05/08 22:15:52
This is the same as checking it before the ssl_ret
|
| + pending_read_error_ = ERR_SSL_CLIENT_AUTH_CERT_NEEDED; |
| } else { |
| pending_read_error_ = MapOpenSSLErrorWithDetails( |
| pending_read_ssl_error_, err_tracer, &pending_read_error_info_); |
| @@ -1614,7 +1613,6 @@ int SSLClientSocketOpenSSL::ClientCertRequestCallback(SSL* ssl) { |
| if (!ssl_config_.send_client_cert) { |
| // First pass: we know that a client certificate is needed, but we do not |
| // have one at hand. |
| - client_auth_cert_needed_ = true; |
| STACK_OF(X509_NAME) *authorities = SSL_get_client_CA_list(ssl); |
| for (size_t i = 0; i < sk_X509_NAME_num(authorities); i++) { |
| X509_NAME *ca_name = (X509_NAME *)sk_X509_NAME_value(authorities, i); |
| @@ -1634,7 +1632,8 @@ int SSLClientSocketOpenSSL::ClientCertRequestCallback(SSL* ssl) { |
| static_cast<SSLClientCertType>(client_cert_types[i])); |
| } |
| - return -1; // Suspends handshake. |
| + // Suspends handshake. SSL_get_error will return SSL_ERROR_WANT_X509_LOOKUP. |
| + return -1; |
| } |
| // Second pass: a client certificate should have been selected. |