Chromium Code Reviews| Index: net/socket/ssl_client_socket_nss.cc |
| =================================================================== |
| --- net/socket/ssl_client_socket_nss.cc (revision 139421) |
| +++ net/socket/ssl_client_socket_nss.cc (working copy) |
| @@ -421,6 +421,36 @@ |
| return r; |
| } |
| +// Client-side error mapping functions. |
| + |
| +// Map NSS error code to network error code. |
| +int MapNSSClientError(PRErrorCode err) { |
| + switch (err) { |
| + case SSL_ERROR_BAD_CERT_ALERT: |
| + case SSL_ERROR_UNSUPPORTED_CERT_ALERT: |
| + case SSL_ERROR_REVOKED_CERT_ALERT: |
| + case SSL_ERROR_EXPIRED_CERT_ALERT: |
| + case SSL_ERROR_CERTIFICATE_UNKNOWN_ALERT: |
| + case SSL_ERROR_UNKNOWN_CA_ALERT: |
| + case SSL_ERROR_ACCESS_DENIED_ALERT: |
| + return ERR_BAD_SSL_CLIENT_AUTH_CERT; |
| + default: |
| + return MapNSSError(err); |
| + } |
| +} |
| + |
| +// Map NSS error code from the first SSL handshake to network error code. |
| +int MapNSSClientHandshakeError(PRErrorCode err) { |
| + switch (err) { |
| + // If the server closed on us, it is a protocol error. |
| + // Some TLS-intolerant servers do this when we request TLS. |
| + case PR_END_OF_FILE_ERROR: |
| + return ERR_SSL_PROTOCOL_ERROR; |
| + default: |
| + return MapNSSClientError(err); |
| + } |
| +} |
| + |
| } // namespace |
| SSLClientSocketNSS::SSLClientSocketNSS(ClientSocketHandle* transport_socket, |
| @@ -1560,9 +1590,10 @@ |
| false, |
| key, |
| &public_key)) { |
| + int error = MapNSSError(PORT_GetError()); |
|
wtc
2012/05/29 23:41:00
Get the NSS error code first, otherwise it could b
|
| CERT_DestroyCertificate(*cert); |
| *cert = NULL; |
| - return MapNSSError(PORT_GetError()); |
| + return error; |
| } |
| SECKEY_DestroyPublicKey(public_key); |
| break; |
| @@ -1587,7 +1618,7 @@ |
| // Failed to get a DBC. Proceed without. |
| rv = SSL_RestartHandshakeAfterCertReq(nss_fd_, NULL, NULL, NULL); |
| if (rv != SECSuccess) |
| - return MapNSSError(PORT_GetError()); |
| + return HandleNSSError(PORT_GetError(), true); |
| GotoState(STATE_HANDSHAKE); |
| return OK; |
| } |
| @@ -1606,7 +1637,7 @@ |
| cert_chain->len))); |
| rv = SSL_RestartHandshakeAfterCertReq(nss_fd_, cert, key, cert_chain); |
| if (rv != SECSuccess) |
| - return MapNSSError(PORT_GetError()); |
| + return HandleNSSError(PORT_GetError(), true); |
| GotoState(STATE_HANDSHAKE); |
| set_domain_bound_cert_type(domain_bound_cert_type_); |
| @@ -2018,8 +2049,8 @@ |
| int SSLClientSocketNSS::HandleNSSError(PRErrorCode nss_error, |
| bool handshake_error) { |
| - int net_error = handshake_error ? MapNSSHandshakeError(nss_error) : |
| - MapNSSError(nss_error); |
| + int net_error = handshake_error ? MapNSSClientHandshakeError(nss_error) : |
| + MapNSSClientError(nss_error); |
| #if defined(OS_WIN) |
| // On Windows, a handle to the HCRYPTPROV is cached in the X509Certificate |