OLD | NEW |
1 Index: net/third_party/nss/ssl/ssl3con.c | 1 Index: net/third_party/nss/ssl/ssl3con.c |
2 =================================================================== | 2 =================================================================== |
3 --- net/third_party/nss/ssl/ssl3con.c» (revision 219342) | 3 --- net/third_party/nss/ssl/ssl3con.c» (revision 220594) |
4 +++ net/third_party/nss/ssl/ssl3con.c (working copy) | 4 +++ net/third_party/nss/ssl/ssl3con.c (working copy) |
5 @@ -3933,6 +3933,22 @@ | 5 @@ -3933,6 +3933,20 @@ |
6 ssl_MapLowLevelError(SSL_ERROR_DIGEST_FAILURE); | 6 ssl_MapLowLevelError(SSL_ERROR_DIGEST_FAILURE); |
7 return SECFailure; | 7 return SECFailure; |
8 } | 8 } |
9 + | 9 + |
10 +#ifdef _WIN32 | |
11 + /* A backup SHA-1 hash for a potential client auth signature. */ | 10 + /* A backup SHA-1 hash for a potential client auth signature. */ |
12 + if (!ss->sec.isServer) { | 11 + if (!ss->sec.isServer) { |
13 + ss->ssl3.hs.md5 = PK11_CreateDigestContext(SEC_OID_SHA1); | 12 + ss->ssl3.hs.md5 = PK11_CreateDigestContext(SEC_OID_SHA1); |
14 + if (ss->ssl3.hs.md5 == NULL) { | 13 + if (ss->ssl3.hs.md5 == NULL) { |
15 + ssl_MapLowLevelError(SSL_ERROR_SHA_DIGEST_FAILURE); | 14 + ssl_MapLowLevelError(SSL_ERROR_SHA_DIGEST_FAILURE); |
16 + return SECFailure; | 15 + return SECFailure; |
17 + } | 16 + } |
18 + | 17 + |
19 + if (PK11_DigestBegin(ss->ssl3.hs.md5) != SECSuccess) { | 18 + if (PK11_DigestBegin(ss->ssl3.hs.md5) != SECSuccess) { |
20 + ssl_MapLowLevelError(SSL_ERROR_SHA_DIGEST_FAILURE); | 19 + ssl_MapLowLevelError(SSL_ERROR_SHA_DIGEST_FAILURE); |
21 + return SECFailure; | 20 + return SECFailure; |
22 + } | 21 + } |
23 + } | 22 + } |
24 +#endif | |
25 } else { | 23 } else { |
26 /* Both ss->ssl3.hs.md5 and ss->ssl3.hs.sha should be NULL or | 24 /* Both ss->ssl3.hs.md5 and ss->ssl3.hs.sha should be NULL or |
27 * created successfully. */ | 25 * created successfully. */ |
28 @@ -4043,6 +4059,13 @@ | 26 @@ -4043,6 +4057,13 @@ |
29 ssl_MapLowLevelError(SSL_ERROR_DIGEST_FAILURE); | 27 ssl_MapLowLevelError(SSL_ERROR_DIGEST_FAILURE); |
30 return rv; | 28 return rv; |
31 } | 29 } |
32 + if (ss->ssl3.hs.md5) { | 30 + if (ss->ssl3.hs.md5) { |
33 + rv = PK11_DigestOp(ss->ssl3.hs.md5, b, l); | 31 + rv = PK11_DigestOp(ss->ssl3.hs.md5, b, l); |
34 + if (rv != SECSuccess) { | 32 + if (rv != SECSuccess) { |
35 + ssl_MapLowLevelError(SSL_ERROR_SHA_DIGEST_FAILURE); | 33 + ssl_MapLowLevelError(SSL_ERROR_SHA_DIGEST_FAILURE); |
36 + return rv; | 34 + return rv; |
37 + } | 35 + } |
38 + } | 36 + } |
39 } else { | 37 } else { |
40 rv = PK11_DigestOp(ss->ssl3.hs.md5, b, l); | 38 rv = PK11_DigestOp(ss->ssl3.hs.md5, b, l); |
41 if (rv != SECSuccess) { | 39 if (rv != SECSuccess) { |
42 @@ -4791,6 +4814,30 @@ | 40 @@ -4791,6 +4812,30 @@ |
43 return rv; | 41 return rv; |
44 } | 42 } |
45 | 43 |
46 +static SECStatus | 44 +static SECStatus |
47 +ssl3_ComputeBackupHandshakeHashes(sslSocket * ss, | 45 +ssl3_ComputeBackupHandshakeHashes(sslSocket * ss, |
48 + SSL3Hashes * hashes) /* output goes here. */ | 46 + SSL3Hashes * hashes) /* output goes here. */ |
49 +{ | 47 +{ |
50 + SECStatus rv = SECSuccess; | 48 + SECStatus rv = SECSuccess; |
51 + | 49 + |
52 + PORT_Assert( ss->opt.noLocks || ssl_HaveSSL3HandshakeLock(ss) ); | 50 + PORT_Assert( ss->opt.noLocks || ssl_HaveSSL3HandshakeLock(ss) ); |
(...skipping 10 matching lines...) Expand all Loading... |
63 + | 61 + |
64 +loser: | 62 +loser: |
65 + PK11_DestroyContext(ss->ssl3.hs.md5, PR_TRUE); | 63 + PK11_DestroyContext(ss->ssl3.hs.md5, PR_TRUE); |
66 + ss->ssl3.hs.md5 = NULL; | 64 + ss->ssl3.hs.md5 = NULL; |
67 + return rv; | 65 + return rv; |
68 +} | 66 +} |
69 + | 67 + |
70 /* | 68 /* |
71 * SSL 2 based implementations pass in the initial outbound buffer | 69 * SSL 2 based implementations pass in the initial outbound buffer |
72 * so that the handshake hash can contain the included information. | 70 * so that the handshake hash can contain the included information. |
73 @@ -6044,7 +6091,17 @@ | 71 @@ -6044,7 +6089,17 @@ |
74 SSL_GETPID(), ss->fd)); | 72 SSL_GETPID(), ss->fd)); |
75 | 73 |
76 ssl_GetSpecReadLock(ss); | 74 ssl_GetSpecReadLock(ss); |
77 - rv = ssl3_ComputeHandshakeHashes(ss, ss->ssl3.pwSpec, &hashes, 0); | 75 - rv = ssl3_ComputeHandshakeHashes(ss, ss->ssl3.pwSpec, &hashes, 0); |
78 + /* In TLS 1.2, ssl3_ComputeHandshakeHashes always uses the handshake hash | 76 + /* In TLS 1.2, ssl3_ComputeHandshakeHashes always uses the handshake hash |
79 + * function (SHA-256). If the server or the client does not support SHA-256 | 77 + * function (SHA-256). If the server or the client does not support SHA-256 |
80 + * as a signature hash, we can either maintain a backup SHA-1 handshake | 78 + * as a signature hash, we can either maintain a backup SHA-1 handshake |
81 + * hash or buffer all handshake messages. | 79 + * hash or buffer all handshake messages. |
82 + */ | 80 + */ |
83 + if (ss->ssl3.hs.hashType == handshake_hash_single && ss->ssl3.hs.md5) { | 81 + if (ss->ssl3.hs.hashType == handshake_hash_single && ss->ssl3.hs.md5) { |
84 + rv = ssl3_ComputeBackupHandshakeHashes(ss, &hashes); | 82 + rv = ssl3_ComputeBackupHandshakeHashes(ss, &hashes); |
85 + PORT_Assert(ss->ssl3.hs.md5 == NULL); | 83 + PORT_Assert(ss->ssl3.hs.md5 == NULL); |
86 + } else { | 84 + } else { |
87 + rv = ssl3_ComputeHandshakeHashes(ss, ss->ssl3.pwSpec, &hashes, 0); | 85 + rv = ssl3_ComputeHandshakeHashes(ss, ss->ssl3.pwSpec, &hashes, 0); |
88 + } | 86 + } |
89 ssl_ReleaseSpecReadLock(ss); | 87 ssl_ReleaseSpecReadLock(ss); |
90 if (rv != SECSuccess) { | 88 if (rv != SECSuccess) { |
91 goto done; /* err code was set by ssl3_ComputeHandshakeHashes */ | 89 goto done; /* err code was set by ssl3_ComputeHandshakeHashes */ |
92 @@ -6098,11 +6155,6 @@ | 90 @@ -6098,11 +6153,6 @@ |
93 if (rv != SECSuccess) { | 91 if (rv != SECSuccess) { |
94 goto done; | 92 goto done; |
95 } | 93 } |
96 - /* We always sign using the handshake hash function. It's possible that | 94 - /* We always sign using the handshake hash function. It's possible that |
97 - * a server could support SHA-256 as the handshake hash but not as a | 95 - * a server could support SHA-256 as the handshake hash but not as a |
98 - * signature hash. In that case we wouldn't be able to do client | 96 - * signature hash. In that case we wouldn't be able to do client |
99 - * certificates with it. The alternative is to buffer all handshake | 97 - * certificates with it. The alternative is to buffer all handshake |
100 - * messages. */ | 98 - * messages. */ |
101 sigAndHash.hashAlg = hashes.hashAlg; | 99 sigAndHash.hashAlg = hashes.hashAlg; |
102 | 100 |
103 rv = ssl3_AppendSignatureAndHashAlgorithm(ss, &sigAndHash); | 101 rv = ssl3_AppendSignatureAndHashAlgorithm(ss, &sigAndHash); |
104 @@ -6994,6 +7046,31 @@ | 102 @@ -6994,6 +7044,56 @@ |
105 } | 103 } |
106 goto send_no_certificate; | 104 goto send_no_certificate; |
107 } | 105 } |
108 + | 106 + |
109 + if (isTLS12 && ss->ssl3.hs.md5) { | 107 + if (isTLS12 && ss->ssl3.hs.md5) { |
110 + PRBool need_backup_hash = PR_FALSE; | 108 + PRBool need_backup_hash = PR_FALSE; |
| 109 + PRBool prefer_sha1 = PR_FALSE; |
111 +#ifdef _WIN32 | 110 +#ifdef _WIN32 |
112 + /* If the key is in CAPI, assume conservatively that the CAPI | 111 + /* If the key is in CAPI, assume conservatively that the CAPI |
113 + * service provider may be unable to sign SHA-256 hashes. | 112 + * service provider may be unable to sign SHA-256 hashes. |
114 +» » * Use SHA-1 if the server supports it. */ | 113 +» » */ |
115 + if (ss->ssl3.platformClientKey->dwKeySpec != | 114 + if (ss->ssl3.platformClientKey->dwKeySpec != |
116 + CERT_NCRYPT_KEY_SPEC) { | 115 + CERT_NCRYPT_KEY_SPEC) { |
| 116 + /* CAPI only supports RSA and DSA signatures, so we don't |
| 117 + * need to check the key type. */ |
| 118 + prefer_sha1 = PR_TRUE; |
| 119 + } |
| 120 +#endif /* _WIN32 */ |
| 121 + /* If the key is a 1024-bit RSA or DSA key, assume |
| 122 + * conservatively that it may be unable to sign SHA-256 |
| 123 + * hashes. This is the case for older Estonian ID cards that |
| 124 + * have 1024-bit RSA keys. In FIPS 186-2 and older, DSA key |
| 125 + * size is at most 1024 bits and the hash function must be |
| 126 + * SHA-1. |
| 127 + */ |
| 128 + if (!prefer_sha1) { |
| 129 + SECKEYPublicKey *pubk = |
| 130 + CERT_ExtractPublicKey(ss->ssl3.clientCertificate); |
| 131 + if (pubk == NULL) { |
| 132 + errCode = SSL_ERROR_EXTRACT_PUBLIC_KEY_FAILURE; |
| 133 + goto loser; |
| 134 + } |
| 135 + if (pubk->keyType == rsaKey || pubk->keyType == dsaKey) { |
| 136 + prefer_sha1 = SECKEY_PublicKeyStrength(pubk) <= 128; |
| 137 + } |
| 138 + SECKEY_DestroyPublicKey(pubk); |
| 139 + } |
| 140 + /* Use SHA-1 if the server supports it. */ |
| 141 + if (prefer_sha1) { |
117 + for (i = 0; i < algorithms.len; i += 2) { | 142 + for (i = 0; i < algorithms.len; i += 2) { |
118 + /* CAPI only supports RSA and DSA signatures. */ | |
119 + if (algorithms.data[i] == tls_hash_sha1 && | 143 + if (algorithms.data[i] == tls_hash_sha1 && |
120 + (algorithms.data[i+1] == tls_sig_rsa || | 144 + (algorithms.data[i+1] == tls_sig_rsa || |
121 + algorithms.data[i+1] == tls_sig_dsa)) { | 145 + algorithms.data[i+1] == tls_sig_dsa)) { |
122 + need_backup_hash = PR_TRUE; | 146 + need_backup_hash = PR_TRUE; |
123 + break; | 147 + break; |
124 + } | 148 + } |
125 + } | 149 + } |
126 + } | 150 + } |
127 +#endif /* _WIN32 */ | |
128 + if (!need_backup_hash) { | 151 + if (!need_backup_hash) { |
129 + PK11_DestroyContext(ss->ssl3.hs.md5, PR_TRUE); | 152 + PK11_DestroyContext(ss->ssl3.hs.md5, PR_TRUE); |
130 + ss->ssl3.hs.md5 = NULL; | 153 + ss->ssl3.hs.md5 = NULL; |
131 + } | 154 + } |
132 + } | 155 + } |
133 break; /* not an error */ | 156 break; /* not an error */ |
134 } | 157 } |
135 #endif /* NSS_PLATFORM_CLIENT_AUTH */ | 158 #endif /* NSS_PLATFORM_CLIENT_AUTH */ |
136 @@ -7227,6 +7304,13 @@ | 159 @@ -7227,6 +7327,13 @@ |
137 (ss->ssl3.platformClientKey || | 160 (ss->ssl3.platformClientKey || |
138 ss->ssl3.clientPrivateKey != NULL); | 161 ss->ssl3.clientPrivateKey != NULL); |
139 | 162 |
140 + if (!sendClientCert && | 163 + if (!sendClientCert && |
141 + ss->ssl3.hs.hashType == handshake_hash_single && ss->ssl3.hs.md5) { | 164 + ss->ssl3.hs.hashType == handshake_hash_single && ss->ssl3.hs.md5) { |
142 + /* Don't need the backup handshake hash. */ | 165 + /* Don't need the backup handshake hash. */ |
143 + PK11_DestroyContext(ss->ssl3.hs.md5, PR_TRUE); | 166 + PK11_DestroyContext(ss->ssl3.hs.md5, PR_TRUE); |
144 + ss->ssl3.hs.md5 = NULL; | 167 + ss->ssl3.hs.md5 = NULL; |
145 + } | 168 + } |
146 + | 169 + |
147 /* We must wait for the server's certificate to be authenticated before | 170 /* We must wait for the server's certificate to be authenticated before |
148 * sending the client certificate in order to disclosing the client | 171 * sending the client certificate in order to disclosing the client |
149 * certificate to an attacker that does not have a valid cert for the | 172 * certificate to an attacker that does not have a valid cert for the |
150 Index: net/third_party/nss/ssl/sslimpl.h | 173 Index: net/third_party/nss/ssl/sslimpl.h |
151 =================================================================== | 174 =================================================================== |
152 --- net/third_party/nss/ssl/sslimpl.h» (revision 219342) | 175 --- net/third_party/nss/ssl/sslimpl.h» (revision 220594) |
153 +++ net/third_party/nss/ssl/sslimpl.h (working copy) | 176 +++ net/third_party/nss/ssl/sslimpl.h (working copy) |
154 @@ -838,6 +838,9 @@ | 177 @@ -838,6 +838,9 @@ |
155 * SSL 3.0 - TLS 1.1 use both |md5| and |sha|. |md5| is used for MD5 and | 178 * SSL 3.0 - TLS 1.1 use both |md5| and |sha|. |md5| is used for MD5 and |
156 * |sha| for SHA-1. | 179 * |sha| for SHA-1. |
157 * TLS 1.2 and later use only |sha|, for SHA-256. */ | 180 * TLS 1.2 and later use only |sha|, for SHA-256. */ |
158 + /* NOTE: On Windows, TLS 1.2 and later use |md5| as a backup handshake hash | 181 + /* NOTE: On the client side, TLS 1.2 and later use |md5| as a backup |
159 + * for generating client auth signatures. Confusingly, the backup hash | 182 + * handshake hash for generating client auth signatures. Confusingly, the |
160 + * function is SHA-1. */ | 183 + * backup hash function is SHA-1. */ |
161 PK11Context * md5; | 184 PK11Context * md5; |
162 PK11Context * sha; | 185 PK11Context * sha; |
163 | 186 |
OLD | NEW |