Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 3 Jun 2020 22:11:06 +0000 (UTC)
From:      John Baldwin <jhb@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r361773 - in head/sys: dev/cxgbe/crypto opencrypto
Message-ID:  <202006032211.053MB6QM027140@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: jhb
Date: Wed Jun  3 22:11:05 2020
New Revision: 361773
URL: https://svnweb.freebsd.org/changeset/base/361773

Log:
  Add explicit bzero's of sensitive data in software crypto consumers.
  
  Explicitly zero IVs, block buffers, and hashes/digests.
  
  Reviewed by:	delphij
  Sponsored by:	Netflix
  Differential Revision:	https://reviews.freebsd.org/D25057

Modified:
  head/sys/dev/cxgbe/crypto/t4_crypto.c
  head/sys/opencrypto/cryptosoft.c

Modified: head/sys/dev/cxgbe/crypto/t4_crypto.c
==============================================================================
--- head/sys/dev/cxgbe/crypto/t4_crypto.c	Wed Jun  3 21:22:14 2020	(r361772)
+++ head/sys/dev/cxgbe/crypto/t4_crypto.c	Wed Jun  3 22:11:05 2020	(r361773)
@@ -1495,11 +1495,15 @@ ccr_gcm_soft(struct ccr_session *s, struct cryptop *cr
 			}
 		} else
 			error = EBADMSG;
+		explicit_bzero(digest2, sizeof(digest2));
 	}
 
 out:
 	zfree(kschedule, M_CCR);
 	zfree(auth_ctx, M_CCR);
+	explicit_bzero(block, sizeof(block));
+	explicit_bzero(iv, sizeof(iv));
+	explicit_bzero(digest, sizeof(digest));
 	crp->crp_etype = error;
 	crypto_done(crp);
 }
@@ -1953,11 +1957,15 @@ ccr_ccm_soft(struct ccr_session *s, struct cryptop *cr
 			}
 		} else
 			error = EBADMSG;
+		explicit_bzero(digest2, sizeof(digest2));
 	}
 
 out:
 	zfree(kschedule, M_CCR);
 	zfree(auth_ctx, M_CCR);
+	explicit_bzero(block, sizeof(block));
+	explicit_bzero(iv, sizeof(iv));
+	explicit_bzero(digest, sizeof(digest));
 	crp->crp_etype = error;
 	crypto_done(crp);
 }

Modified: head/sys/opencrypto/cryptosoft.c
==============================================================================
--- head/sys/opencrypto/cryptosoft.c	Wed Jun  3 21:22:14 2020	(r361772)
+++ head/sys/opencrypto/cryptosoft.c	Wed Jun  3 22:11:05 2020	(r361773)
@@ -131,8 +131,6 @@ swcr_encdec(struct swcr_session *ses, struct cryptop *
 	    (crp->crp_flags & CRYPTO_F_IV_SEPARATE) == 0)
 		return (EINVAL);
 
