]> www.infradead.org Git - users/hch/xfsprogs.git/commitdiff
xfs: use an incore rtgroup rotor for rtpick
authorDarrick J. Wong <djwong@kernel.org>
Thu, 9 Nov 2023 17:35:51 +0000 (09:35 -0800)
committerDarrick J. Wong <djwong@kernel.org>
Wed, 22 Nov 2023 23:03:34 +0000 (15:03 -0800)
During the 6.7 merge window, Linus noticed that the realtime allocator
was doing some sketchy things trying to encode a u64 sequence counter
into the rtbitmap file's atime.  The sketchy casting of a struct pointer
to a u64 pointer has subtly broken several times over the past decade as
the codebase has transitioned to using the VFS i_atime field and that
field has changed in size and layout over time.

Since the goal of the rtpick code is to _suggest_ a starting place for
new rt file allocations, the repeated breakage has not resulted in
inconsistent metadata.  IOWs, it's a hint.

For rtgroups, we don't need this complex code to cut the rtextents space
into fractions.  Add an rtgroup rotor and use that for rtpick, similar
to AG rotoring on the data device.  The new rotor does not persist,
which reduces the logging overhead slightly.

Link: https://lore.kernel.org/linux-xfs/CAHk-=wj3oM3d-Hw2vvxys3KCZ9De+gBN7Gxr2jf96OTisL9udw@mail.gmail.com/
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
include/xfs_mount.h
libxfs/xfs_rtbitmap.c
mkfs/proto.c

index 56d623507423652c9bf786b9674c8117343966eb..8e17235a34d11b6dd052cd3e5a16dbb0e8e591b2 100644 (file)
@@ -51,6 +51,7 @@ typedef struct xfs_mount {
        char                    *m_fsname;      /* filesystem name */
        int                     m_bsize;        /* fs logical block size */
        spinlock_t              m_agirotor_lock;
+       xfs_rgnumber_t          m_rtgrotor;     /* last rtgroup rtpicked */
        xfs_agnumber_t          m_agfrotor;     /* last ag where space found */
        xfs_agnumber_t          m_agirotor;     /* last ag dir inode alloced */
        xfs_agnumber_t          m_maxagi;       /* highest inode alloc group */
index 758f0c2703fe5ef001c0679517f45740cb081393..4f2c9744de3d6c89d177a9ec81f52a38b12753b7 100644 (file)
@@ -1060,10 +1060,14 @@ xfs_rtfree_extent(
                if (!(mp->m_rbmip->i_diflags & XFS_DIFLAG_NEWRTBM))
                        mp->m_rbmip->i_diflags |= XFS_DIFLAG_NEWRTBM;
 
-               atime = inode_get_atime(VFS_I(mp->m_rbmip));
-               atime.tv_sec = 0;
-               inode_set_atime_to_ts(VFS_I(mp->m_rbmip), atime);
-               xfs_trans_log_inode(tp, mp->m_rbmip, XFS_ILOG_CORE);
+               if (xfs_has_rtgroups(mp)) {
+                       mp->m_rtgrotor = 0;
+               } else {
+                       atime = inode_get_atime(VFS_I(mp->m_rbmip));
+                       atime.tv_sec = 0;
+                       inode_set_atime_to_ts(VFS_I(mp->m_rbmip), atime);
+                       xfs_trans_log_inode(tp, mp->m_rbmip, XFS_ILOG_CORE);
+               }
        }
        error = 0;
 out:
index 33d454cffb2a04132d29646f467b3dd8098e211a..36df148018f6bf8ada12811310648d7afa574089 100644 (file)
@@ -810,7 +810,8 @@ rtbitmap_create(
 
        rbmip->i_disk_size = mp->m_sb.sb_rbmblocks * mp->m_sb.sb_blocksize;
        rbmip->i_diflags |= XFS_DIFLAG_NEWRTBM;
-       inode_set_atime(VFS_I(rbmip), 0, 0);
+       if (!xfs_has_rtgroups(mp))
+               inode_set_atime(VFS_I(rbmip), 0, 0);
        libxfs_trans_log_inode(upd.tp, rbmip, XFS_ILOG_CORE);
 
        error = -libxfs_imeta_commit_update(&upd);