xfs: compute maximum AG btree height for critical reservation calculation
authorDarrick J. Wong <djwong@kernel.org>
Thu, 16 Sep 2021 19:27:34 +0000 (12:27 -0700)
committerDarrick J. Wong <djwong@kernel.org>
Tue, 19 Oct 2021 18:45:15 +0000 (11:45 -0700)
Compute the actual maximum AG btree height for deciding if a per-AG
block reservation is critically low.  This only affects the sanity check
condition, since we /generally/ will trigger on the 10% threshold.  This
is a long-winded way of saying that we're removing one more usage of
XFS_BTREE_MAXLEVELS.

Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Dave Chinner <dchinner@redhat.com>
fs/xfs/libxfs/xfs_ag_resv.c
fs/xfs/xfs_mount.c
fs/xfs/xfs_mount.h

index 2aa2b3484c28754962ec21393c5d4083f11e9fa5..fe94058d4e9eb8ed8109d95a96b10c17e6bbbae9 100644 (file)
@@ -91,7 +91,8 @@ xfs_ag_resv_critical(
        trace_xfs_ag_resv_critical(pag, type, avail);
 
        /* Critically low if less than 10% or max btree height remains. */
-       return XFS_TEST_ERROR(avail < orig / 10 || avail < XFS_BTREE_MAXLEVELS,
+       return XFS_TEST_ERROR(avail < orig / 10 ||
+                             avail < pag->pag_mount->m_agbtree_maxlevels,
                        pag->pag_mount, XFS_ERRTAG_AG_RESV_CRITICAL);
 }
 
index 06dac09eddbd8004f935d678b15c90dd184aeb12..359109b6f0d3c005bda3c23bbd86ba94e6b8c174 100644 (file)
@@ -567,6 +567,18 @@ xfs_mount_setup_inode_geom(
        xfs_ialloc_setup_geometry(mp);
 }
 
+/* Compute maximum possible height for per-AG btree types for this fs. */
+static inline void
+xfs_agbtree_compute_maxlevels(
+       struct xfs_mount        *mp)
+{
+       unsigned int            levels;
+
+       levels = max(mp->m_alloc_maxlevels, M_IGEO(mp)->inobt_maxlevels);
+       levels = max(levels, mp->m_rmap_maxlevels);
+       mp->m_agbtree_maxlevels = max(levels, mp->m_refc_maxlevels);
+}
+
 /*
  * This function does the following on an initial mount of a file system:
  *     - reads the superblock from disk and init the mount struct
@@ -638,6 +650,8 @@ xfs_mountfs(
        xfs_rmapbt_compute_maxlevels(mp);
        xfs_refcountbt_compute_maxlevels(mp);
 
+       xfs_agbtree_compute_maxlevels(mp);
+
        /*
         * Check if sb_agblocks is aligned at stripe boundary.  If sb_agblocks
         * is NOT aligned turn off m_dalign since allocator alignment is within
index e4b7a8eb0d06d0e8f6b8fd3b29c1f91dfa6bf8f1..00720a02e7615198454b8296047aa98d0299859c 100644 (file)
@@ -132,6 +132,7 @@ typedef struct xfs_mount {
        uint                    m_bm_maxlevels[2]; /* max bmap btree levels */
        uint                    m_rmap_maxlevels; /* max rmap btree levels */
        uint                    m_refc_maxlevels; /* max refcount btree level */
+       unsigned int            m_agbtree_maxlevels; /* max level of all AG btrees */
        xfs_extlen_t            m_ag_prealloc_blocks; /* reserved ag blocks */
        uint                    m_alloc_set_aside; /* space we can't use */
        uint                    m_ag_max_usable; /* max space per AG */