@@ -2654,6 +2654,19 @@ static bool btrfs_io_needs_validation(struct inode *inode, struct bio *bio)
if (bio->bi_status == BLK_STS_OK)
return false;
+ /*
+ * For subpage case, read bio are always submitted as multiple-sector
+ * bio if the range is in the same page.
+ * For now, let's just skip the validation, and do page sized repair.
+ *
+ * This reduce the granularity for repair, meaning if we have two
+ * copies with different csum mismatch at different location, we're
+ * unable to repair in subpage case.
+ *
+ * TODO: Make validation code to be fully subpage compatible
+ */
+ if (blocksize < PAGE_SIZE)
+ return false;
/*
* We need to validate each sector individually if the failed I/O was
* for multiple sectors.
Unlike PAGE_SIZE == sectorsize case, read in subpage btrfs are always merged if the range is in the same page: E.g: For regular sectorsize case, if we want to read range [0, 16K) of a file, the bio will look like: 0 4K 8K 12K 16K | bvec 1| bvec 2| bvec 3| bvec 4| But for subpage case, above 16K can be merged into one bvec: 0 4K 8K 12K 16K | bvec 1 | This means our bvec is no longer 1:1 mapped to btrfs sector. This makes repair much harder to do, if we want to do sector perfect repair. For now, just skip validation for subpage read repair, this means: - We will submit extra range to repair Even if we only have one sector error for above read, we will still submit full 16K to over-write the bad copy - Less chance to get good copy Now the repair granularity is much lower, we need a copy with all sectors correct to be able to submit a repair. Sector perfect repair needs more modification, but for now the new behavior should be good enough for us to test the basis of subpage support. Signed-off-by: Qu Wenruo <wqu@suse.com> --- fs/btrfs/extent_io.c | 13 +++++++++++++ 1 file changed, 13 insertions(+)