diff options
author | Jan Kara <jack@suse.cz> | 2009-08-18 10:18:20 -0400 |
---|---|---|
committer | Jan Kara <jack@suse.cz> | 2009-09-14 11:08:15 -0400 |
commit | c7b50db21fe8c295092518e224d60b95e69da3b0 (patch) | |
tree | ed73757b475462c4cfccdcf61d95929f4cb32637 /mm/filemap.c | |
parent | e4dd9de3c66bc7e26c5c7f149a060c5a67cf06a0 (diff) |
vfs: Remove syncing from generic_file_direct_write() and generic_file_buffered_write()
generic_file_direct_write() and generic_file_buffered_write() called
generic_osync_inode() if it was called on O_SYNC file or IS_SYNC inode. But
this is superfluous since generic_file_aio_write() does the syncing as well.
Also XFS and OCFS2 which call these functions directly handle syncing
themselves. So let's have a single place where syncing happens:
generic_file_aio_write().
We slightly change the behavior by syncing only the range of file to which the
write happened for buffered writes but that should be all that is required.
CC: ocfs2-devel@oss.oracle.com
CC: Joel Becker <joel.becker@oracle.com>
CC: Felix Blyakher <felixb@sgi.com>
CC: xfs@oss.sgi.com
Signed-off-by: Jan Kara <jack@suse.cz>
Diffstat (limited to 'mm/filemap.c')
-rw-r--r-- | mm/filemap.c | 35 |
1 files changed, 6 insertions, 29 deletions
diff --git a/mm/filemap.c b/mm/filemap.c index 554a396d85e2..f863e1d7e227 100644 --- a/mm/filemap.c +++ b/mm/filemap.c | |||
@@ -2187,20 +2187,7 @@ generic_file_direct_write(struct kiocb *iocb, const struct iovec *iov, | |||
2187 | } | 2187 | } |
2188 | *ppos = end; | 2188 | *ppos = end; |
2189 | } | 2189 | } |
2190 | |||
2191 | /* | ||
2192 | * Sync the fs metadata but not the minor inode changes and | ||
2193 | * of course not the data as we did direct DMA for the IO. | ||
2194 | * i_mutex is held, which protects generic_osync_inode() from | ||
2195 | * livelocking. AIO O_DIRECT ops attempt to sync metadata here. | ||
2196 | */ | ||
2197 | out: | 2190 | out: |
2198 | if ((written >= 0 || written == -EIOCBQUEUED) && | ||
2199 | ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | ||
2200 | int err = generic_osync_inode(inode, mapping, OSYNC_METADATA); | ||
2201 | if (err < 0) | ||
2202 | written = err; | ||
2203 | } | ||
2204 | return written; | 2191 | return written; |
2205 | } | 2192 | } |
2206 | EXPORT_SYMBOL(generic_file_direct_write); | 2193 | EXPORT_SYMBOL(generic_file_direct_write); |
@@ -2332,8 +2319,6 @@ generic_file_buffered_write(struct kiocb *iocb, const struct iovec *iov, | |||
2332 | { | 2319 | { |
2333 | struct file *file = iocb->ki_filp; | 2320 | struct file *file = iocb->ki_filp; |
2334 | struct address_space *mapping = file->f_mapping; | 2321 | struct address_space *mapping = file->f_mapping; |
2335 | const struct address_space_operations *a_ops = mapping->a_ops; | ||
2336 | struct inode *inode = mapping->host; | ||
2337 | ssize_t status; | 2322 | ssize_t status; |
2338 | struct iov_iter i; | 2323 | struct iov_iter i; |
2339 | 2324 | ||
@@ -2343,16 +2328,6 @@ generic_file_buffered_write(struct kiocb *iocb, const struct iovec *iov, | |||
2343 | if (likely(status >= 0)) { | 2328 | if (likely(status >= 0)) { |
2344 | written += status; | 2329 | written += status; |
2345 | *ppos = pos + status; | 2330 | *ppos = pos + status; |
2346 | |||
2347 | /* | ||
2348 | * For now, when the user asks for O_SYNC, we'll actually give | ||
2349 | * O_DSYNC | ||
2350 | */ | ||
2351 | if (unlikely((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | ||
2352 | if (!a_ops->writepage || !is_sync_kiocb(iocb)) | ||
2353 | status = generic_osync_inode(inode, mapping, | ||
2354 | OSYNC_METADATA|OSYNC_DATA); | ||
2355 | } | ||
2356 | } | 2331 | } |
2357 | 2332 | ||
2358 | /* | 2333 | /* |
@@ -2514,11 +2489,12 @@ ssize_t generic_file_aio_write_nolock(struct kiocb *iocb, | |||
2514 | 2489 | ||
2515 | ret = __generic_file_aio_write(iocb, iov, nr_segs, &iocb->ki_pos); | 2490 | ret = __generic_file_aio_write(iocb, iov, nr_segs, &iocb->ki_pos); |
2516 | 2491 | ||
2517 | if (ret > 0 && ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | 2492 | if ((ret > 0 || ret == -EIOCBQUEUED) && |
2493 | ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | ||
2518 | ssize_t err; | 2494 | ssize_t err; |
2519 | 2495 | ||
2520 | err = sync_page_range_nolock(inode, mapping, pos, ret); | 2496 | err = sync_page_range_nolock(inode, mapping, pos, ret); |
2521 | if (err < 0) | 2497 | if (err < 0 && ret > 0) |
2522 | ret = err; | 2498 | ret = err; |
2523 | } | 2499 | } |
2524 | return ret; | 2500 | return ret; |
@@ -2550,11 +2526,12 @@ ssize_t generic_file_aio_write(struct kiocb *iocb, const struct iovec *iov, | |||
2550 | ret = __generic_file_aio_write(iocb, iov, nr_segs, &iocb->ki_pos); | 2526 | ret = __generic_file_aio_write(iocb, iov, nr_segs, &iocb->ki_pos); |
2551 | mutex_unlock(&inode->i_mutex); | 2527 | mutex_unlock(&inode->i_mutex); |
2552 | 2528 | ||
2553 | if (ret > 0 && ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | 2529 | if ((ret > 0 || ret == -EIOCBQUEUED) && |
2530 | ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | ||
2554 | ssize_t err; | 2531 | ssize_t err; |
2555 | 2532 | ||
2556 | err = sync_page_range(inode, mapping, pos, ret); | 2533 | err = sync_page_range(inode, mapping, pos, ret); |
2557 | if (err < 0) | 2534 | if (err < 0 && ret > 0) |
2558 | ret = err; | 2535 | ret = err; |
2559 | } | 2536 | } |
2560 | return ret; | 2537 | return ret; |