On 8/25/25 2:55 AM, Christoph Hellwig wrote:
On Fri, Aug 22, 2025 at 08:21:37AM -0700, Darrick J. Wong wrote:
We only flag corruptions for these two error codes, but ENODATA from the block layer means "critical medium error". I take that to mean the media has permanently lost whatever was persisted there, right?
It can also be a write error. But yes, it's what EIO indidcates in general. Which is why I really think we should be doing something like the patch below. But as I don't have the time to fully shephed this I'm not trying to block this hack, even if I think the issue will continue to byte us in the future.
Right, as I said we need to do something like what you suggest, which is 100% fine by me.
I'd just like a safe, very targeted fix merged first, to handle the currently observed and reported error. A bigger scope change pushed back to stable kernels has somewhat more risk, and I'd like to avoid that.
I'll work on something like this, and send another patch that's something like "xfs: generalize block device error handling" or whatever, that effectively reverts the patch proposed by me, and adds this patch proposed by you.
If it soaks a little and has no regressions, I'd be happy to send the broader fix back to stable as well.
Thanks, -Eric
diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c index f9ef3b2a332a..0252faf038aa 100644 --- a/fs/xfs/xfs_buf.c +++ b/fs/xfs/xfs_buf.c @@ -1290,6 +1290,22 @@ xfs_bwrite( return error; } +static int +xfs_buf_bio_status(
- struct bio *bio)
+{
- switch (bio->bi_status) {
- case BLK_STS_OK:
return 0;
- case BLK_STS_NOSPC:
return -ENOSPC;
- case BLK_STS_OFFLINE:
return -ENODEV;
- default:
return -EIO;
- }
+}
static void xfs_buf_bio_end_io( struct bio *bio) @@ -1297,7 +1313,7 @@ xfs_buf_bio_end_io( struct xfs_buf *bp = bio->bi_private; if (bio->bi_status)
xfs_buf_ioerror(bp, blk_status_to_errno(bio->bi_status));
else if ((bp->b_flags & XBF_WRITE) && (bp->b_flags & XBF_ASYNC) && XFS_TEST_ERROR(false, bp->b_mount, XFS_ERRTAG_BUF_IOERROR)) xfs_buf_ioerror(bp, -EIO);xfs_buf_ioerror(bp, xfs_buf_bio_status(bio));