コード例 #1
0
/*
 * Validate a given inode number.
 */
int
xfs_dir_ino_validate(
	xfs_mount_t	*mp,
	xfs_ino_t	ino)
{
	xfs_agblock_t	agblkno;
	xfs_agino_t	agino;
	xfs_agnumber_t	agno;
	int		ino_ok;
	int		ioff;

	agno = XFS_INO_TO_AGNO(mp, ino);
	agblkno = XFS_INO_TO_AGBNO(mp, ino);
	ioff = XFS_INO_TO_OFFSET(mp, ino);
	agino = XFS_OFFBNO_TO_AGINO(mp, agblkno, ioff);
	ino_ok =
		agno < mp->m_sb.sb_agcount &&
		agblkno < mp->m_sb.sb_agblocks &&
		agblkno != 0 &&
		ioff < (1 << mp->m_sb.sb_inopblog) &&
		XFS_AGINO_TO_INO(mp, agno, agino) == ino;
	if (unlikely(XFS_TEST_ERROR(!ino_ok, mp, XFS_ERRTAG_DIR_INO_VALIDATE,
			XFS_RANDOM_DIR_INO_VALIDATE))) {
		xfs_warn(mp, "Invalid inode number 0x%Lx",
				(unsigned long long) ino);
		XFS_ERROR_REPORT("xfs_dir_ino_validate", XFS_ERRLEVEL_LOW, mp);
		return XFS_ERROR(EFSCORRUPTED);
	}
	return 0;
}
コード例 #2
0
ファイル: inode.c プロジェクト: guribe94/linux
/* Cross-reference with the other btrees. */
STATIC void
xchk_inode_xref(
	struct xfs_scrub	*sc,
	xfs_ino_t		ino,
	struct xfs_dinode	*dip)
{
	struct xfs_owner_info	oinfo;
	xfs_agnumber_t		agno;
	xfs_agblock_t		agbno;
	int			error;

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

	agno = XFS_INO_TO_AGNO(sc->mp, ino);
	agbno = XFS_INO_TO_AGBNO(sc->mp, ino);

	error = xchk_ag_init(sc, agno, &sc->sa);
	if (!xchk_xref_process_error(sc, agno, agbno, &error))
		return;

	xchk_xref_is_used_space(sc, agbno, 1);
	xchk_inode_xref_finobt(sc, ino);
	xfs_rmap_ag_owner(&oinfo, XFS_RMAP_OWN_INODES);
	xchk_xref_is_owned_by(sc, agbno, 1, &oinfo);
	xchk_xref_is_not_shared(sc, agbno, 1);
	xchk_inode_xref_bmap(sc, dip);

	xchk_ag_free(sc, &sc->sa);
}
コード例 #3
0
ファイル: inode.c プロジェクト: guribe94/linux
/*
 * If the reflink iflag disagrees with a scan for shared data fork extents,
 * either flag an error (shared extents w/ no flag) or a preen (flag set w/o
 * any shared extents).  We already checked for reflink iflag set on a non
 * reflink filesystem.
 */
