diff options
author | James Bottomley <jejb@mulgrave.il.steeleye.com> | 2007-01-31 11:24:00 -0600 |
---|---|---|
committer | James Bottomley <jejb@mulgrave.il.steeleye.com> | 2007-01-31 11:24:00 -0600 |
commit | 30716e07ef511ec7525c07eb1e8060ba8943c2a2 (patch) | |
tree | eb6a47cae63d3587fa773cc5a16781eaa2c7810b /fs/buffer.c | |
parent | 03c79cc56e4497cbd09d74a73c1bd0d1d9a8a16c (diff) | |
parent | f56df2f4db6e4af87fb8e941cff69f4501a111df (diff) | |
download | kernel_samsung_smdk4412-30716e07ef511ec7525c07eb1e8060ba8943c2a2.zip kernel_samsung_smdk4412-30716e07ef511ec7525c07eb1e8060ba8943c2a2.tar.gz kernel_samsung_smdk4412-30716e07ef511ec7525c07eb1e8060ba8943c2a2.tar.bz2 |
Merge branch 'linus'
Diffstat (limited to 'fs/buffer.c')
-rw-r--r-- | fs/buffer.c | 19 |
1 files changed, 18 insertions, 1 deletions
diff --git a/fs/buffer.c b/fs/buffer.c index 3b11607..1ad674f 100644 --- a/fs/buffer.c +++ b/fs/buffer.c @@ -2834,7 +2834,7 @@ int try_to_free_buffers(struct page *page) int ret = 0; BUG_ON(!PageLocked(page)); - if (PageDirty(page) || PageWriteback(page)) + if (PageWriteback(page)) return 0; if (mapping == NULL) { /* can this still happen? */ @@ -2844,6 +2844,23 @@ int try_to_free_buffers(struct page *page) spin_lock(&mapping->private_lock); ret = drop_buffers(page, &buffers_to_free); + + /* + * If the filesystem writes its buffers by hand (eg ext3) + * then we can have clean buffers against a dirty page. We + * clean the page here; otherwise the VM will never notice + * that the filesystem did any IO at all. + * + * Also, during truncate, discard_buffer will have marked all + * the page's buffers clean. We discover that here and clean + * the page also. + * + * private_lock must be held over this entire operation in order + * to synchronise against __set_page_dirty_buffers and prevent the + * dirty bit from being lost. + */ + if (ret) + cancel_dirty_page(page, PAGE_CACHE_SIZE); spin_unlock(&mapping->private_lock); out: if (buffers_to_free) { |