aboutsummaryrefslogtreecommitdiffstats
path: root/fs/xfs/linux-2.6/xfs_aops.c
diff options
context:
space:
mode:
authorChristoph Hellwig <hch@infradead.org>2010-12-10 08:42:16 +0000
committerAlex Elder <aelder@sgi.com>2010-12-16 16:05:34 -0600
commit85da94c6b4666582c38579ccdcd90a5d9b5697ef (patch)
tree013edf60a13fd0a551e95bf76a1284209ecd23c2 /fs/xfs/linux-2.6/xfs_aops.c
parentc9f71f5fc4390ea3a8087c00d53a799e7e0f0f8e (diff)
downloadlinux-85da94c6b4666582c38579ccdcd90a5d9b5697ef.tar.gz
xfs: improve mapping type check in xfs_vm_writepage
Currently we only refuse a "read-only" mapping for writing out unwritten and delayed buffers, and refuse any other for overwrites. Improve the checks to require delalloc mappings for delayed buffers, and unwritten extent mappings for unwritten extents. Signed-off-by: Christoph Hellwig <hch@lst.de> Reviewed-by: Dave Chinner <dchinner@redhat.com> Signed-off-by: Alex Elder <aelder@sgi.com>
Diffstat (limited to 'fs/xfs/linux-2.6/xfs_aops.c')
-rw-r--r--fs/xfs/linux-2.6/xfs_aops.c21
1 files changed, 12 insertions, 9 deletions
diff --git a/fs/xfs/linux-2.6/xfs_aops.c b/fs/xfs/linux-2.6/xfs_aops.c
index 691f61223ed628..23a7668e07daca 100644
--- a/fs/xfs/linux-2.6/xfs_aops.c
+++ b/fs/xfs/linux-2.6/xfs_aops.c
@@ -1082,17 +1082,17 @@ xfs_vm_writepage(
if (buffer_unwritten(bh) || buffer_delay(bh)) {
int new_ioend = 0;
- /*
- * Make sure we don't use a read-only iomap
- */
- if (flags == BMAPI_READ)
- imap_valid = 0;
-
if (buffer_unwritten(bh)) {
- type = IO_UNWRITTEN;
+ if (type != IO_UNWRITTEN) {
+ type = IO_UNWRITTEN;
+ imap_valid = 0;
+ }
flags = BMAPI_WRITE | BMAPI_IGNSTATE;
} else if (buffer_delay(bh)) {
- type = IO_DELAY;
+ if (type != IO_DELAY) {
+ type = IO_DELAY;
+ imap_valid = 0;
+ }
flags = BMAPI_ALLOCATE;
if (wbc->sync_mode == WB_SYNC_NONE)
@@ -1128,8 +1128,11 @@ xfs_vm_writepage(
* That means it must already have extents allocated
* underneath it. Map the extent by reading it.
*/
- if (!imap_valid || flags != BMAPI_READ) {
+ if (flags != BMAPI_READ) {
flags = BMAPI_READ;
+ imap_valid = 0;
+ }
+ if (!imap_valid) {
size = xfs_probe_cluster(inode, page, bh, head);
err = xfs_map_blocks(inode, offset, size,
&imap, flags);