xfs: report quota block corruption errors to the health system
Whenever we encounter corrupt quota blocks, we should report that to the health monitoring system for later reporting. Signed-off-by: Darrick J. Wong <djwong@kernel.org> Reviewed-by: Christoph Hellwig <hch@lst.de>
This commit is contained in:
parent
baf44fa5c3
commit
841a5f87e2
@ -24,6 +24,7 @@
|
||||
#include "xfs_log.h"
|
||||
#include "xfs_bmap_btree.h"
|
||||
#include "xfs_error.h"
|
||||
#include "xfs_health.h"
|
||||
|
||||
/*
|
||||
* Lock order:
|
||||
@ -44,6 +45,29 @@ static struct kmem_cache *xfs_dquot_cache;
|
||||
static struct lock_class_key xfs_dquot_group_class;
|
||||
static struct lock_class_key xfs_dquot_project_class;
|
||||
|
||||
/* Record observations of quota corruption with the health tracking system. */
|
||||
static void
|
||||
xfs_dquot_mark_sick(
|
||||
struct xfs_dquot *dqp)
|
||||
{
|
||||
struct xfs_mount *mp = dqp->q_mount;
|
||||
|
||||
switch (dqp->q_type) {
|
||||
case XFS_DQTYPE_USER:
|
||||
xfs_fs_mark_sick(mp, XFS_SICK_FS_UQUOTA);
|
||||
break;
|
||||
case XFS_DQTYPE_GROUP:
|
||||
xfs_fs_mark_sick(mp, XFS_SICK_FS_GQUOTA);
|
||||
break;
|
||||
case XFS_DQTYPE_PROJ:
|
||||
xfs_fs_mark_sick(mp, XFS_SICK_FS_PQUOTA);
|
||||
break;
|
||||
default:
|
||||
ASSERT(0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* This is called to free all the memory associated with a dquot
|
||||
*/
|
||||
@ -451,6 +475,8 @@ xfs_dquot_disk_read(
|
||||
error = xfs_trans_read_buf(mp, NULL, mp->m_ddev_targp, dqp->q_blkno,
|
||||
mp->m_quotainfo->qi_dqchunklen, 0, &bp,
|
||||
&xfs_dquot_buf_ops);
|
||||
if (xfs_metadata_is_sick(error))
|
||||
xfs_dquot_mark_sick(dqp);
|
||||
if (error) {
|
||||
ASSERT(bp == NULL);
|
||||
return error;
|
||||
@ -574,6 +600,7 @@ xfs_dquot_from_disk(
|
||||
"Metadata corruption detected at %pS, quota %u",
|
||||
__this_address, dqp->q_id);
|
||||
xfs_alert(bp->b_mount, "Unmount and run xfs_repair");
|
||||
xfs_dquot_mark_sick(dqp);
|
||||
return -EFSCORRUPTED;
|
||||
}
|
||||
|
||||
@ -1238,6 +1265,8 @@ xfs_qm_dqflush(
|
||||
&bp, &xfs_dquot_buf_ops);
|
||||
if (error == -EAGAIN)
|
||||
goto out_unlock;
|
||||
if (xfs_metadata_is_sick(error))
|
||||
xfs_dquot_mark_sick(dqp);
|
||||
if (error)
|
||||
goto out_abort;
|
||||
|
||||
@ -1246,6 +1275,7 @@ xfs_qm_dqflush(
|
||||
xfs_alert(mp, "corrupt dquot ID 0x%x in memory at %pS",
|
||||
dqp->q_id, fa);
|
||||
xfs_buf_relse(bp);
|
||||
xfs_dquot_mark_sick(dqp);
|
||||
error = -EFSCORRUPTED;
|
||||
goto out_abort;
|
||||
}
|
||||
|
@ -17,6 +17,7 @@
|
||||
#include "xfs_btree.h"
|
||||
#include "xfs_da_format.h"
|
||||
#include "xfs_da_btree.h"
|
||||
#include "xfs_quota_defs.h"
|
||||
|
||||
/*
|
||||
* Warn about metadata corruption that we detected but haven't fixed, and
|
||||
|
@ -763,14 +763,18 @@ xfs_qm_qino_alloc(
|
||||
(mp->m_sb.sb_gquotino != NULLFSINO)) {
|
||||
ino = mp->m_sb.sb_gquotino;
|
||||
if (XFS_IS_CORRUPT(mp,
|
||||
mp->m_sb.sb_pquotino != NULLFSINO))
|
||||
mp->m_sb.sb_pquotino != NULLFSINO)) {
|
||||
xfs_fs_mark_sick(mp, XFS_SICK_FS_PQUOTA);
|
||||
return -EFSCORRUPTED;
|
||||
}
|
||||
} else if ((flags & XFS_QMOPT_GQUOTA) &&
|
||||
(mp->m_sb.sb_pquotino != NULLFSINO)) {
|
||||
ino = mp->m_sb.sb_pquotino;
|
||||
if (XFS_IS_CORRUPT(mp,
|
||||
mp->m_sb.sb_gquotino != NULLFSINO))
|
||||
mp->m_sb.sb_gquotino != NULLFSINO)) {
|
||||
xfs_fs_mark_sick(mp, XFS_SICK_FS_GQUOTA);
|
||||
return -EFSCORRUPTED;
|
||||
}
|
||||
}
|
||||
if (ino != NULLFSINO) {
|
||||
error = xfs_iget(mp, NULL, ino, 0, 0, ipp);
|
||||
|
Loading…
Reference in New Issue
Block a user