77#include "xfs_fs.h"
88#include "xfs_shared.h"
99#include "xfs_format.h"
10+ #include "xfs_log_format.h"
1011#include "xfs_trans_resv.h"
1112#include "xfs_mount.h"
13+ #include "xfs_trans.h"
1214#include "xfs_btree.h"
1315#include "xfs_rmap.h"
1416#include "xfs_refcount.h"
1517#include "xfs_ag.h"
1618#include "xfs_bit.h"
19+ #include "xfs_alloc.h"
20+ #include "xfs_alloc_btree.h"
1721#include "scrub/scrub.h"
1822#include "scrub/common.h"
1923#include "scrub/btree.h"
@@ -51,6 +55,7 @@ struct xchk_rmap {
5155 /* Bitmaps containing all blocks for each type of AG metadata. */
5256 struct xagb_bitmap fs_owned ;
5357 struct xagb_bitmap log_owned ;
58+ struct xagb_bitmap ag_owned ;
5459
5560 /* Did we complete the AG space metadata bitmaps? */
5661 bool bitmaps_complete ;
@@ -291,6 +296,9 @@ xchk_rmapbt_mark_bitmap(
291296 case XFS_RMAP_OWN_LOG :
292297 bmp = & cr -> log_owned ;
293298 break ;
299+ case XFS_RMAP_OWN_AG :
300+ bmp = & cr -> ag_owned ;
301+ break ;
294302 }
295303
296304 if (!bmp )
@@ -343,16 +351,36 @@ xchk_rmapbt_rec(
343351 return xchk_rmapbt_mark_bitmap (bs , cr , & irec );
344352}
345353
354+ /* Add an AGFL block to the rmap list. */
355+ STATIC int
356+ xchk_rmapbt_walk_agfl (
357+ struct xfs_mount * mp ,
358+ xfs_agblock_t agbno ,
359+ void * priv )
360+ {
361+ struct xagb_bitmap * bitmap = priv ;
362+
363+ return xagb_bitmap_set (bitmap , agbno , 1 );
364+ }
365+
346366/*
347367 * Set up bitmaps mapping all the AG metadata to compare with the rmapbt
348368 * records.
369+ *
370+ * Grab our own btree cursors here if the scrub setup function didn't give us a
371+ * btree cursor due to reports of poor health. We need to find out if the
372+ * rmapbt disagrees with primary metadata btrees to tag the rmapbt as being
373+ * XCORRUPT.
349374 */
350375STATIC int
351376xchk_rmapbt_walk_ag_metadata (
352377 struct xfs_scrub * sc ,
353378 struct xchk_rmap * cr )
354379{
355380 struct xfs_mount * mp = sc -> mp ;
381+ struct xfs_buf * agfl_bp ;
382+ struct xfs_agf * agf = sc -> sa .agf_bp -> b_addr ;
383+ struct xfs_btree_cur * cur ;
356384 int error ;
357385
358386 /* OWN_FS: AG headers */
@@ -370,6 +398,39 @@ xchk_rmapbt_walk_ag_metadata(
370398 goto out ;
371399 }
372400
401+ /* OWN_AG: bnobt, cntbt, rmapbt, and AGFL */
402+ cur = sc -> sa .bno_cur ;
403+ if (!cur )
404+ cur = xfs_allocbt_init_cursor (sc -> mp , sc -> tp , sc -> sa .agf_bp ,
405+ sc -> sa .pag , XFS_BTNUM_BNO );
406+ error = xagb_bitmap_set_btblocks (& cr -> ag_owned , cur );
407+ if (cur != sc -> sa .bno_cur )
408+ xfs_btree_del_cursor (cur , error );
409+ if (error )
410+ goto out ;
411+
412+ cur = sc -> sa .cnt_cur ;
413+ if (!cur )
414+ cur = xfs_allocbt_init_cursor (sc -> mp , sc -> tp , sc -> sa .agf_bp ,
415+ sc -> sa .pag , XFS_BTNUM_CNT );
416+ error = xagb_bitmap_set_btblocks (& cr -> ag_owned , cur );
417+ if (cur != sc -> sa .cnt_cur )
418+ xfs_btree_del_cursor (cur , error );
419+ if (error )
420+ goto out ;
421+
422+ error = xagb_bitmap_set_btblocks (& cr -> ag_owned , sc -> sa .rmap_cur );
423+ if (error )
424+ goto out ;
425+
426+ error = xfs_alloc_read_agfl (sc -> sa .pag , sc -> tp , & agfl_bp );
427+ if (error )
428+ goto out ;
429+
430+ error = xfs_agfl_walk (sc -> mp , agf , agfl_bp , xchk_rmapbt_walk_agfl ,
431+ & cr -> ag_owned );
432+ xfs_trans_brelse (sc -> tp , agfl_bp );
433+
373434out :
374435 /*
375436 * If there's an error, set XFAIL and disable the bitmap
@@ -411,6 +472,9 @@ xchk_rmapbt_check_bitmaps(
411472
412473 if (xagb_bitmap_hweight (& cr -> log_owned ) != 0 )
413474 xchk_btree_xref_set_corrupt (sc , cur , level );
475+
476+ if (xagb_bitmap_hweight (& cr -> ag_owned ) != 0 )
477+ xchk_btree_xref_set_corrupt (sc , cur , level );
414478}
415479
416480/* Scrub the rmap btree for some AG. */
@@ -427,6 +491,7 @@ xchk_rmapbt(
427491
428492 xagb_bitmap_init (& cr -> fs_owned );
429493 xagb_bitmap_init (& cr -> log_owned );
494+ xagb_bitmap_init (& cr -> ag_owned );
430495
431496 error = xchk_rmapbt_walk_ag_metadata (sc , cr );
432497 if (error )
@@ -440,6 +505,7 @@ xchk_rmapbt(
440505 xchk_rmapbt_check_bitmaps (sc , cr );
441506
442507out :
508+ xagb_bitmap_destroy (& cr -> ag_owned );
443509 xagb_bitmap_destroy (& cr -> log_owned );
444510 xagb_bitmap_destroy (& cr -> fs_owned );
445511 kfree (cr );
0 commit comments