diff options
author | Dave Chinner <dchinner@redhat.com> | 2015-06-03 19:19:18 -0400 |
---|---|---|
committer | Dave Chinner <david@fromorbit.com> | 2015-06-03 19:19:18 -0400 |
commit | cbe4dab119f211ff6642d617f541087894e99e4f (patch) | |
tree | 6751ee32423a7799e7ad31befc1c248365545030 | |
parent | 6e1ba0bcb84b3f97616feb07c27f974509ba57be (diff) |
xfs: add initial DAX support
Add initial DAX support to XFS. To do this we need a new mount
option to turn DAX on filesystem, and we need to propagate this into
the inode flags whenever an inode is instantiated so that the
per-inode checks throughout the code Do The Right Thing.
Signed-off-by: Dave Chinner <dchinner@redhat.com>
Reviewed-by: Brian Foster <bfoster@redhat.com>
Signed-off-by: Dave Chinner <david@fromorbit.com>
-rw-r--r-- | fs/xfs/xfs_iops.c | 24 | ||||
-rw-r--r-- | fs/xfs/xfs_mount.h | 2 | ||||
-rw-r--r-- | fs/xfs/xfs_super.c | 25 |
3 files changed, 37 insertions, 14 deletions
diff --git a/fs/xfs/xfs_iops.c b/fs/xfs/xfs_iops.c index 0994f95c368f..3e8d32d41f35 100644 --- a/fs/xfs/xfs_iops.c +++ b/fs/xfs/xfs_iops.c | |||
@@ -1195,22 +1195,22 @@ xfs_diflags_to_iflags( | |||
1195 | struct inode *inode, | 1195 | struct inode *inode, |
1196 | struct xfs_inode *ip) | 1196 | struct xfs_inode *ip) |
1197 | { | 1197 | { |
1198 | if (ip->i_d.di_flags & XFS_DIFLAG_IMMUTABLE) | 1198 | uint16_t flags = ip->i_d.di_flags; |
1199 | |||
1200 | inode->i_flags &= ~(S_IMMUTABLE | S_APPEND | S_SYNC | | ||
1201 | S_NOATIME | S_DAX); | ||
1202 | |||
1203 | if (flags & XFS_DIFLAG_IMMUTABLE) | ||
1199 | inode->i_flags |= S_IMMUTABLE; | 1204 | inode->i_flags |= S_IMMUTABLE; |
1200 | else | 1205 | if (flags & XFS_DIFLAG_APPEND) |
1201 | inode->i_flags &= ~S_IMMUTABLE; | ||
1202 | if (ip->i_d.di_flags & XFS_DIFLAG_APPEND) | ||
1203 | inode->i_flags |= S_APPEND; | 1206 | inode->i_flags |= S_APPEND; |
1204 | else | 1207 | if (flags & XFS_DIFLAG_SYNC) |
1205 | inode->i_flags &= ~S_APPEND; | ||
1206 | if (ip->i_d.di_flags & XFS_DIFLAG_SYNC) | ||
1207 | inode->i_flags |= S_SYNC; | 1208 | inode->i_flags |= S_SYNC; |
1208 | else | 1209 | if (flags & XFS_DIFLAG_NOATIME) |
1209 | inode->i_flags &= ~S_SYNC; | ||
1210 | if (ip->i_d.di_flags & XFS_DIFLAG_NOATIME) | ||
1211 | inode->i_flags |= S_NOATIME; | 1210 | inode->i_flags |= S_NOATIME; |
1212 | else | 1211 | /* XXX: Also needs an on-disk per inode flag! */ |
1213 | inode->i_flags &= ~S_NOATIME; | 1212 | if (ip->i_mount->m_flags & XFS_MOUNT_DAX) |
1213 | inode->i_flags |= S_DAX; | ||
1214 | } | 1214 | } |
1215 | 1215 | ||
1216 | /* | 1216 | /* |
diff --git a/fs/xfs/xfs_mount.h b/fs/xfs/xfs_mount.h index 8c995a2ccb6f..cd44e88efa53 100644 --- a/fs/xfs/xfs_mount.h +++ b/fs/xfs/xfs_mount.h | |||
@@ -179,6 +179,8 @@ typedef struct xfs_mount { | |||
179 | allocator */ | 179 | allocator */ |
180 | #define XFS_MOUNT_NOATTR2 (1ULL << 25) /* disable use of attr2 format */ | 180 | #define XFS_MOUNT_NOATTR2 (1ULL << 25) /* disable use of attr2 format */ |
181 | 181 | ||
182 | #define XFS_MOUNT_DAX (1ULL << 62) /* TEST ONLY! */ | ||
183 | |||
182 | 184 | ||
183 | /* | 185 | /* |
184 | * Default minimum read and write sizes. | 186 | * Default minimum read and write sizes. |
diff --git a/fs/xfs/xfs_super.c b/fs/xfs/xfs_super.c index 858e1e62bbaa..1fb16562c159 100644 --- a/fs/xfs/xfs_super.c +++ b/fs/xfs/xfs_super.c | |||
@@ -112,6 +112,8 @@ static struct xfs_kobj xfs_dbg_kobj; /* global debug sysfs attrs */ | |||
112 | #define MNTOPT_DISCARD "discard" /* Discard unused blocks */ | 112 | #define MNTOPT_DISCARD "discard" /* Discard unused blocks */ |
113 | #define MNTOPT_NODISCARD "nodiscard" /* Do not discard unused blocks */ | 113 | #define MNTOPT_NODISCARD "nodiscard" /* Do not discard unused blocks */ |
114 | 114 | ||
115 | #define MNTOPT_DAX "dax" /* Enable direct access to bdev pages */ | ||
116 | |||
115 | /* | 117 | /* |
116 | * Table driven mount option parser. | 118 | * Table driven mount option parser. |
117 | * | 119 | * |
@@ -363,6 +365,10 @@ xfs_parseargs( | |||
363 | mp->m_flags |= XFS_MOUNT_DISCARD; | 365 | mp->m_flags |= XFS_MOUNT_DISCARD; |
364 | } else if (!strcmp(this_char, MNTOPT_NODISCARD)) { | 366 | } else if (!strcmp(this_char, MNTOPT_NODISCARD)) { |
365 | mp->m_flags &= ~XFS_MOUNT_DISCARD; | 367 | mp->m_flags &= ~XFS_MOUNT_DISCARD; |
368 | #ifdef CONFIG_FS_DAX | ||
369 | } else if (!strcmp(this_char, MNTOPT_DAX)) { | ||
370 | mp->m_flags |= XFS_MOUNT_DAX; | ||
371 | #endif | ||
366 | } else { | 372 | } else { |
367 | xfs_warn(mp, "unknown mount option [%s].", this_char); | 373 | xfs_warn(mp, "unknown mount option [%s].", this_char); |
368 | return -EINVAL; | 374 | return -EINVAL; |
@@ -452,8 +458,8 @@ done: | |||
452 | } | 458 | } |
453 | 459 | ||
454 | struct proc_xfs_info { | 460 | struct proc_xfs_info { |
455 | int flag; | 461 | uint64_t flag; |
456 | char *str; | 462 | char *str; |
457 | }; | 463 | }; |
458 | 464 | ||
459 | STATIC int | 465 | STATIC int |
@@ -474,6 +480,7 @@ xfs_showargs( | |||
474 | { XFS_MOUNT_GRPID, "," MNTOPT_GRPID }, | 480 | { XFS_MOUNT_GRPID, "," MNTOPT_GRPID }, |
475 | { XFS_MOUNT_DISCARD, "," MNTOPT_DISCARD }, | 481 | { XFS_MOUNT_DISCARD, "," MNTOPT_DISCARD }, |
476 | { XFS_MOUNT_SMALL_INUMS, "," MNTOPT_32BITINODE }, | 482 | { XFS_MOUNT_SMALL_INUMS, "," MNTOPT_32BITINODE }, |
483 | { XFS_MOUNT_DAX, "," MNTOPT_DAX }, | ||
477 | { 0, NULL } | 484 | { 0, NULL } |
478 | }; | 485 | }; |
479 | static struct proc_xfs_info xfs_info_unset[] = { | 486 | static struct proc_xfs_info xfs_info_unset[] = { |
@@ -1507,6 +1514,20 @@ xfs_fs_fill_super( | |||
1507 | if (XFS_SB_VERSION_NUM(&mp->m_sb) == XFS_SB_VERSION_5) | 1514 | if (XFS_SB_VERSION_NUM(&mp->m_sb) == XFS_SB_VERSION_5) |
1508 | sb->s_flags |= MS_I_VERSION; | 1515 | sb->s_flags |= MS_I_VERSION; |
1509 | 1516 | ||
1517 | if (mp->m_flags & XFS_MOUNT_DAX) { | ||
1518 | xfs_warn(mp, | ||
1519 | "DAX enabled. Warning: EXPERIMENTAL, use at your own risk"); | ||
1520 | if (sb->s_blocksize != PAGE_SIZE) { | ||
1521 | xfs_alert(mp, | ||
1522 | "Filesystem block size invalid for DAX Turning DAX off."); | ||
1523 | mp->m_flags &= ~XFS_MOUNT_DAX; | ||
1524 | } else if (!sb->s_bdev->bd_disk->fops->direct_access) { | ||
1525 | xfs_alert(mp, | ||
1526 | "Block device does not support DAX Turning DAX off."); | ||
1527 | mp->m_flags &= ~XFS_MOUNT_DAX; | ||
1528 | } | ||
1529 | } | ||
1530 | |||
1510 | error = xfs_mountfs(mp); | 1531 | error = xfs_mountfs(mp); |
1511 | if (error) | 1532 | if (error) |
1512 | goto out_filestream_unmount; | 1533 | goto out_filestream_unmount; |