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

Configure Feed

Select the types of activity you want to include in your feed.

crypto: chelsio - fix writing tfm flags to wrong place

The chelsio crypto driver is casting 'struct crypto_aead' directly to
'struct crypto_tfm', which is incorrect because the crypto_tfm isn't the
first field of 'struct crypto_aead'. Consequently, the calls to
crypto_tfm_set_flags() are modifying some other field in the struct.

Also, the driver is setting CRYPTO_TFM_RES_BAD_KEY_LEN in
->setauthsize(), not just in ->setkey(). This is incorrect since this
flag is for bad key lengths, not for bad authentication tag lengths.

Fix these bugs by removing the broken crypto_tfm_set_flags() calls from
->setauthsize() and by fixing them in ->setkey().

Fixes: 324429d74127 ("chcr: Support for Chelsio's Crypto Hardware")
Cc: <stable@vger.kernel.org> # v4.9+
Cc: Atul Gupta <atul.gupta@chelsio.com>
Signed-off-by: Eric Biggers <ebiggers@google.com>
Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

authored by

Eric Biggers and committed by
Herbert Xu
bd56cea0 70ffa8fd

+3 -13
+3 -13
drivers/crypto/chelsio/chcr_algo.c
··· 3196 3196 aeadctx->mayverify = VERIFY_SW; 3197 3197 break; 3198 3198 default: 3199 - 3200 - crypto_tfm_set_flags((struct crypto_tfm *) tfm, 3201 - CRYPTO_TFM_RES_BAD_KEY_LEN); 3202 3199 return -EINVAL; 3203 3200 } 3204 3201 return crypto_aead_setauthsize(aeadctx->sw_cipher, authsize); ··· 3220 3223 aeadctx->mayverify = VERIFY_HW; 3221 3224 break; 3222 3225 default: 3223 - crypto_tfm_set_flags((struct crypto_tfm *)tfm, 3224 - CRYPTO_TFM_RES_BAD_KEY_LEN); 3225 3226 return -EINVAL; 3226 3227 } 3227 3228 return crypto_aead_setauthsize(aeadctx->sw_cipher, authsize); ··· 3260 3265 aeadctx->mayverify = VERIFY_HW; 3261 3266 break; 3262 3267 default: 3263 - crypto_tfm_set_flags((struct crypto_tfm *)tfm, 3264 - CRYPTO_TFM_RES_BAD_KEY_LEN); 3265 3268 return -EINVAL; 3266 3269 } 3267 3270 return crypto_aead_setauthsize(aeadctx->sw_cipher, authsize); ··· 3284 3291 ck_size = CHCR_KEYCTX_CIPHER_KEY_SIZE_256; 3285 3292 mk_size = CHCR_KEYCTX_MAC_KEY_SIZE_256; 3286 3293 } else { 3287 - crypto_tfm_set_flags((struct crypto_tfm *)aead, 3288 - CRYPTO_TFM_RES_BAD_KEY_LEN); 3294 + crypto_aead_set_flags(aead, CRYPTO_TFM_RES_BAD_KEY_LEN); 3289 3295 aeadctx->enckey_len = 0; 3290 3296 return -EINVAL; 3291 3297 } ··· 3322 3330 int error; 3323 3331 3324 3332 if (keylen < 3) { 3325 - crypto_tfm_set_flags((struct crypto_tfm *)aead, 3326 - CRYPTO_TFM_RES_BAD_KEY_LEN); 3333 + crypto_aead_set_flags(aead, CRYPTO_TFM_RES_BAD_KEY_LEN); 3327 3334 aeadctx->enckey_len = 0; 3328 3335 return -EINVAL; 3329 3336 } ··· 3372 3381 } else if (keylen == AES_KEYSIZE_256) { 3373 3382 ck_size = CHCR_KEYCTX_CIPHER_KEY_SIZE_256; 3374 3383 } else { 3375 - crypto_tfm_set_flags((struct crypto_tfm *)aead, 3376 - CRYPTO_TFM_RES_BAD_KEY_LEN); 3384 + crypto_aead_set_flags(aead, CRYPTO_TFM_RES_BAD_KEY_LEN); 3377 3385 pr_err("GCM: Invalid key length %d\n", keylen); 3378 3386 ret = -EINVAL; 3379 3387 goto out;