xfs: fix parent pointer scrubber bailing out on unallocated inodes

xfs_iget can return -ENOENT for a file that the inobt thinks is
allocated but has zeroed mode.  This currently causes scrub to exit
with an operational error instead of flagging this as a corruption.  The
end result is that scrub mistakenly reports the ENOENT to the user
instead of "directory parent pointer corrupt" like we do for EINVAL.

Fixes: 5927268f5a ("xfs: flag inode corruption if parent ptr doesn't get us a real inode")
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
Reviewed-by: Christoph Hellwig <hch@lst.de>
This commit is contained in:
Darrick J. Wong 2020-12-02 12:25:44 -08:00
Родитель acf104c233
Коммит da531cc46e
1 изменённых файлов: 5 добавлений и 5 удалений

Просмотреть файл

@ -164,13 +164,13 @@ xchk_parent_validate(
* can't use DONTCACHE here because DONTCACHE inodes can trigger * can't use DONTCACHE here because DONTCACHE inodes can trigger
* immediate inactive cleanup of the inode. * immediate inactive cleanup of the inode.
* *
* If _iget returns -EINVAL then the parent inode number is garbage * If _iget returns -EINVAL or -ENOENT then the parent inode number is
* and the directory is corrupt. If the _iget returns -EFSCORRUPTED * garbage and the directory is corrupt. If the _iget returns
* or -EFSBADCRC then the parent is corrupt which is a cross * -EFSCORRUPTED or -EFSBADCRC then the parent is corrupt which is a
* referencing error. Any other error is an operational error. * cross referencing error. Any other error is an operational error.
*/ */
error = xfs_iget(mp, sc->tp, dnum, XFS_IGET_UNTRUSTED, 0, &dp); error = xfs_iget(mp, sc->tp, dnum, XFS_IGET_UNTRUSTED, 0, &dp);
if (error == -EINVAL) { if (error == -EINVAL || error == -ENOENT) {
error = -EFSCORRUPTED; error = -EFSCORRUPTED;
xchk_fblock_process_error(sc, XFS_DATA_FORK, 0, &error); xchk_fblock_process_error(sc, XFS_DATA_FORK, 0, &error);
goto out; goto out;