Extract SIGPIPE ignoring code to a common place.
[chromium-blink-merge.git] / net / third_party / nss / patches / ocspstapling.patch
blob0abbfe2b7e5b4ee9f51bc74452ad22b81c6ab524
1 diff -pu -r a/net/third_party/nss/ssl/ssl3con.c b/net/third_party/nss/ssl/ssl3con.c
2 --- a/net/third_party/nss/ssl/ssl3con.c 2012-11-09 15:21:56.747322689 -0800
3 +++ b/net/third_party/nss/ssl/ssl3con.c 2012-11-09 15:28:27.933078020 -0800
4 @@ -8365,6 +8365,57 @@ ssl3_CopyPeerCertsToSID(ssl3CertNode *ce
7 /* Called from ssl3_HandleHandshakeMessage() when it has deciphered a complete
8 + * ssl3 CertificateStatus message.
9 + * Caller must hold Handshake and RecvBuf locks.
10 + * This is always called before ssl3_HandleCertificate, even if the Certificate
11 + * message is sent first.
12 + */
13 +static SECStatus
14 +ssl3_HandleCertificateStatus(sslSocket *ss, SSL3Opaque *b, PRUint32 length)
16 + PRInt32 status, len;
17 + int errCode;
18 + SSL3AlertDescription desc;
20 + if (!ss->ssl3.hs.may_get_cert_status ||
21 + ss->ssl3.hs.ws != wait_server_cert ||
22 + !ss->ssl3.hs.pending_cert_msg.data ||
23 + ss->ssl3.hs.cert_status.data) {
24 + errCode = SSL_ERROR_RX_UNEXPECTED_CERT_STATUS;
25 + desc = unexpected_message;
26 + goto alert_loser;
27 + }
29 + /* Consume the CertificateStatusType enum */
30 + status = ssl3_ConsumeHandshakeNumber(ss, 1, &b, &length);
31 + if (status != 1 /* ocsp */) {
32 + goto format_loser;
33 + }
35 + len = ssl3_ConsumeHandshakeNumber(ss, 3, &b, &length);
36 + if (len != length) {
37 + goto format_loser;
38 + }
40 + if (SECITEM_AllocItem(NULL, &ss->ssl3.hs.cert_status, length) == NULL) {
41 + return SECFailure;
42 + }
43 + ss->ssl3.hs.cert_status.type = siBuffer;
44 + PORT_Memcpy(ss->ssl3.hs.cert_status.data, b, length);
46 + return SECSuccess;
48 +format_loser:
49 + errCode = SSL_ERROR_BAD_CERT_STATUS_RESPONSE_ALERT;
50 + desc = bad_certificate_status_response;
52 +alert_loser:
53 + (void)SSL3_SendAlert(ss, alert_fatal, desc);
54 + (void)ssl_MapLowLevelError(errCode);
55 + return SECFailure;
58 +/* Called from ssl3_HandleHandshakeMessage() when it has deciphered a complete
59 * ssl3 Certificate message.
60 * Caller must hold Handshake and RecvBuf locks.
62 @@ -9248,6 +9299,26 @@ ssl3_FinishHandshake(sslSocket * ss)
63 return SECSuccess;
66 +/* This function handles any pending Certificate messages. Certificate messages
67 + * can be pending if we expect a possible CertificateStatus message to follow.
68 + *
69 + * This function must be called immediately after handling the
70 + * CertificateStatus message, and before handling any ServerKeyExchange or
71 + * CertificateRequest messages.
72 + */
73 +static SECStatus
74 +ssl3_MaybeHandlePendingCertificateMessage(sslSocket *ss)
76 + SECStatus rv = SECSuccess;
78 + if (ss->ssl3.hs.pending_cert_msg.data) {
79 + rv = ssl3_HandleCertificate(ss, ss->ssl3.hs.pending_cert_msg.data,
80 + ss->ssl3.hs.pending_cert_msg.len);
81 + SECITEM_FreeItem(&ss->ssl3.hs.pending_cert_msg, PR_FALSE);
82 + }
83 + return rv;
86 /* Called from ssl3_HandleHandshake() when it has gathered a complete ssl3
87 * hanshake message.
88 * Caller must hold Handshake and RecvBuf locks.
89 @@ -9376,14 +9447,42 @@ ssl3_HandleHandshakeMessage(sslSocket *s
90 rv = dtls_HandleHelloVerifyRequest(ss, b, length);
91 break;
92 case certificate:
93 + if (ss->ssl3.hs.may_get_cert_status) {
94 + /* If we might get a CertificateStatus then we want to postpone the
95 + * processing of the Certificate message until after we have
96 + * processed the CertificateStatus */
97 + if (ss->ssl3.hs.pending_cert_msg.data ||
98 + ss->ssl3.hs.ws != wait_server_cert) {
99 + (void)SSL3_SendAlert(ss, alert_fatal, unexpected_message);
100 + (void)ssl_MapLowLevelError(SSL_ERROR_RX_UNEXPECTED_CERTIFICATE);
101 + return SECFailure;
103 + if (SECITEM_AllocItem(NULL, &ss->ssl3.hs.pending_cert_msg,
104 + length) == NULL) {
105 + return SECFailure;
107 + ss->ssl3.hs.pending_cert_msg.type = siBuffer;
108 + PORT_Memcpy(ss->ssl3.hs.pending_cert_msg.data, b, length);
109 + break;
111 rv = ssl3_HandleCertificate(ss, b, length);
112 break;
113 + case certificate_status:
114 + rv = ssl3_HandleCertificateStatus(ss, b, length);
115 + if (rv != SECSuccess)
116 + break;
117 + PORT_Assert(ss->ssl3.hs.pending_cert_msg.data);
118 + rv = ssl3_MaybeHandlePendingCertificateMessage(ss);
119 + break;
120 case server_key_exchange:
121 if (ss->sec.isServer) {
122 (void)SSL3_SendAlert(ss, alert_fatal, unexpected_message);
123 PORT_SetError(SSL_ERROR_RX_UNEXPECTED_SERVER_KEY_EXCH);
124 return SECFailure;
126 + rv = ssl3_MaybeHandlePendingCertificateMessage(ss);
127 + if (rv != SECSuccess)
128 + break;
129 rv = ssl3_HandleServerKeyExchange(ss, b, length);
130 break;
131 case certificate_request:
132 @@ -9392,6 +9491,9 @@ ssl3_HandleHandshakeMessage(sslSocket *s
133 PORT_SetError(SSL_ERROR_RX_UNEXPECTED_CERT_REQUEST);
134 return SECFailure;
136 + rv = ssl3_MaybeHandlePendingCertificateMessage(ss);
137 + if (rv != SECSuccess)
138 + break;
139 rv = ssl3_HandleCertificateRequest(ss, b, length);
140 break;
141 case server_hello_done:
142 @@ -9405,6 +9507,9 @@ ssl3_HandleHandshakeMessage(sslSocket *s
143 PORT_SetError(SSL_ERROR_RX_UNEXPECTED_HELLO_DONE);
144 return SECFailure;
146 + rv = ssl3_MaybeHandlePendingCertificateMessage(ss);
147 + if (rv != SECSuccess)
148 + break;
149 rv = ssl3_HandleServerHelloDone(ss);
150 break;
151 case certificate_verify:
152 @@ -10369,6 +10474,12 @@ ssl3_DestroySSL3Info(sslSocket *ss)
153 ss->ssl3.hs.messages.len = 0;
154 ss->ssl3.hs.messages.space = 0;
156 + if (ss->ssl3.hs.pending_cert_msg.data) {
157 + SECITEM_FreeItem(&ss->ssl3.hs.pending_cert_msg, PR_FALSE);
159 + if (ss->ssl3.hs.cert_status.data) {
160 + SECITEM_FreeItem(&ss->ssl3.hs.cert_status, PR_FALSE);
163 /* free the SSL3Buffer (msg_body) */
164 PORT_Free(ss->ssl3.hs.msg_body.buf);
165 diff -pu -r a/net/third_party/nss/ssl/ssl3ext.c b/net/third_party/nss/ssl/ssl3ext.c
166 --- a/net/third_party/nss/ssl/ssl3ext.c 2012-09-20 17:28:05.000000000 -0700
167 +++ b/net/third_party/nss/ssl/ssl3ext.c 2012-11-09 15:32:11.606363256 -0800
168 @@ -234,6 +234,7 @@ static const ssl3HelloExtensionHandler s
169 { ssl_renegotiation_info_xtn, &ssl3_HandleRenegotiationInfoXtn },
170 { ssl_next_proto_nego_xtn, &ssl3_ClientHandleNextProtoNegoXtn },
171 { ssl_use_srtp_xtn, &ssl3_HandleUseSRTPXtn },
172 + { ssl_cert_status_xtn, &ssl3_ClientHandleStatusRequestXtn },
173 { -1, NULL }
176 @@ -258,7 +259,8 @@ ssl3HelloExtensionSender clientHelloSend
177 #endif
178 { ssl_session_ticket_xtn, &ssl3_SendSessionTicketXtn },
179 { ssl_next_proto_nego_xtn, &ssl3_ClientSendNextProtoNegoXtn },
180 - { ssl_use_srtp_xtn, &ssl3_SendUseSRTPXtn }
181 + { ssl_use_srtp_xtn, &ssl3_SendUseSRTPXtn },
182 + { ssl_cert_status_xtn, &ssl3_ClientSendStatusRequestXtn }
183 /* any extra entries will appear as { 0, NULL } */
186 @@ -640,6 +642,80 @@ loser:
187 return -1;
190 +SECStatus
191 +ssl3_ClientHandleStatusRequestXtn(sslSocket *ss, PRUint16 ex_type,
192 + SECItem *data)
194 + /* If we didn't request this extension, then the server may not echo it. */
195 + if (!ss->opt.enableOCSPStapling)
196 + return SECFailure;
198 + /* The echoed extension must be empty. */
199 + if (data->len != 0)
200 + return SECFailure;
202 + ss->ssl3.hs.may_get_cert_status = PR_TRUE;
204 + /* Keep track of negotiated extensions. */
205 + ss->xtnData.negotiated[ss->xtnData.numNegotiated++] = ex_type;
207 + return SECSuccess;
210 +/* ssl3_ClientSendStatusRequestXtn builds the status_request extension on the
211 + * client side. See RFC 4366 section 3.6. */
212 +PRInt32
213 +ssl3_ClientSendStatusRequestXtn(sslSocket * ss, PRBool append,
214 + PRUint32 maxBytes)
216 + PRInt32 extension_length;
218 + if (!ss->opt.enableOCSPStapling)
219 + return 0;
221 + /* extension_type (2-bytes) +
222 + * length(extension_data) (2-bytes) +
223 + * status_type (1) +
224 + * responder_id_list length (2) +
225 + * request_extensions length (2)
226 + */
227 + extension_length = 9;
229 + if (append && maxBytes >= extension_length) {
230 + SECStatus rv;
231 + TLSExtensionData *xtnData;
233 + /* extension_type */
234 + rv = ssl3_AppendHandshakeNumber(ss, ssl_cert_status_xtn, 2);
235 + if (rv != SECSuccess)
236 + return -1;
237 + rv = ssl3_AppendHandshakeNumber(ss, extension_length - 4, 2);
238 + if (rv != SECSuccess)
239 + return -1;
240 + rv = ssl3_AppendHandshakeNumber(ss, 1 /* status_type ocsp */, 1);
241 + if (rv != SECSuccess)
242 + return -1;
243 + /* A zero length responder_id_list means that the responders are
244 + * implicitly known to the server. */
245 + rv = ssl3_AppendHandshakeNumber(ss, 0, 2);
246 + if (rv != SECSuccess)
247 + return -1;
248 + /* A zero length request_extensions means that there are no extensions.
249 + * Specifically, we don't set the id-pkix-ocsp-nonce extension. This
250 + * means that the server can replay a cached OCSP response to us. */
251 + rv = ssl3_AppendHandshakeNumber(ss, 0, 2);
252 + if (rv != SECSuccess)
253 + return -1;
255 + xtnData = &ss->xtnData;
256 + xtnData->advertised[xtnData->numAdvertised++] = ssl_cert_status_xtn;
257 + } else if (maxBytes < extension_length) {
258 + PORT_Assert(0);
259 + return 0;
261 + return extension_length;
265 * NewSessionTicket
266 * Called from ssl3_HandleFinished
267 diff -pu -r a/net/third_party/nss/ssl/ssl3prot.h b/net/third_party/nss/ssl/ssl3prot.h
268 --- a/net/third_party/nss/ssl/ssl3prot.h 2012-04-25 07:50:12.000000000 -0700
269 +++ b/net/third_party/nss/ssl/ssl3prot.h 2012-11-09 15:28:27.933078020 -0800
270 @@ -129,6 +129,7 @@ typedef enum {
271 certificate_verify = 15,
272 client_key_exchange = 16,
273 finished = 20,
274 + certificate_status = 22,
275 next_proto = 67
276 } SSL3HandshakeType;
278 diff -pu -r a/net/third_party/nss/ssl/sslerr.h b/net/third_party/nss/ssl/sslerr.h
279 --- a/net/third_party/nss/ssl/sslerr.h 2012-07-12 17:51:57.000000000 -0700
280 +++ b/net/third_party/nss/ssl/sslerr.h 2012-11-09 15:30:36.804971319 -0800
281 @@ -188,6 +188,8 @@ SSL_ERROR_RX_UNEXPECTED_HELLO_VERIFY_REQ
283 SSL_ERROR_FEATURE_NOT_SUPPORTED_FOR_VERSION = (SSL_ERROR_BASE + 124),
285 +SSL_ERROR_RX_UNEXPECTED_CERT_STATUS = (SSL_ERROR_BASE + 125),
287 SSL_ERROR_END_OF_LIST /* let the c compiler determine the value of this. */
288 } SSLErrorCodes;
289 #endif /* NO_SECURITY_ERROR_ENUM */
290 diff -pu -r a/net/third_party/nss/ssl/SSLerrs.h b/net/third_party/nss/ssl/SSLerrs.h
291 --- a/net/third_party/nss/ssl/SSLerrs.h 2012-07-12 17:51:57.000000000 -0700
292 +++ b/net/third_party/nss/ssl/SSLerrs.h 2012-11-09 15:30:19.924723400 -0800
293 @@ -400,3 +400,6 @@ ER3(SSL_ERROR_RX_UNEXPECTED_HELLO_VERIFY
295 ER3(SSL_ERROR_FEATURE_NOT_SUPPORTED_FOR_VERSION, (SSL_ERROR_BASE + 124),
296 "SSL feature not supported for the protocol version.")
298 +ER3(SSL_ERROR_RX_UNEXPECTED_CERT_STATUS, (SSL_ERROR_BASE + 125),
299 +"SSL received an unexpected Certificate Status handshake message.")
300 diff -pu -r a/net/third_party/nss/ssl/ssl.h b/net/third_party/nss/ssl/ssl.h
301 --- a/net/third_party/nss/ssl/ssl.h 2012-11-09 15:27:15.952019947 -0800
302 +++ b/net/third_party/nss/ssl/ssl.h 2012-11-09 15:28:27.933078020 -0800
303 @@ -158,6 +158,7 @@ SSL_IMPORT PRFileDesc *DTLS_ImportFD(PRF
304 * accept fragmented alerts).
306 #define SSL_CBC_RANDOM_IV 23
307 +#define SSL_ENABLE_OCSP_STAPLING 24 /* Request OCSP stapling (client) */
309 #ifdef SSL_DEPRECATED_FUNCTION
310 /* Old deprecated function names */
311 @@ -409,6 +410,23 @@ SSL_IMPORT SECStatus SSL_PeerCertificate
312 PRFileDesc *fd, CERTCertificate **certs,
313 unsigned int *numCerts, unsigned int maxNumCerts);
315 +/* SSL_GetStapledOCSPResponse returns the OCSP response that was provided by
316 + * the TLS server. The resulting data is copied to |out_data|. On entry, |*len|
317 + * must contain the size of |out_data|. On exit, |*len| will contain the size
318 + * of the OCSP stapled response. If the stapled response is too large to fit in
319 + * |out_data| then it will be truncated. If no OCSP response was given by the
320 + * server then it has zero length.
322 + * You must set the SSL_ENABLE_OCSP_STAPLING option in order for OCSP responses
323 + * to be provided by a server.
325 + * You can call this function during the certificate verification callback or
326 + * any time afterwards.
327 + */
328 +SSL_IMPORT SECStatus SSL_GetStapledOCSPResponse(PRFileDesc *fd,
329 + unsigned char *out_data,
330 + unsigned int *len);
333 ** Authenticate certificate hook. Called when a certificate comes in
334 ** (because of SSL_REQUIRE_CERTIFICATE in SSL_Enable) to authenticate the
335 diff -pu -r a/net/third_party/nss/ssl/sslimpl.h b/net/third_party/nss/ssl/sslimpl.h
336 --- a/net/third_party/nss/ssl/sslimpl.h 2012-11-09 15:21:56.747322689 -0800
337 +++ b/net/third_party/nss/ssl/sslimpl.h 2012-11-09 15:28:27.943078167 -0800
338 @@ -316,6 +316,7 @@ typedef struct sslOptionsStr {
339 unsigned int requireSafeNegotiation : 1; /* 22 */
340 unsigned int enableFalseStart : 1; /* 23 */
341 unsigned int cbcRandomIV : 1; /* 24 */
342 + unsigned int enableOCSPStapling : 1; /* 25 */
343 } sslOptions;
345 typedef enum { sslHandshakingUndetermined = 0,
346 @@ -795,6 +796,14 @@ const ssl3CipherSuiteDef *suite_def;
347 PRBool isResuming; /* are we resuming a session */
348 PRBool usedStepDownKey; /* we did a server key exchange. */
349 PRBool sendingSCSV; /* instead of empty RI */
350 + PRBool may_get_cert_status; /* the server echoed a
351 + * status_request extension so
352 + * may send a CertificateStatus
353 + * handshake message. */
354 + SECItem pending_cert_msg; /* a Certificate message which we
355 + * save temporarily if we may get
356 + * a CertificateStatus message */
357 + SECItem cert_status; /* an OCSP response */
358 sslBuffer msgState; /* current state for handshake messages*/
359 /* protected by recvBufLock */
360 sslBuffer messages; /* Accumulated handshake messages */
361 @@ -1625,6 +1634,8 @@ extern SECStatus ssl3_HandleSupportedPoi
362 PRUint16 ex_type, SECItem *data);
363 extern SECStatus ssl3_ClientHandleSessionTicketXtn(sslSocket *ss,
364 PRUint16 ex_type, SECItem *data);
365 +extern SECStatus ssl3_ClientHandleStatusRequestXtn(sslSocket *ss,
366 + PRUint16 ex_type, SECItem *data);
367 extern SECStatus ssl3_ServerHandleSessionTicketXtn(sslSocket *ss,
368 PRUint16 ex_type, SECItem *data);
370 @@ -1634,6 +1645,8 @@ extern SECStatus ssl3_ServerHandleSessio
372 extern PRInt32 ssl3_SendSessionTicketXtn(sslSocket *ss, PRBool append,
373 PRUint32 maxBytes);
374 +extern PRInt32 ssl3_ClientSendStatusRequestXtn(sslSocket *ss, PRBool append,
375 + PRUint32 maxBytes);
377 /* ClientHello and ServerHello extension senders.
378 * The code is in ssl3ext.c.
379 diff -pu -r a/net/third_party/nss/ssl/sslsock.c b/net/third_party/nss/ssl/sslsock.c
380 --- a/net/third_party/nss/ssl/sslsock.c 2012-11-09 15:17:00.432983977 -0800
381 +++ b/net/third_party/nss/ssl/sslsock.c 2012-11-09 15:28:27.943078167 -0800
382 @@ -153,7 +153,8 @@ static sslOptions ssl_defaults = {
383 2, /* enableRenegotiation (default: requires extension) */
384 PR_FALSE, /* requireSafeNegotiation */
385 PR_FALSE, /* enableFalseStart */
386 - PR_TRUE /* cbcRandomIV */
387 + PR_TRUE, /* cbcRandomIV */
388 + PR_FALSE, /* enableOCSPStapling */
392 @@ -827,6 +828,10 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 wh
393 ss->opt.cbcRandomIV = on;
394 break;
396 + case SSL_ENABLE_OCSP_STAPLING:
397 + ss->opt.enableOCSPStapling = on;
398 + break;
400 default:
401 PORT_SetError(SEC_ERROR_INVALID_ARGS);
402 rv = SECFailure;
403 @@ -896,6 +901,7 @@ SSL_OptionGet(PRFileDesc *fd, PRInt32 wh
404 on = ss->opt.requireSafeNegotiation; break;
405 case SSL_ENABLE_FALSE_START: on = ss->opt.enableFalseStart; break;
406 case SSL_CBC_RANDOM_IV: on = ss->opt.cbcRandomIV; break;
407 + case SSL_ENABLE_OCSP_STAPLING: on = ss->opt.enableOCSPStapling; break;
409 default:
410 PORT_SetError(SEC_ERROR_INVALID_ARGS);
411 @@ -954,6 +960,9 @@ SSL_OptionGetDefault(PRInt32 which, PRBo
412 break;
413 case SSL_ENABLE_FALSE_START: on = ssl_defaults.enableFalseStart; break;
414 case SSL_CBC_RANDOM_IV: on = ssl_defaults.cbcRandomIV; break;
415 + case SSL_ENABLE_OCSP_STAPLING:
416 + on = ssl_defaults.enableOCSPStapling;
417 + break;
419 default:
420 PORT_SetError(SEC_ERROR_INVALID_ARGS);
421 @@ -1117,6 +1126,10 @@ SSL_OptionSetDefault(PRInt32 which, PRBo
422 ssl_defaults.cbcRandomIV = on;
423 break;
425 + case SSL_ENABLE_OCSP_STAPLING:
426 + ssl_defaults.enableOCSPStapling = on;
427 + break;
429 default:
430 PORT_SetError(SEC_ERROR_INVALID_ARGS);
431 return SECFailure;
432 @@ -1859,6 +1872,36 @@ SSL_VersionRangeSet(PRFileDesc *fd, cons
433 return SECSuccess;
436 +SECStatus
437 +SSL_GetStapledOCSPResponse(PRFileDesc *fd, unsigned char *out_data,
438 + unsigned int *len) {
439 + sslSocket *ss = ssl_FindSocket(fd);
441 + if (!ss) {
442 + SSL_DBG(("%d: SSL[%d]: bad socket in SSL_GetStapledOCSPResponse",
443 + SSL_GETPID(), fd));
444 + return SECFailure;
447 + ssl_Get1stHandshakeLock(ss);
448 + ssl_GetSSL3HandshakeLock(ss);
450 + if (ss->ssl3.hs.cert_status.data) {
451 + unsigned int todo = ss->ssl3.hs.cert_status.len;
452 + if (todo > *len)
453 + todo = *len;
454 + *len = ss->ssl3.hs.cert_status.len;
455 + PORT_Memcpy(out_data, ss->ssl3.hs.cert_status.data, todo);
456 + } else {
457 + *len = 0;
460 + ssl_ReleaseSSL3HandshakeLock(ss);
461 + ssl_Release1stHandshakeLock(ss);
463 + return SECSuccess;
466 /************************************************************************/
467 /* The following functions are the TOP LEVEL SSL functions.
468 ** They all get called through the NSPRIOMethods table below.
469 diff -pu -r a/net/third_party/nss/ssl/sslt.h b/net/third_party/nss/ssl/sslt.h
470 --- a/net/third_party/nss/ssl/sslt.h 2012-06-06 19:06:19.000000000 -0700
471 +++ b/net/third_party/nss/ssl/sslt.h 2012-11-09 15:29:10.333701086 -0800
472 @@ -175,6 +175,7 @@ typedef enum {
473 /* Update SSL_MAX_EXTENSIONS whenever a new extension type is added. */
474 typedef enum {
475 ssl_server_name_xtn = 0,
476 + ssl_cert_status_xtn = 5,
477 #ifdef NSS_ENABLE_ECC
478 ssl_elliptic_curves_xtn = 10,
479 ssl_ec_point_formats_xtn = 11,
480 @@ -185,6 +186,6 @@ typedef enum {
481 ssl_renegotiation_info_xtn = 0xff01 /* experimental number */
482 } SSLExtensionType;
484 -#define SSL_MAX_EXTENSIONS 7
485 +#define SSL_MAX_EXTENSIONS 8
487 #endif /* __sslt_h_ */