[PATCH v2 11/12] fuse: support large folios for writeback

Joanne Koong
2024-11-25T22:06:11Z

Add support for folios larger than one page size for writeback.

Signed-off-by: Joanne Koong <joannelkoong@gmail.com>
Reviewed-by: Josef Bacik <josef@toxicpanda.com>
---
fs/fuse/file.c | 12 ++++++++----
1 file changed, 8 insertions(+), 4 deletions(-)

diff --git a/fs/fuse/file.c b/fs/fuse/file.c
index a907848f387a..487e68b59e1a 100644
--- a/fs/fuse/file.c
+++ b/fs/fuse/file.c
@@ -1991,7 +1991,7 @@ static void fuse_writepage_args_page_fill(struct fuse_writepage_args *wpa, struc
folio_get(folio);
ap->folios[folio_index] = folio;
ap->descs[folio_index].offset = 0;
- ap->descs[folio_index].length = PAGE_SIZE;
+ ap->descs[folio_index].length = folio_size(folio);

inc_wb_stat(&inode_to_bdi(inode)->wb, WB_WRITEBACK);
node_stat_add_folio(folio, NR_WRITEBACK);
@@ -2066,6 +2066,7 @@ struct fuse_fill_wb_data {
struct fuse_file *ff;
struct inode *inode;
unsigned int max_folios;
+ unsigned int nr_pages;
};

static bool fuse_pages_realloc(struct fuse_fill_wb_data *data)
@@ -2113,15 +2114,15 @@ static bool fuse_writepage_need_send(struct fuse_conn *fc, struct folio *folio,
WARN_ON(!ap->num_folios);

/* Reached max pages */
- if (ap->num_folios == fc->max_pages)
+ if (data->nr_pages + folio_nr_pages(folio) > fc->max_pages)
return true;

/* Reached max write bytes */
- if ((ap->num_folios + 1) * PAGE_SIZE > fc->max_write)
+ if ((data->nr_pages * PAGE_SIZE) + folio_size(folio) > fc->max_write)
return true;

/* Discontinuity */
- if (ap->folios[ap->num_folios - 1]->index + 1 != folio_index(folio))
+ if (folio_next_index(ap->folios[ap->num_folios - 1]) != folio_index(folio))
return true;

/* Need to grow the pages array? If so, did the expansion fail? */
@@ -2152,6 +2153,7 @@ static int fuse_writepages_fill(struct folio *folio,
if (wpa && fuse_writepage_need_send(fc, folio, ap, data)) {
fuse_writepages_send(data);
data->wpa = NULL;
+ data->nr_pages = 0;
}

if (data->wpa == NULL) {
@@ -2166,6 +2168,7 @@ static int fuse_writepages_fill(struct folio *folio,
folio_start_writeback(folio);

fuse_writepage_args_page_fill(wpa, folio, ap->num_folios);
+ data->nr_pages += folio_nr_pages(folio);

err = 0;
ap->num_folios++;
@@ -2196,6 +2199,7 @@ static int fuse_writepages(struct address_space *mapping,
data.inode = inode;
data.wpa = NULL;
data.ff = NULL;
+ data.nr_pages = 0;

err = write_cache_pages(mapping, wbc, fuse_writepages_fill, &data);
if (data.wpa) {
--
2.43.5