Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(842)

Side by Side Diff: net/third_party/nss/patches/alpnserver.patch

Issue 595823003: Merge the server-side support of ALPN from the NSS upstream. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Remove a comment that wasn't useful. Created 6 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « net/third_party/nss/README.chromium ('k') | net/third_party/nss/patches/applypatches.sh » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 diff --git a/net/third_party/nss/ssl/SSLerrs.h b/net/third_party/nss/ssl/SSLerrs .h
2 index 4ff0b7d..3f0078c 100644
3 --- a/net/third_party/nss/ssl/SSLerrs.h
4 +++ b/net/third_party/nss/ssl/SSLerrs.h
5 @@ -413,16 +413,22 @@ ER3(SSL_ERROR_DIGEST_FAILURE, (SSL_ERROR_BASE + 127),
6 ER3(SSL_ERROR_INCORRECT_SIGNATURE_ALGORITHM, (SSL_ERROR_BASE + 128),
7 "Incorrect signature algorithm specified in a digitally-signed element.")
8
9 -ER3(SSL_ERROR_BAD_CHANNEL_ID_DATA, (SSL_ERROR_BASE + 129),
10 -"SSL received a malformed TLS Channel ID extension.")
11 +ER3(SSL_ERROR_NEXT_PROTOCOL_NO_CALLBACK, (SSL_ERROR_BASE + 129),
12 +"The next protocol negotiation extension was enabled, but the callback was clea red prior to being needed.")
13
14 -ER3(SSL_ERROR_INVALID_CHANNEL_ID_KEY, (SSL_ERROR_BASE + 130),
15 -"The application provided an invalid TLS Channel ID key.")
16 +ER3(SSL_ERROR_NEXT_PROTOCOL_NO_PROTOCOL, (SSL_ERROR_BASE + 130),
17 +"The server supports no protocols that the client advertises in the ALPN extens ion.")
18
19 -ER3(SSL_ERROR_GET_CHANNEL_ID_FAILED, (SSL_ERROR_BASE + 131),
20 -"The application could not get a TLS Channel ID.")
21 -
22 -ER3(SSL_ERROR_INAPPROPRIATE_FALLBACK_ALERT, (SSL_ERROR_BASE + 132),
23 +ER3(SSL_ERROR_INAPPROPRIATE_FALLBACK_ALERT, (SSL_ERROR_BASE + 131),
24 "The connection was using a lesser TLS version as a result of a previous"
25 " handshake failure, but the server indicated that it should not have been"
26 " needed.")
27 +
28 +ER3(SSL_ERROR_BAD_CHANNEL_ID_DATA, (SSL_ERROR_BASE + 132),
29 +"SSL received a malformed TLS Channel ID extension.")
30 +
31 +ER3(SSL_ERROR_INVALID_CHANNEL_ID_KEY, (SSL_ERROR_BASE + 133),
32 +"The application provided an invalid TLS Channel ID key.")
33 +
34 +ER3(SSL_ERROR_GET_CHANNEL_ID_FAILED, (SSL_ERROR_BASE + 134),
35 +"The application could not get a TLS Channel ID.")
36 diff --git a/net/third_party/nss/ssl/ssl3ext.c b/net/third_party/nss/ssl/ssl3ext .c
37 index 523e49a..f6530fe 100644
38 --- a/net/third_party/nss/ssl/ssl3ext.c
39 +++ b/net/third_party/nss/ssl/ssl3ext.c
40 @@ -56,10 +56,14 @@ static SECStatus ssl3_ClientHandleAppProtoXtn(sslSocket *ss,
41 PRUint16 ex_type, SECItem *data);
42 static SECStatus ssl3_ServerHandleNextProtoNegoXtn(sslSocket *ss,
43 PRUint16 ex_type, SECItem *data);
44 +static SECStatus ssl3_ServerHandleAppProtoXtn(sslSocket *ss, PRUint16 ex_type,
45 + SECItem *data);
46 +static PRInt32 ssl3_ClientSendNextProtoNegoXtn(sslSocket *ss, PRBool append,
47 + PRUint32 maxBytes);
48 static PRInt32 ssl3_ClientSendAppProtoXtn(sslSocket *ss, PRBool append,
49 PRUint32 maxBytes);
50 -static PRInt32 ssl3_ClientSendNextProtoNegoXtn(sslSocket *ss, PRBool append,
51 - PRUint32 maxBytes);
52 +static PRInt32 ssl3_ServerSendAppProtoXtn(sslSocket *ss, PRBool append,
53 + PRUint32 maxBytes);
54 static PRInt32 ssl3_SendUseSRTPXtn(sslSocket *ss, PRBool append,
55 PRUint32 maxBytes);
56 static SECStatus ssl3_HandleUseSRTPXtn(sslSocket * ss, PRUint16 ex_type,
57 @@ -247,6 +251,7 @@ static const ssl3HelloExtensionHandler clientHelloHandlers[] = {
58 { ssl_session_ticket_xtn, &ssl3_ServerHandleSessionTicketXtn },
59 { ssl_renegotiation_info_xtn, &ssl3_HandleRenegotiationInfoXtn },
60 { ssl_next_proto_nego_xtn, &ssl3_ServerHandleNextProtoNegoXtn },
61 + { ssl_app_layer_protocol_xtn, &ssl3_ServerHandleAppProtoXtn },
62 { ssl_use_srtp_xtn, &ssl3_HandleUseSRTPXtn },
63 { ssl_cert_status_xtn, &ssl3_ServerHandleStatusRequestXtn },
64 { ssl_signature_algorithms_xtn, &ssl3_ServerHandleSigAlgsXtn },
65 @@ -578,7 +583,8 @@ ssl3_SendSessionTicketXtn(
66
67 /* handle an incoming Next Protocol Negotiation extension. */
68 static SECStatus
69 -ssl3_ServerHandleNextProtoNegoXtn(sslSocket * ss, PRUint16 ex_type, SECItem *da ta)
70 +ssl3_ServerHandleNextProtoNegoXtn(sslSocket * ss, PRUint16 ex_type,
71 + SECItem *data)
72 {
73 if (ss->firstHsDone || data->len != 0) {
74 /* Clients MUST send an empty NPN extension, if any. */
75 @@ -623,14 +629,93 @@ ssl3_ValidateNextProtoNego(const unsigned char* data, unsi gned int length)
76 return SECSuccess;
77 }
78
79 +/* protocol selection handler for ALPN (server side) and NPN (client side) */
80 static SECStatus
81 -ssl3_ClientHandleNextProtoNegoXtn(sslSocket *ss, PRUint16 ex_type,
82 - SECItem *data)
83 +ssl3_SelectAppProtocol(sslSocket *ss, PRUint16 ex_type, SECItem *data)
84 {
85 SECStatus rv;
86 unsigned char resultBuffer[255];
87 SECItem result = { siBuffer, resultBuffer, 0 };
88
89 + rv = ssl3_ValidateNextProtoNego(data->data, data->len);
90 + if (rv != SECSuccess)
91 + return rv;
92 +
93 + PORT_Assert(ss->nextProtoCallback);
94 + rv = ss->nextProtoCallback(ss->nextProtoArg, ss->fd, data->data, data->len,
95 + result.data, &result.len, sizeof resultBuffer);
96 + if (rv != SECSuccess)
97 + return rv;
98 + /* If the callback wrote more than allowed to |result| it has corrupted our
99 + * stack. */
100 + if (result.len > sizeof resultBuffer) {
101 + PORT_SetError(SEC_ERROR_OUTPUT_LEN);
102 + return SECFailure;
103 + }
104 +
105 + if (ex_type == ssl_app_layer_protocol_xtn &&
106 + ss->ssl3.nextProtoState != SSL_NEXT_PROTO_NEGOTIATED) {
107 + /* The callback might say OK, but then it's picked a default.
108 + * That's OK for NPN, but not ALPN. */
109 + SECITEM_FreeItem(&ss->ssl3.nextProto, PR_FALSE);
110 + PORT_SetError(SSL_ERROR_NEXT_PROTOCOL_NO_PROTOCOL);
111 + (void)SSL3_SendAlert(ss, alert_fatal, no_application_protocol);
112 + return SECFailure;
113 + }
114 +
115 + ss->xtnData.negotiated[ss->xtnData.numNegotiated++] = ex_type;
116 +
117 + SECITEM_FreeItem(&ss->ssl3.nextProto, PR_FALSE);
118 + return SECITEM_CopyItem(NULL, &ss->ssl3.nextProto, &result);
119 +}
120 +
121 +/* handle an incoming ALPN extension at the server */
122 +static SECStatus
123 +ssl3_ServerHandleAppProtoXtn(sslSocket *ss, PRUint16 ex_type, SECItem *data)
124 +{
125 + int count;
126 + SECStatus rv;
127 +
128 + /* We expressly don't want to allow ALPN on renegotiation,
129 + * despite it being permitted by the spec. */
130 + if (ss->firstHsDone || data->len == 0) {
131 + /* Clients MUST send a non-empty ALPN extension. */
132 + PORT_SetError(SSL_ERROR_NEXT_PROTOCOL_DATA_INVALID);
133 + return SECFailure;
134 + }
135 +
136 + /* unlike NPN, ALPN has extra redundant length information so that
137 + * the extension is the same in both ClientHello and ServerHello */
138 + count = ssl3_ConsumeHandshakeNumber(ss, 2, &data->data, &data->len);
139 + if (count < 0) {
140 + return SECFailure; /* fatal alert was sent */
141 + }
142 + if (count != data->len) {
143 + return ssl3_DecodeError(ss);
144 + }
145 +
146 + if (!ss->nextProtoCallback) {
147 + /* we're not configured for it */
148 + return SECSuccess;
149 + }
150 +
151 + rv = ssl3_SelectAppProtocol(ss, ex_type, data);
152 + if (rv != SECSuccess) {
153 + return rv;
154 + }
155 +
156 + /* prepare to send back a response, if we negotiated */
157 + if (ss->ssl3.nextProtoState == SSL_NEXT_PROTO_NEGOTIATED) {
158 + return ssl3_RegisterServerHelloExtensionSender(
159 + ss, ex_type, ssl3_ServerSendAppProtoXtn);
160 + }
161 + return SECSuccess;
162 +}
163 +
164 +static SECStatus
165 +ssl3_ClientHandleNextProtoNegoXtn(sslSocket *ss, PRUint16 ex_type,
166 + SECItem *data)
167 +{
168 PORT_Assert(!ss->firstHsDone);
169
170 if (ssl3_ExtensionNegotiated(ss, ssl_app_layer_protocol_xtn)) {
171 @@ -643,37 +728,16 @@ ssl3_ClientHandleNextProtoNegoXtn(sslSocket *ss, PRUint16 ex_type,
172 return SECFailure;
173 }
174
175 - rv = ssl3_ValidateNextProtoNego(data->data, data->len);
176 - if (rv != SECSuccess)
177 - return rv;
178 -
179 - /* ss->nextProtoCallback cannot normally be NULL if we negotiated the
180 - * extension. However, It is possible that an application erroneously
181 - * cleared the callback between the time we sent the ClientHello and now.
182 - */
183 - PORT_Assert(ss->nextProtoCallback != NULL);
184 + /* We should only get this call if we sent the extension, so
185 + * ss->nextProtoCallback needs to be non-NULL. However, it is possible
186 + * that an application erroneously cleared the callback between the time
187 + * we sent the ClientHello and now. */
188 if (!ss->nextProtoCallback) {
189 - /* XXX Use a better error code. This is an application error, not an
190 - * NSS bug. */
191 - PORT_SetError(SEC_ERROR_LIBRARY_FAILURE);
192 + PORT_SetError(SSL_ERROR_NEXT_PROTOCOL_NO_CALLBACK);
193 return SECFailure;
194 }
195
196 - rv = ss->nextProtoCallback(ss->nextProtoArg, ss->fd, data->data, data->len,
197 - result.data, &result.len, sizeof resultBuffer);
198 - if (rv != SECSuccess)
199 - return rv;
200 - /* If the callback wrote more than allowed to |result| it has corrupted our
201 - * stack. */
202 - if (result.len > sizeof resultBuffer) {
203 - PORT_SetError(SEC_ERROR_OUTPUT_LEN);
204 - return SECFailure;
205 - }
206 -
207 - ss->xtnData.negotiated[ss->xtnData.numNegotiated++] = ex_type;
208 -
209 - SECITEM_FreeItem(&ss->ssl3.nextProto, PR_FALSE);
210 - return SECITEM_CopyItem(NULL, &ss->ssl3.nextProto, &result);
211 + return ssl3_SelectAppProtocol(ss, ex_type, data);
212 }
213
214 static SECStatus
215 @@ -814,6 +878,47 @@ loser:
216 return -1;
217 }
218
219 +static PRInt32
220 +ssl3_ServerSendAppProtoXtn(sslSocket * ss, PRBool append, PRUint32 maxBytes)
221 +{
222 + PRInt32 extension_length;
223 +
224 + PORT_Assert(ss->opt.enableALPN);
225 + PORT_Assert(ss->ssl3.nextProto.data);
226 + PORT_Assert(ss->ssl3.nextProto.len > 0);
227 + PORT_Assert(ss->ssl3.nextProtoState == SSL_NEXT_PROTO_NEGOTIATED);
228 + PORT_Assert(!ss->firstHsDone);
229 +
230 + extension_length = 2 /* extension type */ + 2 /* extension length */ +
231 + 2 /* protocol name list */ + 1 /* name length */ +
232 + ss->ssl3.nextProto.len;
233 +
234 + if (append && maxBytes >= extension_length) {
235 + SECStatus rv;
236 + rv = ssl3_AppendHandshakeNumber(ss, ssl_app_layer_protocol_xtn, 2);
237 + if (rv != SECSuccess) {
238 + return -1;
239 + }
240 + rv = ssl3_AppendHandshakeNumber(ss, extension_length - 4, 2);
241 + if (rv != SECSuccess) {
242 + return -1;
243 + }
244 + rv = ssl3_AppendHandshakeNumber(ss, ss->ssl3.nextProto.len + 1, 2);
245 + if (rv != SECSuccess) {
246 + return -1;
247 + }
248 + rv = ssl3_AppendHandshakeVariable(ss, ss->ssl3.nextProto.data,
249 + ss->ssl3.nextProto.len, 1);
250 + if (rv != SECSuccess) {
251 + return -1;
252 + }
253 + } else if (maxBytes < extension_length) {
254 + return 0;
255 + }
256 +
257 + return extension_length;
258 +}
259 +
260 static SECStatus
261 ssl3_ClientHandleChannelIDXtn(sslSocket *ss, PRUint16 ex_type,
262 SECItem *data)
263 diff --git a/net/third_party/nss/ssl/ssl3prot.h b/net/third_party/nss/ssl/ssl3pr ot.h
264 index 4c19ade..d32be38 100644
265 --- a/net/third_party/nss/ssl/ssl3prot.h
266 +++ b/net/third_party/nss/ssl/ssl3prot.h
267 @@ -107,7 +107,8 @@ typedef enum {
268 certificate_unobtainable = 111,
269 unrecognized_name = 112,
270 bad_certificate_status_response = 113,
271 - bad_certificate_hash_value = 114
272 + bad_certificate_hash_value = 114,
273 + no_application_protocol = 120
274
275 } SSL3AlertDescription;
276
277 diff --git a/net/third_party/nss/ssl/sslerr.h b/net/third_party/nss/ssl/sslerr.h
278 index 82ae7df..5184a6e 100644
279 --- a/net/third_party/nss/ssl/sslerr.h
280 +++ b/net/third_party/nss/ssl/sslerr.h
281 @@ -193,10 +193,14 @@ SSL_ERROR_UNSUPPORTED_HASH_ALGORITHM = (SSL_ERROR_BASE + 1 26),
282 SSL_ERROR_DIGEST_FAILURE = (SSL_ERROR_BASE + 127),
283 SSL_ERROR_INCORRECT_SIGNATURE_ALGORITHM = (SSL_ERROR_BASE + 128),
284
285 -SSL_ERROR_BAD_CHANNEL_ID_DATA = (SSL_ERROR_BASE + 129),
286 -SSL_ERROR_INVALID_CHANNEL_ID_KEY = (SSL_ERROR_BASE + 130),
287 -SSL_ERROR_GET_CHANNEL_ID_FAILED = (SSL_ERROR_BASE + 131),
288 -SSL_ERROR_INAPPROPRIATE_FALLBACK_ALERT = (SSL_ERROR_BASE + 132),
289 +SSL_ERROR_NEXT_PROTOCOL_NO_CALLBACK = (SSL_ERROR_BASE + 129),
290 +SSL_ERROR_NEXT_PROTOCOL_NO_PROTOCOL = (SSL_ERROR_BASE + 130),
291 +
292 +SSL_ERROR_INAPPROPRIATE_FALLBACK_ALERT = (SSL_ERROR_BASE + 131),
293 +
294 +SSL_ERROR_BAD_CHANNEL_ID_DATA = (SSL_ERROR_BASE + 132),
295 +SSL_ERROR_INVALID_CHANNEL_ID_KEY = (SSL_ERROR_BASE + 133),
296 +SSL_ERROR_GET_CHANNEL_ID_FAILED = (SSL_ERROR_BASE + 134),
297
298 SSL_ERROR_END_OF_LIST /* let the c compiler determine the value of this. */
299 } SSLErrorCodes;
300 diff --git a/net/third_party/nss/ssl/sslsock.c b/net/third_party/nss/ssl/sslsock .c
301 index 028cd98..421ba21 100644
302 --- a/net/third_party/nss/ssl/sslsock.c
303 +++ b/net/third_party/nss/ssl/sslsock.c
304 @@ -1432,6 +1432,11 @@ DTLS_ImportFD(PRFileDesc *model, PRFileDesc *fd)
305 return ssl_ImportFD(model, fd, ssl_variant_datagram);
306 }
307
308 +/* SSL_SetNextProtoCallback is used to select an application protocol
309 + * for ALPN and NPN. For ALPN, this runs on the server; for NPN it
310 + * runs on the client. */
311 +/* Note: The ALPN version doesn't allow for the use of a default, setting a
312 + * status of SSL_NEXT_PROTO_NO_OVERLAP is treated as a failure. */
313 SECStatus
314 SSL_SetNextProtoCallback(PRFileDesc *fd, SSLNextProtoCallback callback,
315 void *arg)
316 @@ -1452,7 +1457,7 @@ SSL_SetNextProtoCallback(PRFileDesc *fd, SSLNextProtoCallb ack callback,
317 return SECSuccess;
318 }
319
320 -/* ssl_NextProtoNegoCallback is set as an NPN callback for the case when
321 +/* ssl_NextProtoNegoCallback is set as an ALPN/NPN callback when
322 * SSL_SetNextProtoNego is used.
323 */
324 static SECStatus
325 @@ -1471,12 +1476,6 @@ ssl_NextProtoNegoCallback(void *arg, PRFileDesc *fd,
326 return SECFailure;
327 }
328
329 - if (protos_len == 0) {
330 - /* The server supports the extension, but doesn't have any protocols
331 - * configured. In this case we request our favoured protocol. */
332 - goto pick_first;
333 - }
334 -
335 /* For each protocol in server preference, see if we support it. */
336 for (i = 0; i < protos_len; ) {
337 for (j = 0; j < ss->opt.nextProtoNego.len; ) {
338 @@ -1493,7 +1492,10 @@ ssl_NextProtoNegoCallback(void *arg, PRFileDesc *fd,
339 i += 1 + (unsigned int)protos[i];
340 }
341
342 -pick_first:
343 + /* The other side supports the extension, and either doesn't have any
344 + * protocols configured, or none of its options match ours. In this case we
345 + * request our favoured protocol. */
346 + /* This will be treated as a failure for ALPN. */
347 ss->ssl3.nextProtoState = SSL_NEXT_PROTO_NO_OVERLAP;
348 result = ss->opt.nextProtoNego.data;
349
OLDNEW
« no previous file with comments | « net/third_party/nss/README.chromium ('k') | net/third_party/nss/patches/applypatches.sh » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698