static void
xchk_inode_check_reflink_iflag(
	struct xfs_scrub	*sc,
	xfs_ino_t		ino)
{
	struct xfs_mount	*mp = sc->mp;
	bool			has_shared;
	int			error;

	if (!xfs_sb_version_hasreflink(&mp->m_sb))
		return;

	error = xfs_reflink_inode_has_shared_extents(sc->tp, sc->ip,
			&has_shared);
	if (!xchk_xref_process_error(sc, XFS_INO_TO_AGNO(mp, ino),
			XFS_INO_TO_AGBNO(mp, ino), &error))
		return;
	if (xfs_is_reflink_inode(sc->ip) && !has_shared)
		xchk_ino_set_preen(sc, ino);
	else if (!xfs_is_reflink_inode(sc->ip) && has_shared)
		xchk_ino_set_corrupt(sc, ino);
}
コード例 #4
0
ファイル: phase2.c プロジェクト: brkt/fuse-xfs
void
phase2(
	struct xfs_mount	*mp,
	int			scan_threads)
{
	int			j;
	ino_tree_node_t		*ino_rec;

	/* now we can start using the buffer cache routines */
	set_mp(mp);

	/* Check whether this fs has internal or external log */
	if (mp->m_sb.sb_logstart == 0) {
		if (!x.logname)
			do_error(_("This filesystem has an external log.  "
				   "Specify log device with the -l option.\n"));

		do_log(_("Phase 2 - using external log on %s\n"), x.logname);
	} else
		do_log(_("Phase 2 - using internal log\n"));

	/* Zero log if applicable */
	if (!no_modify)  {
		do_log(_("        - zero log...\n"));
		zero_log(mp);
	}

	do_log(_("        - scan filesystem freespace and inode maps...\n"));

	bad_ino_btree = 0;

	set_progress_msg(PROG_FMT_SCAN_AG, (__uint64_t) glob_agcount);

	scan_ags(mp, scan_threads);

	print_final_rpt();

	/*
	 * make sure we know about the root inode chunk
	 */
	if ((ino_rec = find_inode_rec(0, mp->m_sb.sb_rootino)) == NULL)  {
		ASSERT(mp->m_sb.sb_rbmino == mp->m_sb.sb_rootino + 1 &&
			mp->m_sb.sb_rsumino == mp->m_sb.sb_rootino + 2);
		do_warn(_("root inode chunk not found\n"));

		/*
		 * mark the first 3 used, the rest are free
		 */
		ino_rec = set_inode_used_alloc(0,
				(xfs_agino_t) mp->m_sb.sb_rootino);
		set_inode_used(ino_rec, 1);
		set_inode_used(ino_rec, 2);

		for (j = 3; j < XFS_INODES_PER_CHUNK; j++)
			set_inode_free(ino_rec, j);

		/*
		 * also mark blocks
		 */
		set_bmap_ext(0, XFS_INO_TO_AGBNO(mp, mp->m_sb.sb_rootino),
			     mp->m_ialloc_blks, XR_E_INO);
	} else  {
		do_log(_("        - found root inode chunk\n"));

		/*
		 * blocks are marked, just make sure they're in use
		 */
		if (is_inode_free(ino_rec, 0))  {
			do_warn(_("root inode marked free, "));
			set_inode_used(ino_rec, 0);
			if (!no_modify)
				do_warn(_("correcting\n"));
			else
				do_warn(_("would correct\n"));
		}

		if (is_inode_free(ino_rec, 1))  {
			do_warn(_("realtime bitmap inode marked free, "));
			set_inode_used(ino_rec, 1);
			if (!no_modify)
				do_warn(_("correcting\n"));
			else
				do_warn(_("would correct\n"));
		}

		if (is_inode_free(ino_rec, 2))  {
			do_warn(_("realtime summary inode marked free, "));
			set_inode_used(ino_rec, 2);
			if (!no_modify)
				do_warn(_("correcting\n"));
			else
				do_warn(_("would correct\n"));
		}
	}
}
コード例 #5
0
ファイル: phase2.c プロジェクト: hyakki-/sgi
void
phase2(xfs_mount_t *mp, libxfs_init_t *args)
{
    xfs_agnumber_t		i;
    xfs_agblock_t		b;
    int			j;
    ino_tree_node_t		*ino_rec;

    /* now we can start using the buffer cache routines */
    set_mp(mp);

    /* Check whether this fs has internal or external log */
    if (mp->m_sb.sb_logstart == 0) {
        if (!args->logname) {
            fprintf (stderr,
                     "This filesystem has an external log.  "
                     "Specify log device with the -l option.\n");
            exit (1);
        }

        fprintf (stderr, "Phase 2 - using external log on %s\n",
                 args->logname);
    } else
        fprintf (stderr, "Phase 2 - using internal log\n");

    /* Zero log if applicable */
    if (!no_modify)  {
        do_log("        - zero log...\n");
        zero_log(mp, args);
    }

    do_log("        - scan filesystem freespace and inode maps...\n");

    /*
     * account for space used by ag headers and log if internal
     */
    set_bmap_log(mp);
    set_bmap_fs(mp);

    bad_ino_btree = 0;

    for (i = 0; i < mp->m_sb.sb_agcount; i++)  {
        scan_ag(i);
#ifdef XR_INODE_TRACE
        print_inode_list(i);
#endif
    }

    /*
     * make sure we know about the root inode chunk
     */
    if ((ino_rec = find_inode_rec(0, mp->m_sb.sb_rootino)) == NULL)  {
        ASSERT(mp->m_sb.sb_rbmino == mp->m_sb.sb_rootino + 1 &&
               mp->m_sb.sb_rsumino == mp->m_sb.sb_rootino + 2);
        do_warn("root inode chunk not found\n");

        /*
         * mark the first 3 used, the rest are free
         */
        ino_rec = set_inode_used_alloc(0,
                                       (xfs_agino_t) mp->m_sb.sb_rootino);
        set_inode_used(ino_rec, 1);
        set_inode_used(ino_rec, 2);

        for (j = 3; j < XFS_INODES_PER_CHUNK; j++)
            set_inode_free(ino_rec, j);

        /*
         * also mark blocks
         */
        for (b = 0; b < mp->m_ialloc_blks; b++)  {
            set_agbno_state(mp, 0,
                            b + XFS_INO_TO_AGBNO(mp, mp->m_sb.sb_rootino),
                            XR_E_INO);
        }
    } else  {
        do_log("        - found root inode chunk\n");

        /*
         * blocks are marked, just make sure they're in use
         */
        if (is_inode_free(ino_rec, 0))  {
            do_warn("root inode marked free, ");
            set_inode_used(ino_rec, 0);
            if (!no_modify)
                do_warn("correcting\n");
            else
                do_warn("would correct\n");
        }

        if (is_inode_free(ino_rec, 1))  {
            do_warn("realtime bitmap inode marked free, ");
            set_inode_used(ino_rec, 1);
            if (!no_modify)
                do_warn("correcting\n");
            else
                do_warn("would correct\n");
        }

        if (is_inode_free(ino_rec, 2))  {
            do_warn("realtime summary inode marked free, ");
            set_inode_used(ino_rec, 2);
            if (!no_modify)
                do_warn("correcting\n");
            else
                do_warn("would correct\n");
        }
    }
}
コード例 #6
0
ファイル: xfs_macros.c プロジェクト: kzlin129/tt-gpl
xfs_agblock_t
xfs_ino_to_agbno(xfs_mount_t *mp, xfs_ino_t i)
{
    return XFS_INO_TO_AGBNO(mp, i);
}