Commit ed5c3e66 authored by Dave Chinner's avatar Dave Chinner Committed by Darrick J. Wong

xfs: move generic_write_sync calls inwards

To prepare for iomap iinfrastructure based DSYNC optimisations.

While moving the code araound, move the XFS write bytes metric
update for direct IO into xfs_dio_write_end_io callback so that we
always capture the amount of data written via AIO+DIO. This fixes
the problem where queued AIO+DIO writes are not accounted to this
metric.
Signed-Off-By: default avatarDave Chinner <dchinner@redhat.com>
Reviewed-by: default avatarChristoph Hellwig <hch@lst.de>
Reviewed-by: default avatarDarrick J. Wong <darrick.wong@oracle.com>
Signed-off-by: default avatarDarrick J. Wong <darrick.wong@oracle.com>
parent b027d4c9
...@@ -414,6 +414,12 @@ xfs_dio_write_end_io( ...@@ -414,6 +414,12 @@ xfs_dio_write_end_io(
if (size <= 0) if (size <= 0)
return size; return size;
/*
* Capture amount written on completion as we can't reliably account
* for it on submission.
*/
XFS_STATS_ADD(ip->i_mount, xs_write_bytes, size);
if (flags & IOMAP_DIO_COW) { if (flags & IOMAP_DIO_COW) {
error = xfs_reflink_end_cow(ip, offset, size); error = xfs_reflink_end_cow(ip, offset, size);
if (error) if (error)
...@@ -562,6 +568,11 @@ xfs_file_dio_aio_write( ...@@ -562,6 +568,11 @@ xfs_file_dio_aio_write(
* complete fully or fail. * complete fully or fail.
*/ */
ASSERT(ret < 0 || ret == count); ASSERT(ret < 0 || ret == count);
if (ret > 0) {
/* Handle various SYNC-type writes */
ret = generic_write_sync(iocb, ret);
}
return ret; return ret;
} }
...@@ -599,7 +610,16 @@ xfs_file_dax_write( ...@@ -599,7 +610,16 @@ xfs_file_dax_write(
} }
out: out:
xfs_iunlock(ip, iolock); xfs_iunlock(ip, iolock);
return error ? error : ret; if (error)
return error;
if (ret > 0) {
XFS_STATS_ADD(ip->i_mount, xs_write_bytes, ret);
/* Handle various SYNC-type writes */
ret = generic_write_sync(iocb, ret);
}
return ret;
} }
STATIC ssize_t STATIC ssize_t
...@@ -669,6 +689,12 @@ xfs_file_buffered_aio_write( ...@@ -669,6 +689,12 @@ xfs_file_buffered_aio_write(
out: out:
if (iolock) if (iolock)
xfs_iunlock(ip, iolock); xfs_iunlock(ip, iolock);
if (ret > 0) {
XFS_STATS_ADD(ip->i_mount, xs_write_bytes, ret);
/* Handle various SYNC-type writes */
ret = generic_write_sync(iocb, ret);
}
return ret; return ret;
} }
...@@ -693,8 +719,9 @@ xfs_file_write_iter( ...@@ -693,8 +719,9 @@ xfs_file_write_iter(
return -EIO; return -EIO;
if (IS_DAX(inode)) if (IS_DAX(inode))
ret = xfs_file_dax_write(iocb, from); return xfs_file_dax_write(iocb, from);
else if (iocb->ki_flags & IOCB_DIRECT) {
if (iocb->ki_flags & IOCB_DIRECT) {
/* /*
* Allow a directio write to fall back to a buffered * Allow a directio write to fall back to a buffered
* write *only* in the case that we're doing a reflink * write *only* in the case that we're doing a reflink
...@@ -702,20 +729,11 @@ xfs_file_write_iter( ...@@ -702,20 +729,11 @@ xfs_file_write_iter(
* allow an operation to fall back to buffered mode. * allow an operation to fall back to buffered mode.
*/ */
ret = xfs_file_dio_aio_write(iocb, from); ret = xfs_file_dio_aio_write(iocb, from);
if (ret == -EREMCHG) if (ret != -EREMCHG)
goto buffered; return ret;
} else {
buffered:
ret = xfs_file_buffered_aio_write(iocb, from);
} }
if (ret > 0) { return xfs_file_buffered_aio_write(iocb, from);
XFS_STATS_ADD(ip->i_mount, xs_write_bytes, ret);
/* Handle various SYNC-type writes */
ret = generic_write_sync(iocb, ret);
}
return ret;
} }
#define XFS_FALLOC_FL_SUPPORTED \ #define XFS_FALLOC_FL_SUPPORTED \
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment