]> git.ipfire.org Git - thirdparty/xfsprogs-dev.git/commitdiff
xfs_repair: support repairing zoned file systems
authorChristoph Hellwig <hch@lst.de>
Mon, 14 Apr 2025 05:36:10 +0000 (07:36 +0200)
committerAndrey Albershteyn <aalbersh@kernel.org>
Tue, 29 Apr 2025 16:09:57 +0000 (18:09 +0200)
Note really much to do here.  Mostly ignore the validation and
regeneration of the bitmap and summary inodes.  Eventually this
could grow a bit of validation of the hardware zone state.

Signed-off-by: Christoph Hellwig <hch@lst.de>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
repair/dinode.c
repair/phase5.c
repair/phase6.c
repair/rt.c
repair/rtrmap_repair.c
repair/xfs_repair.c

index 8696a838087f1b351e08cee20fa193c481a078d6..7bdd3dcf15c13b785d2caa7ce5a5e7064d079066 100644 (file)
@@ -3585,7 +3585,9 @@ _("bad (negative) size %" PRId64 " on inode %" PRIu64 "\n"),
 
        validate_extsize(mp, dino, lino, dirty);
 
-       if (dino->di_version >= 3)
+       if (dino->di_version >= 3 &&
+           (!xfs_has_zoned(mp) ||
+            dino->di_metatype != cpu_to_be16(XFS_METAFILE_RTRMAP)))
                validate_cowextsize(mp, dino, lino, dirty);
 
        /* nsec fields cannot be larger than 1 billion */
index 4cf28d8ae1a2503212ffac0acf8b8e344a917507..e350b411c2434b7425617b9aa38f3dc3be86a50a 100644 (file)
@@ -630,6 +630,19 @@ void
 check_rtmetadata(
        struct xfs_mount        *mp)
 {
+       if (xfs_has_zoned(mp)) {
+               /*
+                * Here we could/should verify the zone state a bit when we are
+                * on actual zoned devices:
+                *      - compare hw write pointer to last written
+                *      - compare zone state to last written
+                *
+                * Note much we can do when running in zoned mode on a
+                * conventional device.
+                */
+               return;
+       }
+
        generate_rtinfo(mp);
        check_rtbitmap(mp);
        check_rtsummary(mp);
index a67cc0abd21ec07e1fe07787dc24e0dde4e0823b..75429d4ca111d463e05480440800d9d9d750e3e6 100644 (file)
@@ -3469,8 +3469,10 @@ _("        - resetting contents of realtime bitmap and summary inodes\n"));
                return;
 
        while ((rtg = xfs_rtgroup_next(mp, rtg))) {
-               ensure_rtgroup_bitmap(rtg);
-               ensure_rtgroup_summary(rtg);
+               if (!xfs_has_zoned(mp)) {
+                       ensure_rtgroup_bitmap(rtg);
+                       ensure_rtgroup_summary(rtg);
+               }
                ensure_rtgroup_rmapbt(rtg, est_fdblocks);
                ensure_rtgroup_refcountbt(rtg, est_fdblocks);
        }
index e0a4943ee3b766c44fdb3b78ab488cbb1ae659c4..a2478fb635e33b94f02bce7e3de9d70c811ca5e5 100644 (file)
@@ -222,6 +222,8 @@ check_rtfile_contents(
        xfs_fileoff_t           bno = 0;
        int                     error;
 
+       ASSERT(!xfs_has_zoned(mp));
+
        if (!ip) {
                do_warn(_("unable to open %s file\n"), filename);
                return;
index 2b07e8943e591d03433acd93ed83dea2e6c3b6e0..955db1738fe240ca31e619f2ac8363e1d11da303 100644 (file)
@@ -141,6 +141,37 @@ xrep_rtrmap_btree_load(
        return error;
 }
 
+static void
+rtgroup_update_counters(
+       struct xfs_rtgroup      *rtg)
+{
+       struct xfs_inode        *rmapip = rtg->rtg_inodes[XFS_RTGI_RMAP];
+       struct xfs_mount        *mp = rtg_mount(rtg);
+       uint64_t                end =
+               xfs_rtbxlen_to_blen(mp, rtg->rtg_extents);
+       xfs_agblock_t           gbno = 0;
+       uint64_t                used = 0;
+
+       do {
+               int             bstate;
+               xfs_extlen_t    blen;
+
+               bstate = get_bmap_ext(rtg_rgno(rtg), gbno, end, &blen, true);
+               switch (bstate) {
+               case XR_E_INUSE:
+               case XR_E_INUSE_FS:
+                       used += blen;
+                       break;
+               default:
+                       break;
+               }
+
+               gbno += blen;
+       } while (gbno < end);
+
+       rmapip->i_used_blocks = used;
+}
+
 /* Update the inode counters. */
 STATIC int
 xrep_rtrmap_reset_counters(
@@ -153,6 +184,8 @@ xrep_rtrmap_reset_counters(
         * generated.
         */
        sc->ip->i_nblocks = rr->new_fork_info.ifake.if_blocks;
+       if (xfs_has_zoned(sc->mp))
+               rtgroup_update_counters(rr->rtg);
        libxfs_trans_log_inode(sc->tp, sc->ip, XFS_ILOG_CORE);
 
        /* Quotas don't exist so we're done. */
index eeaaf643468941ae677d5001d131b89f1ab26bac..7bf75c09b94542f3d7ca8905c8e978d7f28ae4c1 100644 (file)
@@ -1388,16 +1388,19 @@ main(int argc, char **argv)
         * Done with the block usage maps, toss them.  Realtime metadata aren't
         * rebuilt until phase 6, so we have to keep them around.
         */
-       if (mp->m_sb.sb_rblocks == 0)
+       if (mp->m_sb.sb_rblocks == 0) {
                rmaps_free(mp);
-       free_bmaps(mp);
+               free_bmaps(mp);
+       }
 
        if (!bad_ino_btree)  {
                phase6(mp);
                phase_end(mp, 6);
 
-               if (mp->m_sb.sb_rblocks != 0)
+               if (mp->m_sb.sb_rblocks != 0) {
                        rmaps_free(mp);
+                       free_bmaps(mp);
+               }
                free_rtgroup_inodes();
 
                phase7(mp, phase2_threads);