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

Unified Diff: net/third_party/nss/ssl/ssl3con.c

Issue 166273026: Implement the encrypt-then-MAC TLS extension. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: Remove nss_ssl_util.cc from the CL Created 6 years, 10 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « net/third_party/nss/ssl/ssl.h ('k') | net/third_party/nss/ssl/ssl3ext.c » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: net/third_party/nss/ssl/ssl3con.c
===================================================================
--- net/third_party/nss/ssl/ssl3con.c (revision 252347)
+++ net/third_party/nss/ssl/ssl3con.c (working copy)
@@ -1384,6 +1384,7 @@
ssl3_CleanupKeyMaterial(&spec->client);
ssl3_CleanupKeyMaterial(&spec->server);
spec->bypassCiphers = PR_FALSE;
+ spec->encryptThenMAC = PR_FALSE;
spec->destroy=NULL;
spec->destroyCompressContext = NULL;
spec->destroyDecompressContext = NULL;
@@ -1469,6 +1470,9 @@
pwSpec->compressContext = NULL;
pwSpec->decompressContext = NULL;
+ pwSpec->encryptThenMAC =
+ ssl3_ExtensionNegotiated(ss, ssl_encrypt_then_mac_xtn);
+
ssl_ReleaseSpecWriteLock(ss); /*******************************/
return SECSuccess;
}
@@ -2732,20 +2736,26 @@
return SECFailure;
}
} else {
- /*
- * Add the MAC
- */
- rv = ssl3_ComputeRecordMAC(cwSpec, isServer,
- pseudoHeader, pseudoHeaderLen, pIn, contentLen,
- wrBuf->buf + headerLen + ivLen + contentLen, &macLen);
- if (rv != SECSuccess) {
- ssl_MapLowLevelError(SSL_ERROR_MAC_COMPUTATION_FAILURE);
- return SECFailure;
+ if (!cwSpec->encryptThenMAC) {
+ /*
+ * Add the MAC
+ */
+ rv = ssl3_ComputeRecordMAC(cwSpec, isServer,
+ pseudoHeader, pseudoHeaderLen, pIn, contentLen,
+ wrBuf->buf + headerLen + ivLen + contentLen, &macLen);
+ if (rv != SECSuccess) {
+ ssl_MapLowLevelError(SSL_ERROR_MAC_COMPUTATION_FAILURE);
+ return SECFailure;
+ }
+ p1Len = contentLen;
+ p2Len = macLen;
+ fragLen = contentLen + macLen; /* needs to be encrypted */
+ PORT_Assert(fragLen <= MAX_FRAGMENT_LENGTH + 1024);
+ } else {
+ p1Len = contentLen;
+ p2Len = 0;
+ fragLen = contentLen; /* needs to be encrypted */
}
- p1Len = contentLen;
- p2Len = macLen;
- fragLen = contentLen + macLen; /* needs to be encrypted */
- PORT_Assert(fragLen <= MAX_FRAGMENT_LENGTH + 1024);
/*
* Pad the text (if we're doing a block cipher)
@@ -2813,6 +2823,29 @@
}
cipherBytes += cipherBytesPart2;
}
+
+ if (cwSpec->encryptThenMAC) {
+ /*
+ * Add the MAC
+ */
+ pseudoHeaderLen = ssl3_BuildRecordPseudoHeader(
+ pseudoHeader, cwSpec->write_seq_num, type,
+ cwSpec->version >= SSL_LIBRARY_VERSION_TLS_1_0, cwSpec->version,
+ isDTLS, cipherBytes /* + crSpec->mac_size */);
+ PORT_Assert(pseudoHeaderLen <= sizeof(pseudoHeader));
+
+ rv = ssl3_ComputeRecordMAC(cwSpec, isServer,
+ pseudoHeader, pseudoHeaderLen,
+ wrBuf->buf + headerLen, cipherBytes,
+ wrBuf->buf + headerLen + cipherBytes, &macLen);
+ if (rv != SECSuccess) {
+ ssl_MapLowLevelError(SSL_ERROR_MAC_COMPUTATION_FAILURE);
+ return SECFailure;
+ }
+ PORT_Assert(macLen == cwSpec->mac_size);
+ cipherBytes += macLen;
+ PORT_Assert(cipherBytes <= MAX_FRAGMENT_LENGTH + 1024);
+ }
}
PORT_Assert(cipherBytes <= MAX_FRAGMENT_LENGTH + 1024);
@@ -9079,7 +9112,7 @@
extensions_len -= 2;
rv = ssl3_AppendHandshakeNumber(ss, extensions_len, 2);
if (rv != SECSuccess)
- return rv; /* err set by ssl3_SetupPendingCipherSpec */
+ return rv; /* err set by AppendHandshake. */
sent_len = ssl3_CallHelloExtensionSenders(ss, PR_TRUE, extensions_len,
&ss->xtnData.serverSenders[0]);
PORT_Assert(sent_len == extensions_len);
@@ -11921,6 +11954,7 @@
rType = content_handshake;
goto process_it;
}
+ rType = cText->type;
ssl_GetSpecReadLock(ss); /******************************************/
@@ -11979,6 +12013,31 @@
goto decrypt_loser;
}
+ if (crSpec->encryptThenMAC) {
+ /* compute the MAC */
+ headerLen = ssl3_BuildRecordPseudoHeader(
+ header, IS_DTLS(ss) ? cText->seq_num : crSpec->read_seq_num,
+ rType, isTLS, cText->version, IS_DTLS(ss),
+ cText->buf->len - crSpec->mac_size);
+ PORT_Assert(headerLen <= sizeof(header));
+ /* This is safe because we checked the minLength above. */
+ cText->buf->len -= crSpec->mac_size;
+
+ rv = ssl3_ComputeRecordMAC(
+ crSpec, (PRBool)(!ss->sec.isServer), header, headerLen,
+ cText->buf->buf, cText->buf->len, hash, &hashBytes);
+
+ /* We can read the MAC directly from the record because its location
+ * is public when a stream cipher is used. */
+ givenHash = cText->buf->buf + cText->buf->len;
+
+ if (hashBytes != (unsigned)crSpec->mac_size ||
+ NSS_SecureMemcmp(givenHash, hash, crSpec->mac_size) != 0) {
+ /* We're allowed to leak whether or not the MAC check was correct */
+ goto decrypt_loser;
+ }
+ }
+
if (cipher_def->type == type_block &&
crSpec->version >= SSL_LIBRARY_VERSION_TLS_1_1) {
/* Consume the per-record explicit IV. RFC 4346 Section 6.2.3.2 states
@@ -12044,7 +12103,6 @@
return SECFailure;
}
- rType = cText->type;
if (cipher_def->type == type_aead) {
/* XXX For many AEAD ciphers, the plaintext is shorter than the
* ciphertext by a fixed byte count, but it is not true in general.
@@ -12090,7 +12148,8 @@
/* If it's a block cipher, check and strip the padding. */
if (cipher_def->type == type_block) {
const unsigned int blockSize = cipher_def->block_size;
- const unsigned int macSize = crSpec->mac_size;
+ const unsigned int macSize =
+ crSpec->encryptThenMAC ? 0 : crSpec->mac_size;
if (!isTLS) {
good &= SECStatusToMask(ssl_RemoveSSLv3CBCPadding(
@@ -12101,6 +12160,7 @@
}
}
+ if (!crSpec->encryptThenMAC) {
/* compute the MAC */
headerLen = ssl3_BuildRecordPseudoHeader(
header, IS_DTLS(ss) ? cText->seq_num : crSpec->read_seq_num,
@@ -12142,6 +12202,7 @@
/* We're allowed to leak whether or not the MAC check was correct */
good = 0;
}
+ }
}
if (good == 0) {
@@ -12317,6 +12378,7 @@
spec->mac_size = 0;
spec->master_secret = NULL;
spec->bypassCiphers = PR_FALSE;
+ spec->encryptThenMAC = PR_FALSE;
spec->msItem.data = NULL;
spec->msItem.len = 0;
« no previous file with comments | « net/third_party/nss/ssl/ssl.h ('k') | net/third_party/nss/ssl/ssl3ext.c » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698