\n
-----BEGIN PGP SIGNATURE----- iQEzBAABCAAdFiEEq1nRK9aeMoq1VSgcnJ2qBz9kQNkFAmEmTZcACgkQnJ2qBz9k QNkkmAgArW6XoF1CePds/ZaC9vfg/nk66/zVo0n+J8xXjMWAPxcKbWFfV0uWVixq yk4lcLV47a2Mu/B/1oLNd3vrSmhwU+srWqNwOFn1nv+lP/6wJqr8oztRHn/0L9Q3 ZSRrukSejbQ6AvTL/WzTNnCjjCc2ne3Kyko6W41aU6uyJuzhSM32wbx7qlV6t54Z iint9OrB4gM0avLohNafTUq6I+tEGzBMNwpCG/tqCmkcvDcv3rTDVAnPSCTm0Tx2 hdrYDcY/rLxo93pDBaW1rYA/fohR+mIVye6k2TjkPAL6T1x+rxeT5qnc+YijH5yF sFPDhlD+ZsfOLi8stWXLOJ+8+gLODg== =pDBR -----END PGP SIGNATURE----- Merge tag 'hole_punch_for_v5.15-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/jack/linux-fs Pull fs hole punching vs cache filling race fixes from Jan Kara: "Fix races leading to possible data corruption or stale data exposure in multiple filesystems when hole punching races with operations such as readahead. This is the series I was sending for the last merge window but with your objection fixed - now filemap_fault() has been modified to take invalidate_lock only when we need to create new page in the page cache and / or bring it uptodate" * tag 'hole_punch_for_v5.15-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/jack/linux-fs: filesystems/locking: fix Malformed table warning cifs: Fix race between hole punch and page fault ceph: Fix race between hole punch and page fault fuse: Convert to using invalidate_lock f2fs: Convert to using invalidate_lock zonefs: Convert to using invalidate_lock xfs: Convert double locking of MMAPLOCK to use VFS helpers xfs: Convert to use invalidate_lock xfs: Refactor xfs_isilocked() ext2: Convert to using invalidate_lock ext4: Convert to use mapping->invalidate_lock mm: Add functions to lock invalidate_lock for two mappings mm: Protect operations adding pages to page cache with invalidate_lock documentation: Sync file_operations members with reality mm: Fix comments mentioning i_mutex
This commit is contained in:
commit
aa99f3c2b9
40 changed files with 483 additions and 361 deletions
|
|
@ -436,6 +436,10 @@ int pagecache_write_end(struct file *, struct address_space *mapping,
|
|||
* struct address_space - Contents of a cacheable, mappable object.
|
||||
* @host: Owner, either the inode or the block_device.
|
||||
* @i_pages: Cached pages.
|
||||
* @invalidate_lock: Guards coherency between page cache contents and
|
||||
* file offset->disk block mappings in the filesystem during invalidates.
|
||||
* It is also used to block modification of page cache contents through
|
||||
* memory mappings.
|
||||
* @gfp_mask: Memory allocation flags to use for allocating pages.
|
||||
* @i_mmap_writable: Number of VM_SHARED mappings.
|
||||
* @nr_thps: Number of THPs in the pagecache (non-shmem only).
|
||||
|
|
@ -453,6 +457,7 @@ int pagecache_write_end(struct file *, struct address_space *mapping,
|
|||
struct address_space {
|
||||
struct inode *host;
|
||||
struct xarray i_pages;
|
||||
struct rw_semaphore invalidate_lock;
|
||||
gfp_t gfp_mask;
|
||||
atomic_t i_mmap_writable;
|
||||
#ifdef CONFIG_READ_ONLY_THP_FOR_FS
|
||||
|
|
@ -814,9 +819,42 @@ static inline void inode_lock_shared_nested(struct inode *inode, unsigned subcla
|
|||
down_read_nested(&inode->i_rwsem, subclass);
|
||||
}
|
||||
|
||||
static inline void filemap_invalidate_lock(struct address_space *mapping)
|
||||
{
|
||||
down_write(&mapping->invalidate_lock);
|
||||
}
|
||||
|
||||
static inline void filemap_invalidate_unlock(struct address_space *mapping)
|
||||
{
|
||||
up_write(&mapping->invalidate_lock);
|
||||
}
|
||||
|
||||
static inline void filemap_invalidate_lock_shared(struct address_space *mapping)
|
||||
{
|
||||
down_read(&mapping->invalidate_lock);
|
||||
}
|
||||
|
||||
static inline int filemap_invalidate_trylock_shared(
|
||||
struct address_space *mapping)
|
||||
{
|
||||
return down_read_trylock(&mapping->invalidate_lock);
|
||||
}
|
||||
|
||||
static inline void filemap_invalidate_unlock_shared(
|
||||
struct address_space *mapping)
|
||||
{
|
||||
up_read(&mapping->invalidate_lock);
|
||||
}
|
||||
|
||||
void lock_two_nondirectories(struct inode *, struct inode*);
|
||||
void unlock_two_nondirectories(struct inode *, struct inode*);
|
||||
|
||||
void filemap_invalidate_lock_two(struct address_space *mapping1,
|
||||
struct address_space *mapping2);
|
||||
void filemap_invalidate_unlock_two(struct address_space *mapping1,
|
||||
struct address_space *mapping2);
|
||||
|
||||
|
||||
/*
|
||||
* NOTE: in a 32bit arch with a preemptable kernel and
|
||||
* an UP compile the i_size_read/write must be atomic
|
||||
|
|
@ -2490,6 +2528,7 @@ struct file_system_type {
|
|||
|
||||
struct lock_class_key i_lock_key;
|
||||
struct lock_class_key i_mutex_key;
|
||||
struct lock_class_key invalidate_lock_key;
|
||||
struct lock_class_key i_mutex_dir_key;
|
||||
};
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue