diff mbox series

[v2,07/41] SUNRPC: Obscure Kerberos encryption keys

Message ID 167380326106.10651.3883618931801361872.stgit@bazille.1015granger.net (mailing list archive)
State New, archived
Headers show
Series RPCSEC GSS krb5 enhancements | expand

Commit Message

Chuck Lever Jan. 15, 2023, 5:21 p.m. UTC
From: Chuck Lever <chuck.lever@oracle.com>

The encryption subkeys are not used after the cipher transforms have
been allocated and keyed. There is no need to retain them in struct
krb5_ctx.

Tested-by: Scott Mayhew <smayhew@redhat.com>
Signed-off-by: Chuck Lever <chuck.lever@oracle.com>
---
 include/linux/sunrpc/gss_krb5.h     |    2 --
 net/sunrpc/auth_gss/gss_krb5_mech.c |   43 +++++++++++++++++++++--------------
 2 files changed, 26 insertions(+), 19 deletions(-)
diff mbox series

Patch

diff --git a/include/linux/sunrpc/gss_krb5.h b/include/linux/sunrpc/gss_krb5.h
index 34d54714c6a3..46eaa2ee9c21 100644
--- a/include/linux/sunrpc/gss_krb5.h
+++ b/include/linux/sunrpc/gss_krb5.h
@@ -110,8 +110,6 @@  struct krb5_ctx {
 	struct xdr_netobj	mech_used;
 	u8			initiator_sign[GSS_KRB5_MAX_KEYLEN];
 	u8			acceptor_sign[GSS_KRB5_MAX_KEYLEN];
-	u8			initiator_seal[GSS_KRB5_MAX_KEYLEN];
-	u8			acceptor_seal[GSS_KRB5_MAX_KEYLEN];
 	u8			initiator_integ[GSS_KRB5_MAX_KEYLEN];
 	u8			acceptor_integ[GSS_KRB5_MAX_KEYLEN];
 };
diff --git a/net/sunrpc/auth_gss/gss_krb5_mech.c b/net/sunrpc/auth_gss/gss_krb5_mech.c
index afa6a692ccdd..8bc24c0684cb 100644
--- a/net/sunrpc/auth_gss/gss_krb5_mech.c
+++ b/net/sunrpc/auth_gss/gss_krb5_mech.c
@@ -350,42 +350,49 @@  context_derive_keys_des3(struct krb5_ctx *ctx, gfp_t gfp_mask)
 static int
 context_derive_keys_new(struct krb5_ctx *ctx, gfp_t gfp_mask)
 {
-	struct xdr_netobj c, keyin, keyout;
 	u8 cdata[GSS_KRB5_K5CLENGTH];
+	struct xdr_netobj c = {
+		.len	= sizeof(cdata),
+		.data	= cdata,
+	};
+	struct xdr_netobj keyin = {
+		.len	= ctx->gk5e->keylength,
+		.data	= ctx->Ksess,
+	};
+	struct xdr_netobj keyout;
+	int ret = -EINVAL;
+	void *subkey;
 	u32 err;
 
-	c.len = GSS_KRB5_K5CLENGTH;
-	c.data = cdata;
-
-	keyin.data = ctx->Ksess;
-	keyin.len = ctx->gk5e->keylength;
+	subkey = kmalloc(ctx->gk5e->keylength, gfp_mask);
+	if (!subkey)
+		return -ENOMEM;
 	keyout.len = ctx->gk5e->keylength;
+	keyout.data = subkey;
 
 	/* initiator seal encryption */
 	set_cdata(cdata, KG_USAGE_INITIATOR_SEAL, KEY_USAGE_SEED_ENCRYPTION);
-	keyout.data = ctx->initiator_seal;
 	err = krb5_derive_key(ctx->gk5e, &keyin, &keyout, &c, gfp_mask);
 	if (err) {
 		dprintk("%s: Error %d deriving initiator_seal key\n",
 			__func__, err);
-		goto out_err;
+		goto out;
 	}
 	ctx->initiator_enc = context_v2_alloc_cipher(ctx,
 						     ctx->gk5e->encrypt_name,
-						     ctx->initiator_seal);
+						     subkey);
 	if (ctx->initiator_enc == NULL)
-		goto out_err;
+		goto out;
 	if (ctx->gk5e->aux_cipher) {
 		ctx->initiator_enc_aux =
 			context_v2_alloc_cipher(ctx, ctx->gk5e->aux_cipher,
-						ctx->initiator_seal);
+						subkey);
 		if (ctx->initiator_enc_aux == NULL)
 			goto out_free;
 	}
 
 	/* acceptor seal encryption */
 	set_cdata(cdata, KG_USAGE_ACCEPTOR_SEAL, KEY_USAGE_SEED_ENCRYPTION);
-	keyout.data = ctx->acceptor_seal;
 	err = krb5_derive_key(ctx->gk5e, &keyin, &keyout, &c, gfp_mask);
 	if (err) {
 		dprintk("%s: Error %d deriving acceptor_seal key\n",
@@ -394,13 +401,13 @@  context_derive_keys_new(struct krb5_ctx *ctx, gfp_t gfp_mask)
 	}
 	ctx->acceptor_enc = context_v2_alloc_cipher(ctx,
 						    ctx->gk5e->encrypt_name,
-						    ctx->acceptor_seal);
+						    subkey);
 	if (ctx->acceptor_enc == NULL)
 		goto out_free;
 	if (ctx->gk5e->aux_cipher) {
 		ctx->acceptor_enc_aux =
 			context_v2_alloc_cipher(ctx, ctx->gk5e->aux_cipher,
-						ctx->acceptor_seal);
+						subkey);
 		if (ctx->acceptor_enc_aux == NULL)
 			goto out_free;
 	}
@@ -445,15 +452,17 @@  context_derive_keys_new(struct krb5_ctx *ctx, gfp_t gfp_mask)
 		goto out_free;
 	}
 
-	return 0;
+	ret = 0;
+out:
+	kfree_sensitive(subkey);
+	return ret;
 
 out_free:
 	crypto_free_sync_skcipher(ctx->acceptor_enc_aux);
 	crypto_free_sync_skcipher(ctx->acceptor_enc);
 	crypto_free_sync_skcipher(ctx->initiator_enc_aux);
 	crypto_free_sync_skcipher(ctx->initiator_enc);
-out_err:
-	return -EINVAL;
+	goto out;
 }
 
 static int