aboutsummaryrefslogtreecommitdiffstats
path: root/fs/btrfs/extent_io.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/btrfs/extent_io.c')
-rw-r--r--fs/btrfs/extent_io.c82
1 files changed, 46 insertions, 36 deletions
diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c
index d247fc0eea19..2f83448d34fe 100644
--- a/fs/btrfs/extent_io.c
+++ b/fs/btrfs/extent_io.c
@@ -3200,14 +3200,10 @@ int extent_read_full_page(struct extent_io_tree *tree, struct page *page,
3200 return ret; 3200 return ret;
3201} 3201}
3202 3202
3203static noinline void update_nr_written(struct page *page, 3203static void update_nr_written(struct page *page, struct writeback_control *wbc,
3204 struct writeback_control *wbc, 3204 unsigned long nr_written)
3205 unsigned long nr_written)
3206{ 3205{
3207 wbc->nr_to_write -= nr_written; 3206 wbc->nr_to_write -= nr_written;
3208 if (wbc->range_cyclic || (wbc->nr_to_write > 0 &&
3209 wbc->range_start == 0 && wbc->range_end == LLONG_MAX))
3210 page->mapping->writeback_index = page->index + nr_written;
3211} 3207}
3212 3208
3213/* 3209/*
@@ -3368,6 +3364,8 @@ static noinline_for_stack int __extent_writepage_io(struct inode *inode,
3368 3364
3369 while (cur <= end) { 3365 while (cur <= end) {
3370 u64 em_end; 3366 u64 em_end;
3367 unsigned long max_nr;
3368
3371 if (cur >= i_size) { 3369 if (cur >= i_size) {
3372 if (tree->ops && tree->ops->writepage_end_io_hook) 3370 if (tree->ops && tree->ops->writepage_end_io_hook)
3373 tree->ops->writepage_end_io_hook(page, cur, 3371 tree->ops->writepage_end_io_hook(page, cur,
@@ -3423,32 +3421,23 @@ static noinline_for_stack int __extent_writepage_io(struct inode *inode,
3423 continue; 3421 continue;
3424 } 3422 }
3425 3423
3426 if (tree->ops && tree->ops->writepage_io_hook) { 3424 max_nr = (i_size >> PAGE_SHIFT) + 1;
3427 ret = tree->ops->writepage_io_hook(page, cur, 3425
3428 cur + iosize - 1); 3426 set_range_writeback(tree, cur, cur + iosize - 1);
3429 } else { 3427 if (!PageWriteback(page)) {
3430 ret = 0; 3428 btrfs_err(BTRFS_I(inode)->root->fs_info,
3429 "page %lu not writeback, cur %llu end %llu",
3430 page->index, cur, end);
3431 } 3431 }
3432 if (ret) {
3433 SetPageError(page);
3434 } else {
3435 unsigned long max_nr = (i_size >> PAGE_SHIFT) + 1;
3436 3432
3437 set_range_writeback(tree, cur, cur + iosize - 1); 3433 ret = submit_extent_page(write_flags, tree, wbc, page,
3438 if (!PageWriteback(page)) { 3434 sector, iosize, pg_offset,
3439 btrfs_err(BTRFS_I(inode)->root->fs_info, 3435 bdev, &epd->bio, max_nr,
3440 "page %lu not writeback, cur %llu end %llu", 3436 end_bio_extent_writepage,
3441 page->index, cur, end); 3437 0, 0, 0, false);
3442 } 3438 if (ret)
3439 SetPageError(page);
3443 3440
3444 ret = submit_extent_page(write_flags, tree, wbc, page,
3445 sector, iosize, pg_offset,
3446 bdev, &epd->bio, max_nr,
3447 end_bio_extent_writepage,
3448 0, 0, 0, false);
3449 if (ret)
3450 SetPageError(page);
3451 }
3452 cur = cur + iosize; 3441 cur = cur + iosize;
3453 pg_offset += iosize; 3442 pg_offset += iosize;
3454 nr++; 3443 nr++;
@@ -3920,12 +3909,13 @@ static int extent_write_cache_pages(struct extent_io_tree *tree,
3920 struct inode *inode = mapping->host; 3909 struct inode *inode = mapping->host;
3921 int ret = 0; 3910 int ret = 0;
3922 int done = 0; 3911 int done = 0;
3923 int err = 0;
3924 int nr_to_write_done = 0; 3912 int nr_to_write_done = 0;
3925 struct pagevec pvec; 3913 struct pagevec pvec;
3926 int nr_pages; 3914 int nr_pages;
3927 pgoff_t index; 3915 pgoff_t index;
3928 pgoff_t end; /* Inclusive */ 3916 pgoff_t end; /* Inclusive */
3917 pgoff_t done_index;
3918 int range_whole = 0;
3929 int scanned = 0; 3919 int scanned = 0;
3930 int tag; 3920 int tag;
3931 3921
@@ -3948,6 +3938,8 @@ static int extent_write_cache_pages(struct extent_io_tree *tree,
3948 } else { 3938 } else {
3949 index = wbc->range_start >> PAGE_SHIFT; 3939 index = wbc->range_start >> PAGE_SHIFT;
3950 end = wbc->range_end >> PAGE_SHIFT; 3940 end = wbc->range_end >> PAGE_SHIFT;
3941 if (wbc->range_start == 0 && wbc->range_end == LLONG_MAX)
3942 range_whole = 1;
3951 scanned = 1; 3943 scanned = 1;
3952 } 3944 }
3953 if (wbc->sync_mode == WB_SYNC_ALL) 3945 if (wbc->sync_mode == WB_SYNC_ALL)
@@ -3957,6 +3949,7 @@ static int extent_write_cache_pages(struct extent_io_tree *tree,
3957retry: 3949retry:
3958 if (wbc->sync_mode == WB_SYNC_ALL) 3950 if (wbc->sync_mode == WB_SYNC_ALL)
3959 tag_pages_for_writeback(mapping, index, end); 3951 tag_pages_for_writeback(mapping, index, end);
3952 done_index = index;
3960 while (!done && !nr_to_write_done && (index <= end) && 3953 while (!done && !nr_to_write_done && (index <= end) &&
3961 (nr_pages = pagevec_lookup_tag(&pvec, mapping, &index, tag, 3954 (nr_pages = pagevec_lookup_tag(&pvec, mapping, &index, tag,
3962 min(end - index, (pgoff_t)PAGEVEC_SIZE-1) + 1))) { 3955 min(end - index, (pgoff_t)PAGEVEC_SIZE-1) + 1))) {
@@ -3966,6 +3959,7 @@ retry:
3966 for (i = 0; i < nr_pages; i++) { 3959 for (i = 0; i < nr_pages; i++) {
3967 struct page *page = pvec.pages[i]; 3960 struct page *page = pvec.pages[i];
3968 3961
3962 done_index = page->index;
3969 /* 3963 /*
3970 * At this point we hold neither mapping->tree_lock nor 3964 * At this point we hold neither mapping->tree_lock nor
3971 * lock on the page itself: the page may be truncated or 3965 * lock on the page itself: the page may be truncated or
@@ -4007,8 +4001,20 @@ retry:
4007 unlock_page(page); 4001 unlock_page(page);
4008 ret = 0; 4002 ret = 0;
4009 } 4003 }
4010 if (!err && ret < 0) 4004 if (ret < 0) {
4011 err = ret; 4005 /*
4006 * done_index is set past this page,
4007 * so media errors will not choke
4008 * background writeout for the entire
4009 * file. This has consequences for
4010 * range_cyclic semantics (ie. it may
4011 * not be suitable for data integrity
4012 * writeout).
4013 */
4014 done_index = page->index + 1;
4015 done = 1;
4016 break;
4017 }
4012 4018
4013 /* 4019 /*
4014 * the filesystem may choose to bump up nr_to_write. 4020 * the filesystem may choose to bump up nr_to_write.
@@ -4020,7 +4026,7 @@ retry:
4020 pagevec_release(&pvec); 4026 pagevec_release(&pvec);
4021 cond_resched(); 4027 cond_resched();
4022 } 4028 }
4023 if (!scanned && !done && !err) { 4029 if (!scanned && !done) {
4024 /* 4030 /*
4025 * We hit the last page and there is more work to be done: wrap 4031 * We hit the last page and there is more work to be done: wrap
4026 * back to the start of the file 4032 * back to the start of the file
@@ -4029,8 +4035,12 @@ retry:
4029 index = 0; 4035 index = 0;
4030 goto retry; 4036 goto retry;
4031 } 4037 }
4038
4039 if (wbc->range_cyclic || (wbc->nr_to_write > 0 && range_whole))
4040 mapping->writeback_index = done_index;
4041
4032 btrfs_add_delayed_iput(inode); 4042 btrfs_add_delayed_iput(inode);
4033 return err; 4043 return ret;
4034} 4044}
4035 4045
4036static void flush_epd_write_bio(struct extent_page_data *epd) 4046static void flush_epd_write_bio(struct extent_page_data *epd)
@@ -4822,7 +4832,7 @@ struct extent_buffer *alloc_test_extent_buffer(struct btrfs_fs_info *fs_info,
4822 return NULL; 4832 return NULL;
4823 eb->fs_info = fs_info; 4833 eb->fs_info = fs_info;
4824again: 4834again:
4825 ret = radix_tree_preload(GFP_NOFS & ~__GFP_HIGHMEM); 4835 ret = radix_tree_preload(GFP_NOFS);
4826 if (ret) 4836 if (ret)
4827 goto free_eb; 4837 goto free_eb;
4828 spin_lock(&fs_info->buffer_lock); 4838 spin_lock(&fs_info->buffer_lock);
@@ -4923,7 +4933,7 @@ struct extent_buffer *alloc_extent_buffer(struct btrfs_fs_info *fs_info,
4923 if (uptodate) 4933 if (uptodate)
4924 set_bit(EXTENT_BUFFER_UPTODATE, &eb->bflags); 4934 set_bit(EXTENT_BUFFER_UPTODATE, &eb->bflags);
4925again: 4935again:
4926 ret = radix_tree_preload(GFP_NOFS & ~__GFP_HIGHMEM); 4936 ret = radix_tree_preload(GFP_NOFS);
4927 if (ret) 4937 if (ret)
4928 goto free_eb; 4938 goto free_eb;
4929 4939