linux-stable/fs/crypto
Eric Biggers 2b4eae95c7 fscrypt: don't evict dirty inodes after removing key
After FS_IOC_REMOVE_ENCRYPTION_KEY removes a key, it syncs the
filesystem and tries to get and put all inodes that were unlocked by the
key so that unused inodes get evicted via fscrypt_drop_inode().
Normally, the inodes are all clean due to the sync.

However, after the filesystem is sync'ed, userspace can modify and close
one of the files.  (Userspace is *supposed* to close the files before
removing the key.  But it doesn't always happen, and the kernel can't
assume it.)  This causes the inode to be dirtied and have i_count == 0.
Then, fscrypt_drop_inode() failed to consider this case and indicated
that the inode can be dropped, causing the write to be lost.

On f2fs, other problems such as a filesystem freeze could occur due to
the inode being freed while still on f2fs's dirty inode list.

Fix this bug by making fscrypt_drop_inode() only drop clean inodes.

I've written an xfstest which detects this bug on ext4, f2fs, and ubifs.

Fixes: b1c0ec3599 ("fscrypt: add FS_IOC_REMOVE_ENCRYPTION_KEY ioctl")
Cc: <stable@vger.kernel.org> # v5.4+
Link: https://lore.kernel.org/r/20200305084138.653498-1-ebiggers@kernel.org
Signed-off-by: Eric Biggers <ebiggers@google.com>
2020-03-07 18:43:07 -08:00
..
Kconfig fscrypt: improve format of no-key names 2020-01-22 14:50:03 -08:00
Makefile fscrypt: add an HKDF-SHA512 implementation 2019-08-12 19:18:50 -07:00
bio.c fscrypt: optimize fscrypt_zeroout_range() 2020-01-14 12:50:33 -08:00
crypto.c fscrypt: document gfp_flags for bounce page allocation 2020-01-14 12:51:12 -08:00
fname.c fscrypt: improve format of no-key names 2020-01-22 14:50:03 -08:00
fscrypt_private.h fscrypt: clarify what is meant by a per-file key 2020-01-22 14:49:56 -08:00
hkdf.c fscrypt: constify struct fscrypt_hkdf parameter to fscrypt_hkdf_expand() 2019-12-31 10:33:50 -06:00
hooks.c fscrypt: derive dirhash key for casefolded directories 2020-01-22 14:49:55 -08:00
keyring.c fscrypt: don't print name of busy file when removing key 2020-01-22 14:45:08 -08:00
keysetup.c fscrypt: don't evict dirty inodes after removing key 2020-03-07 18:43:07 -08:00
keysetup_v1.c fscrypt: clarify what is meant by a per-file key 2020-01-22 14:49:56 -08:00
policy.c fscrypt: don't allow v1 policies with casefolding 2020-01-22 14:47:15 -08:00