summaryrefslogtreecommitdiff
path: root/fs/xfs
diff options
context:
space:
mode:
authorDave Chinner <david@fromorbit.com>2023-04-14 00:09:27 +0300
committerDave Chinner <dchinner@redhat.com>2023-04-14 00:09:27 +0300
commitb764ea207fba692bc8195513ab4a63fbc4af6e66 (patch)
treeee6a34fd984769c3ce5c08106b6639aa4f682c41 /fs/xfs
parent01822a74ca5e49dfdc4003be21cb96e4f3d42606 (diff)
parentde1a9ce225e93b22d189f8ffbce20074bc803121 (diff)
downloadlinux-b764ea207fba692bc8195513ab4a63fbc4af6e66.tar.xz
Merge tag 'btree-hoist-scrub-checks-6.4_2023-04-11' of git://git.kernel.org/pub/scm/linux/kernel/git/djwong/xfs-linux into guilt/xfs-for-next
xfs: hoist scrub record checks into libxfs [v24.5] There are a few things about btree records that scrub checked but the libxfs _get_rec functions didn't. Move these bits into libxfs so that everyone can benefit. Signed-off-by: Darrick J. Wong <djwong@kernel.org> Signed-off-by: Dave Chinner <david@fromorbit.com>
Diffstat (limited to 'fs/xfs')
-rw-r--r--fs/xfs/libxfs/xfs_ialloc.c4
-rw-r--r--fs/xfs/libxfs/xfs_rmap.c27
-rw-r--r--fs/xfs/scrub/ialloc.c6
-rw-r--r--fs/xfs/scrub/rmap.c22
4 files changed, 31 insertions, 28 deletions
diff --git a/fs/xfs/libxfs/xfs_ialloc.c b/fs/xfs/libxfs/xfs_ialloc.c
index b7dc8b81a133..0d2980accd3c 100644
--- a/fs/xfs/libxfs/xfs_ialloc.c
+++ b/fs/xfs/libxfs/xfs_ialloc.c
@@ -103,8 +103,12 @@ xfs_inobt_check_irec(
{
uint64_t realfree;
+ /* Record has to be properly aligned within the AG. */
if (!xfs_verify_agino(cur->bc_ag.pag, irec->ir_startino))
return __this_address;
+ if (!xfs_verify_agino(cur->bc_ag.pag,
+ irec->ir_startino + XFS_INODES_PER_CHUNK - 1))
+ return __this_address;
if (irec->ir_count < XFS_INODES_PER_HOLEMASK_BIT ||
irec->ir_count > XFS_INODES_PER_CHUNK)
return __this_address;
diff --git a/fs/xfs/libxfs/xfs_rmap.c b/fs/xfs/libxfs/xfs_rmap.c
index 641114a023f2..da008d317f83 100644
--- a/fs/xfs/libxfs/xfs_rmap.c
+++ b/fs/xfs/libxfs/xfs_rmap.c
@@ -212,6 +212,10 @@ xfs_rmap_check_irec(
const struct xfs_rmap_irec *irec)
{
struct xfs_mount *mp = cur->bc_mp;
+ bool is_inode;
+ bool is_unwritten;
+ bool is_bmbt;
+ bool is_attr;
if (irec->rm_blockcount == 0)
return __this_address;
@@ -232,6 +236,29 @@ xfs_rmap_check_irec(
irec->rm_owner >= XFS_RMAP_OWN_MIN)))
return __this_address;
+ /* Check flags. */
+ is_inode = !XFS_RMAP_NON_INODE_OWNER(irec->rm_owner);
+ is_bmbt = irec->rm_flags & XFS_RMAP_BMBT_BLOCK;
+ is_attr = irec->rm_flags & XFS_RMAP_ATTR_FORK;
+ is_unwritten = irec->rm_flags & XFS_RMAP_UNWRITTEN;
+
+ if (is_bmbt && irec->rm_offset != 0)
+ return __this_address;
+
+ if (!is_inode && irec->rm_offset != 0)
+ return __this_address;
+
+ if (is_unwritten && (is_bmbt || !is_inode || is_attr))
+ return __this_address;
+
+ if (!is_inode && (is_bmbt || is_unwritten || is_attr))
+ return __this_address;
+
+ /* Check for a valid fork offset, if applicable. */
+ if (is_inode && !is_bmbt &&
+ !xfs_verify_fileext(mp, irec->rm_offset, irec->rm_blockcount))
+ return __this_address;
+
return NULL;
}
diff --git a/fs/xfs/scrub/ialloc.c b/fs/xfs/scrub/ialloc.c
index 11afb4c5a161..ca5a7e0f5451 100644
--- a/fs/xfs/scrub/ialloc.c
+++ b/fs/xfs/scrub/ialloc.c
@@ -413,7 +413,6 @@ xchk_iallocbt_rec(
const union xfs_btree_rec *rec)
{
struct xfs_mount *mp = bs->cur->bc_mp;
- struct xfs_perag *pag = bs->cur->bc_ag.pag;
struct xchk_iallocbt *iabt = bs->private;
struct xfs_inobt_rec_incore irec;
uint64_t holes;
@@ -431,11 +430,6 @@ xchk_iallocbt_rec(
}
agino = irec.ir_startino;
- /* Record has to be properly aligned within the AG. */
- if (!xfs_verify_agino(pag, agino + XFS_INODES_PER_CHUNK - 1)) {
- xchk_btree_set_corrupt(bs->sc, bs->cur, 0);
- goto out;
- }
xchk_iallocbt_rec_alignment(bs, &irec);
if (bs->sc->sm->sm_flags & XFS_SCRUB_OFLAG_CORRUPT)
diff --git a/fs/xfs/scrub/rmap.c b/fs/xfs/scrub/rmap.c
index 353cf9d90027..ef6e4b8546a6 100644
--- a/fs/xfs/scrub/rmap.c
+++ b/fs/xfs/scrub/rmap.c
@@ -94,10 +94,6 @@ xchk_rmapbt_rec(
const union xfs_btree_rec *rec)
{
struct xfs_rmap_irec irec;
- bool non_inode;
- bool is_unwritten;
- bool is_bmbt;
- bool is_attr;
if (xfs_rmap_btrec_to_irec(rec, &irec) != NULL ||
xfs_rmap_check_irec(bs->cur, &irec) != NULL) {
@@ -105,24 +101,6 @@ xchk_rmapbt_rec(
return 0;
}
- /* Check flags. */
- non_inode = XFS_RMAP_NON_INODE_OWNER(irec.rm_owner);
- is_bmbt = irec.rm_flags & XFS_RMAP_BMBT_BLOCK;
- is_attr = irec.rm_flags & XFS_RMAP_ATTR_FORK;
- is_unwritten = irec.rm_flags & XFS_RMAP_UNWRITTEN;
-
- if (is_bmbt && irec.rm_offset != 0)
- xchk_btree_set_corrupt(bs->sc, bs->cur, 0);
-
- if (non_inode && irec.rm_offset != 0)
- xchk_btree_set_corrupt(bs->sc, bs->cur, 0);
-
- if (is_unwritten && (is_bmbt || non_inode || is_attr))
- xchk_btree_set_corrupt(bs->sc, bs->cur, 0);
-
- if (non_inode && (is_bmbt || is_unwritten || is_attr))
- xchk_btree_set_corrupt(bs->sc, bs->cur, 0);
-
xchk_rmapbt_xref(bs->sc, &irec);
return 0;
}