Re: [PATCH v7 3/5] mm/hugetlb: add support for mempolicy MPOL_PREFERRED_MANY
From: Michal Hocko <mhocko@suse.com>
Date: 2021-08-06 13:35:56
Also in:
linux-api, lkml
On Tue 03-08-21 13:59:20, Feng Tang wrote:
From: Ben Widawsky <redacted> Implement the missing huge page allocation functionality while obeying the preferred node semantics. This is similar to the implementation for general page allocation, as it uses a fallback mechanism to try multiple preferred nodes first, and then all other nodes. [akpm: fix compling issue when merging with other hugetlb patch] [Thanks to 0day bot for catching the missing #ifdef CONFIG_NUMA issue] Link: https://lore.kernel.org/r/20200630212517.308045-12-ben.widawsky@intel.com (local) Suggested-by: Michal Hocko <mhocko@suse.com> Signed-off-by: Ben Widawsky <redacted> Co-developed-by: Feng Tang <redacted> Signed-off-by: Feng Tang <redacted>
ifdefery is just ugly as hell. One way to get rid of that would be to provide a mpol_is_preferred_many() wrapper and hide the CONFIG_NUMA in mempolicy.h. I haven't checked but this might help to remove some other ifdefery as well. I especially dislike the label hidden in the ifdef. You can get rid of that by checking the page for NULL.
quoted hunk ↗ jump to hunk
--- mm/hugetlb.c | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+)diff --git a/mm/hugetlb.c b/mm/hugetlb.c index 95714fb28150..9279f6d478d9 100644 --- a/mm/hugetlb.c +++ b/mm/hugetlb.c@@ -1166,7 +1166,20 @@ static struct page *dequeue_huge_page_vma(struct hstate *h, gfp_mask = htlb_alloc_mask(h); nid = huge_node(vma, address, gfp_mask, &mpol, &nodemask); +#ifdef CONFIG_NUMA + if (mpol->mode == MPOL_PREFERRED_MANY) { + page = dequeue_huge_page_nodemask(h, gfp_mask, nid, nodemask); + if (page) + goto check_reserve; + /* Fallback to all nodes */ + nodemask = NULL; + } +#endif page = dequeue_huge_page_nodemask(h, gfp_mask, nid, nodemask); + +#ifdef CONFIG_NUMA +check_reserve: +#endif if (page && !avoid_reserve && vma_has_reserves(vma, chg)) { SetHPageRestoreReserve(page); h->resv_huge_pages--;@@ -2147,6 +2160,21 @@ struct page *alloc_buddy_huge_page_with_mpol(struct hstate *h, nodemask_t *nodemask; nid = huge_node(vma, addr, gfp_mask, &mpol, &nodemask); +#ifdef CONFIG_NUMA + if (mpol->mode == MPOL_PREFERRED_MANY) { + gfp_t gfp = gfp_mask | __GFP_NOWARN; + + gfp &= ~(__GFP_DIRECT_RECLAIM | __GFP_NOFAIL); + page = alloc_surplus_huge_page(h, gfp, nid, nodemask, false); + if (page) { + mpol_cond_put(mpol); + return page; + } + + /* Fallback to all nodes */ + nodemask = NULL; + } +#endif page = alloc_surplus_huge_page(h, gfp_mask, nid, nodemask, false); mpol_cond_put(mpol);-- 2.14.1
-- Michal Hocko SUSE Labs