xfs: allow logical-sector sized O_DIRECT for any fs sector size
v3 cover xfs: allow logical-sector sized O_DIRECT for any fs sector size
Ok once more with feeling.
Patchset to allow sub-fs-metadata-sector-sized DIOs.
I have (still) explicitly not changed XFS_IOC_DIOINFO output for now; it still reports the actual minimum sizes and alignments which will be allowed by the filesystem (and block layer beneath it).
Thanks,
-Eric
_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs
PATCH v3 1/3 xfs: clean up xfs_buftarg
Clean up the xfs_buftarg structure a bit:
- remove bt_bsize which is never used
- replace bt_sshift with bt_ssize; we only ever shift it back
---
fs/xfs/xfs_buf.c +2 -3
@@ -445,7 +445,7 @@ _xfs_buf_find( numbytes =BBTOB (numblks);/* Check for IOs smaller than the sector size / not sector aligned */ -ASSERT (!(numbytes < (1 << btp->bt_sshift))); +ASSERT (!(numbytes < btp->bt_ssize));ASSERT (!(BBTOB (blkno) & (xfs_off_t )btp->bt_smask));/*
@@ -1599,8 +1599,7 @@ xfs_setsize_buftarg(unsigned int blocksize, unsigned int sectorsize) { - btp->bt_bsize = blocksize; - btp->bt_sshift =ffs (sectorsize) -1 ; + btp->bt_ssize = sectorsize; btp->bt_smask = sectorsize -1 ;if (set_blocksize (btp->bt_bdev, sectorsize)) {
fs/xfs/xfs_buf.h +1 -2
@@ -93,8 +93,7 @@ typedef struct xfs_buftarg {struct block_device *bt_bdev;struct backing_dev_info *bt_bdi;struct xfs_mount *bt_mount; -unsigned int bt_bsize; -unsigned int bt_sshift; +unsigned int bt_ssize;size_t bt_smask;/* LRU control structures */
fs/xfs/xfs_ioctl.c +1 -1
@@ -1587,7 +1587,7 @@ xfs_file_ioctl(XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; - da.d_mem = da.d_miniosz =1 << target->bt_sshift; + da.d_mem = da.d_miniosz = target->bt_ssize; da.d_maxiosz =INT_MAX & ~(da.d_miniosz -1 );if (copy_to_user (arg, &da,sizeof (da)))
_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs
Re: [PATCH 1/3 V3] xfs: clean up xfs_buftarg
Quoted 5 lines · Eric Sandeen
Clean up the
xfs_buftargstructure a bit:
- removebt_bsizewhich is never used
- replacebt_sshiftwithbt_ssize; we only ever shift it backSigned-off-by Eric Sandeen <[email protected]>
Looks good.
Signature · 7 lines
Dave Chinner [email protected] _______________________________________________ xfs mailing list [email protected] http://oss.sgi.com/mailman/listinfo/xfs
PATCH v3 2/3 xfs: rename xfs_buftarg structure members
In reply to Eric SandeenIn preparation for adding new members to the structure, give these old ones more descriptive names:
bt_ssize -> bt_meta_sectorsize bt_smask -> bt_meta_sectormask
---
fs/xfs/xfs_buf.c +4 -4
@@ -445,8 +445,8 @@ _xfs_buf_find( numbytes =BBTOB (numblks);/* Check for IOs smaller than the sector size / not sector aligned */ -ASSERT (!(numbytes < btp->bt_ssize)); -ASSERT (!(BBTOB (blkno) & (xfs_off_t )btp->bt_smask)); +ASSERT (!(numbytes < btp->bt_meta_sectorsize)); +ASSERT (!(BBTOB (blkno) & (xfs_off_t )btp->bt_meta_sectormask));/* * Corrupted block numbers can get through to here, unfortunately, so we
@@ -1599,8 +1599,8 @@ xfs_setsize_buftarg(unsigned int blocksize, unsigned int sectorsize) { - btp->bt_ssize = sectorsize; - btp->bt_smask = sectorsize -1 ; + btp->bt_meta_sectorsize = sectorsize; + btp->bt_meta_sectormask = sectorsize -1 ;if (set_blocksize (btp->bt_bdev, sectorsize)) {char name[BDEVNAME_SIZE ];
fs/xfs/xfs_buf.h +2 -2
@@ -93,8 +93,8 @@ typedef struct xfs_buftarg {struct block_device *bt_bdev;struct backing_dev_info *bt_bdi;struct xfs_mount *bt_mount; -unsigned int bt_ssize; -size_t bt_smask; +unsigned int bt_meta_sectorsize; +size_t bt_meta_sectormask;/* LRU control structures */ struct shrinker bt_shrinker;
fs/xfs/xfs_file.c +2 -2
@@ -261,7 +261,7 @@ xfs_file_aio_read(xfs_buftarg_t *target =XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; -if ((pos & target->bt_smask) || (size & target->bt_smask)) { +if ((pos | size) & target->bt_meta_sectormask) {if (pos ==i_size_read (inode))return 0 ;return -XFS_ERROR (EINVAL );
@@ -641,7 +641,7 @@ xfs_file_dio_aio_write(struct xfs_buftarg *target =XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; -if ((pos & target->bt_smask) || (count & target->bt_smask)) +if ((pos | count) & target->bt_meta_sectormask)return -XFS_ERROR (EINVAL );if ((pos & mp->m_blockmask) || ((pos + count) & mp->m_blockmask))
fs/xfs/xfs_ioctl.c +1 -1
@@ -1587,7 +1587,7 @@ xfs_file_ioctl(XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; - da.d_mem = da.d_miniosz = target->bt_ssize; + da.d_mem = da.d_miniosz = target->bt_meta_sectorsize; da.d_maxiosz =INT_MAX & ~(da.d_miniosz -1 );if (copy_to_user (arg, &da,sizeof (da)))
_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs
Re: [PATCH 2/3 V3] xfs: rename xfs_buftarg structure members
Quoted 7 lines · Eric Sandeen
In preparation for adding new members to the structure, give these old ones more descriptive names:
bt_ssize -> bt_meta_sectorsize bt_smask -> bt_meta_sectormaskSigned-off-by Eric Sandeen <[email protected]>
looks good. Thanks for renaming these ;)
Signature · 7 lines
Dave Chinner [email protected] _______________________________________________ xfs mailing list [email protected] http://oss.sgi.com/mailman/listinfo/xfs
PATCH v3 3/3 xfs: allow logical-sector sized O_DIRECT
In reply to Eric SandeenSome time ago, mkfs.xfs started picking the storage physical sector size as the default filesystem "sector size" in order to avoid RMW costs incurred by doing IOs at logical sector size alignments.
However, this means that for a filesystem made with i.e. a 4k sector size on an "advanced format" 4k/512 disk, 512-byte direct IOs are no longer allowed. This means that XFS has essentially turned this AF drive into a hard 4K device, from the filesystem on up.
XFS's mkfs-specified "sector size" is really just controlling the minimum size & alignment of filesystem metadata.
There is no real need to tightly couple XFS's minimal metadata size to the minimum allowed direct IO size; XFS can continue doing metadata in optimal sizes, but still allow smaller DIOs for apps which issue them, for whatever reason.
This patch adds a new field to the xfs_buftarg, so that we now track 2 sizes:
1) The metadata sector size, which is the minimum unit and alignment of IO which will be performed by metadata operations.
2) The device logical sector size
The first is used internally by the file system for metadata alignment and IOs.
The second is used for the minimum allowed direct IO alignment.
This has passed xfstests on filesystems made with 4k sectors, including when run under the patch I sent to ignore XFS_IOC_DIOINFO, and issue 512 DIOs anyway. I also directly tested end of block behavior on preallocated, sparse, and existing files when we do a 512 IO into a 4k file on a 4k-sector filesystem, to be sure there were no unexpected behaviors.
---
fs/xfs/xfs_buf.c +5 -0
@@ -1599,6 +1599,7 @@ xfs_setsize_buftarg(unsigned int blocksize, unsigned int sectorsize) { +/* Set up metadata sector size info */ btp->bt_meta_sectorsize = sectorsize; btp->bt_meta_sectormask = sectorsize -1 ;
@@ -1613,6 +1614,10 @@ xfs_setsize_buftarg(return EINVAL ; } +/* Set up device logical sector size mask */ + btp->bt_logical_sectorsize =bdev_logical_block_size (btp->bt_bdev); + btp->bt_logical_sectormask =bdev_logical_block_size (btp->bt_bdev) -1 ; +return 0 ; }
fs/xfs/xfs_buf.h +15 -0
@@ -88,6 +88,19 @@ typedef unsigned int xfs_buf_flags_t;*/ #define XFS_BSTATE_DISPOSE (1 << 0)/* buffer being discarded */ +/* +* The xfs_buftarg contains 2 notions of "sector size" - +* +* 1) The metadata sector size, which is the minimum unit and +* alignment of IO which will be performed by metadata operations. +* 2) The device logical sector size +* +* The first is specified at mkfs time, and is stored on-disk in the +* superblock's sb_sectsize. +* +* The latter is derived from the underlying device, and controls direct IO +* alignment constraints. +*/ typedef struct xfs_buftarg { dev_t bt_dev; struct block_device *bt_bdev;
@@ -95,6 +108,8 @@ typedef struct xfs_buftarg {struct xfs_mount *bt_mount;unsigned int bt_meta_sectorsize;size_t bt_meta_sectormask; +size_t bt_logical_sectorsize; +size_t bt_logical_sectormask;/* LRU control structures */ struct shrinker bt_shrinker;
fs/xfs/xfs_file.c +5 -2
@@ -261,7 +261,8 @@ xfs_file_aio_read(xfs_buftarg_t *target =XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; -if ((pos | size) & target->bt_meta_sectormask) { +/* DIO must be aligned to device logical sector size */ +if ((pos | size) & target->bt_logical_sectormask) {if (pos ==i_size_read (inode))return 0 ;return -XFS_ERROR (EINVAL );
@@ -641,9 +642,11 @@ xfs_file_dio_aio_write(struct xfs_buftarg *target =XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; -if ((pos | count) & target->bt_meta_sectormask) +/* DIO must be aligned to device logical sector size */ +if ((pos | count) & target->bt_logical_sectormask)return -XFS_ERROR (EINVAL ); +/* "unaligned" here means not aligned to a filesystem block */ if ((pos & mp->m_blockmask) || ((pos + count) & mp->m_blockmask)) unaligned_io =1 ;
fs/xfs/xfs_ioctl.c +1 -1
@@ -1587,7 +1587,7 @@ xfs_file_ioctl(XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; - da.d_mem = da.d_miniosz = target->bt_meta_sectorsize; + da.d_mem = da.d_miniosz = target->bt_logical_sectorsize; da.d_maxiosz =INT_MAX & ~(da.d_miniosz -1 );if (copy_to_user (arg, &da,sizeof (da)))
_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs
Re: [PATCH 3/3 V3] xfs: allow logical-sector sized O_DIRECT
Quoted 39 lines · Eric Sandeen
Some time ago, mkfs.xfs started picking the storage physical sector size as the default filesystem "sector size" in order to avoid RMW costs incurred by doing IOs at logical sector size alignments.
However, this means that for a filesystem made with i.e. a 4k sector size on an "advanced format" 4k/512 disk, 512-byte direct IOs are no longer allowed. This means that XFS has essentially turned this AF drive into a hard 4K device, from the filesystem on up.
XFS's mkfs-specified "sector size" is really just controlling the minimum size & alignment of filesystem metadata.
There is no real need to tightly couple XFS's minimal metadata size to the minimum allowed direct IO size; XFS can continue doing metadata in optimal sizes, but still allow smaller DIOs for apps which issue them, for whatever reason.
This patch adds a new field to the
xfs_buftarg, so that we now track 2 sizes:1) The metadata sector size, which is the minimum unit and alignment of IO which will be performed by metadata operations.
2) The device logical sector sizeThe first is used internally by the file system for metadata alignment and IOs.
The second is used for the minimum allowed direct IO alignment.This has passed xfstests on filesystems made with 4k sectors, including when run under the patch I sent to ignore
XFS_IOC_DIOINFO, and issue 512 DIOs anyway. I also directly tested end of block behavior on preallocated, sparse, and existing files when we do a 512 IO into a 4k file on a 4k-sector filesystem, to be sure there were no unexpected behaviors.
Quoted 2 lines
Signed-off-by Eric Sandeen <[email protected]>---
Looks good to me...
Quoted 98 lines
fs/xfs/xfs_buf.c +5
-0@@ -1599,6 +1599,7 @@ xfs_setsize_buftarg(unsigned int blocksize, unsigned int sectorsize) { +/* Set up metadata sector size info */ btp->bt_meta_sectorsize = sectorsize; btp->bt_meta_sectormask = sectorsize -1 ;@@ -1613,6 +1614,10 @@ xfs_setsize_buftarg(return EINVAL ; } +/* Set up device logical sector size mask */ + btp->bt_logical_sectorsize =bdev_logical_block_size (btp->bt_bdev); + btp->bt_logical_sectormask =bdev_logical_block_size (btp->bt_bdev) -1 ; +return 0 ; }fs/xfs/xfs_buf.h +15
-0@@ -88,6 +88,19 @@ typedef unsigned int xfs_buf_flags_t;*/ #define XFS_BSTATE_DISPOSE (1 << 0)/* buffer being discarded */ +/* +* The xfs_buftarg contains 2 notions of "sector size" - +* +* 1) The metadata sector size, which is the minimum unit and +* alignment of IO which will be performed by metadata operations. +* 2) The device logical sector size +* +* The first is specified at mkfs time, and is stored on-disk in the +* superblock's sb_sectsize. +* +* The latter is derived from the underlying device, and controls direct IO +* alignment constraints. +*/ typedef struct xfs_buftarg { dev_t bt_dev; struct block_device *bt_bdev;@@ -95,6 +108,8 @@ typedef struct xfs_buftarg {struct xfs_mount *bt_mount;unsigned int bt_meta_sectorsize;size_t bt_meta_sectormask; +size_t bt_logical_sectorsize; +size_t bt_logical_sectormask;/* LRU control structures */ struct shrinker bt_shrinker;fs/xfs/xfs_file.c +5
-2@@ -261,7 +261,8 @@ xfs_file_aio_read(xfs_buftarg_t *target =XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; -if ((pos | size) & target->bt_meta_sectormask) { +/* DIO must be aligned to device logical sector size */ +if ((pos | size) & target->bt_logical_sectormask) {if (pos ==i_size_read (inode))return 0 ;return -XFS_ERROR (EINVAL );@@ -641,9 +642,11 @@ xfs_file_dio_aio_write(struct xfs_buftarg *target =XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; -if ((pos | count) & target->bt_meta_sectormask) +/* DIO must be aligned to device logical sector size */ +if ((pos | count) & target->bt_logical_sectormask)return -XFS_ERROR (EINVAL ); +/* "unaligned" here means not aligned to a filesystem block */ if ((pos & mp->m_blockmask) || ((pos + count) & mp->m_blockmask)) unaligned_io =1 ;fs/xfs/xfs_ioctl.c +1
-1@@ -1587,7 +1587,7 @@ xfs_file_ioctl(XFS_IS_REALTIME_INODE (ip) ? mp->m_rtdev_targp : mp->m_ddev_targp; - da.d_mem = da.d_miniosz = target->bt_meta_sectorsize; + da.d_mem = da.d_miniosz = target->bt_logical_sectorsize; da.d_maxiosz =INT_MAX & ~(da.d_miniosz -1 );if (copy_to_user (arg, &da,sizeof (da)))
Quoted 5 lines
_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs
_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs
Re: [PATCH 3/3 V3] xfs: allow logical-sector sized O_DIRECT
In reply to Eric SandeenQuoted 39 lines · Eric Sandeen
Some time ago, mkfs.xfs started picking the storage physical sector size as the default filesystem "sector size" in order to avoid RMW costs incurred by doing IOs at logical sector size alignments.
However, this means that for a filesystem made with i.e. a 4k sector size on an "advanced format" 4k/512 disk, 512-byte direct IOs are no longer allowed. This means that XFS has essentially turned this AF drive into a hard 4K device, from the filesystem on up.
XFS's mkfs-specified "sector size" is really just controlling the minimum size & alignment of filesystem metadata.
There is no real need to tightly couple XFS's minimal metadata size to the minimum allowed direct IO size; XFS can continue doing metadata in optimal sizes, but still allow smaller DIOs for apps which issue them, for whatever reason.
This patch adds a new field to the
xfs_buftarg, so that we now track 2 sizes:1) The metadata sector size, which is the minimum unit and alignment of IO which will be performed by metadata operations.
2) The device logical sector sizeThe first is used internally by the file system for metadata alignment and IOs.
The second is used for the minimum allowed direct IO alignment.This has passed xfstests on filesystems made with 4k sectors, including when run under the patch I sent to ignore
XFS_IOC_DIOINFO, and issue 512 DIOs anyway. I also directly tested end of block behavior on preallocated, sparse, and existing files when we do a 512 IO into a 4k file on a 4k-sector filesystem, to be sure there were no unexpected behaviors.
Quoted 1 line
Signed-off-by Eric Sandeen <[email protected]>
Looks good. Nice work with the comments.
Signature · 7 lines
Dave Chinner [email protected] _______________________________________________ xfs mailing list [email protected] http://oss.sgi.com/mailman/listinfo/xfs