diff options
author | Mallikarjun Kasoju <mkasoju@nvidia.com> | 2018-03-16 15:40:06 +0530 |
---|---|---|
committer | Winnie Hsu <whsu@nvidia.com> | 2018-03-19 11:32:05 -0700 |
commit | 7b67aa2c06e6906c6c190aabb1fa9722fd3cfb36 (patch) | |
tree | 0488df72ffcea001929007adcccd64a7cb0f19af /drivers | |
parent | b6d6e5af1450ed5ccae042ab1125a6b799433b73 (diff) |
tegra-cryptodev:Avoid untrusted usrptr dereference
In RSA operations use copy_from_user to get key data
into local buffer before using it.
This will avoid untrusted user pointer dereference.
Coverity ID 24040
Bug 200192571
Bug 1932494
Change-Id: I9c8f3fd7cfc18121d9c2179127dfb28202f38cdb
Signed-off-by: Mallikarjun Kasoju <mkasoju@nvidia.com>
Reviewed-on: https://git-master.nvidia.com/r/1676570
GVS: Gerrit_Virtual_Submit
Reviewed-by: Bibek Basu <bbasu@nvidia.com>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/misc/tegra-cryptodev.c | 32 |
1 files changed, 29 insertions, 3 deletions
diff --git a/drivers/misc/tegra-cryptodev.c b/drivers/misc/tegra-cryptodev.c index d1fa004367b1..4dc6ca63226d 100644 --- a/drivers/misc/tegra-cryptodev.c +++ b/drivers/misc/tegra-cryptodev.c @@ -425,6 +425,33 @@ static int tegra_crypt_rsa(struct tegra_crypto_ctx *ctx, int ret = 0; unsigned long *xbuf[XBUFSIZE]; struct tegra_crypto_completion rsa_complete; + unsigned int total_key_len; + char *key_mem; + + if ((((rsa_req->keylen >> 16) & 0xFFFF) > + MAX_RSA_MSG_LEN) || + ((rsa_req->keylen & 0xFFFF) > + MAX_RSA_MSG_LEN)) { + pr_err("Invalid rsa key length\n"); + return -EINVAL; + } + + total_key_len = (((rsa_req->keylen >> 16) & 0xFFFF) + + (rsa_req->keylen & 0xFFFF)); + + key_mem = kzalloc(total_key_len, GFP_KERNEL); + if (!key_mem) + return -ENOMEM; + + ret = copy_from_user(key_mem, (void __user *)rsa_req->key, + total_key_len); + if (ret) { + pr_err("%s: copy_from_user fail(%d)\n", __func__, ret); + kfree(key_mem); + return -EINVAL; + } + + rsa_req->key = key_mem; switch (rsa_req->algo) { case TEGRA_RSA512: @@ -475,10 +502,8 @@ static int tegra_crypt_rsa(struct tegra_crypto_ctx *ctx, init_completion(&rsa_complete.restart); result = kzalloc(rsa_req->keylen >> 16, GFP_KERNEL); - if (!result) { - pr_err("\nresult alloc fail\n"); + if (!result) goto result_fail; - } hash_buff = xbuf[0]; @@ -528,6 +553,7 @@ result_fail: buf_fail: ahash_request_free(req); req_fail: + kfree(key_mem); return ret; } |