Index: net/third_party/nss/patches/secret_exporter2.patch |
=================================================================== |
--- net/third_party/nss/patches/secret_exporter2.patch (revision 0) |
+++ net/third_party/nss/patches/secret_exporter2.patch (revision 0) |
@@ -0,0 +1,228 @@ |
+Index: net/third_party/nss/ssl/ssl.h |
+=================================================================== |
+--- net/third_party/nss/ssl/ssl.h (revision 125777) |
++++ net/third_party/nss/ssl/ssl.h (working copy) |
+@@ -792,12 +792,14 @@ |
+ |
+ /* Export keying material according to RFC 5705. |
+ ** fd must correspond to a TLS 1.0 or higher socket and out must |
+-** already be allocated. If contextLen is zero it uses the no-context |
+-** construction from the RFC. |
++** already be allocated. If hasContext is false, it uses the no-context |
++** construction from the RFC and ignores the context and contextLen |
++** arguments. |
+ */ |
+ SSL_IMPORT SECStatus SSL_ExportKeyingMaterial(PRFileDesc *fd, |
+ const char *label, |
+ unsigned int labelLen, |
++ PRBool hasContext, |
+ const unsigned char *context, |
+ unsigned int contextLen, |
+ unsigned char *out, |
+Index: net/third_party/nss/ssl/sslinfo.c |
+=================================================================== |
+--- net/third_party/nss/ssl/sslinfo.c (revision 125777) |
++++ net/third_party/nss/ssl/sslinfo.c (working copy) |
+@@ -317,18 +317,12 @@ |
+ return PR_FALSE; |
+ } |
+ |
+-/* Export keying material according to RFC 5705. |
+-** fd must correspond to a TLS 1.0 or higher socket, out must |
+-** be already allocated. |
+-*/ |
+ SECStatus |
+ SSL_ExportKeyingMaterial(PRFileDesc *fd, |
+- const char *label, |
+- unsigned int labelLen, |
+- const unsigned char *context, |
+- unsigned int contextLen, |
+- unsigned char *out, |
+- unsigned int outLen) |
++ const char *label, unsigned int labelLen, |
++ PRBool hasContext, |
++ const unsigned char *context, unsigned int contextLen, |
++ unsigned char *out, unsigned int outLen) |
+ { |
+ sslSocket *ss; |
+ unsigned char *val = NULL; |
+@@ -347,18 +341,21 @@ |
+ return SECFailure; |
+ } |
+ |
++ /* construct PRF arguments */ |
+ valLen = SSL3_RANDOM_LENGTH * 2; |
+- if (contextLen > 0) |
++ if (hasContext) { |
+ valLen += 2 /* uint16 length */ + contextLen; |
++ } |
+ val = PORT_Alloc(valLen); |
+- if (val == NULL) |
++ if (!val) { |
+ return SECFailure; |
++ } |
+ i = 0; |
+ PORT_Memcpy(val + i, &ss->ssl3.hs.client_random.rand, SSL3_RANDOM_LENGTH); |
+ i += SSL3_RANDOM_LENGTH; |
+ PORT_Memcpy(val + i, &ss->ssl3.hs.server_random.rand, SSL3_RANDOM_LENGTH); |
+ i += SSL3_RANDOM_LENGTH; |
+- if (contextLen > 0) { |
++ if (hasContext) { |
+ val[i++] = contextLen >> 8; |
+ val[i++] = contextLen; |
+ PORT_Memcpy(val + i, context, contextLen); |
+@@ -366,6 +363,9 @@ |
+ } |
+ PORT_Assert(i == valLen); |
+ |
++ /* Allow TLS keying material to be exported sooner, when the master |
++ * secret is available and we have sent ChangeCipherSpec. |
++ */ |
+ ssl_GetSpecReadLock(ss); |
+ if (!ss->ssl3.cwSpec->master_secret && !ss->ssl3.cwSpec->msItem.len) { |
+ PORT_SetError(SSL_ERROR_HANDSHAKE_NOT_COMPLETED); |
+Index: net/third_party/nss/ssl/sslimpl.h |
+=================================================================== |
+--- net/third_party/nss/ssl/sslimpl.h (revision 125777) |
++++ net/third_party/nss/ssl/sslimpl.h (working copy) |
+@@ -1715,11 +1715,11 @@ |
+ SECStatus SSL_DisableExportCipherSuites(PRFileDesc * fd); |
+ PRBool SSL_IsExportCipherSuite(PRUint16 cipherSuite); |
+ |
+-SECStatus ssl3_TLSPRFWithMasterSecret( |
+- ssl3CipherSpec *spec, const char *label, |
+- unsigned int labelLen, const unsigned char *val, |
+- unsigned int valLen, unsigned char *out, |
+- unsigned int outLen); |
++extern SECStatus |
++ssl3_TLSPRFWithMasterSecret(ssl3CipherSpec *spec, |
++ const char *label, unsigned int labelLen, |
++ const unsigned char *val, unsigned int valLen, |
++ unsigned char *out, unsigned int outLen); |
+ |
+ #ifdef TRACE |
+ #define SSL_TRACE(msg) ssl_Trace msg |
+Index: net/third_party/nss/ssl/ssl3ext.c |
+=================================================================== |
+--- net/third_party/nss/ssl/ssl3ext.c (revision 125777) |
++++ net/third_party/nss/ssl/ssl3ext.c (working copy) |
+@@ -606,10 +606,7 @@ |
+ unsigned char resultBuffer[255]; |
+ SECItem result = { siBuffer, resultBuffer, 0 }; |
+ |
+- if (ss->firstHsDone) { |
+- PORT_SetError(SSL_ERROR_NEXT_PROTOCOL_DATA_INVALID); |
+- return SECFailure; |
+- } |
++ PORT_Assert(!ss->firstHsDone); |
+ |
+ rv = ssl3_ValidateNextProtoNego(data->data, data->len); |
+ if (rv != SECSuccess) |
+@@ -621,6 +618,8 @@ |
+ */ |
+ PORT_Assert(ss->nextProtoCallback != NULL); |
+ if (!ss->nextProtoCallback) { |
++ /* XXX Use a better error code. This is an application error, not an |
++ * NSS bug. */ |
+ PORT_SetError(SEC_ERROR_LIBRARY_FAILURE); |
+ return SECFailure; |
+ } |
+@@ -631,7 +630,7 @@ |
+ return rv; |
+ /* If the callback wrote more than allowed to |result| it has corrupted our |
+ * stack. */ |
+- if (result.len > sizeof result) { |
++ if (result.len > sizeof resultBuffer) { |
+ PORT_SetError(SEC_ERROR_OUTPUT_LEN); |
+ return SECFailure; |
+ } |
+Index: net/third_party/nss/ssl/sslsock.c |
+=================================================================== |
+--- net/third_party/nss/ssl/sslsock.c (revision 125777) |
++++ net/third_party/nss/ssl/sslsock.c (working copy) |
+@@ -1344,7 +1344,7 @@ |
+ return SECSuccess; |
+ } |
+ |
+-/* NextProtoStandardCallback is set as an NPN callback for the case when |
++/* ssl_NextProtoNegoCallback is set as an NPN callback for the case when |
+ * SSL_SetNextProtoNego is used. |
+ */ |
+ static SECStatus |
+@@ -1390,12 +1390,12 @@ |
+ result = ss->opt.nextProtoNego.data; |
+ |
+ found: |
+- *protoOutLen = result[0]; |
+ if (protoMaxLen < result[0]) { |
+ PORT_SetError(SEC_ERROR_OUTPUT_LEN); |
+ return SECFailure; |
+ } |
+ memcpy(protoOut, result + 1, result[0]); |
++ *protoOutLen = result[0]; |
+ return SECSuccess; |
+ } |
+ |
+@@ -1449,13 +1449,12 @@ |
+ |
+ if (ss->ssl3.nextProtoState != SSL_NEXT_PROTO_NO_SUPPORT && |
+ ss->ssl3.nextProto.data) { |
+- *bufLen = ss->ssl3.nextProto.len; |
+- if (*bufLen > bufLenMax) { |
++ if (ss->ssl3.nextProto.len > bufLenMax) { |
+ PORT_SetError(SEC_ERROR_OUTPUT_LEN); |
+- *bufLen = 0; |
+ return SECFailure; |
+ } |
+ PORT_Memcpy(buf, ss->ssl3.nextProto.data, ss->ssl3.nextProto.len); |
++ *bufLen = ss->ssl3.nextProto.len; |
+ } else { |
+ *bufLen = 0; |
+ } |
+Index: net/third_party/nss/ssl/ssl3con.c |
+=================================================================== |
+--- net/third_party/nss/ssl/ssl3con.c (revision 125777) |
++++ net/third_party/nss/ssl/ssl3con.c (working copy) |
+@@ -8484,9 +8484,9 @@ |
+ return rv; |
+ } |
+ |
+-/* The calling function must acquire and release the appropriate lock (i.e., |
+- * ssl_GetSpecReadLock / ssl_ReleaseSpecReadLock for ss->ssl3.crSpec). Any |
+- * label must already be concatenated onto the beginning of val. |
++/* The calling function must acquire and release the appropriate |
++ * lock (e.g., ssl_GetSpecReadLock / ssl_ReleaseSpecReadLock for |
++ * ss->ssl3.crSpec). |
+ */ |
+ SECStatus |
+ ssl3_TLSPRFWithMasterSecret(ssl3CipherSpec *spec, const char *label, |
+@@ -8508,8 +8508,7 @@ |
+ rv = PK11_DigestBegin(prf_context); |
+ rv |= PK11_DigestOp(prf_context, (unsigned char *) label, labelLen); |
+ rv |= PK11_DigestOp(prf_context, val, valLen); |
+- rv |= PK11_DigestFinal(prf_context, out, |
+- &retLen, outLen); |
++ rv |= PK11_DigestFinal(prf_context, out, &retLen, outLen); |
+ PORT_Assert(rv != SECSuccess || retLen == outLen); |
+ |
+ PK11_DestroyContext(prf_context, PR_TRUE); |
+@@ -8532,15 +8531,15 @@ |
+ static SECStatus |
+ ssl3_ComputeTLSFinished(ssl3CipherSpec *spec, |
+ PRBool isServer, |
+- const SSL3Finished * hashes, |
+- TLSFinished * tlsFinished) |
++ const SSL3Finished * hashes, |
++ TLSFinished * tlsFinished) |
+ { |
+ const char * label; |
+- SECStatus rv; |
+ unsigned int len; |
++ SECStatus rv; |
+ |
+ label = isServer ? "server finished" : "client finished"; |
+- len = 15; |
++ len = 15; |
+ |
+ rv = ssl3_TLSPRFWithMasterSecret(spec, label, len, hashes->md5, |
+ sizeof *hashes, tlsFinished->verify_data, |