Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'folio-5.17a' of git://git.infradead.org/users/willy/pagecache

Pull more folio updates from Matthew Wilcox:
"Three small folio patches.

One bug fix, one patch pulled forward from the patches destined for
5.18 and then a patch to make use of that functionality"

* tag 'folio-5.17a' of git://git.infradead.org/users/willy/pagecache:
filemap: Use folio_put_refs() in filemap_free_folio()
mm: Add folio_put_refs()
pagevec: Initialise folio_batch->percpu_pvec_drained

+25 -6
+20
include/linux/mm.h
··· 1199 1199 __put_page(&folio->page); 1200 1200 } 1201 1201 1202 + /** 1203 + * folio_put_refs - Reduce the reference count on a folio. 1204 + * @folio: The folio. 1205 + * @refs: The amount to subtract from the folio's reference count. 1206 + * 1207 + * If the folio's reference count reaches zero, the memory will be 1208 + * released back to the page allocator and may be used by another 1209 + * allocation immediately. Do not access the memory or the struct folio 1210 + * after calling folio_put_refs() unless you can be sure that these weren't 1211 + * the last references. 1212 + * 1213 + * Context: May be called in process or interrupt context, but not in NMI 1214 + * context. May be called while holding a spinlock. 1215 + */ 1216 + static inline void folio_put_refs(struct folio *folio, int refs) 1217 + { 1218 + if (folio_ref_sub_and_test(folio, refs)) 1219 + __put_page(&folio->page); 1220 + } 1221 + 1202 1222 static inline void put_page(struct page *page) 1203 1223 { 1204 1224 struct folio *folio = page_folio(page);
+1
include/linux/pagevec.h
··· 111 111 static inline void folio_batch_init(struct folio_batch *fbatch) 112 112 { 113 113 fbatch->nr = 0; 114 + fbatch->percpu_pvec_drained = false; 114 115 } 115 116 116 117 static inline unsigned int folio_batch_count(struct folio_batch *fbatch)
+4 -6
mm/filemap.c
··· 231 231 void filemap_free_folio(struct address_space *mapping, struct folio *folio) 232 232 { 233 233 void (*freepage)(struct page *); 234 + int refs = 1; 234 235 235 236 freepage = mapping->a_ops->freepage; 236 237 if (freepage) 237 238 freepage(&folio->page); 238 239 239 - if (folio_test_large(folio) && !folio_test_hugetlb(folio)) { 240 - folio_ref_sub(folio, folio_nr_pages(folio)); 241 - VM_BUG_ON_FOLIO(folio_ref_count(folio) <= 0, folio); 242 - } else { 243 - folio_put(folio); 244 - } 240 + if (folio_test_large(folio) && !folio_test_hugetlb(folio)) 241 + refs = folio_nr_pages(folio); 242 + folio_put_refs(folio, refs); 245 243 } 246 244 247 245 /**