Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

crypto: authenc - Export key parsing helper function

AEAD key parsing is duplicated to multiple places in the kernel. Add a
common helper function to consolidate that functionality.

Cc: Herbert Xu <herbert@gondor.apana.org.au>
Cc: "David S. Miller" <davem@davemloft.net>
Signed-off-by: Mathias Krause <mathias.krause@secunet.com>
Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

authored by

Mathias Krause and committed by
Herbert Xu
bc6e2bdb 6d3aab4e

+41 -19
+30 -18
crypto/authenc.c
··· 52 52 aead_request_complete(req, err); 53 53 } 54 54 55 - static int crypto_authenc_setkey(struct crypto_aead *authenc, const u8 *key, 56 - unsigned int keylen) 55 + int crypto_authenc_extractkeys(struct crypto_authenc_keys *keys, const u8 *key, 56 + unsigned int keylen) 57 57 { 58 - unsigned int authkeylen; 59 - unsigned int enckeylen; 60 - struct crypto_authenc_ctx *ctx = crypto_aead_ctx(authenc); 61 - struct crypto_ahash *auth = ctx->auth; 62 - struct crypto_ablkcipher *enc = ctx->enc; 63 - struct rtattr *rta = (void *)key; 58 + struct rtattr *rta = (struct rtattr *)key; 64 59 struct crypto_authenc_key_param *param; 65 - int err = -EINVAL; 66 60 67 61 if (!RTA_OK(rta, keylen)) 68 - goto badkey; 62 + return -EINVAL; 69 63 if (rta->rta_type != CRYPTO_AUTHENC_KEYA_PARAM) 70 - goto badkey; 64 + return -EINVAL; 71 65 if (RTA_PAYLOAD(rta) < sizeof(*param)) 72 - goto badkey; 66 + return -EINVAL; 73 67 74 68 param = RTA_DATA(rta); 75 - enckeylen = be32_to_cpu(param->enckeylen); 69 + keys->enckeylen = be32_to_cpu(param->enckeylen); 76 70 77 71 key += RTA_ALIGN(rta->rta_len); 78 72 keylen -= RTA_ALIGN(rta->rta_len); 79 73 80 - if (keylen < enckeylen) 81 - goto badkey; 74 + if (keylen < keys->enckeylen) 75 + return -EINVAL; 82 76 83 - authkeylen = keylen - enckeylen; 77 + keys->authkeylen = keylen - keys->enckeylen; 78 + keys->authkey = key; 79 + keys->enckey = key + keys->authkeylen; 80 + 81 + return 0; 82 + } 83 + EXPORT_SYMBOL_GPL(crypto_authenc_extractkeys); 84 + 85 + static int crypto_authenc_setkey(struct crypto_aead *authenc, const u8 *key, 86 + unsigned int keylen) 87 + { 88 + struct crypto_authenc_ctx *ctx = crypto_aead_ctx(authenc); 89 + struct crypto_ahash *auth = ctx->auth; 90 + struct crypto_ablkcipher *enc = ctx->enc; 91 + struct crypto_authenc_keys keys; 92 + int err = -EINVAL; 93 + 94 + if (crypto_authenc_extractkeys(&keys, key, keylen) != 0) 95 + goto badkey; 84 96 85 97 crypto_ahash_clear_flags(auth, CRYPTO_TFM_REQ_MASK); 86 98 crypto_ahash_set_flags(auth, crypto_aead_get_flags(authenc) & 87 99 CRYPTO_TFM_REQ_MASK); 88 - err = crypto_ahash_setkey(auth, key, authkeylen); 100 + err = crypto_ahash_setkey(auth, keys.authkey, keys.authkeylen); 89 101 crypto_aead_set_flags(authenc, crypto_ahash_get_flags(auth) & 90 102 CRYPTO_TFM_RES_MASK); 91 103 ··· 107 95 crypto_ablkcipher_clear_flags(enc, CRYPTO_TFM_REQ_MASK); 108 96 crypto_ablkcipher_set_flags(enc, crypto_aead_get_flags(authenc) & 109 97 CRYPTO_TFM_REQ_MASK); 110 - err = crypto_ablkcipher_setkey(enc, key + authkeylen, enckeylen); 98 + err = crypto_ablkcipher_setkey(enc, keys.enckey, keys.enckeylen); 111 99 crypto_aead_set_flags(authenc, crypto_ablkcipher_get_flags(enc) & 112 100 CRYPTO_TFM_RES_MASK); 113 101
+11 -1
include/crypto/authenc.h
··· 23 23 __be32 enckeylen; 24 24 }; 25 25 26 - #endif /* _CRYPTO_AUTHENC_H */ 26 + struct crypto_authenc_keys { 27 + const u8 *authkey; 28 + const u8 *enckey; 27 29 30 + unsigned int authkeylen; 31 + unsigned int enckeylen; 32 + }; 33 + 34 + int crypto_authenc_extractkeys(struct crypto_authenc_keys *keys, const u8 *key, 35 + unsigned int keylen); 36 + 37 + #endif /* _CRYPTO_AUTHENC_H */