From: Tao Cui btrfs_ioctl_defrag() checks MAY_WRITE with nop_mnt_idmap, which skips the mount idmap. On an idmapped mount the owner comparison then uses the caller's fsuid against the raw on-disk uid, dropping the mapping. Every other permission/owner check in btrfs ioctl uses file_mnt_idmap(file) (e.g. :1152, :1310, :1946); this one missed it. Switch to file_mnt_idmap(file). It equals nop_mnt_idmap on a normal mount, and the check stays behind !capable(CAP_SYS_ADMIN), so only unprivileged callers on idmapped btrfs change. The RO-fd note in the comment above is about the file descriptor, not this inode check, and is unaffected. Signed-off-by: Tao Cui --- fs/btrfs/ioctl.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c index 72bc9d4f7708..607329dedd50 100644 --- a/fs/btrfs/ioctl.c +++ b/fs/btrfs/ioctl.c @@ -2458,7 +2458,7 @@ static int btrfs_ioctl_defrag(struct file *file, void __user *argp) * running and allows defrag on files open in read-only mode. */ if (!capable(CAP_SYS_ADMIN) && - inode_permission(&nop_mnt_idmap, inode, MAY_WRITE)) { + inode_permission(file_mnt_idmap(file), inode, MAY_WRITE)) { ret = -EPERM; goto out; } -- 2.43.0