diff options
Diffstat (limited to 'fs/buffer.c')
| -rw-r--r-- | fs/buffer.c | 28 |
1 files changed, 14 insertions, 14 deletions
diff --git a/fs/buffer.c b/fs/buffer.c index b58208f1640a..891e1c78e4f1 100644 --- a/fs/buffer.c +++ b/fs/buffer.c | |||
| @@ -760,15 +760,9 @@ EXPORT_SYMBOL(mark_buffer_dirty_inode); | |||
| 760 | * If warn is true, then emit a warning if the page is not uptodate and has | 760 | * If warn is true, then emit a warning if the page is not uptodate and has |
| 761 | * not been truncated. | 761 | * not been truncated. |
| 762 | */ | 762 | */ |
| 763 | static int __set_page_dirty(struct page *page, | 763 | static void __set_page_dirty(struct page *page, |
| 764 | struct address_space *mapping, int warn) | 764 | struct address_space *mapping, int warn) |
| 765 | { | 765 | { |
| 766 | if (unlikely(!mapping)) | ||
| 767 | return !TestSetPageDirty(page); | ||
| 768 | |||
| 769 | if (TestSetPageDirty(page)) | ||
| 770 | return 0; | ||
| 771 | |||
| 772 | spin_lock_irq(&mapping->tree_lock); | 766 | spin_lock_irq(&mapping->tree_lock); |
| 773 | if (page->mapping) { /* Race with truncate? */ | 767 | if (page->mapping) { /* Race with truncate? */ |
| 774 | WARN_ON_ONCE(warn && !PageUptodate(page)); | 768 | WARN_ON_ONCE(warn && !PageUptodate(page)); |
| @@ -777,6 +771,7 @@ static int __set_page_dirty(struct page *page, | |||
| 777 | __inc_zone_page_state(page, NR_FILE_DIRTY); | 771 | __inc_zone_page_state(page, NR_FILE_DIRTY); |
| 778 | __inc_bdi_stat(mapping->backing_dev_info, | 772 | __inc_bdi_stat(mapping->backing_dev_info, |
| 779 | BDI_RECLAIMABLE); | 773 | BDI_RECLAIMABLE); |
| 774 | task_dirty_inc(current); | ||
| 780 | task_io_account_write(PAGE_CACHE_SIZE); | 775 | task_io_account_write(PAGE_CACHE_SIZE); |
| 781 | } | 776 | } |
| 782 | radix_tree_tag_set(&mapping->page_tree, | 777 | radix_tree_tag_set(&mapping->page_tree, |
| @@ -784,8 +779,6 @@ static int __set_page_dirty(struct page *page, | |||
| 784 | } | 779 | } |
| 785 | spin_unlock_irq(&mapping->tree_lock); | 780 | spin_unlock_irq(&mapping->tree_lock); |
| 786 | __mark_inode_dirty(mapping->host, I_DIRTY_PAGES); | 781 | __mark_inode_dirty(mapping->host, I_DIRTY_PAGES); |
| 787 | |||
| 788 | return 1; | ||
| 789 | } | 782 | } |
| 790 | 783 | ||
| 791 | /* | 784 | /* |
| @@ -815,6 +808,7 @@ static int __set_page_dirty(struct page *page, | |||
| 815 | */ | 808 | */ |
| 816 | int __set_page_dirty_buffers(struct page *page) | 809 | int __set_page_dirty_buffers(struct page *page) |
| 817 | { | 810 | { |
| 811 | int newly_dirty; | ||
| 818 | struct address_space *mapping = page_mapping(page); | 812 | struct address_space *mapping = page_mapping(page); |
| 819 | 813 | ||
| 820 | if (unlikely(!mapping)) | 814 | if (unlikely(!mapping)) |
| @@ -830,9 +824,12 @@ int __set_page_dirty_buffers(struct page *page) | |||
| 830 | bh = bh->b_this_page; | 824 | bh = bh->b_this_page; |
| 831 | } while (bh != head); | 825 | } while (bh != head); |
| 832 | } | 826 | } |
| 827 | newly_dirty = !TestSetPageDirty(page); | ||
| 833 | spin_unlock(&mapping->private_lock); | 828 | spin_unlock(&mapping->private_lock); |
| 834 | 829 | ||
| 835 | return __set_page_dirty(page, mapping, 1); | 830 | if (newly_dirty) |
| 831 | __set_page_dirty(page, mapping, 1); | ||
| 832 | return newly_dirty; | ||
| 836 | } | 833 | } |
| 837 | EXPORT_SYMBOL(__set_page_dirty_buffers); | 834 | EXPORT_SYMBOL(__set_page_dirty_buffers); |
| 838 | 835 | ||
| @@ -1261,8 +1258,11 @@ void mark_buffer_dirty(struct buffer_head *bh) | |||
| 1261 | return; | 1258 | return; |
| 1262 | } | 1259 | } |
| 1263 | 1260 | ||
| 1264 | if (!test_set_buffer_dirty(bh)) | 1261 | if (!test_set_buffer_dirty(bh)) { |
| 1265 | __set_page_dirty(bh->b_page, page_mapping(bh->b_page), 0); | 1262 | struct page *page = bh->b_page; |
| 1263 | if (!TestSetPageDirty(page)) | ||
| 1264 | __set_page_dirty(page, page_mapping(page), 0); | ||
| 1265 | } | ||
| 1266 | } | 1266 | } |
| 1267 | 1267 | ||
| 1268 | /* | 1268 | /* |
| @@ -2688,7 +2688,7 @@ int nobh_write_end(struct file *file, struct address_space *mapping, | |||
| 2688 | struct buffer_head *bh; | 2688 | struct buffer_head *bh; |
| 2689 | BUG_ON(fsdata != NULL && page_has_buffers(page)); | 2689 | BUG_ON(fsdata != NULL && page_has_buffers(page)); |
| 2690 | 2690 | ||
| 2691 | if (unlikely(copied < len) && !page_has_buffers(page)) | 2691 | if (unlikely(copied < len) && head) |
| 2692 | attach_nobh_buffers(page, head); | 2692 | attach_nobh_buffers(page, head); |
| 2693 | if (page_has_buffers(page)) | 2693 | if (page_has_buffers(page)) |
| 2694 | return generic_write_end(file, mapping, pos, len, | 2694 | return generic_write_end(file, mapping, pos, len, |
| @@ -3108,7 +3108,7 @@ int sync_dirty_buffer(struct buffer_head *bh) | |||
| 3108 | if (test_clear_buffer_dirty(bh)) { | 3108 | if (test_clear_buffer_dirty(bh)) { |
| 3109 | get_bh(bh); | 3109 | get_bh(bh); |
| 3110 | bh->b_end_io = end_buffer_write_sync; | 3110 | bh->b_end_io = end_buffer_write_sync; |
| 3111 | ret = submit_bh(WRITE_SYNC, bh); | 3111 | ret = submit_bh(WRITE, bh); |
| 3112 | wait_on_buffer(bh); | 3112 | wait_on_buffer(bh); |
| 3113 | if (buffer_eopnotsupp(bh)) { | 3113 | if (buffer_eopnotsupp(bh)) { |
| 3114 | clear_buffer_eopnotsupp(bh); | 3114 | clear_buffer_eopnotsupp(bh); |
