From 76bdaa161cd93d9c033bf6fe2b0a5661c8204441 Mon Sep 17 00:00:00 2001 From: Dan Carpenter Date: Mon, 30 Jan 2017 13:51:49 +0300 Subject: [PATCH] staging: lustre: libcfs: double copy bug The problem is that we copy hdr.ioc_len, we verify it, then we copy it again without checking to see if it has changed in between the two copies. This could result in an information leak. Signed-off-by: Dan Carpenter Signed-off-by: Greg Kroah-Hartman --- .../lustre/lnet/libcfs/linux/linux-module.c | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/drivers/staging/lustre/lnet/libcfs/linux/linux-module.c b/drivers/staging/lustre/lnet/libcfs/linux/linux-module.c index 3f5d58babc2f..075826bd3a2a 100644 --- a/drivers/staging/lustre/lnet/libcfs/linux/linux-module.c +++ b/drivers/staging/lustre/lnet/libcfs/linux/linux-module.c @@ -122,7 +122,7 @@ int libcfs_ioctl_getdata(struct libcfs_ioctl_hdr **hdr_pp, const struct libcfs_ioctl_hdr __user *uhdr) { struct libcfs_ioctl_hdr hdr; - int err = 0; + int err; if (copy_from_user(&hdr, uhdr, sizeof(hdr))) return -EFAULT; @@ -150,9 +150,20 @@ int libcfs_ioctl_getdata(struct libcfs_ioctl_hdr **hdr_pp, return -ENOMEM; if (copy_from_user(*hdr_pp, uhdr, hdr.ioc_len)) { - LIBCFS_FREE(*hdr_pp, hdr.ioc_len); err = -EFAULT; + goto free; } + + if ((*hdr_pp)->ioc_version != hdr.ioc_version || + (*hdr_pp)->ioc_len != hdr.ioc_len) { + err = -EINVAL; + goto free; + } + + return 0; + +free: + LIBCFS_FREE(*hdr_pp, hdr.ioc_len); return err; } -- 2.20.1