From 807a11dab9dc42dc999ece92d1277b3da37ecfab Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:11 +0100 Subject: ecryptfs: Convert ecryptfs_writepage() to ecryptfs_writepages() By adding a ->migrate_folio implementation, theree is no need to keep the ->writepage implementation. The new writepages removes the unnecessary call to SetPageUptodate(); the folio should already be uptodate at this point. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-2-willy@infradead.org Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 41 ++++++++++++++++++++--------------------- 1 file changed, 20 insertions(+), 21 deletions(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index ceda5555971a..92ea39d907de 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -38,32 +38,30 @@ struct page *ecryptfs_get_locked_page(struct inode *inode, loff_t index) return page; } -/** - * ecryptfs_writepage - * @page: Page that is locked before this call is made - * @wbc: Write-back control structure - * - * Returns zero on success; non-zero otherwise - * +/* * This is where we encrypt the data and pass the encrypted data to * the lower filesystem. In OpenPGP-compatible mode, we operate on * entire underlying packets. */ -static int ecryptfs_writepage(struct page *page, struct writeback_control *wbc) +static int ecryptfs_writepages(struct address_space *mapping, + struct writeback_control *wbc) { - int rc; - - rc = ecryptfs_encrypt_page(page); - if (rc) { - ecryptfs_printk(KERN_WARNING, "Error encrypting " - "page (upper index [0x%.16lx])\n", page->index); - ClearPageUptodate(page); - goto out; + struct folio *folio = NULL; + int error; + + while ((folio = writeback_iter(mapping, wbc, folio, &error))) { + error = ecryptfs_encrypt_page(&folio->page); + if (error) { + ecryptfs_printk(KERN_WARNING, + "Error encrypting folio (index [0x%.16lx])\n", + folio->index); + folio_clear_uptodate(folio); + mapping_set_error(mapping, error); + } + folio_unlock(folio); } - SetPageUptodate(page); -out: - unlock_page(page); - return rc; + + return error; } static void strip_xattr_flag(char *page_virt, @@ -548,9 +546,10 @@ const struct address_space_operations ecryptfs_aops = { .dirty_folio = block_dirty_folio, .invalidate_folio = block_invalidate_folio, #endif - .writepage = ecryptfs_writepage, + .writepages = ecryptfs_writepages, .read_folio = ecryptfs_read_folio, .write_begin = ecryptfs_write_begin, .write_end = ecryptfs_write_end, + .migrate_folio = filemap_migrate_folio, .bmap = ecryptfs_bmap, }; -- cgit From 064fe6b4752c41cc4d00d1532f65ef98acd107a2 Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:12 +0100 Subject: ecryptfs: Use a folio throughout ecryptfs_read_folio() Remove the conversion to a struct page. Removes a few hidden calls to compound_head(). Use 'err' instead of 'rc' for clarity. Also remove the unnecessary call to ClearPageUptodate(); the uptodate flag is already clear if this function is being called. That lets us switch to folio_end_read() which does one atomic flag operation instead of two. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-3-willy@infradead.org Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 50 +++++++++++++++++++++++--------------------------- 1 file changed, 23 insertions(+), 27 deletions(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index 92ea39d907de..25a756fec5c2 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -178,55 +178,51 @@ out: */ static int ecryptfs_read_folio(struct file *file, struct folio *folio) { - struct page *page = &folio->page; + struct inode *inode = folio->mapping->host; struct ecryptfs_crypt_stat *crypt_stat = - &ecryptfs_inode_to_private(page->mapping->host)->crypt_stat; - int rc = 0; + &ecryptfs_inode_to_private(inode)->crypt_stat; + int err = 0; if (!crypt_stat || !(crypt_stat->flags & ECRYPTFS_ENCRYPTED)) { - rc = ecryptfs_read_lower_page_segment(page, page->index, 0, - PAGE_SIZE, - page->mapping->host); + err = ecryptfs_read_lower_page_segment(&folio->page, folio->index, 0, + folio_size(folio), + inode); } else if (crypt_stat->flags & ECRYPTFS_VIEW_AS_ENCRYPTED) { if (crypt_stat->flags & ECRYPTFS_METADATA_IN_XATTR) { - rc = ecryptfs_copy_up_encrypted_with_header(page, + err = ecryptfs_copy_up_encrypted_with_header(&folio->page, crypt_stat); - if (rc) { + if (err) { printk(KERN_ERR "%s: Error attempting to copy " "the encrypted content from the lower " "file whilst inserting the metadata " - "from the xattr into the header; rc = " - "[%d]\n", __func__, rc); + "from the xattr into the header; err = " + "[%d]\n", __func__, err); goto out; } } else { - rc = ecryptfs_read_lower_page_segment( - page, page->index, 0, PAGE_SIZE, - page->mapping->host); - if (rc) { - printk(KERN_ERR "Error reading page; rc = " - "[%d]\n", rc); + err = ecryptfs_read_lower_page_segment(&folio->page, + folio->index, 0, folio_size(folio), + inode); + if (err) { + printk(KERN_ERR "Error reading page; err = " + "[%d]\n", err); goto out; } } } else { - rc = ecryptfs_decrypt_page(page); - if (rc) { + err = ecryptfs_decrypt_page(&folio->page); + if (err) { ecryptfs_printk(KERN_ERR, "Error decrypting page; " - "rc = [%d]\n", rc); + "err = [%d]\n", err); goto out; } } out: - if (rc) - ClearPageUptodate(page); - else - SetPageUptodate(page); - ecryptfs_printk(KERN_DEBUG, "Unlocking page with index = [0x%.16lx]\n", - page->index); - unlock_page(page); - return rc; + ecryptfs_printk(KERN_DEBUG, "Unlocking folio with index = [0x%.16lx]\n", + folio->index); + folio_end_read(folio, err == 0); + return err; } /* -- cgit From 497eb79c3191f30467787f81958e75be16c4eb53 Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:13 +0100 Subject: ecryptfs: Convert ecryptfs_copy_up_encrypted_with_header() to take a folio Both callers have a folio, so pass it in and use it throughout. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-4-willy@infradead.org Reviewed-by: Pankaj Raghav Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index 25a756fec5c2..bd78a36ed479 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -95,7 +95,7 @@ static void strip_xattr_flag(char *page_virt, /** * ecryptfs_copy_up_encrypted_with_header - * @page: Sort of a ``virtual'' representation of the encrypted lower + * @folio: Sort of a ``virtual'' representation of the encrypted lower * file. The actual lower file does not have the metadata in * the header. This is locked. * @crypt_stat: The eCryptfs inode's cryptographic context @@ -104,7 +104,7 @@ static void strip_xattr_flag(char *page_virt, * seeing, with the header information inserted. */ static int -ecryptfs_copy_up_encrypted_with_header(struct page *page, +ecryptfs_copy_up_encrypted_with_header(struct folio *folio, struct ecryptfs_crypt_stat *crypt_stat) { loff_t extent_num_in_page = 0; @@ -113,9 +113,9 @@ ecryptfs_copy_up_encrypted_with_header(struct page *page, int rc = 0; while (extent_num_in_page < num_extents_per_page) { - loff_t view_extent_num = ((((loff_t)page->index) + loff_t view_extent_num = ((loff_t)folio->index * num_extents_per_page) - + extent_num_in_page); + + extent_num_in_page; size_t num_header_extents_at_front = (crypt_stat->metadata_size / crypt_stat->extent_size); @@ -123,21 +123,21 @@ ecryptfs_copy_up_encrypted_with_header(struct page *page, /* This is a header extent */ char *page_virt; - page_virt = kmap_local_page(page); + page_virt = kmap_local_folio(folio, 0); memset(page_virt, 0, PAGE_SIZE); /* TODO: Support more than one header extent */ if (view_extent_num == 0) { size_t written; rc = ecryptfs_read_xattr_region( - page_virt, page->mapping->host); + page_virt, folio->mapping->host); strip_xattr_flag(page_virt + 16, crypt_stat); ecryptfs_write_header_metadata(page_virt + 20, crypt_stat, &written); } kunmap_local(page_virt); - flush_dcache_page(page); + flush_dcache_folio(folio); if (rc) { printk(KERN_ERR "%s: Error reading xattr " "region; rc = [%d]\n", __func__, rc); @@ -150,9 +150,9 @@ ecryptfs_copy_up_encrypted_with_header(struct page *page, - crypt_stat->metadata_size); rc = ecryptfs_read_lower_page_segment( - page, (lower_offset >> PAGE_SHIFT), + &folio->page, (lower_offset >> PAGE_SHIFT), (lower_offset & ~PAGE_MASK), - crypt_stat->extent_size, page->mapping->host); + crypt_stat->extent_size, folio->mapping->host); if (rc) { printk(KERN_ERR "%s: Error attempting to read " "extent at offset [%lld] in the lower " @@ -189,8 +189,8 @@ static int ecryptfs_read_folio(struct file *file, struct folio *folio) inode); } else if (crypt_stat->flags & ECRYPTFS_VIEW_AS_ENCRYPTED) { if (crypt_stat->flags & ECRYPTFS_METADATA_IN_XATTR) { - err = ecryptfs_copy_up_encrypted_with_header(&folio->page, - crypt_stat); + err = ecryptfs_copy_up_encrypted_with_header(folio, + crypt_stat); if (err) { printk(KERN_ERR "%s: Error attempting to copy " "the encrypted content from the lower " @@ -291,7 +291,7 @@ static int ecryptfs_write_begin(struct file *file, } else if (crypt_stat->flags & ECRYPTFS_VIEW_AS_ENCRYPTED) { if (crypt_stat->flags & ECRYPTFS_METADATA_IN_XATTR) { rc = ecryptfs_copy_up_encrypted_with_header( - &folio->page, crypt_stat); + folio, crypt_stat); if (rc) { printk(KERN_ERR "%s: Error attempting " "to copy the encrypted content " -- cgit From 890d477a0fcdfdd9e15b5d997cbbb05004045b13 Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:14 +0100 Subject: ecryptfs: Convert ecryptfs_read_lower_page_segment() to take a folio All callers have a folio, so pass it in and use it directly. This will not work for large folios, but I doubt anybody wants to use large folios with ecryptfs. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-5-willy@infradead.org Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index bd78a36ed479..1fc87c83e43c 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -150,7 +150,7 @@ ecryptfs_copy_up_encrypted_with_header(struct folio *folio, - crypt_stat->metadata_size); rc = ecryptfs_read_lower_page_segment( - &folio->page, (lower_offset >> PAGE_SHIFT), + folio, (lower_offset >> PAGE_SHIFT), (lower_offset & ~PAGE_MASK), crypt_stat->extent_size, folio->mapping->host); if (rc) { @@ -184,9 +184,8 @@ static int ecryptfs_read_folio(struct file *file, struct folio *folio) int err = 0; if (!crypt_stat || !(crypt_stat->flags & ECRYPTFS_ENCRYPTED)) { - err = ecryptfs_read_lower_page_segment(&folio->page, folio->index, 0, - folio_size(folio), - inode); + err = ecryptfs_read_lower_page_segment(folio, folio->index, 0, + folio_size(folio), inode); } else if (crypt_stat->flags & ECRYPTFS_VIEW_AS_ENCRYPTED) { if (crypt_stat->flags & ECRYPTFS_METADATA_IN_XATTR) { err = ecryptfs_copy_up_encrypted_with_header(folio, @@ -201,7 +200,7 @@ static int ecryptfs_read_folio(struct file *file, struct folio *folio) } } else { - err = ecryptfs_read_lower_page_segment(&folio->page, + err = ecryptfs_read_lower_page_segment(folio, folio->index, 0, folio_size(folio), inode); if (err) { @@ -279,7 +278,7 @@ static int ecryptfs_write_begin(struct file *file, if (!(crypt_stat->flags & ECRYPTFS_ENCRYPTED)) { rc = ecryptfs_read_lower_page_segment( - &folio->page, index, 0, PAGE_SIZE, mapping->host); + folio, index, 0, PAGE_SIZE, mapping->host); if (rc) { printk(KERN_ERR "%s: Error attempting to read " "lower page segment; rc = [%d]\n", @@ -305,7 +304,7 @@ static int ecryptfs_write_begin(struct file *file, folio_mark_uptodate(folio); } else { rc = ecryptfs_read_lower_page_segment( - &folio->page, index, 0, PAGE_SIZE, + folio, index, 0, PAGE_SIZE, mapping->host); if (rc) { printk(KERN_ERR "%s: Error reading " -- cgit From 4d3727fd065b2c36a69daa4790e1e8007f051e10 Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:15 +0100 Subject: ecryptfs: Convert ecryptfs_write() to use a folio Remove ecryptfs_get_locked_page() and call read_mapping_folio() directly. Use the folio throught this function. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-6-willy@infradead.org Reviewed-by: Pankaj Raghav Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 16 ---------------- 1 file changed, 16 deletions(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index 1fc87c83e43c..f6b9390e720a 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -22,22 +22,6 @@ #include #include "ecryptfs_kernel.h" -/* - * ecryptfs_get_locked_page - * - * Get one page from cache or lower f/s, return error otherwise. - * - * Returns locked and up-to-date page (if ok), with increased - * refcnt. - */ -struct page *ecryptfs_get_locked_page(struct inode *inode, loff_t index) -{ - struct page *page = read_mapping_page(inode->i_mapping, index, NULL); - if (!IS_ERR(page)) - lock_page(page); - return page; -} - /* * This is where we encrypt the data and pass the encrypted data to * the lower filesystem. In OpenPGP-compatible mode, we operate on -- cgit From de5ced2721f96002c7e6c108242d5ead293dcccc Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:16 +0100 Subject: ecryptfs: Convert ecryptfs_write_lower_page_segment() to take a folio Both callers now have a folio, so pass it in and use it throughout. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-7-willy@infradead.org Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index f6b9390e720a..1c1eb9437505 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -454,7 +454,7 @@ static int ecryptfs_write_end(struct file *file, "(page w/ index = [0x%.16lx], to = [%d])\n", index, to); if (!(crypt_stat->flags & ECRYPTFS_ENCRYPTED)) { rc = ecryptfs_write_lower_page_segment(ecryptfs_inode, - &folio->page, 0, to); + folio, 0, to); if (!rc) { rc = copied; fsstack_copy_inode_size(ecryptfs_inode, -- cgit From 6b9c0e8137434f2e22a109f68d4e0a66894a1e33 Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:17 +0100 Subject: ecryptfs: Convert ecryptfs_encrypt_page() to take a folio All three callers have a folio, so pass it in and use it throughout. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-8-willy@infradead.org Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index 1c1eb9437505..b2c22f49ef6f 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -34,7 +34,7 @@ static int ecryptfs_writepages(struct address_space *mapping, int error; while ((folio = writeback_iter(mapping, wbc, folio, &error))) { - error = ecryptfs_encrypt_page(&folio->page); + error = ecryptfs_encrypt_page(folio); if (error) { ecryptfs_printk(KERN_WARNING, "Error encrypting folio (index [0x%.16lx])\n", @@ -476,7 +476,7 @@ static int ecryptfs_write_end(struct file *file, "zeros in page with index = [0x%.16lx]\n", index); goto out; } - rc = ecryptfs_encrypt_page(&folio->page); + rc = ecryptfs_encrypt_page(folio); if (rc) { ecryptfs_printk(KERN_WARNING, "Error encrypting page (upper " "index [0x%.16lx])\n", index); -- cgit From c15b81461df9d08ff2b8f93b9d051c6f5d2b6483 Mon Sep 17 00:00:00 2001 From: "Matthew Wilcox (Oracle)" Date: Fri, 25 Oct 2024 20:08:18 +0100 Subject: ecryptfs: Convert ecryptfs_decrypt_page() to take a folio Both callers have a folio, so pass it in and use it throughout. Signed-off-by: Matthew Wilcox (Oracle) Link: https://lore.kernel.org/r/20241025190822.1319162-9-willy@infradead.org Signed-off-by: Christian Brauner --- fs/ecryptfs/mmap.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'fs/ecryptfs/mmap.c') diff --git a/fs/ecryptfs/mmap.c b/fs/ecryptfs/mmap.c index b2c22f49ef6f..60f0ac8744b5 100644 --- a/fs/ecryptfs/mmap.c +++ b/fs/ecryptfs/mmap.c @@ -194,7 +194,7 @@ static int ecryptfs_read_folio(struct file *file, struct folio *folio) } } } else { - err = ecryptfs_decrypt_page(&folio->page); + err = ecryptfs_decrypt_page(folio); if (err) { ecryptfs_printk(KERN_ERR, "Error decrypting page; " "err = [%d]\n", err); @@ -305,7 +305,7 @@ static int ecryptfs_write_begin(struct file *file, folio_zero_range(folio, 0, PAGE_SIZE); folio_mark_uptodate(folio); } else if (len < PAGE_SIZE) { - rc = ecryptfs_decrypt_page(&folio->page); + rc = ecryptfs_decrypt_page(folio); if (rc) { printk(KERN_ERR "%s: Error decrypting " "page at index [%ld]; " -- cgit