diff options
author | Dave Chinner <dchinner@redhat.com> | 2021-08-18 18:46:52 -0700 |
---|---|---|
committer | Darrick J. Wong <djwong@kernel.org> | 2021-08-19 10:07:13 -0700 |
commit | 2e973b2cd4cdb993be94cca4c33f532f1ed05316 (patch) | |
tree | b44d08a1f5af0ef6be12f8b178975de8ac5bef92 /fs/xfs/xfs_log.c | |
parent | 0560f31a09e523090d1ab2bfe21c69d028c2bdf2 (diff) |
xfs: convert remaining mount flags to state flags
The remaining mount flags kept in m_flags are actually runtime state
flags. These change dynamically, so they really should be updated
atomically so we don't potentially lose an update due to racing
modifications.
Convert these remaining flags to be stored in m_opstate and use
atomic bitops to set and clear the flags. This also adds a couple of
simple wrappers for common state checks - read only and shutdown.
Signed-off-by: Dave Chinner <dchinner@redhat.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Diffstat (limited to 'fs/xfs/xfs_log.c')
-rw-r--r-- | fs/xfs/xfs_log.c | 31 |
1 files changed, 17 insertions, 14 deletions
diff --git a/fs/xfs/xfs_log.c b/fs/xfs/xfs_log.c index f7c1fe964a0f..f6cd2d4aa770 100644 --- a/fs/xfs/xfs_log.c +++ b/fs/xfs/xfs_log.c @@ -640,7 +640,7 @@ xfs_log_mount( xfs_notice(mp, "Mounting V%d filesystem in no-recovery mode. Filesystem will be inconsistent.", XFS_SB_VERSION_NUM(&mp->m_sb)); - ASSERT(mp->m_flags & XFS_MOUNT_RDONLY); + ASSERT(xfs_is_readonly(mp)); } log = xlog_alloc_log(mp, log_target, blk_offset, num_bblks); @@ -720,15 +720,15 @@ xfs_log_mount( * just worked. */ if (!xfs_has_norecovery(mp)) { - bool readonly = (mp->m_flags & XFS_MOUNT_RDONLY); - - if (readonly) - mp->m_flags &= ~XFS_MOUNT_RDONLY; - + /* + * log recovery ignores readonly state and so we need to clear + * mount-based read only state so it can write to disk. + */ + bool readonly = test_and_clear_bit(XFS_OPSTATE_READONLY, + &mp->m_opstate); error = xlog_recover(log); - if (readonly) - mp->m_flags |= XFS_MOUNT_RDONLY; + set_bit(XFS_OPSTATE_READONLY, &mp->m_opstate); if (error) { xfs_warn(mp, "log mount/recovery failed: error %d", error); @@ -777,18 +777,21 @@ xfs_log_mount_finish( struct xfs_mount *mp) { struct xlog *log = mp->m_log; - bool readonly = (mp->m_flags & XFS_MOUNT_RDONLY); + bool readonly; int error = 0; if (xfs_has_norecovery(mp)) { - ASSERT(readonly); + ASSERT(xfs_is_readonly(mp)); return 0; - } else if (readonly) { - /* Allow unlinked processing to proceed */ - mp->m_flags &= ~XFS_MOUNT_RDONLY; } /* + * log recovery ignores readonly state and so we need to clear + * mount-based read only state so it can write to disk. + */ + readonly = test_and_clear_bit(XFS_OPSTATE_READONLY, &mp->m_opstate); + + /* * During the second phase of log recovery, we need iget and * iput to behave like they do for an active filesystem. * xfs_fs_drop_inode needs to be able to prevent the deletion @@ -839,7 +842,7 @@ xfs_log_mount_finish( clear_bit(XLOG_RECOVERY_NEEDED, &log->l_opstate); if (readonly) - mp->m_flags |= XFS_MOUNT_RDONLY; + set_bit(XFS_OPSTATE_READONLY, &mp->m_opstate); /* Make sure the log is dead if we're returning failure. */ ASSERT(!error || xlog_is_shutdown(log)); |