From 48bec246f88d06c80d2918284cb9d78fa767c140 Mon Sep 17 00:00:00 2001 From: "Darrick J. Wong" Date: Wed, 1 Sep 2021 10:45:54 -0700 Subject: xfs: reintroduce reaping of file extents to xrep_reap_extents Reintroduce to xrep_reap_extents the ability to reap extents from any AG. We dropped this before because it was buggy, but in the next patch we will gain the ability to reap old bmap btrees, which can have blocks in any AG. To do this, we require that sc->sa is uninitialized, so that we can use it to hold all the per-AG context for a given extent. Signed-off-by: Darrick J. Wong --- fs/xfs/scrub/repair.c | 43 +++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 41 insertions(+), 2 deletions(-) (limited to 'fs/xfs/scrub') diff --git a/fs/xfs/scrub/repair.c b/fs/xfs/scrub/repair.c index 832926c1fa9d..20667b8b2754 100644 --- a/fs/xfs/scrub/repair.c +++ b/fs/xfs/scrub/repair.c @@ -1027,6 +1027,20 @@ xrep_reap_ag_extent( roll_out: rs->deferred = 0; + if (sc->ip) { + /* + * If we're reaping file data, hold the AGF buffer across the + * transaction roll so that we don't have to reattach it to the + * xchk_ag structure. + */ + xfs_trans_bhold(sc->tp, sc->sa.agf_bp); + error = xfs_trans_roll_inode(&sc->tp, sc->ip); + if (error) + return error; + xfs_trans_bjoin(sc->tp, sc->sa.agf_bp); + return 0; + } + return xrep_roll_ag_trans(sc); } @@ -1086,8 +1100,24 @@ xrep_reap_extent( ASSERT(len <= MAXEXTLEN); - /* We don't support reaping file extents yet. */ - if (sc->ip != NULL || sc->sa.pag->pag_agno != agno) { + if (sc->ip != NULL) { + /* + * We're reaping blocks after repairing file metadata, which + * means that the blocks can be in any AG, so we have to init + * the xchk_ag structure before we can reap each extent and + * release it afterwards. + */ + ASSERT(!sc->sa.pag); + + sc->sa.pag = xfs_perag_get(sc->mp, agno); + if (!sc->sa.pag) + return -EFSCORRUPTED; + + error = xfs_alloc_read_agf(sc->mp, sc->tp, agno, 0, + &sc->sa.agf_bp); + if (error) + goto out_pag; + } else if (sc->sa.pag == NULL || sc->sa.pag->pag_agno != agno) { ASSERT(0); return -EFSCORRUPTED; } @@ -1124,6 +1154,15 @@ xrep_reap_extent( out_cur: if (cur) xfs_btree_del_cursor(cur, error); + if (sc->ip != NULL) { + xfs_trans_brelse(sc->tp, sc->sa.agf_bp); + sc->sa.agf_bp = NULL; + } +out_pag: + if (sc->ip != NULL) { + xfs_perag_put(sc->sa.pag); + sc->sa.pag = NULL; + } return error; } -- cgit v1.2.3