-	crypto_read_iv(crp, iv);
-
 	if (crp->crp_cipher_key != NULL) {
 		csp = crypto_get_params(crp->crp_session);
 		error = exf->setkey(sw->sw_kschedule,
@@ -141,6 +139,8 @@ swcr_encdec(struct swcr_session *ses, struct cryptop *
 			return (error);
 	}
 
+	crypto_read_iv(crp, iv);
+
 	if (exf->reinit) {
 		/*
 		 * xforms that provide a reinit method perform all IV
@@ -277,6 +277,9 @@ swcr_encdec(struct swcr_session *ses, struct cryptop *
 			crypto_cursor_copyback(&cc_out, resid, blk);
 	}
 
+	explicit_bzero(blk, sizeof(blk));
+	explicit_bzero(iv, sizeof(iv));
+	explicit_bzero(iv2, sizeof(iv2));
 	return (0);
 }
 
@@ -314,7 +317,6 @@ static int
 swcr_authcompute(struct swcr_session *ses, struct cryptop *crp)
 {
 	u_char aalg[HASH_MAX_LEN];
-	u_char uaalg[HASH_MAX_LEN];
 	const struct crypto_session_params *csp;
 	struct swcr_auth *sw;
 	struct auth_hash *axf;
@@ -383,14 +385,18 @@ swcr_authcompute(struct swcr_session *ses, struct cryp
 	}
 
 	if (crp->crp_op & CRYPTO_OP_VERIFY_DIGEST) {
+		u_char uaalg[HASH_MAX_LEN];
+
 		crypto_copydata(crp, crp->crp_digest_start, sw->sw_mlen, uaalg);
 		if (timingsafe_bcmp(aalg, uaalg, sw->sw_mlen) != 0)
-			return (EBADMSG);
+			err = EBADMSG;
+		explicit_bzero(uaalg, sizeof(uaalg));
 	} else {
 		/* Inject the authentication data */
 		crypto_copyback(crp, crp->crp_digest_start, sw->sw_mlen, aalg);
 	}
-	return (0);
+	explicit_bzero(aalg, sizeof(aalg));
+	return (err);
 }
 
 CTASSERT(INT_MAX <= (1ll<<39) - 256);	/* GCM: plain text < 2^39-256 */
@@ -402,14 +408,13 @@ swcr_gmac(struct swcr_session *ses, struct cryptop *cr
 	uint32_t blkbuf[howmany(EALG_MAX_BLOCK_LEN, sizeof(uint32_t))];
 	u_char *blk = (u_char *)blkbuf;
 	u_char aalg[AALG_MAX_RESULT_LEN];
-	u_char uaalg[AALG_MAX_RESULT_LEN];
 	u_char iv[EALG_MAX_BLOCK_LEN];
 	struct crypto_buffer_cursor cc;
 	union authctx ctx;
 	struct swcr_auth *swa;
 	struct auth_hash *axf;
 	uint32_t *blkp;
-	int blksz, ivlen, len, resid;
+	int blksz, error, ivlen, len, resid;
 
 	swa = &ses->swcr_auth;
 	axf = swa->sw_axf;
@@ -440,16 +445,23 @@ swcr_gmac(struct swcr_session *ses, struct cryptop *cr
 	/* Finalize MAC */
 	axf->Final(aalg, &ctx);
 
+	error = 0;
 	if (crp->crp_op & CRYPTO_OP_VERIFY_DIGEST) {
+		u_char uaalg[AALG_MAX_RESULT_LEN];
+
 		crypto_copydata(crp, crp->crp_digest_start, swa->sw_mlen,
 		    uaalg);
 		if (timingsafe_bcmp(aalg, uaalg, swa->sw_mlen) != 0)
-			return (EBADMSG);
+			error = EBADMSG;
+		explicit_bzero(uaalg, sizeof(uaalg));
 	} else {
 		/* Inject the authentication data */
 		crypto_copyback(crp, crp->crp_digest_start, swa->sw_mlen, aalg);
 	}
-	return (0);
+	explicit_bzero(blkbuf, sizeof(blkbuf));
+	explicit_bzero(aalg, sizeof(aalg));
+	explicit_bzero(iv, sizeof(iv));
+	return (error);
 }
 
 static int
@@ -458,7 +470,6 @@ swcr_gcm(struct swcr_session *ses, struct cryptop *crp
 	uint32_t blkbuf[howmany(EALG_MAX_BLOCK_LEN, sizeof(uint32_t))];
 	u_char *blk = (u_char *)blkbuf;
 	u_char aalg[AALG_MAX_RESULT_LEN];
-	u_char uaalg[AALG_MAX_RESULT_LEN];
 	u_char iv[EALG_MAX_BLOCK_LEN];
 	struct crypto_buffer_cursor cc_in, cc_out;
 	union authctx ctx;
@@ -467,7 +478,7 @@ swcr_gcm(struct swcr_session *ses, struct cryptop *crp
 	struct auth_hash *axf;
 	struct enc_xform *exf;
 	uint32_t *blkp;
-	int blksz, ivlen, len, r, resid;
+	int blksz, error, ivlen, len, r, resid;
 
 	swa = &ses->swcr_auth;
 	axf = swa->sw_axf;
@@ -536,13 +547,19 @@ swcr_gcm(struct swcr_session *ses, struct cryptop *crp
 	axf->Final(aalg, &ctx);
 
 	/* Validate tag */
+	error = 0;
 	if (!CRYPTO_OP_IS_ENCRYPT(crp->crp_op)) {
+		u_char uaalg[AALG_MAX_RESULT_LEN];
+
 		crypto_copydata(crp, crp->crp_digest_start, swa->sw_mlen,
 		    uaalg);
 
 		r = timingsafe_bcmp(aalg, uaalg, swa->sw_mlen);
-		if (r != 0)
-			return (EBADMSG);
+		explicit_bzero(uaalg, sizeof(uaalg));
+		if (r != 0) {
+			error = EBADMSG;
+			goto out;
+		}
 		
 		/* tag matches, decrypt data */
 		crypto_cursor_init(&cc_in, &crp->crp_buf);
@@ -562,7 +579,12 @@ swcr_gcm(struct swcr_session *ses, struct cryptop *crp
 		    aalg);
 	}
 
-	return (0);
+out:
+	explicit_bzero(blkbuf, sizeof(blkbuf));
+	explicit_bzero(aalg, sizeof(aalg));
+	explicit_bzero(iv, sizeof(iv));
+
+	return (error);
 }
 
 static int
@@ -571,13 +593,12 @@ swcr_ccm_cbc_mac(struct swcr_session *ses, struct cryp
 	uint32_t blkbuf[howmany(EALG_MAX_BLOCK_LEN, sizeof(uint32_t))];
 	u_char *blk = (u_char *)blkbuf;
 	u_char aalg[AALG_MAX_RESULT_LEN];
-	u_char uaalg[AALG_MAX_RESULT_LEN];
 	u_char iv[EALG_MAX_BLOCK_LEN];
 	struct crypto_buffer_cursor cc;
 	union authctx ctx;
 	struct swcr_auth *swa;
 	struct auth_hash *axf;
-	int blksz, ivlen, len, resid;
+	int blksz, error, ivlen, len, resid;
 
 	swa = &ses->swcr_auth;
 	axf = swa->sw_axf;
@@ -609,16 +630,23 @@ swcr_ccm_cbc_mac(struct swcr_session *ses, struct cryp
 	/* Finalize MAC */
 	axf->Final(aalg, &ctx);
 
+	error = 0;
 	if (crp->crp_op & CRYPTO_OP_VERIFY_DIGEST) {
+		u_char uaalg[AALG_MAX_RESULT_LEN];
+
 		crypto_copydata(crp, crp->crp_digest_start, swa->sw_mlen,
 		    uaalg);
 		if (timingsafe_bcmp(aalg, uaalg, swa->sw_mlen) != 0)
-			return (EBADMSG);
+			error = EBADMSG;
+		explicit_bzero(uaalg, sizeof(uaalg));
 	} else {
 		/* Inject the authentication data */
 		crypto_copyback(crp, crp->crp_digest_start, swa->sw_mlen, aalg);
 	}
-	return (0);
+	explicit_bzero(blkbuf, sizeof(blkbuf));
+	explicit_bzero(aalg, sizeof(aalg));
+	explicit_bzero(iv, sizeof(iv));
+	return (error);
 }
 
 static int
@@ -627,7 +655,6 @@ swcr_ccm(struct swcr_session *ses, struct cryptop *crp
 	uint32_t blkbuf[howmany(EALG_MAX_BLOCK_LEN, sizeof(uint32_t))];
 	u_char *blk = (u_char *)blkbuf;
 	u_char aalg[AALG_MAX_RESULT_LEN];
-	u_char uaalg[AALG_MAX_RESULT_LEN];
 	u_char iv[EALG_MAX_BLOCK_LEN];
 	struct crypto_buffer_cursor cc_in, cc_out;
 	union authctx ctx;
@@ -635,7 +662,7 @@ swcr_ccm(struct swcr_session *ses, struct cryptop *crp
 	struct swcr_encdec *swe;
 	struct auth_hash *axf;
 	struct enc_xform *exf;
-	int blksz, ivlen, len, r, resid;
+	int blksz, error, ivlen, len, r, resid;
 
 	swa = &ses->swcr_auth;
 	axf = swa->sw_axf;
@@ -712,13 +739,19 @@ swcr_ccm(struct swcr_session *ses, struct cryptop *crp
 	axf->Final(aalg, &ctx);
 
 	/* Validate tag */
+	error = 0;
 	if (!CRYPTO_OP_IS_ENCRYPT(crp->crp_op)) {
+		u_char uaalg[AALG_MAX_RESULT_LEN];
+
 		crypto_copydata(crp, crp->crp_digest_start, swa->sw_mlen,
 		    uaalg);
 
 		r = timingsafe_bcmp(aalg, uaalg, swa->sw_mlen);
-		if (r != 0)
-			return (EBADMSG);
+		explicit_bzero(uaalg, sizeof(uaalg));
+		if (r != 0) {
+			error = EBADMSG;
+			goto out;
+		}
 		
 		/* tag matches, decrypt data */
 		exf->reinit(swe->sw_kschedule, iv);
@@ -739,7 +772,11 @@ swcr_ccm(struct swcr_session *ses, struct cryptop *crp
 		    aalg);
 	}
 
-	return (0);
+out:
+	explicit_bzero(blkbuf, sizeof(blkbuf));
+	explicit_bzero(aalg, sizeof(aalg));
+	explicit_bzero(iv, sizeof(iv));
+	return (error);
 }
 
 /*



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202006032211.053MB6QM027140>