summaryrefslogtreecommitdiff
path: root/scripts/Makefile.thinlto
diff options
context:
space:
mode:
authorHongling Zeng <zenghongling@kylinos.cn>2026-09-15 16:32:48 +0800
committerNamjae Jeon <linkinjeon@kernel.org>2026-10-20 18:41:44 +0900
commit521978c4f4441953d67297286e5804485ae05698 (patch)
treea1493b6a993f6399b36108b6a73c4106723ebccd /scripts/Makefile.thinlto
parent55af94ca0ee3512c08d12ffbbb948229da4e1565 (diff)
downloadlinux-521978c4f4441953d67297286e5804485ae05698.tar.gz
linux-521978c4f4441953d67297286e5804485ae05698.zip
ntfs: sync the volume dirty bit with the recorded error state
The runtime metadata-corruption paths in fs/ntfs only record the in-memory NVolErrors() flag; whether VOLUME_IS_DIRTY ever reaches disk depends on ntfs_set_volume_flags() being called by some other path, which for most error sites never happens. A volume can therefore unmount with a clean on-disk flag despite recorded corruption, and chkdsk will not run on the next mount. Persisting the dirty bit from the error paths themselves does not work: they run under a wide variety of ntfs locks, and the dirty-bit write takes the $Volume mrec_lock and maps the $Volume mft record, which on an $MFT page-cache miss takes the $MFT runlist lock for writing. That is enough to self-deadlock or form ABBA cycles from several of them: the $MFT extend undo paths hold the $MFT runlist lock and then take vol->lcnbmp_lock inside ntfs_cluster_free(); the cluster allocation and free rollback paths hold vol->lcnbmp_lock; and the whole mft record allocation tree is reachable from ntfs_write_volume_label()'s attribute-list maintenance while it holds the $Volume mrec_lock itself. Instead, make the persistence a property of the sync paths, which run without ntfs locks held. The new ntfs_sync_volume_dirty_state() sets VOLUME_IS_DIRTY when NVolErrors() is recorded and clears it otherwise, evaluating the error flag under the $Volume mrec_lock. It is called from ntfs_sync_fs(), from the remount-to-read-only path of ntfs_reconfigure(), and from ntfs_put_super(), which previously evaluated NVolErrors() outside the lock before clearing the dirty bit unconditionally, and which now also persists the dirty bit for volumes with recorded errors so they unmount with chkdsk scheduled. The ntfs_clear_volume_flags() wrapper, whose last callers this patch replaces, has no users left and is removed. The guarantee this provides is eventual, not instantaneous: the error paths record NVolErrors() with a lock-free set_bit(), so a persistence point that evaluates the flag just before an error is recorded can still leave the on-disk bit clean until the next one. This is sound because NVolErrors() is sticky for the lifetime of the mount and every persistence point re-derives the on-disk bit from it; the last one, ntfs_put_super(), runs after evict_inodes() on a quiesced filesystem, so a volume that is read-write at unmount time cannot unmount clean. A volume that is already read-only when the error is recorded (errors=remount-ro flips the superblock on the first error, as does an earlier remount-ro) has no persistence point left and keeps whatever on-disk bit it had; that behaviour is unchanged. The residual window is a crash between the error and the next persistence point. The persistence paths never write a hibernated volume: resuming Windows from a modified image corrupts it. Record the mount-time hibernation verdict in the new NV_Hibernated volume flag and make ntfs_sync_volume_dirty_state() a no-op while it is set, so the dirty bit is left exactly as it is on disk and only the in-memory error state is kept. Without this, an rw mount of a hibernated volume with the default errors=continue would gain a filesystem-internal write on the first sync, remount or unmount. Other writes to such a mount, like the mount-time logfile emptying, are pre-existing and unchanged. Cc: stable@vger.kernel.org Signed-off-by: Hongling Zeng <zenghongling@kylinos.cn> Reviewed-by: Hyunchul Lee <hyc.lee@gmail.com> Reviewed-by: Baolin Liu <liubaolin@kylinos.cn> Signed-off-by: Namjae Jeon <linkinjeon@kernel.org>
Diffstat (limited to 'scripts/Makefile.thinlto')
0 files changed, 0 insertions, 0 deletions