| Index: net/third_party/nss/patches/nextproto.patch
|
| diff --git a/net/third_party/nss/patches/nextproto.patch b/net/third_party/nss/patches/nextproto.patch
|
| index a01f2404b15b992ae578bcd462e360ef5de5797a..46021b425f3cbed78b4aef4119069982274b9206 100644
|
| --- a/net/third_party/nss/patches/nextproto.patch
|
| +++ b/net/third_party/nss/patches/nextproto.patch
|
| @@ -1,68 +1,89 @@
|
| -From 6b594dc531e7a1d1d5bca2f0f78e7bc0ac3ff937 Mon Sep 17 00:00:00 2001
|
| +From 3caa0f573d2637bfed99dcc0e5887fe3a52462ba Mon Sep 17 00:00:00 2001
|
| From: Adam Langley <agl@chromium.org>
|
| Date: Mon, 3 Oct 2011 12:19:28 -0400
|
| -Subject: [PATCH] nextproto.patch
|
| +Subject: [PATCH 01/15] nextproto.patch
|
|
|
| ---
|
| - mozilla/security/nss/cmd/tstclnt/tstclnt.c | 6 ++
|
| - mozilla/security/nss/lib/ssl/ssl.def | 7 ++
|
| - mozilla/security/nss/lib/ssl/ssl.h | 12 +++
|
| - mozilla/security/nss/lib/ssl/ssl3con.c | 54 ++++++++++++
|
| - mozilla/security/nss/lib/ssl/ssl3ext.c | 122 +++++++++++++++++++++++++++-
|
| - mozilla/security/nss/lib/ssl/ssl3prot.h | 3 +-
|
| - mozilla/security/nss/lib/ssl/sslimpl.h | 24 ++++++
|
| - mozilla/security/nss/lib/ssl/sslsock.c | 74 +++++++++++++++++
|
| - mozilla/security/nss/lib/ssl/sslt.h | 3 +-
|
| - 9 files changed, 302 insertions(+), 3 deletions(-)
|
| + mozilla/security/nss/lib/ssl/ssl.def | 6 ++
|
| + mozilla/security/nss/lib/ssl/ssl.h | 51 ++++++++++++
|
| + mozilla/security/nss/lib/ssl/ssl3con.c | 54 +++++++++++++
|
| + mozilla/security/nss/lib/ssl/ssl3ext.c | 104 ++++++++++++++++++++++++-
|
| + mozilla/security/nss/lib/ssl/ssl3prot.h | 3 +-
|
| + mozilla/security/nss/lib/ssl/sslerr.h | 2 +
|
| + mozilla/security/nss/lib/ssl/sslimpl.h | 21 +++++
|
| + mozilla/security/nss/lib/ssl/sslsock.c | 131 +++++++++++++++++++++++++++++++
|
| + mozilla/security/nss/lib/ssl/sslt.h | 3 +-
|
| + 9 files changed, 372 insertions(+), 3 deletions(-)
|
|
|
| -diff --git a/mozilla/security/nss/cmd/tstclnt/tstclnt.c b/mozilla/security/nss/cmd/tstclnt/tstclnt.c
|
| -index 55684e6..d209a33 100644
|
| ---- a/mozilla/security/nss/cmd/tstclnt/tstclnt.c
|
| -+++ b/mozilla/security/nss/cmd/tstclnt/tstclnt.c
|
| -@@ -868,6 +868,12 @@ int main(int argc, char **argv)
|
| - return 1;
|
| - }
|
| -
|
| -+ rv = SSL_SetNextProtoNego(s, "\004flip\004http1.1", 10);
|
| -+ if (rv != SECSuccess) {
|
| -+ SECU_PrintError(progName, "error enabling next protocol negotiation");
|
| -+ return 1;
|
| -+ }
|
| -+
|
| - /* enable false start. */
|
| - rv = SSL_OptionSet(s, SSL_ENABLE_FALSE_START, enableFalseStart);
|
| - if (rv != SECSuccess) {
|
| diff --git a/mozilla/security/nss/lib/ssl/ssl.def b/mozilla/security/nss/lib/ssl/ssl.def
|
| -index d3f455c..a1f4b51 100644
|
| +index d3f455c..5256ae2 100644
|
| --- a/mozilla/security/nss/lib/ssl/ssl.def
|
| +++ b/mozilla/security/nss/lib/ssl/ssl.def
|
| -@@ -152,3 +152,10 @@ SSL_SNISocketConfigHook;
|
| +@@ -152,3 +152,9 @@ SSL_SNISocketConfigHook;
|
| ;+ local:
|
| ;+*;
|
| ;+};
|
| +;+NSS_CHROMIUM {
|
| +;+ global:
|
| -+SSL_GetNextProto;
|
| -+SSL_SetNextProtoNego;
|
| ++SSL_SetNextProtoCallback;
|
| +;+ local:
|
| +;+*;
|
| +;+};
|
| diff --git a/mozilla/security/nss/lib/ssl/ssl.h b/mozilla/security/nss/lib/ssl/ssl.h
|
| -index 4a9e89d..ffa973c 100644
|
| +index 4a9e89d..2cf777d 100644
|
| --- a/mozilla/security/nss/lib/ssl/ssl.h
|
| +++ b/mozilla/security/nss/lib/ssl/ssl.h
|
| -@@ -153,6 +153,18 @@ SSL_IMPORT SECStatus SSL_OptionSetDefault(PRInt32 option, PRBool on);
|
| +@@ -153,6 +153,57 @@ SSL_IMPORT SECStatus SSL_OptionSetDefault(PRInt32 option, PRBool on);
|
| SSL_IMPORT SECStatus SSL_OptionGetDefault(PRInt32 option, PRBool *on);
|
| SSL_IMPORT SECStatus SSL_CertDBHandleSet(PRFileDesc *fd, CERTCertDBHandle *dbHandle);
|
|
|
| ++/* SSLNextProtoCallback is called, during the handshake, when the server has
|
| ++ * sent a Next Protocol Negotiation extension. |protos| and |protosLen| define
|
| ++ * a buffer which contains the server's advertisement. This data is guaranteed
|
| ++ * to be well formed per the NPN spec. |protoOut| is a buffer provided by the
|
| ++ * caller, of length 255 (the maximum allowed by the protocol).
|
| ++ * On successful return, the protocol to be announced to the server will be in
|
| ++ * |protoOut| and its length in |protoOutLen|. */
|
| ++typedef SECStatus (PR_CALLBACK *SSLNextProtoCallback)(
|
| ++ void *arg,
|
| ++ PRFileDesc *fd,
|
| ++ const unsigned char* protos,
|
| ++ unsigned int protosLen,
|
| ++ unsigned char* protoOut,
|
| ++ unsigned int* protoOutLen);
|
| ++
|
| ++/* SSL_SetNextProtoCallback sets a callback function to handle Next Protocol
|
| ++ * Negotiation. It causes a client to advertise NPN. */
|
| ++SSL_IMPORT SECStatus SSL_SetNextProtoCallback(PRFileDesc *fd,
|
| ++ SSLNextProtoCallback callback,
|
| ++ void *arg);
|
| ++
|
| ++/* SSL_SetNextProtoNego can be used as an alternative to
|
| ++ * SSL_SetNextProtoCallback. It also causes a client to advertise NPN and
|
| ++ * installs a default callback function which selects the first supported
|
| ++ * protocol in server-preference order. If no matching protocol is found it
|
| ++ * selects the first supported protocol.
|
| ++ *
|
| ++ * The supported protocols are specified in |data| in wire-format (8-bit
|
| ++ * length-prefixed). For example: "\010http/1.1\006spdy/2". */
|
| +SSL_IMPORT SECStatus SSL_SetNextProtoNego(PRFileDesc *fd,
|
| + const unsigned char *data,
|
| -+ unsigned short length);
|
| ++ unsigned int length);
|
| ++/* SSL_GetNextProto can be used after a handshake on a socket where
|
| ++ * SSL_SetNextProtoNego was called to retrieve the result of the Next Protocol
|
| ++ * negotiation.
|
| ++ *
|
| ++ * state is set to one of the SSL_NEXT_PROTO_* constants. The negotiated
|
| ++ * protocol, if any, is written into buf, which must be at least buf_len bytes
|
| ++ * long. If the negotiated protocol is longer than this, it is truncated. The
|
| ++ * number of bytes copied is written into *length. */
|
| +SSL_IMPORT SECStatus SSL_GetNextProto(PRFileDesc *fd,
|
| + int *state,
|
| + unsigned char *buf,
|
| -+ unsigned *length,
|
| -+ unsigned buf_len);
|
| ++ unsigned int *length,
|
| ++ unsigned int buf_len);
|
| ++
|
| ++// TODO(wtc): it may be a good idea to define these as an enum type.
|
| +#define SSL_NEXT_PROTO_NO_SUPPORT 0 /* No peer support */
|
| +#define SSL_NEXT_PROTO_NEGOTIATED 1 /* Mutual agreement */
|
| +#define SSL_NEXT_PROTO_NO_OVERLAP 2 /* No protocol overlap found */
|
| @@ -71,7 +92,7 @@ index 4a9e89d..ffa973c 100644
|
| ** Control ciphers that SSL uses. If on is non-zero then the named cipher
|
| ** is enabled, otherwise it is disabled.
|
| diff --git a/mozilla/security/nss/lib/ssl/ssl3con.c b/mozilla/security/nss/lib/ssl/ssl3con.c
|
| -index 8048913..e0cb4e9 100644
|
| +index 8048913..8f860a9 100644
|
| --- a/mozilla/security/nss/lib/ssl/ssl3con.c
|
| +++ b/mozilla/security/nss/lib/ssl/ssl3con.c
|
| @@ -81,6 +81,7 @@ static SECStatus ssl3_InitState( sslSocket *ss);
|
| @@ -107,7 +128,7 @@ index 8048913..e0cb4e9 100644
|
| + int padding_len;
|
| + static const unsigned char padding[32] = {0};
|
| +
|
| -+ if (ss->ssl3.nextProtoState == SSL_NEXT_PROTO_NO_SUPPORT)
|
| ++ if (ss->ssl3.nextProto.len == 0)
|
| + return SECSuccess;
|
| +
|
| + PORT_Assert( ss->opt.noLocks || ssl_HaveXmitBufLock(ss));
|
| @@ -164,7 +185,7 @@ index 8048913..e0cb4e9 100644
|
|
|
| /* End of ssl3con.c */
|
| diff --git a/mozilla/security/nss/lib/ssl/ssl3ext.c b/mozilla/security/nss/lib/ssl/ssl3ext.c
|
| -index becbfe9..fbd5a91 100644
|
| +index becbfe9..36ac4de 100644
|
| --- a/mozilla/security/nss/lib/ssl/ssl3ext.c
|
| +++ b/mozilla/security/nss/lib/ssl/ssl3ext.c
|
| @@ -235,6 +235,7 @@ static const ssl3HelloExtensionHandler clientHelloHandlers[] = {
|
| @@ -193,7 +214,7 @@ index becbfe9..fbd5a91 100644
|
| /* any extra entries will appear as { 0, NULL } */
|
| };
|
|
|
| -@@ -534,6 +537,123 @@ ssl3_SendSessionTicketXtn(
|
| +@@ -534,6 +537,105 @@ ssl3_SendSessionTicketXtn(
|
| return -1;
|
| }
|
|
|
| @@ -206,12 +227,11 @@ index becbfe9..fbd5a91 100644
|
| + return SECFailure;
|
| + }
|
| +
|
| -+ ss->ssl3.hs.nextProtoNego = PR_TRUE;
|
| + return SECSuccess;
|
| +}
|
| +
|
| +/* ssl3_ValidateNextProtoNego checks that the given block of data is valid: none
|
| -+ * of the length may be 0 and the sum of the lengths must equal the length of
|
| ++ * of the lengths may be 0 and the sum of the lengths must equal the length of
|
| + * the block. */
|
| +SECStatus
|
| +ssl3_ValidateNextProtoNego(const unsigned char* data, unsigned short length)
|
| @@ -220,63 +240,46 @@ index becbfe9..fbd5a91 100644
|
| +
|
| + while (offset < length) {
|
| + if (data[offset] == 0) {
|
| ++ PORT_SetError(SSL_ERROR_NEXT_PROTOCOL_DATA_INVALID);
|
| + return SECFailure;
|
| + }
|
| + offset += (unsigned int)data[offset] + 1;
|
| + }
|
| +
|
| -+ if (offset > length)
|
| ++ if (offset > length) {
|
| ++ PORT_SetError(SSL_ERROR_NEXT_PROTOCOL_DATA_INVALID);
|
| + return SECFailure;
|
| ++ }
|
| +
|
| + return SECSuccess;
|
| +}
|
| +
|
| +SECStatus
|
| +ssl3_ClientHandleNextProtoNegoXtn(sslSocket *ss, PRUint16 ex_type,
|
| -+ SECItem *data)
|
| ++ SECItem *data)
|
| +{
|
| -+ unsigned int i, j;
|
| + SECStatus rv;
|
| -+ unsigned char *result;
|
| -+
|
| -+ if (data->len == 0) {
|
| -+ /* The server supports the extension, but doesn't have any
|
| -+ * protocols configured. In this case we request our favoured
|
| -+ * protocol. */
|
| -+ goto pick_first;
|
| -+ }
|
| ++ unsigned char result[255];
|
| ++ unsigned int result_len;
|
| +
|
| + rv = ssl3_ValidateNextProtoNego(data->data, data->len);
|
| + if (rv != SECSuccess)
|
| + return rv;
|
| +
|
| -+ /* For each protocol in server preference order, see if we support it. */
|
| -+ for (i = 0; i < data->len; ) {
|
| -+ for (j = 0; j < ss->opt.nextProtoNego.len; ) {
|
| -+ if (data->data[i] == ss->opt.nextProtoNego.data[j] &&
|
| -+ memcmp(&data->data[i+1], &ss->opt.nextProtoNego.data[j+1],
|
| -+ data->data[i]) == 0) {
|
| -+ /* We found a match */
|
| -+ ss->ssl3.nextProtoState = SSL_NEXT_PROTO_NEGOTIATED;
|
| -+ result = &data->data[i];
|
| -+ goto found;
|
| -+ }
|
| -+ j += (unsigned int)ss->opt.nextProtoNego.data[j] + 1;
|
| -+ }
|
| -+
|
| -+ i += (unsigned int)data->data[i] + 1;
|
| -+ }
|
| -+
|
| -+ pick_first:
|
| -+ ss->ssl3.nextProtoState = SSL_NEXT_PROTO_NO_OVERLAP;
|
| -+ result = ss->opt.nextProtoNego.data;
|
| ++ rv = ss->nextProtoCallback(ss->nextProtoArg, ss->fd,
|
| ++ data->data, data->len,
|
| ++ result, &result_len);
|
| ++ if (rv != SECSuccess)
|
| ++ return rv;
|
| ++ // If the callback wrote more than allowed to |result| it has corrupted our
|
| ++ // stack.
|
| ++ PORT_Assert(result_len <= sizeof(result));
|
| +
|
| -+ found:
|
| + if (ss->ssl3.nextProto.data)
|
| + PORT_Free(ss->ssl3.nextProto.data);
|
| -+ ss->ssl3.nextProto.data = PORT_Alloc(result[0]);
|
| -+ PORT_Memcpy(ss->ssl3.nextProto.data, result + 1, result[0]);
|
| -+ ss->ssl3.nextProto.len = result[0];
|
| ++ ss->ssl3.nextProto.data = PORT_Alloc(result_len);
|
| ++ PORT_Memcpy(ss->ssl3.nextProto.data, result, result_len);
|
| ++ ss->ssl3.nextProto.len = result_len;
|
| + return SECSuccess;
|
| +}
|
| +
|
| @@ -288,7 +291,7 @@ index becbfe9..fbd5a91 100644
|
| + PRInt32 extension_length;
|
| +
|
| + /* Renegotiations do not send this extension. */
|
| -+ if (ss->opt.nextProtoNego.len == 0 || ss->firstHsDone) {
|
| ++ if (!ss->nextProtoCallback || ss->firstHsDone) {
|
| + return 0;
|
| + }
|
| +
|
| @@ -331,48 +334,58 @@ index 4702fcc..f3c950e 100644
|
| } SSL3HandshakeType;
|
|
|
| typedef struct {
|
| +diff --git a/mozilla/security/nss/lib/ssl/sslerr.h b/mozilla/security/nss/lib/ssl/sslerr.h
|
| +index a2f6524..c76ffa9 100644
|
| +--- a/mozilla/security/nss/lib/ssl/sslerr.h
|
| ++++ b/mozilla/security/nss/lib/ssl/sslerr.h
|
| +@@ -203,6 +203,8 @@ SSL_ERROR_RX_UNEXPECTED_UNCOMPRESSED_RECORD = (SSL_ERROR_BASE + 114),
|
| +
|
| + SSL_ERROR_WEAK_SERVER_EPHEMERAL_DH_KEY = (SSL_ERROR_BASE + 115),
|
| +
|
| ++SSL_ERROR_NEXT_PROTOCOL_DATA_INVALID = (SSL_ERROR_BASE + 117),
|
| ++
|
| + SSL_ERROR_END_OF_LIST /* let the c compiler determine the value of this. */
|
| + } SSLErrorCodes;
|
| + #endif /* NO_SECURITY_ERROR_ENUM */
|
| diff --git a/mozilla/security/nss/lib/ssl/sslimpl.h b/mozilla/security/nss/lib/ssl/sslimpl.h
|
| -index 9af471d..d1c1181 100644
|
| +index 9af471d..199c573 100644
|
| --- a/mozilla/security/nss/lib/ssl/sslimpl.h
|
| +++ b/mozilla/security/nss/lib/ssl/sslimpl.h
|
| -@@ -313,6 +313,11 @@ typedef struct {
|
| +@@ -313,6 +313,10 @@ typedef struct {
|
| #endif /* NSS_ENABLE_ECC */
|
|
|
| typedef struct sslOptionsStr {
|
| -+ /* For clients, this is a validated list of protocols in preference order
|
| -+ * and wire format. For servers, this is the list of support protocols,
|
| -+ * also in wire format. */
|
| ++ /* If SSL_SetNextProtoNego has been called, then this contains the
|
| ++ * list of supported protocols. */
|
| + SECItem nextProtoNego;
|
| +
|
| unsigned int useSecurity : 1; /* 1 */
|
| unsigned int useSocks : 1; /* 2 */
|
| unsigned int requestCertificate : 1; /* 3 */
|
| -@@ -786,6 +791,7 @@ const ssl3CipherSuiteDef *suite_def;
|
| - #ifdef NSS_ENABLE_ECC
|
| - PRUint32 negotiatedECCurves; /* bit mask */
|
| - #endif /* NSS_ENABLE_ECC */
|
| -+ PRBool nextProtoNego;/* Our peer has sent this extension */
|
| - } SSL3HandshakeState;
|
| -
|
| -
|
| -@@ -827,6 +833,16 @@ struct ssl3StateStr {
|
| +@@ -827,6 +831,13 @@ struct ssl3StateStr {
|
| PRBool initialized;
|
| SSL3HandshakeState hs;
|
| ssl3CipherSpec specs[2]; /* one is current, one is pending. */
|
| +
|
| + /* In a client: if the server supports Next Protocol Negotiation, then
|
| -+ * this is the protocol that was requested.
|
| -+ * In a server: this is the protocol that the client requested via Next
|
| -+ * Protocol Negotiation.
|
| ++ * this is the protocol that was negotiated.
|
| + *
|
| -+ * In either case, if the data pointer is non-NULL, then it is malloced
|
| -+ * data. */
|
| ++ * If the data pointer is non-NULL, then it is malloced data. */
|
| + SECItem nextProto;
|
| -+ int nextProtoState; /* See SSL_NEXT_PROTO_* defines */
|
| ++ int nextProtoState; /* See NEXT_PROTO_* defines */
|
| };
|
|
|
| typedef struct {
|
| -@@ -1494,8 +1510,12 @@ extern SECStatus ssl3_HandleSupportedPointFormatsXtn(sslSocket * ss,
|
| +@@ -1058,6 +1069,8 @@ const unsigned char * preferredCipher;
|
| + SSLHandshakeCallback handshakeCallback;
|
| + void *handshakeCallbackData;
|
| + void *pkcs11PinArg;
|
| ++ SSLNextProtoCallback nextProtoCallback;
|
| ++ void *nextProtoArg;
|
| +
|
| + PRIntervalTime rTimeout; /* timeout for NSPR I/O */
|
| + PRIntervalTime wTimeout; /* timeout for NSPR I/O */
|
| +@@ -1494,8 +1507,12 @@ extern SECStatus ssl3_HandleSupportedPointFormatsXtn(sslSocket * ss,
|
| PRUint16 ex_type, SECItem *data);
|
| extern SECStatus ssl3_ClientHandleSessionTicketXtn(sslSocket *ss,
|
| PRUint16 ex_type, SECItem *data);
|
| @@ -385,7 +398,7 @@ index 9af471d..d1c1181 100644
|
|
|
| /* ClientHello and ServerHello extension senders.
|
| * Note that not all extension senders are exposed here; only those that
|
| -@@ -1526,6 +1546,10 @@ extern PRInt32 ssl3_SendSupportedCurvesXtn(sslSocket *ss,
|
| +@@ -1526,6 +1543,10 @@ extern PRInt32 ssl3_SendSupportedCurvesXtn(sslSocket *ss,
|
| extern PRInt32 ssl3_SendSupportedPointFormatsXtn(sslSocket *ss,
|
| PRBool append, PRUint32 maxBytes);
|
| #endif
|
| @@ -397,7 +410,7 @@ index 9af471d..d1c1181 100644
|
| /* call the registered extension handlers. */
|
| extern SECStatus ssl3_HandleHelloExtensions(sslSocket *ss,
|
| diff --git a/mozilla/security/nss/lib/ssl/sslsock.c b/mozilla/security/nss/lib/ssl/sslsock.c
|
| -index bc770a1..4c8fbfd 100644
|
| +index bc770a1..769ea0a 100644
|
| --- a/mozilla/security/nss/lib/ssl/sslsock.c
|
| +++ b/mozilla/security/nss/lib/ssl/sslsock.c
|
| @@ -163,6 +163,7 @@ static const sslSocketOps ssl_secure_ops = { /* SSL. */
|
| @@ -419,16 +432,14 @@ index bc770a1..4c8fbfd 100644
|
| PORT_Assert(!ss->xtnData.sniNameArr);
|
| if (ss->xtnData.sniNameArr) {
|
| PORT_Free(ss->xtnData.sniNameArr);
|
| -@@ -1266,6 +1271,75 @@ SSL_ImportFD(PRFileDesc *model, PRFileDesc *fd)
|
| +@@ -1266,6 +1271,132 @@ SSL_ImportFD(PRFileDesc *model, PRFileDesc *fd)
|
| return fd;
|
| }
|
|
|
| -+/* SSL_SetNextProtoNego sets the list of supported protocols for the given
|
| -+ * socket. The list is a series of 8-bit, length prefixed strings. */
|
| +SECStatus
|
| -+SSL_SetNextProtoNego(PRFileDesc *fd, const unsigned char *data,
|
| -+ unsigned short length)
|
| -+{
|
| ++SSL_SetNextProtoCallback(PRFileDesc *fd,
|
| ++ SSLNextProtoCallback callback,
|
| ++ void *arg) {
|
| + sslSocket *ss = ssl_FindSocket(fd);
|
| +
|
| + if (!ss) {
|
| @@ -437,6 +448,74 @@ index bc770a1..4c8fbfd 100644
|
| + return SECFailure;
|
| + }
|
| +
|
| ++ ssl_GetSSL3HandshakeLock(ss);
|
| ++ ss->nextProtoCallback = callback;
|
| ++ ss->nextProtoArg = arg;
|
| ++ ssl_ReleaseSSL3HandshakeLock(ss);
|
| ++}
|
| ++
|
| ++/* NextProtoStandardCallback is set as an NPN callback for the case when the
|
| ++ * user of the sockets wants the standard selection algorithm. */
|
| ++static SECStatus
|
| ++NextProtoStandardCallback(void *arg,
|
| ++ PRFileDesc *fd,
|
| ++ const unsigned char *protos,
|
| ++ unsigned int protos_len,
|
| ++ unsigned char *protoOut,
|
| ++ unsigned int *protoOutLen)
|
| ++{
|
| ++ unsigned int i, j;
|
| ++ const unsigned char *result;
|
| ++
|
| ++ sslSocket *ss = ssl_FindSocket(fd);
|
| ++ PORT_Assert(ss);
|
| ++
|
| ++ if (protos_len == 0) {
|
| ++ /* The server supports the extension, but doesn't have any protocols
|
| ++ * configured. In this case we request our favoured protocol. */
|
| ++ goto pick_first;
|
| ++ }
|
| ++
|
| ++ /* For each protocol in server preference, see if we support it. */
|
| ++ for (i = 0; i < protos_len; ) {
|
| ++ for (j = 0; j < ss->opt.nextProtoNego.len; ) {
|
| ++ if (protos[i] == ss->opt.nextProtoNego.data[j] &&
|
| ++ memcmp(&protos[i+1], &ss->opt.nextProtoNego.data[j+1],
|
| ++ protos[i]) == 0) {
|
| ++ /* We found a match. */
|
| ++ ss->ssl3.nextProtoState = SSL_NEXT_PROTO_NEGOTIATED;
|
| ++ result = &protos[i];
|
| ++ goto found;
|
| ++ }
|
| ++ j += (unsigned int)ss->opt.nextProtoNego.data[j] + 1;
|
| ++ }
|
| ++ i += (unsigned int)protos[i] + 1;
|
| ++ }
|
| ++
|
| ++pick_first:
|
| ++ ss->ssl3.nextProtoState = SSL_NEXT_PROTO_NO_OVERLAP;
|
| ++ result = ss->opt.nextProtoNego.data;
|
| ++
|
| ++found:
|
| ++ memcpy(protoOut, result + 1, result[0]);
|
| ++ *protoOutLen = result[0];
|
| ++ return SECSuccess;
|
| ++}
|
| ++
|
| ++SECStatus
|
| ++SSL_SetNextProtoNego(PRFileDesc *fd, const unsigned char *data,
|
| ++ unsigned int length)
|
| ++{
|
| ++ SECStatus rv;
|
| ++
|
| ++ sslSocket *ss = ssl_FindSocket(fd);
|
| ++
|
| ++ if (!ss) {
|
| ++ SSL_DBG(("%d: SSL[%d]: bad socket in SSL_SetNextProtoNego",
|
| ++ SSL_GETPID(), fd));
|
| ++ return SECFailure;
|
| ++ }
|
| ++
|
| + if (ssl3_ValidateNextProtoNego(data, length) != SECSuccess)
|
| + return SECFailure;
|
| +
|
| @@ -453,18 +532,9 @@ index bc770a1..4c8fbfd 100644
|
| + ss->opt.nextProtoNego.type = siBuffer;
|
| + ssl_ReleaseSSL3HandshakeLock(ss);
|
| +
|
| -+ return SECSuccess;
|
| ++ return SSL_SetNextProtoCallback(fd, NextProtoStandardCallback, NULL);
|
| +}
|
| +
|
| -+/* SSL_GetNextProto reads the resulting Next Protocol Negotiation result for
|
| -+ * the given socket. It's only valid to call this once the handshake has
|
| -+ * completed.
|
| -+ *
|
| -+ * state is set to one of the SSL_NEXT_PROTO_* constants. The negotiated
|
| -+ * protocol, if any, is written into buf, which must be at least buf_len
|
| -+ * bytes long. If the negotiated protocol is longer than this, it is truncated.
|
| -+ * The number of bytes copied is written into length.
|
| -+ */
|
| +SECStatus
|
| +SSL_GetNextProto(PRFileDesc *fd, int *state, unsigned char *buf,
|
| + unsigned int *length, unsigned int buf_len)
|
|
|