summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDarrick J. Wong <djwong@kernel.org>2026-07-27 08:25:35 +0300
committerCarlos Maiolino <cem@kernel.org>2026-08-03 11:20:43 +0300
commit5644fab990fc72406dddc91cbb8304659d77f3f1 (patch)
treef9880b862f712eaa0eba861f984efcdfc16acbee
parent6b9cd540138a06660a843a519facc147060acbef (diff)
downloadlinux-5644fab990fc72406dddc91cbb8304659d77f3f1.tar.xz
xfs: pass runtime errors from xrep_iunlink_mark_ondisk_rec up to callers
LOLLM points out that the only error that xrep_iunlink_mark_ondisk_rec returns is ENOMEM, but we ignore that, and can end up writing a garbage AGI based on incomplete information. We shouldn't do that, though here we must be screen out EFSCORRUPTED/EFSBASDCRC because we haven't checked the inobt yet. Cc: stable@vger.kernel.org # v6.10 Fixes: ab97f4b1c03075 ("xfs: repair AGI unlinked inode bucket lists") Signed-off-by: Darrick J. Wong <djwong@kernel.org> Assisted-by: LOLLM # finding obvious bugs Reviewed-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Carlos Maiolino <cem@kernel.org>
-rw-r--r--fs/xfs/scrub/agheader_repair.c14
1 files changed, 12 insertions, 2 deletions
diff --git a/fs/xfs/scrub/agheader_repair.c b/fs/xfs/scrub/agheader_repair.c
index 5204eab09c64..7f1955484303 100644
--- a/fs/xfs/scrub/agheader_repair.c
+++ b/fs/xfs/scrub/agheader_repair.c
@@ -1309,7 +1309,7 @@ xrep_iunlink_mark_ondisk_rec(
* iunlink_bmp. We haven't checked the inobt yet, so we don't error out if
* the btree is corrupt.
*/
-STATIC void
+STATIC int
xrep_iunlink_mark_ondisk(
struct xrep_agi *ragi)
{
@@ -1321,6 +1321,14 @@ xrep_iunlink_mark_ondisk(
cur = xfs_inobt_init_cursor(sc->sa.pag, sc->tp, agi_bp);
error = xfs_btree_query_all(cur, xrep_iunlink_mark_ondisk_rec, ragi);
xfs_btree_del_cursor(cur, error);
+
+ /*
+ * Don't proceed if we couldn't set a bit in the bitmap. All other
+ * errors we ignore because we haven't actually checked the inobt yet.
+ */
+ if (error == -ENOMEM)
+ return -ENOMEM;
+ return 0;
}
/*
@@ -1508,7 +1516,9 @@ xrep_iunlink_rebuild_buckets(
* If there are ondisk inodes that are unlinked and are not been loaded
* into cache, record them in iunlink_bmp.
*/
- xrep_iunlink_mark_ondisk(ragi);
+ error = xrep_iunlink_mark_ondisk(ragi);
+ if (error)
+ return error;
/*
* Walk each iunlink bucket to (re)construct as much of the incore list