v3
2026-08-25
follow_page_mask 批量返回页 · v3
重构 follow_page_mask() 一次返回多页并填充数组,大 folio 在解锁后填页,避免逐页重走页表加锁。
原始补丁链接
子 Patch(8)
1/8
mm/gup: break out gup_fill_pages() helper
__get_user_pages() fills pages[] and flushes each page’s caches in an open-coded loop. Move it into a gup_fill_pages() helper, which the follow_page_mask() call chain can then use to fill its own pag
2/8
mm/gup: convert follow_page_mask() to return a long
follow_page_mask() and its helpers return a struct page pointer: NULL, ERR_PTR(), or the page found. Change the return type to long instead: 0, a negative errno, or 1 with the page stored in a new pag
3/8
mm/gup: split follow_page_pte_commit() out of follow_page_pte()
follow_page_pte() does two things once it has resolved a present PTE to a page: run the per-PTE safety checks (write-fault, unshare), then commit to that page: grab a ref, fault it in if pinning, mark
4/8
mm/gup: break out follow_one_pte() helper
follow_page_pte() is 92 lines and does two separate things: work out which page a PTE maps, if any, and commit to the page it found. The first half reaches the second through five exit paths, two of w
5/8
mm/gup: fill the pages array outside the pud/pmd lock
follow_huge_pud() and follow_huge_pmd() fill pages[] and flush the page’s caches while still holding the pud or pmd lock. Neither flush_anon_page() nor flush_dcache_page() needs that lock. Have the h
6/8
mm/gup: return a huge page's full count from follow_page_mask()
follow_huge_pud()/follow_huge_pmd() already know the huge page’s full size but report it via a separate *page_mask output; __get_user_pages() does a second try_grab_folio() call and subpage loop for e
7/8
mm/gup: walk multiple PTEs per follow_page_pte() call
follow_page_pte() looks at one PTE per call, so __get_user_pages() calls it once per page, restarting the pgd/p4d/pud/pmd descent and retaking the PTE lock each time. Walk every PTE from @address to
8/8
mm/gup: batch contiguous same-folio PTEs into one refcount grab
follow_page_pte() now walks a whole page table in one call, but still resolves and commits each PTE on its own, so a PTE-mapped large folio (mTHP) pays one try_grab_folio() per subpage. Add follow_pt