public inbox for linux-xfs@vger.kernel.org
 help / color / mirror / Atom feed
From: Eric Sandeen <esandeen@redhat.com>
To: "Darrick J. Wong" <djwong@kernel.org>,
	Dave Chinner <david@fromorbit.com>
Cc: xfs <linux-xfs@vger.kernel.org>
Subject: Re: [PATCH 1/2] xfs: kill the XFS_IOC_{ALLOC,FREE}SP* ioctls
Date: Mon, 10 Jan 2022 12:37:33 -0600	[thread overview]
Message-ID: <4e135a9f-159a-a06a-a9b2-939d711ebc52@redhat.com> (raw)
In-Reply-To: <20220110174827.GW656707@magnolia>

On 1/10/22 11:48 AM, Darrick J. Wong wrote:
> From: Darrick J. Wong <djwong@kernel.org>
> 
> According to Dave lore, these ioctls originated in the early 1990s in
> Irix EFS as a (somewhat clunky) way to preallocate space at the end of a
> file.  Irix XFS, naturally, picked up these ioctls to maintain
> compatibility, which meant that they were ported to Linux in the early
> 2000s.
> 
> Recently it was pointed out to me they still lurk in the kernel, even
> though the Linux fallocate syscall supplanted the functionality a long
> time ago.  fstests doesn't seem to include any real functional or stress
> tests for these ioctls, which means that the code quality is ... very
> questionable.  Most notably, it was a stale disk block exposure vector
> for 21 years and nobody noticed or complained.  As mature programmers
> say, "If you're not testing it, it's broken."
> 
> Given all that, let's withdraw these ioctls from the XFS userspace API.
> Normally we'd set a long deprecation process, but I estimate that there
> aren't any real users, so let's trigger a warning in dmesg and return
> -ENOTTY.
> 
> See: CVE-2021-4155
> 
> Augments: 983d8e60f508 ("xfs: map unwritten blocks in XFS_IOC_{ALLOC,FREE}SP just like fallocate")
> Signed-off-by: Darrick J. Wong <djwong@kernel.org>

Thanks Darrick.

Random thoughts, take them or leave them.

We could suggest fallocate in the warning, unless we don't want to
prescribe solutions.

Since xfs_alloc_file_space() only does one thing, we could change it
to xfs_prealloc_file_space() for clarity.

With or wiithout those changes, this looks fine to me.

Reviewed-by: Eric Sandeen <sandeen@redhat.com>


