diff mbox series

nouveau/u_memcpya: use vmemdup_user

Message ID 20230810185020.231135-1-airlied@gmail.com (mailing list archive)
State New, archived
Headers show
Series nouveau/u_memcpya: use vmemdup_user | expand

Commit Message

Dave Airlie Aug. 10, 2023, 6:50 p.m. UTC
From: Dave Airlie <airlied@redhat.com>

I think there are limit checks in places for most things but the
new api wants to not have them.

Add a limit check and use the vmemdup_user helper instead.

Signed-off-by: Dave Airlie <airlied@redhat.com>
---
 drivers/gpu/drm/nouveau/nouveau_drv.h | 19 +++++--------------
 1 file changed, 5 insertions(+), 14 deletions(-)

Comments

Danilo Krummrich Aug. 10, 2023, 8:46 p.m. UTC | #1
On 8/10/23 20:50, Dave Airlie wrote:
> From: Dave Airlie <airlied@redhat.com>
> 
> I think there are limit checks in places for most things but the
> new api wants to not have them.
> 
> Add a limit check and use the vmemdup_user helper instead.

Reviewed-by: Danilo Krummrich <dakr@redhat.com>

> 
> Signed-off-by: Dave Airlie <airlied@redhat.com>
> ---
>   drivers/gpu/drm/nouveau/nouveau_drv.h | 19 +++++--------------
>   1 file changed, 5 insertions(+), 14 deletions(-)
> 
> diff --git a/drivers/gpu/drm/nouveau/nouveau_drv.h b/drivers/gpu/drm/nouveau/nouveau_drv.h
> index 54063b094a69..8a7357688aff 100644
> --- a/drivers/gpu/drm/nouveau/nouveau_drv.h
> +++ b/drivers/gpu/drm/nouveau/nouveau_drv.h
> @@ -189,21 +189,12 @@ u_free(void *addr)
>   static inline void *
>   u_memcpya(uint64_t user, unsigned nmemb, unsigned size)
>   {
> -	void *mem;
> -	void __user *userptr = (void __force __user *)(uintptr_t)user;
> +	void __user *userptr = u64_to_user_ptr(user);
> +	size_t bytes;
>   
> -	size *= nmemb;
> -
> -	mem = kvmalloc(size, GFP_KERNEL);
> -	if (!mem)
> -		return ERR_PTR(-ENOMEM);
> -
> -	if (copy_from_user(mem, userptr, size)) {
> -		u_free(mem);
> -		return ERR_PTR(-EFAULT);
> -	}
> -
> -	return mem;
> +	if (unlikely(check_mul_overflow(nmemb, size, &bytes)))
> +		return NULL;
> +	return vmemdup_user(userptr, bytes);
>   }
>   
>   #include <nvif/object.h>
diff mbox series

Patch

diff --git a/drivers/gpu/drm/nouveau/nouveau_drv.h b/drivers/gpu/drm/nouveau/nouveau_drv.h
index 54063b094a69..8a7357688aff 100644
--- a/drivers/gpu/drm/nouveau/nouveau_drv.h
+++ b/drivers/gpu/drm/nouveau/nouveau_drv.h
@@ -189,21 +189,12 @@  u_free(void *addr)
 static inline void *
 u_memcpya(uint64_t user, unsigned nmemb, unsigned size)
 {
-	void *mem;
-	void __user *userptr = (void __force __user *)(uintptr_t)user;
+	void __user *userptr = u64_to_user_ptr(user);
+	size_t bytes;
 
-	size *= nmemb;
-
-	mem = kvmalloc(size, GFP_KERNEL);
-	if (!mem)
-		return ERR_PTR(-ENOMEM);
-
-	if (copy_from_user(mem, userptr, size)) {
-		u_free(mem);
-		return ERR_PTR(-EFAULT);
-	}
-
-	return mem;
+	if (unlikely(check_mul_overflow(nmemb, size, &bytes)))
+		return NULL;
+	return vmemdup_user(userptr, bytes);
 }
 
 #include <nvif/object.h>