xfs: factor out a xfs_validate_rt_geometry helper

Split the RT geometry validation in the early mount code into a
helper than can be reused by repair (from which this code was
apparently originally stolen anyway).

Signed-off-by: Christoph Hellwig <hch@lst.de>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
[djwong: u64 return value for calc_rbmblocks]
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
This commit is contained in:
Christoph Hellwig 2024-08-30 15:36:51 -07:00 committed by Darrick J. Wong
parent 021d9c107e
commit 6529eef810
2 changed files with 36 additions and 29 deletions

View File

@ -232,6 +232,38 @@ xfs_validate_sb_read(
return 0;
}
static uint64_t
xfs_sb_calc_rbmblocks(
struct xfs_sb *sbp)
{
return howmany_64(sbp->sb_rextents, NBBY * sbp->sb_blocksize);
}
/* Validate the realtime geometry */
bool
xfs_validate_rt_geometry(
struct xfs_sb *sbp)
{
if (sbp->sb_rextsize * sbp->sb_blocksize > XFS_MAX_RTEXTSIZE ||
sbp->sb_rextsize * sbp->sb_blocksize < XFS_MIN_RTEXTSIZE)
return false;
if (sbp->sb_rblocks == 0) {
if (sbp->sb_rextents != 0 || sbp->sb_rbmblocks != 0 ||
sbp->sb_rextslog != 0 || sbp->sb_frextents != 0)
return false;
return true;
}
if (sbp->sb_rextents == 0 ||
sbp->sb_rextents != div_u64(sbp->sb_rblocks, sbp->sb_rextsize) ||
sbp->sb_rextslog != xfs_compute_rextslog(sbp->sb_rextents) ||
sbp->sb_rbmblocks != xfs_sb_calc_rbmblocks(sbp))
return false;
return true;
}
/* Check all the superblock fields we care about when writing one out. */
STATIC int
xfs_validate_sb_write(
@ -491,39 +523,13 @@ xfs_validate_sb_common(
}
}
/* Validate the realtime geometry; stolen from xfs_repair */
if (sbp->sb_rextsize * sbp->sb_blocksize > XFS_MAX_RTEXTSIZE ||
sbp->sb_rextsize * sbp->sb_blocksize < XFS_MIN_RTEXTSIZE) {
if (!xfs_validate_rt_geometry(sbp)) {
xfs_notice(mp,
"realtime extent sanity check failed");
"realtime %sgeometry check failed",
sbp->sb_rblocks ? "" : "zeroed ");
return -EFSCORRUPTED;
}
if (sbp->sb_rblocks == 0) {
if (sbp->sb_rextents != 0 || sbp->sb_rbmblocks != 0 ||
sbp->sb_rextslog != 0 || sbp->sb_frextents != 0) {
xfs_notice(mp,
"realtime zeroed geometry check failed");
return -EFSCORRUPTED;
}
} else {
uint64_t rexts;
uint64_t rbmblocks;
rexts = div_u64(sbp->sb_rblocks, sbp->sb_rextsize);
rbmblocks = howmany_64(sbp->sb_rextents,
NBBY * sbp->sb_blocksize);
if (sbp->sb_rextents == 0 ||
sbp->sb_rextents != rexts ||
sbp->sb_rextslog != xfs_compute_rextslog(rexts) ||
sbp->sb_rbmblocks != rbmblocks) {
xfs_notice(mp,
"realtime geometry sanity check failed");
return -EFSCORRUPTED;
}
}
/*
* Either (sb_unit and !hasdalign) or (!sb_unit and hasdalign)
* would imply the image is corrupted.

View File

@ -38,6 +38,7 @@ extern int xfs_sb_get_secondary(struct xfs_mount *mp,
bool xfs_validate_stripe_geometry(struct xfs_mount *mp,
__s64 sunit, __s64 swidth, int sectorsize, bool may_repair,
bool silent);
bool xfs_validate_rt_geometry(struct xfs_sb *sbp);
uint8_t xfs_compute_rextslog(xfs_rtbxlen_t rtextents);