aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDarrick J. Wong <darrick.wong@oracle.com>2018-05-31 18:07:47 -0400
committerDarrick J. Wong <darrick.wong@oracle.com>2018-06-04 17:45:29 -0400
commitaaacdd257fd038a7d265fe4dc30d71fb1bfcadda (patch)
treee42f466a3e2d46aacc137813ec113e90d58f85df
parent9f96cc958e8ae9864e6d597a5f3e80b5fca35ae4 (diff)
xfs: don't forbid setting dax flag on directories if device doesn't dax
On a directory, the DAX flag is merely a hint that files created in the directory should have the DAX flag set at creation time. We don't care if the underlying device supports DAX or not because directory metadata are always cached in DRAM. We don't care if new files get the flag even if the device doesn't support DAX because we always check for DAX support before setting the VFS flag (S_DAX). Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com> Reviewed-by: Dave Chinner <dchinner@redhat.com>
-rw-r--r--fs/xfs/xfs_ioctl.c9
1 files changed, 7 insertions, 2 deletions
diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c
index 5dd9e22b4a4c..82f7c83c1dad 100644
--- a/fs/xfs/xfs_ioctl.c
+++ b/fs/xfs/xfs_ioctl.c
@@ -1098,12 +1098,14 @@ xfs_ioctl_setattr_dax_invalidate(
1098 /* 1098 /*
1099 * It is only valid to set the DAX flag on regular files and 1099 * It is only valid to set the DAX flag on regular files and
1100 * directories on filesystems where the block size is equal to the page 1100 * directories on filesystems where the block size is equal to the page
1101 * size. On directories it serves as an inherit hint. 1101 * size. On directories it serves as an inherited hint so we don't
1102 * have to check the device for dax support or flush pagecache.
1102 */ 1103 */
1103 if (fa->fsx_xflags & FS_XFLAG_DAX) { 1104 if (fa->fsx_xflags & FS_XFLAG_DAX) {
1104 if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode))) 1105 if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode)))
1105 return -EINVAL; 1106 return -EINVAL;
1106 if (!bdev_dax_supported(xfs_find_bdev_for_inode(VFS_I(ip)), 1107 if (S_ISREG(inode->i_mode) &&
1108 !bdev_dax_supported(xfs_find_bdev_for_inode(VFS_I(ip)),
1107 sb->s_blocksize)) 1109 sb->s_blocksize))
1108 return -EINVAL; 1110 return -EINVAL;
1109 } 1111 }
@@ -1114,6 +1116,9 @@ xfs_ioctl_setattr_dax_invalidate(
1114 if (!(fa->fsx_xflags & FS_XFLAG_DAX) && !IS_DAX(inode)) 1116 if (!(fa->fsx_xflags & FS_XFLAG_DAX) && !IS_DAX(inode))
1115 return 0; 1117 return 0;
1116 1118
1119 if (S_ISDIR(inode->i_mode))
1120 return 0;
1121
1117 /* lock, flush and invalidate mapping in preparation for flag change */ 1122 /* lock, flush and invalidate mapping in preparation for flag change */
1118 xfs_ilock(ip, XFS_MMAPLOCK_EXCL | XFS_IOLOCK_EXCL); 1123 xfs_ilock(ip, XFS_MMAPLOCK_EXCL | XFS_IOLOCK_EXCL);
1119 error = filemap_write_and_wait(inode->i_mapping); 1124 error = filemap_write_and_wait(inode->i_mapping);