fs/xfs/scrub/agheader.c

Source file repositories/reference/linux-study-clean/fs/xfs/scrub/agheader.c

File Facts

System
Linux kernel
Corpus path
fs/xfs/scrub/agheader.c
Extension
.c
Size
28587 bytes
Lines
1062
Domain
Core OS
Bucket
VFS And Filesystem Core
Inferred role
Core OS: implementation source
Status
source implementation candidate

Why This File Exists

Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.

Dependency Surface

Detected Declarations

Annotated Snippet

struct xchk_agfl_info {
	/* Number of AGFL entries that the AGF claims are in use. */
	unsigned int		agflcount;

	/* Number of AGFL entries that we found. */
	unsigned int		nr_entries;

	/* Buffer to hold AGFL entries for extent checking. */
	xfs_agblock_t		*entries;

	struct xfs_buf		*agfl_bp;
	struct xfs_scrub	*sc;
};

/* Cross-reference with the other btrees. */
STATIC void
xchk_agfl_block_xref(
	struct xfs_scrub	*sc,
	xfs_agblock_t		agbno)
{
	if (sc->sm->sm_flags & XFS_SCRUB_OFLAG_CORRUPT)
		return;

	xchk_xref_is_used_space(sc, agbno, 1);
	xchk_xref_is_not_inode_chunk(sc, agbno, 1);
	xchk_xref_is_only_owned_by(sc, agbno, 1, &XFS_RMAP_OINFO_AG);
	xchk_xref_is_not_shared(sc, agbno, 1);
	xchk_xref_is_not_cow_staging(sc, agbno, 1);
}

/* Scrub an AGFL block. */
STATIC int
xchk_agfl_block(
	struct xfs_mount	*mp,
	xfs_agblock_t		agbno,
	void			*priv)
{
	struct xchk_agfl_info	*sai = priv;
	struct xfs_scrub	*sc = sai->sc;

	if (xfs_verify_agbno(sc->sa.pag, agbno) &&
	    sai->nr_entries < sai->agflcount)
		sai->entries[sai->nr_entries++] = agbno;
	else
		xchk_block_set_corrupt(sc, sai->agfl_bp);

	xchk_agfl_block_xref(sc, agbno);

	if (sc->sm->sm_flags & XFS_SCRUB_OFLAG_CORRUPT)
		return -ECANCELED;

	return 0;
}

static int
xchk_agblock_cmp(
	const void		*pa,
	const void		*pb)
{
	const xfs_agblock_t	*a = pa;
	const xfs_agblock_t	*b = pb;

	return (int)*a - (int)*b;
}

/* Cross-reference with the other btrees. */
STATIC void
xchk_agfl_xref(
	struct xfs_scrub	*sc)
{
	struct xfs_mount	*mp = sc->mp;
	xfs_agblock_t		agbno;

	if (sc->sm->sm_flags & XFS_SCRUB_OFLAG_CORRUPT)
		return;

	agbno = XFS_AGFL_BLOCK(mp);

	xchk_ag_btcur_init(sc, &sc->sa);

	xchk_xref_is_used_space(sc, agbno, 1);
	xchk_xref_is_not_inode_chunk(sc, agbno, 1);
	xchk_xref_is_only_owned_by(sc, agbno, 1, &XFS_RMAP_OINFO_FS);
	xchk_xref_is_not_shared(sc, agbno, 1);
	xchk_xref_is_not_cow_staging(sc, agbno, 1);

	/*
	 * Scrub teardown will take care of sc->sa for us.  Leave sc->sa
	 * active so that the agfl block xref can use it too.
	 */

Annotation

Implementation Notes