aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/btrfs/disk-io.c16
-rw-r--r--fs/btrfs/extent_io.c15
-rw-r--r--fs/btrfs/extent_io.h4
-rw-r--r--fs/btrfs/inode.c2
4 files changed, 17 insertions, 20 deletions
diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c
index b9866f27ebd7..d0c969beaad4 100644
--- a/fs/btrfs/disk-io.c
+++ b/fs/btrfs/disk-io.c
@@ -383,17 +383,16 @@ static int btree_read_extent_buffer_pages(struct btrfs_root *root,
383 if (test_bit(EXTENT_BUFFER_CORRUPT, &eb->bflags)) 383 if (test_bit(EXTENT_BUFFER_CORRUPT, &eb->bflags))
384 break; 384 break;
385 385
386 if (!failed_mirror) {
387 failed = 1;
388 printk(KERN_ERR "failed mirror was %d\n", eb->failed_mirror);
389 failed_mirror = eb->failed_mirror;
390 }
391
392 num_copies = btrfs_num_copies(&root->fs_info->mapping_tree, 386 num_copies = btrfs_num_copies(&root->fs_info->mapping_tree,
393 eb->start, eb->len); 387 eb->start, eb->len);
394 if (num_copies == 1) 388 if (num_copies == 1)
395 break; 389 break;
396 390
391 if (!failed_mirror) {
392 failed = 1;
393 failed_mirror = eb->read_mirror;
394 }
395
397 mirror_num++; 396 mirror_num++;
398 if (mirror_num == failed_mirror) 397 if (mirror_num == failed_mirror)
399 mirror_num++; 398 mirror_num++;
@@ -564,7 +563,7 @@ struct extent_buffer *find_eb_for_page(struct extent_io_tree *tree,
564} 563}
565 564
566static int btree_readpage_end_io_hook(struct page *page, u64 start, u64 end, 565static int btree_readpage_end_io_hook(struct page *page, u64 start, u64 end,
567 struct extent_state *state) 566 struct extent_state *state, int mirror)
568{ 567{
569 struct extent_io_tree *tree; 568 struct extent_io_tree *tree;
570 u64 found_start; 569 u64 found_start;
@@ -589,6 +588,7 @@ static int btree_readpage_end_io_hook(struct page *page, u64 start, u64 end,
589 if (!reads_done) 588 if (!reads_done)
590 goto err; 589 goto err;
591 590
591 eb->read_mirror = mirror;
592 if (test_bit(EXTENT_BUFFER_IOERR, &eb->bflags)) { 592 if (test_bit(EXTENT_BUFFER_IOERR, &eb->bflags)) {
593 ret = -EIO; 593 ret = -EIO;
594 goto err; 594 goto err;
@@ -652,7 +652,7 @@ static int btree_io_failed_hook(struct page *page, int failed_mirror)
652 652
653 eb = (struct extent_buffer *)page->private; 653 eb = (struct extent_buffer *)page->private;
654 set_bit(EXTENT_BUFFER_IOERR, &eb->bflags); 654 set_bit(EXTENT_BUFFER_IOERR, &eb->bflags);
655 eb->failed_mirror = failed_mirror; 655 eb->read_mirror = failed_mirror;
656 if (test_and_clear_bit(EXTENT_BUFFER_READAHEAD, &eb->bflags)) 656 if (test_and_clear_bit(EXTENT_BUFFER_READAHEAD, &eb->bflags))
657 btree_readahead_hook(root, eb, eb->start, -EIO); 657 btree_readahead_hook(root, eb, eb->start, -EIO);
658 return -EIO; /* we fixed nothing */ 658 return -EIO; /* we fixed nothing */
diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c
index 11eeb81fe695..0c23e57077c6 100644
--- a/fs/btrfs/extent_io.c
+++ b/fs/btrfs/extent_io.c
@@ -2304,7 +2304,7 @@ static void end_bio_extent_readpage(struct bio *bio, int err)
2304 u64 start; 2304 u64 start;
2305 u64 end; 2305 u64 end;
2306 int whole_page; 2306 int whole_page;
2307 int failed_mirror; 2307 int mirror;
2308 int ret; 2308 int ret;
2309 2309
2310 if (err) 2310 if (err)
@@ -2343,20 +2343,18 @@ static void end_bio_extent_readpage(struct bio *bio, int err)
2343 } 2343 }
2344 spin_unlock(&tree->lock); 2344 spin_unlock(&tree->lock);
2345 2345
2346 mirror = (int)(unsigned long)bio->bi_bdev;
2346 if (uptodate && tree->ops && tree->ops->readpage_end_io_hook) { 2347 if (uptodate && tree->ops && tree->ops->readpage_end_io_hook) {
2347 ret = tree->ops->readpage_end_io_hook(page, start, end, 2348 ret = tree->ops->readpage_end_io_hook(page, start, end,
2348 state); 2349 state, mirror);
2349 if (ret) 2350 if (ret)
2350 uptodate = 0; 2351 uptodate = 0;
2351 else 2352 else
2352 clean_io_failure(start, page); 2353 clean_io_failure(start, page);
2353 } 2354 }
2354 2355
2355 if (!uptodate)
2356 failed_mirror = (int)(unsigned long)bio->bi_bdev;
2357
2358 if (!uptodate && tree->ops && tree->ops->readpage_io_failed_hook) { 2356 if (!uptodate && tree->ops && tree->ops->readpage_io_failed_hook) {
2359 ret = tree->ops->readpage_io_failed_hook(page, failed_mirror); 2357 ret = tree->ops->readpage_io_failed_hook(page, mirror);
2360 if (!ret && !err && 2358 if (!ret && !err &&
2361 test_bit(BIO_UPTODATE, &bio->bi_flags)) 2359 test_bit(BIO_UPTODATE, &bio->bi_flags))
2362 uptodate = 1; 2360 uptodate = 1;
@@ -2371,8 +2369,7 @@ static void end_bio_extent_readpage(struct bio *bio, int err)
2371 * can't handle the error it will return -EIO and we 2369 * can't handle the error it will return -EIO and we
2372 * remain responsible for that page. 2370 * remain responsible for that page.
2373 */ 2371 */
2374 ret = bio_readpage_error(bio, page, start, end, 2372 ret = bio_readpage_error(bio, page, start, end, mirror, NULL);
2375 failed_mirror, NULL);
2376 if (ret == 0) { 2373 if (ret == 0) {
2377 uptodate = 2374 uptodate =
2378 test_bit(BIO_UPTODATE, &bio->bi_flags); 2375 test_bit(BIO_UPTODATE, &bio->bi_flags);
@@ -4465,7 +4462,7 @@ int read_extent_buffer_pages(struct extent_io_tree *tree,
4465 } 4462 }
4466 4463
4467 clear_bit(EXTENT_BUFFER_IOERR, &eb->bflags); 4464 clear_bit(EXTENT_BUFFER_IOERR, &eb->bflags);
4468 eb->failed_mirror = 0; 4465 eb->read_mirror = 0;
4469 atomic_set(&eb->io_pages, num_reads); 4466 atomic_set(&eb->io_pages, num_reads);
4470 for (i = start_i; i < num_pages; i++) { 4467 for (i = start_i; i < num_pages; i++) {
4471 page = extent_buffer_page(eb, i); 4468 page = extent_buffer_page(eb, i);
diff --git a/fs/btrfs/extent_io.h b/fs/btrfs/extent_io.h
index faf10eb57f75..b516c3b8dec6 100644
--- a/fs/btrfs/extent_io.h
+++ b/fs/btrfs/extent_io.h
@@ -79,7 +79,7 @@ struct extent_io_ops {
79 u64 start, u64 end, 79 u64 start, u64 end,
80 struct extent_state *state); 80 struct extent_state *state);
81 int (*readpage_end_io_hook)(struct page *page, u64 start, u64 end, 81 int (*readpage_end_io_hook)(struct page *page, u64 start, u64 end,
82 struct extent_state *state); 82 struct extent_state *state, int mirror);
83 int (*writepage_end_io_hook)(struct page *page, u64 start, u64 end, 83 int (*writepage_end_io_hook)(struct page *page, u64 start, u64 end,
84 struct extent_state *state, int uptodate); 84 struct extent_state *state, int uptodate);
85 void (*set_bit_hook)(struct inode *inode, struct extent_state *state, 85 void (*set_bit_hook)(struct inode *inode, struct extent_state *state,
@@ -135,7 +135,7 @@ struct extent_buffer {
135 spinlock_t refs_lock; 135 spinlock_t refs_lock;
136 atomic_t refs; 136 atomic_t refs;
137 atomic_t io_pages; 137 atomic_t io_pages;
138 int failed_mirror; 138 int read_mirror;
139 struct list_head leak_list; 139 struct list_head leak_list;
140 struct rcu_head rcu_head; 140 struct rcu_head rcu_head;
141 pid_t lock_owner; 141 pid_t lock_owner;
diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c
index 98ee5a51aa29..d953f8820464 100644
--- a/fs/btrfs/inode.c
+++ b/fs/btrfs/inode.c
@@ -1947,7 +1947,7 @@ static int btrfs_writepage_end_io_hook(struct page *page, u64 start, u64 end,
1947 * extent_io.c will try to find good copies for us. 1947 * extent_io.c will try to find good copies for us.
1948 */ 1948 */
1949static int btrfs_readpage_end_io_hook(struct page *page, u64 start, u64 end, 1949static int btrfs_readpage_end_io_hook(struct page *page, u64 start, u64 end,
1950 struct extent_state *state) 1950 struct extent_state *state, int mirror)
1951{ 1951{
1952 size_t offset = start - ((u64)page->index << PAGE_CACHE_SHIFT); 1952 size_t offset = start - ((u64)page->index << PAGE_CACHE_SHIFT);
1953 struct inode *inode = page->mapping->host; 1953 struct inode *inode = page->mapping->host;