Executing xfs/057 can lead to an unmount task to wait indefinitely for XFS_IFLUSHING flag on some inodes to be cleared. The following timeline describes as to how inodes can get into such a state. Task A Task B Iclog endio processing ---------------------------------------------------------------------------- Inodes are freed Inodes items are added to the CIL CIL contents are written to iclog iclog->ic_fail_crc is set to true iclog is submitted for writing to the disk Last inode in the cluster buffer is freed XFS_[ISTALE/IFLUSHING] is set on all inodes in the cluster buffer XFS_STALE is set on the cluster buffer iclog crc error is detected ... during endio processing During xfs_trans_commit, Set XFS_LI_ABORTED on inode log shutdown is detected items XFS_LI_ABORTED is set xfs_inode_item_committed() on xfs_buf_log_item - Unpin the inode since it is stale and return -1 xfs_buf_log_item is freed Inode log items are not xfs_buf is not freed here processed further since since b_hold has a xfs_inode_item_committed() non-zero value returns -1 During normal operation, the stale inodes are processed by xfs_buf_item_unpin() => xfs_buf_inode_iodone(). This ends up calling xfs_iflush_abort() which in turn clears the XFS_IFLUSHING flag. However, in the case of this bug, the xfs_buf_log_item is freed just before the high level transaction is committed to the CIL. To overcome this bug, this commit removes the check for log shutdown during high level transaction commit operation. The log items in the high level transaction will now be committed to the CIL despite the log being shutdown. This will allow the CIL processing logic (i.e. xlog_cil_push_work()) to invoke xlog_cil_committed() as part of error handling. This will cause xfs_buf log item to to be unpinned and the corresponding inodes to be aborted and have their XFS_IFLUSHING flag cleared. Signed-off-by: Chandan Babu R <chandanbabu@xxxxxxxxxx> --- PS: I have tested this patch by executing xfs/057 in a loop for about 24 hours. On a non-patched kernel, this issue gets recreated within 24 hours. fs/xfs/xfs_trans.c | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/fs/xfs/xfs_trans.c b/fs/xfs/xfs_trans.c index bdf3704dc301..b43436c8abaa 100644 --- a/fs/xfs/xfs_trans.c +++ b/fs/xfs/xfs_trans.c @@ -868,17 +868,6 @@ __xfs_trans_commit( if (!(tp->t_flags & XFS_TRANS_DIRTY)) goto out_unreserve; - /* - * We must check against log shutdown here because we cannot abort log - * items and leave them dirty, inconsistent and unpinned in memory while - * the log is active. This leaves them open to being written back to - * disk, and that will lead to on-disk corruption. - */ - if (xlog_is_shutdown(log)) { - error = -EIO; - goto out_unreserve; - } - ASSERT(tp->t_ticket != NULL); /* -- 2.43.0