btrfs-progs: check blocks in btrfs_next_sibling_block
By enabling the lowmem checks properly I uncovered the case where test fsck/007 will infinite loop at the detection stage. This is because when checking the inode item we will just btrfs_next_item(), and because we ignore check tree block failures at read time we don't get an -EIO from btrfs_next_leaf. This occurs because we allow fsck to raw-read blocks even if they fail basic sanity checks, because we want the opportunity to repair the blocks. However this means corrupt blocks are sitting in cache marked as uptodate. btrfs_search_slot() handles this by doing a check_block() on every block we add to the path, so that anything that is doing a search gets a proper -EIO. btrfs_next_sibling_block() needs a similar check. With this fix we now return -EIO on btrfs_next_leaf() properly and we no longer infinite loop on fsck/007 with lowmem. Signed-off-by: Josef Bacik <josef@toxicpanda.com> Signed-off-by: David Sterba <dsterba@suse.com>
This commit is contained in:
parent
71404c50e8
commit
8c3c13bb45
|
@ -3125,6 +3125,13 @@ int btrfs_next_sibling_tree_block(struct btrfs_fs_info *fs_info,
|
|||
free_extent_buffer(c);
|
||||
path->nodes[level] = next;
|
||||
path->slots[level] = 0;
|
||||
/*
|
||||
* Fsck will happily load corrupt blocks in order to fix them,
|
||||
* so we need an extra check just to make sure this block isn't
|
||||
* marked uptodate but invalid.
|
||||
*/
|
||||
if (check_block(fs_info, path, level))
|
||||
return -EIO;
|
||||
if (level == path->lowest_level)
|
||||
break;
|
||||
if (path->reada)
|
||||
|
|
Loading…
Reference in New Issue