diff options
author | Brian Foster <bfoster@redhat.com> | 2018-05-09 18:45:04 +0300 |
---|---|---|
committer | Darrick J. Wong <darrick.wong@oracle.com> | 2018-05-10 18:56:47 +0300 |
commit | 13b86fc33718c6b504baa472437ae14a33abc138 (patch) | |
tree | fb504176f81507e48e89c44721ff55410dedb19d /fs/xfs/xfs_inode.c | |
parent | fcb762f5de2e534ab47b5f034fe484c2b25b4d51 (diff) | |
download | linux-13b86fc33718c6b504baa472437ae14a33abc138.tar.xz |
xfs: skip online discard during eofblocks trims
We've had reports of online discard operations being sent from XFS
on write-only workloads. These discards occur as a result of
eofblocks trims that can occur after a large file copy completes.
These discards are slightly confusing for users who might be paying
close attention to online discards (i.e., vdo) due to performance
sensitivity. They also happen to be spurious because freed post-eof
blocks by definition have not been written to during the current
allocation cycle.
Update xfs_free_eofblocks() to skip discards that are purely
attributed to eofblocks trims. This cuts down the number of spurious
discards that may occur on write-only workloads due to normal
preallocation activity.
Note that discards of post-eof extents can still occur from other
codepaths that do not isolate handling of post-eof blocks from those
within eof. For example, file unlinks and truncates may still cause
discards for any file blocks affected by the operation.
Signed-off-by: Brian Foster <bfoster@redhat.com>
Reviewed-by: Darrick J. Wong <darrick.wong@oracle.com>
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
Diffstat (limited to 'fs/xfs/xfs_inode.c')
-rw-r--r-- | fs/xfs/xfs_inode.c | 19 |
1 files changed, 11 insertions, 8 deletions
diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index 42781bae6794..5b2e08488107 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -1548,11 +1548,12 @@ xfs_itruncate_clear_reflink_flags( * dirty on error so that transactions can be easily aborted if possible. */ int -xfs_itruncate_extents( +__xfs_itruncate_extents( struct xfs_trans **tpp, struct xfs_inode *ip, int whichfork, - xfs_fsize_t new_size) + xfs_fsize_t new_size, + bool skip_discard) { struct xfs_mount *mp = ip->i_mount; struct xfs_trans *tp = *tpp; @@ -1563,6 +1564,7 @@ xfs_itruncate_extents( xfs_filblks_t unmap_len; int error = 0; int done = 0; + int flags; ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL)); ASSERT(!atomic_read(&VFS_I(ip)->i_count) || @@ -1575,6 +1577,10 @@ xfs_itruncate_extents( trace_xfs_itruncate_extents_start(ip, new_size); + flags = xfs_bmapi_aflag(whichfork); + if (skip_discard) + flags |= XFS_BMAPI_NODISCARD; + /* * Since it is possible for space to become allocated beyond * the end of the file (in a crash where the space is allocated @@ -1593,12 +1599,9 @@ xfs_itruncate_extents( unmap_len = last_block - first_unmap_block + 1; while (!done) { xfs_defer_init(&dfops, &first_block); - error = xfs_bunmapi(tp, ip, - first_unmap_block, unmap_len, - xfs_bmapi_aflag(whichfork), - XFS_ITRUNC_MAX_EXTENTS, - &first_block, &dfops, - &done); + error = xfs_bunmapi(tp, ip, first_unmap_block, unmap_len, flags, + XFS_ITRUNC_MAX_EXTENTS, &first_block, + &dfops, &done); if (error) goto out_bmap_cancel; |