diff options
author | Trond Myklebust <Trond.Myklebust@netapp.com> | 2008-01-22 17:13:06 -0500 |
---|---|---|
committer | Trond Myklebust <Trond.Myklebust@netapp.com> | 2008-01-30 02:05:23 -0500 |
commit | 8b1f9ee56e21e505a3d5d3e33f823006d1abdbaf (patch) | |
tree | 4f26bf0ceb4f834040e02cefc6385087a25ad6ba /fs/nfs/file.c | |
parent | 77f111929d024165e736e919187cff017279bebe (diff) |
NFS: Optimise nfs_vm_page_mkwrite()
The current model locks the page twice for no good reason. Optimise by
inlining the parts of nfs_write_begin()/nfs_write_end() that we care about.
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Diffstat (limited to 'fs/nfs/file.c')
-rw-r--r-- | fs/nfs/file.c | 36 |
1 files changed, 14 insertions, 22 deletions
diff --git a/fs/nfs/file.c b/fs/nfs/file.c index b3bb89f7d5d2..4560fc2ddb4a 100644 --- a/fs/nfs/file.c +++ b/fs/nfs/file.c | |||
@@ -392,35 +392,27 @@ static int nfs_vm_page_mkwrite(struct vm_area_struct *vma, struct page *page) | |||
392 | struct file *filp = vma->vm_file; | 392 | struct file *filp = vma->vm_file; |
393 | unsigned pagelen; | 393 | unsigned pagelen; |
394 | int ret = -EINVAL; | 394 | int ret = -EINVAL; |
395 | void *fsdata; | ||
396 | struct address_space *mapping; | 395 | struct address_space *mapping; |
397 | loff_t offset; | ||
398 | 396 | ||
399 | lock_page(page); | 397 | lock_page(page); |
400 | mapping = page->mapping; | 398 | mapping = page->mapping; |
401 | if (mapping != vma->vm_file->f_path.dentry->d_inode->i_mapping) { | 399 | if (mapping != vma->vm_file->f_path.dentry->d_inode->i_mapping) |
402 | unlock_page(page); | 400 | goto out_unlock; |
403 | return -EINVAL; | 401 | |
404 | } | 402 | ret = 0; |
405 | pagelen = nfs_page_length(page); | 403 | pagelen = nfs_page_length(page); |
406 | offset = (loff_t)page->index << PAGE_CACHE_SHIFT; | 404 | if (pagelen == 0) |
407 | unlock_page(page); | 405 | goto out_unlock; |
408 | 406 | ||
409 | /* | 407 | ret = nfs_flush_incompatible(filp, page); |
410 | * we can use mapping after releasing the page lock, because: | 408 | if (ret != 0) |
411 | * we hold mmap_sem on the fault path, which should pin the vma | 409 | goto out_unlock; |
412 | * which should pin the file, which pins the dentry which should | ||
413 | * hold a reference on inode. | ||
414 | */ | ||
415 | 410 | ||
416 | if (pagelen) { | 411 | ret = nfs_updatepage(filp, page, 0, pagelen); |
417 | struct page *page2 = NULL; | 412 | if (ret == 0) |
418 | ret = nfs_write_begin(filp, mapping, offset, pagelen, | 413 | ret = pagelen; |
419 | 0, &page2, &fsdata); | 414 | out_unlock: |
420 | if (!ret) | 415 | unlock_page(page); |
421 | ret = nfs_write_end(filp, mapping, offset, pagelen, | ||
422 | pagelen, page2, fsdata); | ||
423 | } | ||
424 | return ret; | 416 | return ret; |
425 | } | 417 | } |
426 | 418 | ||