| From: "Matthew Wilcox (Oracle)" <willy@infradead.org> |
| Subject: readahead: convert readahead_expand() to use a folio |
| Date: Mon, 16 Jan 2023 19:39:41 +0000 |
| |
| Replace the uses of page with a folio. Also add a missing test for |
| workingset in the leading edge expansion. |
| |
| Link: https://lkml.kernel.org/r/20230116193941.2148487-4-willy@infradead.org |
| Signed-off-by: Matthew Wilcox (Oracle) <willy@infradead.org> |
| Reviewed-by: William Kucharski <william.kucharski@oracle.com> |
| Signed-off-by: Andrew Morton <akpm@linux-foundation.org> |
| --- |
| |
| |
| --- a/mm/readahead.c~readahead-convert-readahead_expand-to-use-a-folio |
| +++ a/mm/readahead.c |
| @@ -801,21 +801,25 @@ void readahead_expand(struct readahead_c |
| /* Expand the leading edge downwards */ |
| while (ractl->_index > new_index) { |
| unsigned long index = ractl->_index - 1; |
| - struct page *page = xa_load(&mapping->i_pages, index); |
| + struct folio *folio = xa_load(&mapping->i_pages, index); |
| |
| - if (page && !xa_is_value(page)) |
| - return; /* Page apparently present */ |
| + if (folio && !xa_is_value(folio)) |
| + return; /* Folio apparently present */ |
| |
| - page = __page_cache_alloc(gfp_mask); |
| - if (!page) |
| + folio = filemap_alloc_folio(gfp_mask, 0); |
| + if (!folio) |
| return; |
| - if (add_to_page_cache_lru(page, mapping, index, gfp_mask) < 0) { |
| - put_page(page); |
| + if (filemap_add_folio(mapping, folio, index, gfp_mask) < 0) { |
| + folio_put(folio); |
| return; |
| } |
| - |
| + if (unlikely(folio_test_workingset(folio)) && |
| + !ractl->_workingset) { |
| + ractl->_workingset = true; |
| + psi_memstall_enter(&ractl->_pflags); |
| + } |
| ractl->_nr_pages++; |
| - ractl->_index = page->index; |
| + ractl->_index = folio->index; |
| } |
| |
| new_len += new_start - readahead_pos(ractl); |
| @@ -824,19 +828,20 @@ void readahead_expand(struct readahead_c |
| /* Expand the trailing edge upwards */ |
| while (ractl->_nr_pages < new_nr_pages) { |
| unsigned long index = ractl->_index + ractl->_nr_pages; |
| - struct page *page = xa_load(&mapping->i_pages, index); |
| + struct folio *folio = xa_load(&mapping->i_pages, index); |
| |
| - if (page && !xa_is_value(page)) |
| - return; /* Page apparently present */ |
| + if (folio && !xa_is_value(folio)) |
| + return; /* Folio apparently present */ |
| |
| - page = __page_cache_alloc(gfp_mask); |
| - if (!page) |
| + folio = filemap_alloc_folio(gfp_mask, 0); |
| + if (!folio) |
| return; |
| - if (add_to_page_cache_lru(page, mapping, index, gfp_mask) < 0) { |
| - put_page(page); |
| + if (filemap_add_folio(mapping, folio, index, gfp_mask) < 0) { |
| + folio_put(folio); |
| return; |
| } |
| - if (unlikely(PageWorkingset(page)) && !ractl->_workingset) { |
| + if (unlikely(folio_test_workingset(folio)) && |
| + !ractl->_workingset) { |
| ractl->_workingset = true; |
| psi_memstall_enter(&ractl->_pflags); |
| } |
| _ |