> ---
>   fs/xfs/xfs_bmap_util.c |    7 ++--
>   fs/xfs/xfs_bmap_util.h |    2 +
>   fs/xfs/xfs_file.c      |    3 +-
>   fs/xfs/xfs_ioctl.c     |   92 ++----------------------------------------------
>   fs/xfs/xfs_ioctl.h     |    6 ---
>   fs/xfs/xfs_ioctl32.c   |   27 --------------
>   6 files changed, 9 insertions(+), 128 deletions(-)
> 
> diff --git a/fs/xfs/xfs_bmap_util.c b/fs/xfs/xfs_bmap_util.c
> index 73a36b7be3bd..575060a7c768 100644
> --- a/fs/xfs/xfs_bmap_util.c
> +++ b/fs/xfs/xfs_bmap_util.c
> @@ -771,8 +771,7 @@ int
>   xfs_alloc_file_space(
>   	struct xfs_inode	*ip,
>   	xfs_off_t		offset,
> -	xfs_off_t		len,
> -	int			alloc_type)
> +	xfs_off_t		len)
>   {
>   	xfs_mount_t		*mp = ip->i_mount;
>   	xfs_off_t		count;
> @@ -865,8 +864,8 @@ xfs_alloc_file_space(
>   			goto error;
>   
>   		error = xfs_bmapi_write(tp, ip, startoffset_fsb,
> -					allocatesize_fsb, alloc_type, 0, imapp,
> -					&nimaps);
> +				allocatesize_fsb, XFS_BMAPI_PREALLOC, 0, imapp,
> +				&nimaps);
>   		if (error)
>   			goto error;
>   
> diff --git a/fs/xfs/xfs_bmap_util.h b/fs/xfs/xfs_bmap_util.h
> index 9f993168b55b..24b37d211f1d 100644
> --- a/fs/xfs/xfs_bmap_util.h
> +++ b/fs/xfs/xfs_bmap_util.h
> @@ -54,7 +54,7 @@ int	xfs_bmap_last_extent(struct xfs_trans *tp, struct xfs_inode *ip,
>   
>   /* preallocation and hole punch interface */
>   int	xfs_alloc_file_space(struct xfs_inode *ip, xfs_off_t offset,
> -			     xfs_off_t len, int alloc_type);
> +			     xfs_off_t len);
>   int	xfs_free_file_space(struct xfs_inode *ip, xfs_off_t offset,
>   			    xfs_off_t len);
>   int	xfs_collapse_file_space(struct xfs_inode *, xfs_off_t offset,
> diff --git a/fs/xfs/xfs_file.c b/fs/xfs/xfs_file.c
> index 27594738b0d1..d81a28cada35 100644
> --- a/fs/xfs/xfs_file.c
> +++ b/fs/xfs/xfs_file.c
> @@ -1052,8 +1052,7 @@ xfs_file_fallocate(
>   		}
>   
>   		if (!xfs_is_always_cow_inode(ip)) {
> -			error = xfs_alloc_file_space(ip, offset, len,
> -						     XFS_BMAPI_PREALLOC);
> +			error = xfs_alloc_file_space(ip, offset, len);
>   			if (error)
>   				goto out_unlock;
>   		}
> diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c
> index 8ea47a9d5aad..38b2a1e881a6 100644
> --- a/fs/xfs/xfs_ioctl.c
> +++ b/fs/xfs/xfs_ioctl.c
> @@ -627,87 +627,6 @@ xfs_attrmulti_by_handle(
>   	return error;
>   }
>   
> -int
> -xfs_ioc_space(
> -	struct file		*filp,
> -	xfs_flock64_t		*bf)
> -{
> -	struct inode		*inode = file_inode(filp);
> -	struct xfs_inode	*ip = XFS_I(inode);
> -	struct iattr		iattr;
> -	enum xfs_prealloc_flags	flags = XFS_PREALLOC_CLEAR;
> -	uint			iolock = XFS_IOLOCK_EXCL | XFS_MMAPLOCK_EXCL;
> -	int			error;
> -
> -	if (inode->i_flags & (S_IMMUTABLE|S_APPEND))
> -		return -EPERM;
> -
> -	if (!(filp->f_mode & FMODE_WRITE))
> -		return -EBADF;
> -
> -	if (!S_ISREG(inode->i_mode))
> -		return -EINVAL;
> -
> -	if (xfs_is_always_cow_inode(ip))
> -		return -EOPNOTSUPP;
> -
> -	if (filp->f_flags & O_DSYNC)
> -		flags |= XFS_PREALLOC_SYNC;
> -	if (filp->f_mode & FMODE_NOCMTIME)
> -		flags |= XFS_PREALLOC_INVISIBLE;
> -
> -	error = mnt_want_write_file(filp);
> -	if (error)
> -		return error;
> -
> -	xfs_ilock(ip, iolock);
> -	error = xfs_break_layouts(inode, &iolock, BREAK_UNMAP);
> -	if (error)
> -		goto out_unlock;
> -	inode_dio_wait(inode);
> -
> -	switch (bf->l_whence) {
> -	case 0: /*SEEK_SET*/
> -		break;
> -	case 1: /*SEEK_CUR*/
> -		bf->l_start += filp->f_pos;
> -		break;
> -	case 2: /*SEEK_END*/
> -		bf->l_start += XFS_ISIZE(ip);
> -		break;
> -	default:
> -		error = -EINVAL;
> -		goto out_unlock;
> -	}
> -
> -	if (bf->l_start < 0 || bf->l_start > inode->i_sb->s_maxbytes) {
> -		error = -EINVAL;
> -		goto out_unlock;
> -	}
> -
> -	if (bf->l_start > XFS_ISIZE(ip)) {
> -		error = xfs_alloc_file_space(ip, XFS_ISIZE(ip),
> -				bf->l_start - XFS_ISIZE(ip),
> -				XFS_BMAPI_PREALLOC);
> -		if (error)
> -			goto out_unlock;
> -	}
> -
> -	iattr.ia_valid = ATTR_SIZE;
> -	iattr.ia_size = bf->l_start;
> -	error = xfs_vn_setattr_size(file_mnt_user_ns(filp), file_dentry(filp),
> -				    &iattr);
> -	if (error)
> -		goto out_unlock;
> -
> -	error = xfs_update_prealloc_flags(ip, flags);
> -
> -out_unlock:
> -	xfs_iunlock(ip, iolock);
> -	mnt_drop_write_file(filp);
> -	return error;
> -}
> -
>   /* Return 0 on success or positive error */
>   int
>   xfs_fsbulkstat_one_fmt(
> @@ -1965,13 +1884,10 @@ xfs_file_ioctl(
>   	case XFS_IOC_ALLOCSP:
>   	case XFS_IOC_FREESP:
>   	case XFS_IOC_ALLOCSP64:
> -	case XFS_IOC_FREESP64: {
> -		xfs_flock64_t		bf;
> -
> -		if (copy_from_user(&bf, arg, sizeof(bf)))
> -			return -EFAULT;
> -		return xfs_ioc_space(filp, &bf);
> -	}
> +	case XFS_IOC_FREESP64:
> +		xfs_warn_once(mp,
> +	"dangerous XFS_IOC_{ALLOC,FREE}SP ioctls no longer supported");
> +		return -ENOTTY;
>   	case XFS_IOC_DIOINFO: {
>   		struct xfs_buftarg	*target = xfs_inode_buftarg(ip);
>   		struct dioattr		da;
> diff --git a/fs/xfs/xfs_ioctl.h b/fs/xfs/xfs_ioctl.h
> index 845d3bcab74b..d4abba2c13c1 100644
> --- a/fs/xfs/xfs_ioctl.h
> +++ b/fs/xfs/xfs_ioctl.h
> @@ -10,12 +10,6 @@ struct xfs_bstat;
>   struct xfs_ibulk;
>   struct xfs_inogrp;
>   
> -
> -extern int
> -xfs_ioc_space(
> -	struct file		*filp,
> -	xfs_flock64_t		*bf);
> -
>   int
>   xfs_ioc_swapext(
>   	xfs_swapext_t	*sxp);
> diff --git a/fs/xfs/xfs_ioctl32.c b/fs/xfs/xfs_ioctl32.c
> index 8783af203cfc..004ed2a251e8 100644
> --- a/fs/xfs/xfs_ioctl32.c
> +++ b/fs/xfs/xfs_ioctl32.c
> @@ -27,22 +27,6 @@
>   	  _IOC(_IOC_DIR(cmd), _IOC_TYPE(cmd), _IOC_NR(cmd), sizeof(type))
>   
>   #ifdef BROKEN_X86_ALIGNMENT
> -STATIC int
> -xfs_compat_flock64_copyin(
> -	xfs_flock64_t		*bf,
> -	compat_xfs_flock64_t	__user *arg32)
> -{
> -	if (get_user(bf->l_type,	&arg32->l_type) ||
> -	    get_user(bf->l_whence,	&arg32->l_whence) ||
> -	    get_user(bf->l_start,	&arg32->l_start) ||
> -	    get_user(bf->l_len,		&arg32->l_len) ||
> -	    get_user(bf->l_sysid,	&arg32->l_sysid) ||
> -	    get_user(bf->l_pid,		&arg32->l_pid) ||
> -	    copy_from_user(bf->l_pad,	&arg32->l_pad,	4*sizeof(u32)))
> -		return -EFAULT;
> -	return 0;
> -}
> -
>   STATIC int
>   xfs_compat_ioc_fsgeometry_v1(
>   	struct xfs_mount	  *mp,
> @@ -445,17 +429,6 @@ xfs_file_compat_ioctl(
>   
>   	switch (cmd) {
>   #if defined(BROKEN_X86_ALIGNMENT)
> -	case XFS_IOC_ALLOCSP_32:
> -	case XFS_IOC_FREESP_32:
> -	case XFS_IOC_ALLOCSP64_32:
> -	case XFS_IOC_FREESP64_32: {
> -		struct xfs_flock64	bf;
> -
> -		if (xfs_compat_flock64_copyin(&bf, arg))
> -			return -EFAULT;
> -		cmd = _NATIVE_IOC(cmd, struct xfs_flock64);
> -		return xfs_ioc_space(filp, &bf);
> -	}
>   	case XFS_IOC_FSGEOMETRY_V1_32:
>   		return xfs_compat_ioc_fsgeometry_v1(ip->i_mount, arg);
>   	case XFS_IOC_FSGROWFSDATA_32: {
> 


  parent reply	other threads:[~2022-01-10 18:37 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-01-10 17:48 [PATCH 1/2] xfs: kill the XFS_IOC_{ALLOC,FREE}SP* ioctls Darrick J. Wong
2022-01-10 17:51 ` [PATCH 2/2] xfs: hide the XFS_IOC_{ALLOC,FREE}SP* definitions Darrick J. Wong
2022-01-10 18:39   ` Eric Sandeen
2022-01-10 19:59     ` Darrick J. Wong
2022-01-10 19:58   ` [PATCH v2 " Darrick J. Wong
2022-01-10 21:10     ` Dave Chinner
2022-01-11 16:24     ` Eric Sandeen
2022-01-10 18:37 ` Eric Sandeen [this message]
2022-01-10 21:08 ` [PATCH 1/2] xfs: kill the XFS_IOC_{ALLOC,FREE}SP* ioctls Dave Chinner
2022-01-18  2:26 ` [xfs] 270a6968dc: xfstests.xfs.009.fail kernel test robot

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=4e135a9f-159a-a06a-a9b2-939d711ebc52@redhat.com \
    --to=esandeen@redhat.com \
    --cc=david@fromorbit.com \
    --cc=djwong@kernel.org \
    --cc=linux-xfs@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox