]> git.ipfire.org Git - people/ms/linux.git/commitdiff
btrfs: track compressed bio errors as blk_status_t
authorJosef Bacik <josef@toxicpanda.com>
Fri, 18 Feb 2022 15:03:26 +0000 (10:03 -0500)
committerDavid Sterba <dsterba@suse.com>
Mon, 14 Mar 2022 12:13:51 +0000 (13:13 +0100)
Right now we just have a binary "errors" flag, so any error we get on
the compressed bio's gets translated to EIO.  This isn't necessarily a
bad thing, but if we get an ENOMEM it may be nice to know that's what
happened instead of an EIO.  Track our errors as a blk_status_t, and do
the appropriate setting of the errors accordingly.

Signed-off-by: Josef Bacik <josef@toxicpanda.com>
Signed-off-by: David Sterba <dsterba@suse.com>
fs/btrfs/compression.c
fs/btrfs/compression.h

index 14409b3c838a1f74696d8d1ced0e9e0eb9102ffd..f459e1832cad92f6aaef64175f4d7360ecc0dbdb 100644 (file)
@@ -219,7 +219,7 @@ static bool dec_and_test_compressed_bio(struct compressed_bio *cb, struct bio *b
                bi_size += bvec->bv_len;
 
        if (bio->bi_status)
-               cb->errors = 1;
+               cb->status = bio->bi_status;
 
        ASSERT(bi_size && bi_size <= cb->compressed_len);
        last_io = refcount_sub_and_test(bi_size >> fs_info->sectorsize_bits,
@@ -247,8 +247,9 @@ static void finish_compressed_bio_read(struct compressed_bio *cb)
        }
 
        /* Do io completion on the original bio */
-       if (cb->errors) {
-               bio_io_error(cb->orig_bio);
+       if (cb->status != BLK_STS_OK) {
+               cb->orig_bio->bi_status = cb->status;
+               bio_endio(cb->orig_bio);
        } else {
                struct bio_vec *bvec;
                struct bvec_iter_all iter_all;
@@ -306,7 +307,7 @@ static void end_compressed_bio_read(struct bio *bio)
         * Some IO in this cb have failed, just skip checksum as there
         * is no way it could be correct.
         */
-       if (cb->errors == 1)
+       if (cb->status != BLK_STS_OK)
                goto csum_failed;
 
        inode = cb->inode;
@@ -322,7 +323,7 @@ static void end_compressed_bio_read(struct bio *bio)
 
 csum_failed:
        if (ret)
-               cb->errors = 1;
+               cb->status = errno_to_blk_status(ret);
        finish_compressed_bio_read(cb);
 out:
        bio_put(bio);
@@ -340,11 +341,12 @@ static noinline void end_compressed_writeback(struct inode *inode,
        unsigned long end_index = (cb->start + cb->len - 1) >> PAGE_SHIFT;
        struct page *pages[16];
        unsigned long nr_pages = end_index - index + 1;
+       const int errno = blk_status_to_errno(cb->status);
        int i;
        int ret;
 
-       if (cb->errors)
-               mapping_set_error(inode->i_mapping, -EIO);
+       if (errno)
+               mapping_set_error(inode->i_mapping, errno);
 
        while (nr_pages > 0) {
                ret = find_get_pages_contig(inode->i_mapping, index,
@@ -356,7 +358,7 @@ static noinline void end_compressed_writeback(struct inode *inode,
                        continue;
                }
                for (i = 0; i < ret; i++) {
-                       if (cb->errors)
+                       if (errno)
                                SetPageError(pages[i]);
                        btrfs_page_clamp_clear_writeback(fs_info, pages[i],
                                                         cb->start, cb->len);
@@ -379,7 +381,7 @@ static void finish_compressed_bio_write(struct compressed_bio *cb)
         */
        btrfs_writepage_endio_finish_ordered(BTRFS_I(inode), NULL,
                        cb->start, cb->start + cb->len - 1,
-                       !cb->errors);
+                       cb->status == BLK_STS_OK);
 
        if (cb->writeback)
                end_compressed_writeback(inode, cb);
@@ -524,7 +526,7 @@ blk_status_t btrfs_submit_compressed_write(struct btrfs_inode *inode, u64 start,
        if (!cb)
                return BLK_STS_RESOURCE;
        refcount_set(&cb->pending_sectors, compressed_len >> fs_info->sectorsize_bits);
-       cb->errors = 0;
+       cb->status = BLK_STS_OK;
        cb->inode = &inode->vfs_inode;
        cb->start = start;
        cb->len = len;
@@ -832,7 +834,7 @@ blk_status_t btrfs_submit_compressed_read(struct inode *inode, struct bio *bio,
                goto out;
 
        refcount_set(&cb->pending_sectors, compressed_len >> fs_info->sectorsize_bits);
-       cb->errors = 0;
+       cb->status = BLK_STS_OK;
        cb->inode = inode;
        cb->mirror_num = mirror_num;
        sums = cb->sums;
index 7773953470e391ed304053563e13392663ad7d0d..ac5b20731d2ad4b1092fd28e685296f7d6fb479c 100644 (file)
@@ -58,7 +58,7 @@ struct compressed_bio {
        bool writeback;
 
        /* IO errors */
-       u8 errors;
+       blk_status_t status;
        int mirror_num;
 
        /* for reads, this is the bio we are copying the data into */