Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 04f13060 authored by Darrick J. Wong's avatar Darrick J. Wong Committed by Dave Chinner
Browse files

xfs: don't update rmapbt when fixing agfl



Allow a caller of xfs_alloc_fix_freelist to disable rmapbt updates
when fixing the AG freelist.  xfs_repair needs this during phase 5
to be able to adjust the freelist while it's reconstructing the rmap
btree; the missing entries will be added back at the very end of
phase 5 once the AGFL contents settle down.

Signed-off-by: default avatarDarrick J. Wong <darrick.wong@oracle.com>
Reviewed-by: default avatarDave Chinner <dchinner@redhat.com>
Signed-off-by: default avatarDave Chinner <david@fromorbit.com>
parent 2b0eeb5e
Loading
Loading
Loading
Loading
+14 −4
Original line number Diff line number Diff line
@@ -2090,9 +2090,21 @@ xfs_alloc_fix_freelist(
	 * anything other than extra overhead when we need to put more blocks
	 * back on the free list? Maybe we should only do this when space is
	 * getting low or the AGFL is more than half full?
	 *
	 * The NOSHRINK flag prevents the AGFL from being shrunk if it's too
	 * big; the NORMAP flag prevents AGFL expand/shrink operations from
	 * updating the rmapbt.  Both flags are used in xfs_repair while we're
	 * rebuilding the rmapbt, and neither are used by the kernel.  They're
	 * both required to ensure that rmaps are correctly recorded for the
	 * regenerated AGFL, bnobt, and cntbt.  See repair/phase5.c and
	 * repair/rmap.c in xfsprogs for details.
	 */
	memset(&targs, 0, sizeof(targs));
	if (flags & XFS_ALLOC_FLAG_NORMAP)
		xfs_rmap_skip_owner_update(&targs.oinfo);
	else
		xfs_rmap_ag_owner(&targs.oinfo, XFS_RMAP_OWN_AG);
	while (pag->pagf_flcount > need) {
	while (!(flags & XFS_ALLOC_FLAG_NOSHRINK) && pag->pagf_flcount > need) {
		struct xfs_buf	*bp;

		error = xfs_alloc_get_freelist(tp, agbp, &bno, 0);
@@ -2106,10 +2118,8 @@ xfs_alloc_fix_freelist(
		xfs_trans_binval(tp, bp);
	}

	memset(&targs, 0, sizeof(targs));
	targs.tp = tp;
	targs.mp = mp;
	xfs_rmap_ag_owner(&targs.oinfo, XFS_RMAP_OWN_AG);
	targs.agbp = agbp;
	targs.agno = args->agno;
	targs.alignment = targs.minlen = targs.prod = targs.isfl = 1;
+3 −0
Original line number Diff line number Diff line
@@ -54,6 +54,9 @@ typedef unsigned int xfs_alloctype_t;
 */
#define	XFS_ALLOC_FLAG_TRYLOCK	0x00000001  /* use trylock for buffer locking */
#define	XFS_ALLOC_FLAG_FREEING	0x00000002  /* indicate caller is freeing extents*/
#define	XFS_ALLOC_FLAG_NORMAP	0x00000004  /* don't modify the rmapbt */
#define	XFS_ALLOC_FLAG_NOSHRINK	0x00000008  /* don't shrink the freelist */


/*
 * Argument structure for xfs_alloc routines.