Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  *  linux/fs/ioctl.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  *  Copyright (C) 1991, 1992  Linus Torvalds
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8) #include <linux/syscalls.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9) #include <linux/mm.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10) #include <linux/capability.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) #include <linux/compat.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) #include <linux/file.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) #include <linux/fs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) #include <linux/security.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) #include <linux/export.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) #include <linux/uaccess.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) #include <linux/writeback.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) #include <linux/buffer_head.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) #include <linux/falloc.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) #include <linux/sched/signal.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) #include <linux/fiemap.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) #include "internal.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) #include <asm/ioctls.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) /* So that the fiemap access checks can't overflow on 32 bit machines. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) #define FIEMAP_MAX_EXTENTS	(UINT_MAX / sizeof(struct fiemap_extent))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31)  * vfs_ioctl - call filesystem specific ioctl methods
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32)  * @filp:	open file to invoke ioctl method on
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33)  * @cmd:	ioctl command to execute
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34)  * @arg:	command-specific argument for ioctl
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36)  * Invokes filesystem specific ->unlocked_ioctl, if one exists; otherwise
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37)  * returns -ENOTTY.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39)  * Returns 0 on success, -errno on error.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) long vfs_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) 	int error = -ENOTTY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) 	if (!filp->f_op->unlocked_ioctl)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) 	error = filp->f_op->unlocked_ioctl(filp, cmd, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) 	if (error == -ENOIOCTLCMD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) 		error = -ENOTTY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51)  out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) 	return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) EXPORT_SYMBOL(vfs_ioctl);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) static int ioctl_fibmap(struct file *filp, int __user *p)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) 	struct inode *inode = file_inode(filp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) 	struct super_block *sb = inode->i_sb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) 	int error, ur_block;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) 	sector_t block;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) 	if (!capable(CAP_SYS_RAWIO))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) 		return -EPERM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) 	error = get_user(ur_block, p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 	if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) 		return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) 	if (ur_block < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 	block = ur_block;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 	error = bmap(inode, &block);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 	if (block > INT_MAX) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 		error = -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 		pr_warn_ratelimited("[%s/%d] FS: %s File: %pD4 would truncate fibmap result\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 				    current->comm, task_pid_nr(current),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 				    sb->s_id, filp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) 	if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 		ur_block = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 		ur_block = block;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 	if (put_user(ur_block, p))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 		error = -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 	return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95)  * fiemap_fill_next_extent - Fiemap helper function
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96)  * @fieinfo:	Fiemap context passed into ->fiemap
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97)  * @logical:	Extent logical start offset, in bytes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98)  * @phys:	Extent physical start offset, in bytes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99)  * @len:	Extent length, in bytes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100)  * @flags:	FIEMAP_EXTENT flags that describe this extent
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102)  * Called from file system ->fiemap callback. Will populate extent
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103)  * info as passed in via arguments and copy to user memory. On
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104)  * success, extent count on fieinfo is incremented.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106)  * Returns 0 on success, -errno on error, 1 if this was the last
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107)  * extent that will fit in user array.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) #define SET_UNKNOWN_FLAGS	(FIEMAP_EXTENT_DELALLOC)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) #define SET_NO_UNMOUNTED_IO_FLAGS	(FIEMAP_EXTENT_DATA_ENCRYPTED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) #define SET_NOT_ALIGNED_FLAGS	(FIEMAP_EXTENT_DATA_TAIL|FIEMAP_EXTENT_DATA_INLINE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) int fiemap_fill_next_extent(struct fiemap_extent_info *fieinfo, u64 logical,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 			    u64 phys, u64 len, u32 flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 	struct fiemap_extent extent;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 	struct fiemap_extent __user *dest = fieinfo->fi_extents_start;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 	/* only count the extents */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 	if (fieinfo->fi_extents_max == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 		fieinfo->fi_extents_mapped++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 		return (flags & FIEMAP_EXTENT_LAST) ? 1 : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 	if (fieinfo->fi_extents_mapped >= fieinfo->fi_extents_max)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 		return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 	if (flags & SET_UNKNOWN_FLAGS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) 		flags |= FIEMAP_EXTENT_UNKNOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) 	if (flags & SET_NO_UNMOUNTED_IO_FLAGS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) 		flags |= FIEMAP_EXTENT_ENCODED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) 	if (flags & SET_NOT_ALIGNED_FLAGS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 		flags |= FIEMAP_EXTENT_NOT_ALIGNED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 	memset(&extent, 0, sizeof(extent));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 	extent.fe_logical = logical;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 	extent.fe_physical = phys;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 	extent.fe_length = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 	extent.fe_flags = flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 	dest += fieinfo->fi_extents_mapped;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 	if (copy_to_user(dest, &extent, sizeof(extent)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 		return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 	fieinfo->fi_extents_mapped++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) 	if (fieinfo->fi_extents_mapped == fieinfo->fi_extents_max)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 		return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 	return (flags & FIEMAP_EXTENT_LAST) ? 1 : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) EXPORT_SYMBOL_NS(fiemap_fill_next_extent, ANDROID_GKI_VFS_EXPORT_ONLY);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152)  * fiemap_prep - check validity of requested flags for fiemap
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153)  * @inode:	Inode to operate on
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154)  * @fieinfo:	Fiemap context passed into ->fiemap
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155)  * @start:	Start of the mapped range
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156)  * @len:	Length of the mapped range, can be truncated by this function.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157)  * @supported_flags:	Set of fiemap flags that the file system understands
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159)  * This function must be called from each ->fiemap instance to validate the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160)  * fiemap request against the file system parameters.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162)  * Returns 0 on success, or a negative error on failure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) int fiemap_prep(struct inode *inode, struct fiemap_extent_info *fieinfo,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 		u64 start, u64 *len, u32 supported_flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) 	u64 maxbytes = inode->i_sb->s_maxbytes;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 	u32 incompat_flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) 	int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	if (*len == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 	if (start > maxbytes)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 		return -EFBIG;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) 	 * Shrink request scope to what the fs can actually handle.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) 	if (*len > maxbytes || (maxbytes - *len) < start)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 		*len = maxbytes - start;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 	supported_flags |= FIEMAP_FLAG_SYNC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) 	supported_flags &= FIEMAP_FLAGS_COMPAT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 	incompat_flags = fieinfo->fi_flags & ~supported_flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) 	if (incompat_flags) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) 		fieinfo->fi_flags = incompat_flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 		return -EBADR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 	if (fieinfo->fi_flags & FIEMAP_FLAG_SYNC)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 		ret = filemap_write_and_wait(inode->i_mapping);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) EXPORT_SYMBOL_NS(fiemap_prep, ANDROID_GKI_VFS_EXPORT_ONLY);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) static int ioctl_fiemap(struct file *filp, struct fiemap __user *ufiemap)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 	struct fiemap fiemap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 	struct fiemap_extent_info fieinfo = { 0, };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 	struct inode *inode = file_inode(filp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 	int error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 	if (!inode->i_op->fiemap)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 		return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 	if (copy_from_user(&fiemap, ufiemap, sizeof(fiemap)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 		return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 	if (fiemap.fm_extent_count > FIEMAP_MAX_EXTENTS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) 	fieinfo.fi_flags = fiemap.fm_flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 	fieinfo.fi_extents_max = fiemap.fm_extent_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 	fieinfo.fi_extents_start = ufiemap->fm_extents;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) 	error = inode->i_op->fiemap(inode, &fieinfo, fiemap.fm_start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 			fiemap.fm_length);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) 	fiemap.fm_flags = fieinfo.fi_flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) 	fiemap.fm_mapped_extents = fieinfo.fi_extents_mapped;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) 	if (copy_to_user(ufiemap, &fiemap, sizeof(fiemap)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) 		error = -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 	return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) static long ioctl_file_clone(struct file *dst_file, unsigned long srcfd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 			     u64 off, u64 olen, u64 destoff)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 	struct fd src_file = fdget(srcfd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 	loff_t cloned;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 	if (!src_file.file)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 		return -EBADF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	ret = -EXDEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 	if (src_file.file->f_path.mnt != dst_file->f_path.mnt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 		goto fdput;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 	cloned = vfs_clone_file_range(src_file.file, off, dst_file, destoff,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 				      olen, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) 	if (cloned < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) 		ret = cloned;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 	else if (olen && cloned != olen)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) 		ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 		ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) fdput:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 	fdput(src_file);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) static long ioctl_file_clone_range(struct file *file,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 				   struct file_clone_range __user *argp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 	struct file_clone_range args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 	if (copy_from_user(&args, argp, sizeof(args)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) 		return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 	return ioctl_file_clone(file, args.src_fd, args.src_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) 				args.src_length, args.dest_offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) #ifdef CONFIG_BLOCK
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) static inline sector_t logical_to_blk(struct inode *inode, loff_t offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) 	return (offset >> inode->i_blkbits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) static inline loff_t blk_to_logical(struct inode *inode, sector_t blk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) 	return (blk << inode->i_blkbits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276)  * __generic_block_fiemap - FIEMAP for block based inodes (no locking)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277)  * @inode: the inode to map
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278)  * @fieinfo: the fiemap info struct that will be passed back to userspace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279)  * @start: where to start mapping in the inode
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280)  * @len: how much space to map
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281)  * @get_block: the fs's get_block function
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283)  * This does FIEMAP for block based inodes.  Basically it will just loop
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284)  * through get_block until we hit the number of extents we want to map, or we
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285)  * go past the end of the file and hit a hole.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287)  * If it is possible to have data blocks beyond a hole past @inode->i_size, then
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288)  * please do not use this function, it will stop at the first unmapped block
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289)  * beyond i_size.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291)  * If you use this function directly, you need to do your own locking. Use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292)  * generic_block_fiemap if you want the locking done for you.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) static int __generic_block_fiemap(struct inode *inode,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 			   struct fiemap_extent_info *fieinfo, loff_t start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) 			   loff_t len, get_block_t *get_block)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 	struct buffer_head map_bh;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) 	sector_t start_blk, last_blk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 	loff_t isize = i_size_read(inode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) 	u64 logical = 0, phys = 0, size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 	u32 flags = FIEMAP_EXTENT_MERGED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) 	bool past_eof = false, whole_file = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 	int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 	ret = fiemap_prep(inode, fieinfo, start, &len, FIEMAP_FLAG_SYNC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 	 * Either the i_mutex or other appropriate locking needs to be held
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) 	 * since we expect isize to not change at all through the duration of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 	 * this call.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) 	if (len >= isize) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) 		whole_file = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) 		len = isize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) 	 * Some filesystems can't deal with being asked to map less than
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) 	 * blocksize, so make sure our len is at least block length.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) 	if (logical_to_blk(inode, len) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) 		len = blk_to_logical(inode, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 	start_blk = logical_to_blk(inode, start);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 	last_blk = logical_to_blk(inode, start + len - 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) 	do {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) 		 * we set b_size to the total size we want so it will map as
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) 		 * many contiguous blocks as possible at once
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) 		memset(&map_bh, 0, sizeof(struct buffer_head));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 		map_bh.b_size = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) 		ret = get_block(inode, start_blk, &map_bh, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) 		/* HOLE */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) 		if (!buffer_mapped(&map_bh)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) 			start_blk++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) 			/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) 			 * We want to handle the case where there is an
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) 			 * allocated block at the front of the file, and then
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) 			 * nothing but holes up to the end of the file properly,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) 			 * to make sure that extent at the front gets properly
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) 			 * marked with FIEMAP_EXTENT_LAST
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 			if (!past_eof &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) 			    blk_to_logical(inode, start_blk) >= isize)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) 				past_eof = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) 			/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) 			 * First hole after going past the EOF, this is our
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) 			 * last extent
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) 			if (past_eof && size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) 				flags = FIEMAP_EXTENT_MERGED|FIEMAP_EXTENT_LAST;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) 				ret = fiemap_fill_next_extent(fieinfo, logical,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) 							      phys, size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) 							      flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) 			} else if (size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) 				ret = fiemap_fill_next_extent(fieinfo, logical,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) 							      phys, size, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) 				size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 			/* if we have holes up to/past EOF then we're done */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 			if (start_blk > last_blk || past_eof || ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) 				break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 			/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) 			 * We have gone over the length of what we wanted to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) 			 * map, and it wasn't the entire file, so add the extent
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) 			 * we got last time and exit.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) 			 *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) 			 * This is for the case where say we want to map all the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) 			 * way up to the second to the last block in a file, but
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) 			 * the last block is a hole, making the second to last
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) 			 * block FIEMAP_EXTENT_LAST.  In this case we want to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) 			 * see if there is a hole after the second to last block
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) 			 * so we can mark it properly.  If we found data after
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) 			 * we exceeded the length we were requesting, then we
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) 			 * are good to go, just add the extent to the fieinfo
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) 			 * and break
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) 			if (start_blk > last_blk && !whole_file) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) 				ret = fiemap_fill_next_extent(fieinfo, logical,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) 							      phys, size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) 							      flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) 				break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) 			/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) 			 * if size != 0 then we know we already have an extent
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) 			 * to add, so add it.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) 			if (size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) 				ret = fiemap_fill_next_extent(fieinfo, logical,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) 							      phys, size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) 							      flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) 				if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) 					break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) 			logical = blk_to_logical(inode, start_blk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) 			phys = blk_to_logical(inode, map_bh.b_blocknr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) 			size = map_bh.b_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) 			flags = FIEMAP_EXTENT_MERGED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) 			start_blk += logical_to_blk(inode, size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) 			/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) 			 * If we are past the EOF, then we need to make sure as
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) 			 * soon as we find a hole that the last extent we found
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) 			 * is marked with FIEMAP_EXTENT_LAST
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 			if (!past_eof && logical + size >= isize)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) 				past_eof = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 		cond_resched();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) 		if (fatal_signal_pending(current)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) 			ret = -EINTR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) 	} while (1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) 	/* If ret is 1 then we just hit the end of the extent array */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) 	if (ret == 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) 		ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441)  * generic_block_fiemap - FIEMAP for block based inodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442)  * @inode: The inode to map
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443)  * @fieinfo: The mapping information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444)  * @start: The initial block to map
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445)  * @len: The length of the extect to attempt to map
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446)  * @get_block: The block mapping function for the fs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448)  * Calls __generic_block_fiemap to map the inode, after taking
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449)  * the inode's mutex lock.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) int generic_block_fiemap(struct inode *inode,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) 			 struct fiemap_extent_info *fieinfo, u64 start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) 			 u64 len, get_block_t *get_block)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) 	inode_lock(inode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) 	ret = __generic_block_fiemap(inode, fieinfo, start, len, get_block);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) 	inode_unlock(inode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) EXPORT_SYMBOL(generic_block_fiemap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) #endif  /*  CONFIG_BLOCK  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467)  * This provides compatibility with legacy XFS pre-allocation ioctls
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468)  * which predate the fallocate syscall.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470)  * Only the l_start, l_len and l_whence fields of the 'struct space_resv'
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471)  * are used here, rest are ignored.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) static int ioctl_preallocate(struct file *filp, int mode, void __user *argp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) 	struct inode *inode = file_inode(filp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) 	struct space_resv sr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) 	if (copy_from_user(&sr, argp, sizeof(sr)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) 		return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) 	switch (sr.l_whence) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) 	case SEEK_SET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) 	case SEEK_CUR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) 		sr.l_start += filp->f_pos;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) 	case SEEK_END:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) 		sr.l_start += i_size_read(inode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) 	return vfs_fallocate(filp, mode | FALLOC_FL_KEEP_SIZE, sr.l_start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) 			sr.l_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) /* on ia32 l_start is on a 32-bit boundary */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) #if defined CONFIG_COMPAT && defined(CONFIG_X86_64)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) /* just account for different alignment */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) static int compat_ioctl_preallocate(struct file *file, int mode,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) 				    struct space_resv_32 __user *argp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) 	struct inode *inode = file_inode(file);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) 	struct space_resv_32 sr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) 	if (copy_from_user(&sr, argp, sizeof(sr)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) 		return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) 	switch (sr.l_whence) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) 	case SEEK_SET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) 	case SEEK_CUR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) 		sr.l_start += file->f_pos;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) 	case SEEK_END:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) 		sr.l_start += i_size_read(inode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) 	return vfs_fallocate(file, mode | FALLOC_FL_KEEP_SIZE, sr.l_start, sr.l_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) static int file_ioctl(struct file *filp, unsigned int cmd, int __user *p)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) 	switch (cmd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) 	case FIBMAP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) 		return ioctl_fibmap(filp, p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) 	case FS_IOC_RESVSP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) 	case FS_IOC_RESVSP64:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) 		return ioctl_preallocate(filp, 0, p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) 	case FS_IOC_UNRESVSP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) 	case FS_IOC_UNRESVSP64:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) 		return ioctl_preallocate(filp, FALLOC_FL_PUNCH_HOLE, p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) 	case FS_IOC_ZERO_RANGE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) 		return ioctl_preallocate(filp, FALLOC_FL_ZERO_RANGE, p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) 	return -ENOIOCTLCMD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) static int ioctl_fionbio(struct file *filp, int __user *argp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) 	unsigned int flag;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) 	int on, error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) 	error = get_user(on, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) 	if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) 		return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) 	flag = O_NONBLOCK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) #ifdef __sparc__
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) 	/* SunOS compatibility item. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) 	if (O_NONBLOCK != O_NDELAY)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) 		flag |= O_NDELAY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) 	spin_lock(&filp->f_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) 	if (on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) 		filp->f_flags |= flag;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) 		filp->f_flags &= ~flag;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) 	spin_unlock(&filp->f_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) 	return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) static int ioctl_fioasync(unsigned int fd, struct file *filp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) 			  int __user *argp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) 	unsigned int flag;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) 	int on, error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) 	error = get_user(on, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) 	if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) 		return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) 	flag = on ? FASYNC : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) 	/* Did FASYNC state change ? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) 	if ((flag ^ filp->f_flags) & FASYNC) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) 		if (filp->f_op->fasync)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) 			/* fasync() adjusts filp->f_flags */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) 			error = filp->f_op->fasync(fd, filp, on);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) 		else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) 			error = -ENOTTY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) 	return error < 0 ? error : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) static int ioctl_fsfreeze(struct file *filp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) 	struct super_block *sb = file_inode(filp)->i_sb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) 	if (!ns_capable(sb->s_user_ns, CAP_SYS_ADMIN))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) 		return -EPERM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) 	/* If filesystem doesn't support freeze feature, return. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) 	if (sb->s_op->freeze_fs == NULL && sb->s_op->freeze_super == NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) 		return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) 	/* Freeze */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) 	if (sb->s_op->freeze_super)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) 		return sb->s_op->freeze_super(sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) 	return freeze_super(sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) static int ioctl_fsthaw(struct file *filp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) 	struct super_block *sb = file_inode(filp)->i_sb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) 	if (!ns_capable(sb->s_user_ns, CAP_SYS_ADMIN))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) 		return -EPERM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) 	/* Thaw */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) 	if (sb->s_op->thaw_super)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) 		return sb->s_op->thaw_super(sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) 	return thaw_super(sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) static int ioctl_file_dedupe_range(struct file *file,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) 				   struct file_dedupe_range __user *argp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) 	struct file_dedupe_range *same = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) 	int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) 	unsigned long size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) 	u16 count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) 	if (get_user(count, &argp->dest_count)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) 		ret = -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) 	size = offsetof(struct file_dedupe_range __user, info[count]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) 	if (size > PAGE_SIZE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) 		ret = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) 	same = memdup_user(argp, size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) 	if (IS_ERR(same)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) 		ret = PTR_ERR(same);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) 		same = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) 	same->dest_count = count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) 	ret = vfs_dedupe_file_range(file, same);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) 	ret = copy_to_user(argp, same, size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) 		ret = -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) 	kfree(same);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661)  * do_vfs_ioctl() is not for drivers and not intended to be EXPORT_SYMBOL()'d.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662)  * It's just a simple helper for sys_ioctl and compat_sys_ioctl.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664)  * When you add any new common ioctls to the switches above and below,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665)  * please ensure they have compatible arguments in compat mode.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) static int do_vfs_ioctl(struct file *filp, unsigned int fd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) 			unsigned int cmd, unsigned long arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) 	void __user *argp = (void __user *)arg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) 	struct inode *inode = file_inode(filp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) 	switch (cmd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) 	case FIOCLEX:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) 		set_close_on_exec(fd, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) 	case FIONCLEX:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) 		set_close_on_exec(fd, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) 		return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) 	case FIONBIO:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) 		return ioctl_fionbio(filp, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) 	case FIOASYNC:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) 		return ioctl_fioasync(fd, filp, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) 	case FIOQSIZE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) 		if (S_ISDIR(inode->i_mode) || S_ISREG(inode->i_mode) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) 		    S_ISLNK(inode->i_mode)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) 			loff_t res = inode_get_bytes(inode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) 			return copy_to_user(argp, &res, sizeof(res)) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) 					    -EFAULT : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) 		return -ENOTTY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) 	case FIFREEZE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) 		return ioctl_fsfreeze(filp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) 	case FITHAW:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) 		return ioctl_fsthaw(filp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) 	case FS_IOC_FIEMAP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) 		return ioctl_fiemap(filp, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) 	case FIGETBSZ:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) 		/* anon_bdev filesystems may not have a block size */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) 		if (!inode->i_sb->s_blocksize)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) 			return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) 		return put_user(inode->i_sb->s_blocksize, (int __user *)argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) 	case FICLONE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) 		return ioctl_file_clone(filp, arg, 0, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) 	case FICLONERANGE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) 		return ioctl_file_clone_range(filp, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) 	case FIDEDUPERANGE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) 		return ioctl_file_dedupe_range(filp, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) 	case FIONREAD:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) 		if (!S_ISREG(inode->i_mode))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) 			return vfs_ioctl(filp, cmd, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) 		return put_user(i_size_read(inode) - filp->f_pos,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) 				(int __user *)argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731) 		if (S_ISREG(inode->i_mode))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) 			return file_ioctl(filp, cmd, argp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) 	return -ENOIOCTLCMD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) SYSCALL_DEFINE3(ioctl, unsigned int, fd, unsigned int, cmd, unsigned long, arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) 	struct fd f = fdget(fd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) 	int error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) 	if (!f.file)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) 		return -EBADF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) 	error = security_file_ioctl(f.file, cmd, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) 	if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) 	error = do_vfs_ioctl(f.file, fd, cmd, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) 	if (error == -ENOIOCTLCMD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) 		error = vfs_ioctl(f.file, cmd, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) 	fdput(f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) 	return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) #ifdef CONFIG_COMPAT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762)  * compat_ptr_ioctl - generic implementation of .compat_ioctl file operation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764)  * This is not normally called as a function, but instead set in struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765)  * file_operations as
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767)  *     .compat_ioctl = compat_ptr_ioctl,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769)  * On most architectures, the compat_ptr_ioctl() just passes all arguments
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770)  * to the corresponding ->ioctl handler. The exception is arch/s390, where
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771)  * compat_ptr() clears the top bit of a 32-bit pointer value, so user space
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772)  * pointers to the second 2GB alias the first 2GB, as is the case for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773)  * native 32-bit s390 user space.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775)  * The compat_ptr_ioctl() function must therefore be used only with ioctl
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776)  * functions that either ignore the argument or pass a pointer to a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777)  * compatible data type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779)  * If any ioctl command handled by fops->unlocked_ioctl passes a plain
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780)  * integer instead of a pointer, or any of the passed data types
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781)  * is incompatible between 32-bit and 64-bit architectures, a proper
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782)  * handler is required instead of compat_ptr_ioctl.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) long compat_ptr_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) 	if (!file->f_op->unlocked_ioctl)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) 		return -ENOIOCTLCMD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) 	return file->f_op->unlocked_ioctl(file, cmd, (unsigned long)compat_ptr(arg));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) EXPORT_SYMBOL(compat_ptr_ioctl);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) COMPAT_SYSCALL_DEFINE3(ioctl, unsigned int, fd, unsigned int, cmd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) 		       compat_ulong_t, arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) 	struct fd f = fdget(fd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) 	int error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) 	if (!f.file)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) 		return -EBADF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) 	/* RED-PEN how should LSM module know it's handling 32bit? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) 	error = security_file_ioctl(f.file, cmd, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) 	if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) 	switch (cmd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) 	/* FICLONE takes an int argument, so don't use compat_ptr() */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) 	case FICLONE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) 		error = ioctl_file_clone(f.file, arg, 0, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) #if defined(CONFIG_X86_64)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) 	/* these get messy on amd64 due to alignment differences */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) 	case FS_IOC_RESVSP_32:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) 	case FS_IOC_RESVSP64_32:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) 		error = compat_ioctl_preallocate(f.file, 0, compat_ptr(arg));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) 	case FS_IOC_UNRESVSP_32:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) 	case FS_IOC_UNRESVSP64_32:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) 		error = compat_ioctl_preallocate(f.file, FALLOC_FL_PUNCH_HOLE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) 				compat_ptr(arg));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) 	case FS_IOC_ZERO_RANGE_32:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) 		error = compat_ioctl_preallocate(f.file, FALLOC_FL_ZERO_RANGE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) 				compat_ptr(arg));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) 	 * everything else in do_vfs_ioctl() takes either a compatible
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) 	 * pointer argument or no argument -- call it with a modified
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) 	 * argument.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) 		error = do_vfs_ioctl(f.file, fd, cmd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) 				     (unsigned long)compat_ptr(arg));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) 		if (error != -ENOIOCTLCMD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) 		if (f.file->f_op->compat_ioctl)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) 			error = f.file->f_op->compat_ioctl(f.file, cmd, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) 		if (error == -ENOIOCTLCMD)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) 			error = -ENOTTY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848)  out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) 	fdput(f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) 	return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) #endif