Merge tag 'pull-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs

Pull vfs fix from Al Viro:
"Amir's copy_file_range() fix"

* tag 'pull-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs:
vfs: fix copy_file_range() averts filesystem freeze protection

Changed files
+28 -9
fs
ksmbd
nfsd
include
linux
+3 -3
fs/ksmbd/vfs.c
··· 1794 1794 ret = vfs_copy_file_range(src_fp->filp, src_off, 1795 1795 dst_fp->filp, dst_off, len, 0); 1796 1796 if (ret == -EOPNOTSUPP || ret == -EXDEV) 1797 - ret = generic_copy_file_range(src_fp->filp, src_off, 1798 - dst_fp->filp, dst_off, 1799 - len, 0); 1797 + ret = vfs_copy_file_range(src_fp->filp, src_off, 1798 + dst_fp->filp, dst_off, len, 1799 + COPY_FILE_SPLICE); 1800 1800 if (ret < 0) 1801 1801 return ret; 1802 1802
+2 -2
fs/nfsd/vfs.c
··· 596 596 ret = vfs_copy_file_range(src, src_pos, dst, dst_pos, count, 0); 597 597 598 598 if (ret == -EOPNOTSUPP || ret == -EXDEV) 599 - ret = generic_copy_file_range(src, src_pos, dst, dst_pos, 600 - count, 0); 599 + ret = vfs_copy_file_range(src, src_pos, dst, dst_pos, count, 600 + COPY_FILE_SPLICE); 601 601 return ret; 602 602 } 603 603
+15 -4
fs/read_write.c
··· 1388 1388 struct file *file_out, loff_t pos_out, 1389 1389 size_t len, unsigned int flags) 1390 1390 { 1391 + lockdep_assert(sb_write_started(file_inode(file_out)->i_sb)); 1392 + 1391 1393 return do_splice_direct(file_in, &pos_in, file_out, &pos_out, 1392 1394 len > MAX_RW_COUNT ? MAX_RW_COUNT : len, 0); 1393 1395 } ··· 1426 1424 * and several different sets of file_operations, but they all end up 1427 1425 * using the same ->copy_file_range() function pointer. 1428 1426 */ 1429 - if (file_out->f_op->copy_file_range) { 1427 + if (flags & COPY_FILE_SPLICE) { 1428 + /* cross sb splice is allowed */ 1429 + } else if (file_out->f_op->copy_file_range) { 1430 1430 if (file_in->f_op->copy_file_range != 1431 1431 file_out->f_op->copy_file_range) 1432 1432 return -EXDEV; ··· 1478 1474 size_t len, unsigned int flags) 1479 1475 { 1480 1476 ssize_t ret; 1477 + bool splice = flags & COPY_FILE_SPLICE; 1481 1478 1482 - if (flags != 0) 1479 + if (flags & ~COPY_FILE_SPLICE) 1483 1480 return -EINVAL; 1484 1481 1485 1482 ret = generic_copy_file_checks(file_in, pos_in, file_out, pos_out, &len, ··· 1506 1501 * same sb using clone, but for filesystems where both clone and copy 1507 1502 * are supported (e.g. nfs,cifs), we only call the copy method. 1508 1503 */ 1509 - if (file_out->f_op->copy_file_range) { 1504 + if (!splice && file_out->f_op->copy_file_range) { 1510 1505 ret = file_out->f_op->copy_file_range(file_in, pos_in, 1511 1506 file_out, pos_out, 1512 1507 len, flags); 1513 1508 goto done; 1514 1509 } 1515 1510 1516 - if (file_in->f_op->remap_file_range && 1511 + if (!splice && file_in->f_op->remap_file_range && 1517 1512 file_inode(file_in)->i_sb == file_inode(file_out)->i_sb) { 1518 1513 ret = file_in->f_op->remap_file_range(file_in, pos_in, 1519 1514 file_out, pos_out, ··· 1533 1528 * consistent story about which filesystems support copy_file_range() 1534 1529 * and which filesystems do not, that will allow userspace tools to 1535 1530 * make consistent desicions w.r.t using copy_file_range(). 1531 + * 1532 + * We also get here if caller (e.g. nfsd) requested COPY_FILE_SPLICE. 1536 1533 */ 1537 1534 ret = generic_copy_file_range(file_in, pos_in, file_out, pos_out, len, 1538 1535 flags); ··· 1588 1581 } else { 1589 1582 pos_out = f_out.file->f_pos; 1590 1583 } 1584 + 1585 + ret = -EINVAL; 1586 + if (flags != 0) 1587 + goto out; 1591 1588 1592 1589 ret = vfs_copy_file_range(f_in.file, pos_in, f_out.file, pos_out, len, 1593 1590 flags);
+8
include/linux/fs.h
··· 2089 2089 */ 2090 2090 #define REMAP_FILE_ADVISORY (REMAP_FILE_CAN_SHORTEN) 2091 2091 2092 + /* 2093 + * These flags control the behavior of vfs_copy_file_range(). 2094 + * They are not available to the user via syscall. 2095 + * 2096 + * COPY_FILE_SPLICE: call splice direct instead of fs clone/copy ops 2097 + */ 2098 + #define COPY_FILE_SPLICE (1 << 0) 2099 + 2092 2100 struct iov_iter; 2093 2101 struct io_uring_cmd; 2094 2102