diff options
author | Boaz Harrosh <bharrosh@panasas.com> | 2010-11-22 18:02:45 +0200 |
---|---|---|
committer | Boaz Harrosh <bharrosh@panasas.com> | 2011-03-15 15:02:49 +0200 |
commit | a8f1418f9e9bd4c487a7b703ff26c5dd5ceb2bf3 (patch) | |
tree | 9d72e1be99cf2eb4c8a35cfa8ac3df69dfbca01a /fs/exofs | |
parent | 0a935519cca83f26dc15e7577fa6c2b39606a4ac (diff) |
exofs: Optimize read_4_write
Don't attempt a read passed i_size, just zero the page and be
done with it.
Signed-off-by: Boaz Harrosh <bharrosh@panasas.com>
Diffstat (limited to 'fs/exofs')
-rw-r--r-- | fs/exofs/inode.c | 25 |
1 files changed, 22 insertions, 3 deletions
diff --git a/fs/exofs/inode.c b/fs/exofs/inode.c index a7555238c41..c8f58a96e59 100644 --- a/fs/exofs/inode.c +++ b/fs/exofs/inode.c @@ -350,8 +350,10 @@ static int readpage_strip(void *data, struct page *page) if (!pcol->read_4_write) unlock_page(page); - EXOFS_DBGMSG("readpage_strip(0x%lx, 0x%lx) empty page," - " splitting\n", inode->i_ino, page->index); + EXOFS_DBGMSG("readpage_strip(0x%lx) empty page len=%zx " + "read_4_write=%d index=0x%lx end_index=0x%lx " + "splitting\n", inode->i_ino, len, + pcol->read_4_write, page->index, end_index); return read_exec(pcol); } @@ -722,11 +724,28 @@ int exofs_write_begin(struct file *file, struct address_space *mapping, /* read modify write */ if (!PageUptodate(page) && (len != PAGE_CACHE_SIZE)) { + loff_t i_size = i_size_read(mapping->host); + pgoff_t end_index = i_size >> PAGE_CACHE_SHIFT; + size_t rlen; + + if (page->index < end_index) + rlen = PAGE_CACHE_SIZE; + else if (page->index == end_index) + rlen = i_size & ~PAGE_CACHE_MASK; + else + rlen = 0; + + if (!rlen) { + clear_highpage(page); + SetPageUptodate(page); + goto out; + } + ret = _readpage(page, true); if (ret) { /*SetPageError was done by _readpage. Is it ok?*/ unlock_page(page); - EXOFS_DBGMSG("__readpage_filler failed\n"); + EXOFS_DBGMSG("__readpage failed\n"); } } out: |