diff options
| author | Joanne Koong <joannelkoong@gmail.com> | 2025-08-29 16:56:27 -0700 |
|---|---|---|
| committer | Miklos Szeredi <mszeredi@redhat.com> | 2025-09-02 11:14:15 +0200 |
| commit | 02d47e213dce6e2fa197d0cff66e92f1bc55f00f (patch) | |
| tree | e702fc40c7b6ddb525f1484e4efc4ef0a74ebbb7 | |
| parent | b3c7ab1d2593213c2d3339830b3950a689e83867 (diff) | |
fuse: remove fuse_readpages_end() null mapping check
Remove extra logic in fuse_readpages_end() that checks against null
folio mappings. This was added in commit ce534fb05292 ("fuse: allow
splice to move pages"):
"Since the remove_from_page_cache() + add_to_page_cache_locked()
are non-atomic it is possible that the page cache is repopulated in
between the two and add_to_page_cache_locked() will fail. This
could be fixed by creating a new atomic replace_page_cache_page()
function.
fuse_readpages_end() needed to be reworked so it works even if
page->mapping is NULL for some or all pages which can happen if the
add_to_page_cache_locked() failed."
Commit ef6a3c63112e ("mm: add replace_page_cache_page() function") added
atomic page cache replacement, which means the check against null
mappings can be removed.
Signed-off-by: Joanne Koong <joannelkoong@gmail.com>
Signed-off-by: Miklos Szeredi <mszeredi@redhat.com>
| -rw-r--r-- | fs/fuse/file.c | 24 |
1 files changed, 11 insertions, 13 deletions
diff --git a/fs/fuse/file.c b/fs/fuse/file.c index 0698bcb2f992..54786f62a9d8 100644 --- a/fs/fuse/file.c +++ b/fs/fuse/file.c @@ -865,22 +865,20 @@ static void fuse_readpages_end(struct fuse_mount *fm, struct fuse_args *args, struct fuse_args_pages *ap = &ia->ap; size_t count = ia->read.in.size; size_t num_read = args->out_args[0].size; - struct address_space *mapping = NULL; - - for (i = 0; mapping == NULL && i < ap->num_folios; i++) - mapping = ap->folios[i]->mapping; + struct address_space *mapping; + struct inode *inode; - if (mapping) { - struct inode *inode = mapping->host; + WARN_ON_ONCE(!ap->num_folios); + mapping = ap->folios[0]->mapping; + inode = mapping->host; - /* - * Short read means EOF. If file size is larger, truncate it - */ - if (!err && num_read < count) - fuse_short_read(inode, ia->read.attr_ver, num_read, ap); + /* + * Short read means EOF. If file size is larger, truncate it + */ + if (!err && num_read < count) + fuse_short_read(inode, ia->read.attr_ver, num_read, ap); - fuse_invalidate_atime(inode); - } + fuse_invalidate_atime(inode); for (i = 0; i < ap->num_folios; i++) { folio_end_read(ap->folios[i], !err); |
