summaryrefslogtreecommitdiffstats
path: root/mm/page_alloc.c
diff options
context:
space:
mode:
authorMel Gorman <mgorman@techsingularity.net>2017-11-15 20:38:03 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2017-11-15 21:21:06 -0500
commit453f85d43fa9ee243f0fc3ac4e1be45615301e3f (patch)
treef414b8ef3a3c92903c960225a2ded020a7158494 /mm/page_alloc.c
parent2d4894b5d2ae0fe1725ea7abd57b33bfbbe45492 (diff)
mm: remove __GFP_COLD
As the page free path makes no distinction between cache hot and cold pages, there is no real useful ordering of pages in the free list that allocation requests can take advantage of. Juding from the users of __GFP_COLD, it is likely that a number of them are the result of copying other sites instead of actually measuring the impact. Remove the __GFP_COLD parameter which simplifies a number of paths in the page allocator. This is potentially controversial but bear in mind that the size of the per-cpu pagelists versus modern cache sizes means that the whole per-cpu list can often fit in the L3 cache. Hence, there is only a potential benefit for microbenchmarks that alloc/free pages in a tight loop. It's even worse when THP is taken into account which has little or no chance of getting a cache-hot page as the per-cpu list is bypassed and the zeroing of multiple pages will thrash the cache anyway. The truncate microbenchmarks are not shown as this patch affects the allocation path and not the free path. A page fault microbenchmark was tested but it showed no sigificant difference which is not surprising given that the __GFP_COLD branches are a miniscule percentage of the fault path. Link: http://lkml.kernel.org/r/20171018075952.10627-9-mgorman@techsingularity.net Signed-off-by: Mel Gorman <mgorman@techsingularity.net> Acked-by: Vlastimil Babka <vbabka@suse.cz> Cc: Andi Kleen <ak@linux.intel.com> Cc: Dave Chinner <david@fromorbit.com> Cc: Dave Hansen <dave.hansen@intel.com> Cc: Jan Kara <jack@suse.cz> Cc: Johannes Weiner <hannes@cmpxchg.org> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'mm/page_alloc.c')
-rw-r--r--mm/page_alloc.c20
1 files changed, 6 insertions, 14 deletions
diff --git a/mm/page_alloc.c b/mm/page_alloc.c
index f265d37b3152..370b64d03e3f 100644
--- a/mm/page_alloc.c
+++ b/mm/page_alloc.c
@@ -2336,7 +2336,7 @@ retry:
2336 */ 2336 */
2337static int rmqueue_bulk(struct zone *zone, unsigned int order, 2337static int rmqueue_bulk(struct zone *zone, unsigned int order,
2338 unsigned long count, struct list_head *list, 2338 unsigned long count, struct list_head *list,
2339 int migratetype, bool cold) 2339 int migratetype)
2340{ 2340{
2341 int i, alloced = 0; 2341 int i, alloced = 0;
2342 2342
@@ -2358,10 +2358,7 @@ static int rmqueue_bulk(struct zone *zone, unsigned int order,
2358 * merge IO requests if the physical pages are ordered 2358 * merge IO requests if the physical pages are ordered
2359 * properly. 2359 * properly.
2360 */ 2360 */
2361 if (likely(!cold)) 2361 list_add(&page->lru, list);
2362 list_add(&page->lru, list);
2363 else
2364 list_add_tail(&page->lru, list);
2365 list = &page->lru; 2362 list = &page->lru;
2366 alloced++; 2363 alloced++;
2367 if (is_migrate_cma(get_pcppage_migratetype(page))) 2364 if (is_migrate_cma(get_pcppage_migratetype(page)))
@@ -2795,7 +2792,7 @@ static inline void zone_statistics(struct zone *preferred_zone, struct zone *z)
2795 2792
2796/* Remove page from the per-cpu list, caller must protect the list */ 2793/* Remove page from the per-cpu list, caller must protect the list */
2797static struct page *__rmqueue_pcplist(struct zone *zone, int migratetype, 2794static struct page *__rmqueue_pcplist(struct zone *zone, int migratetype,
2798 bool cold, struct per_cpu_pages *pcp, 2795 struct per_cpu_pages *pcp,
2799 struct list_head *list) 2796 struct list_head *list)
2800{ 2797{
2801 struct page *page; 2798 struct page *page;
@@ -2804,16 +2801,12 @@ static struct page *__rmqueue_pcplist(struct zone *zone, int migratetype,
2804 if (list_empty(list)) { 2801 if (list_empty(list)) {
2805 pcp->count += rmqueue_bulk(zone, 0, 2802 pcp->count += rmqueue_bulk(zone, 0,
2806 pcp->batch, list, 2803 pcp->batch, list,
2807 migratetype, cold); 2804 migratetype);
2808 if (unlikely(list_empty(list))) 2805 if (unlikely(list_empty(list)))
2809 return NULL; 2806 return NULL;
2810 } 2807 }
2811 2808
2812 if (cold) 2809 page = list_first_entry(list, struct page, lru);
2813 page = list_last_entry(list, struct page, lru);
2814 else
2815 page = list_first_entry(list, struct page, lru);
2816
2817 list_del(&page->lru); 2810 list_del(&page->lru);
2818 pcp->count--; 2811 pcp->count--;
2819 } while (check_new_pcp(page)); 2812 } while (check_new_pcp(page));
@@ -2828,14 +2821,13 @@ static struct page *rmqueue_pcplist(struct zone *preferred_zone,
2828{ 2821{
2829 struct per_cpu_pages *pcp; 2822 struct per_cpu_pages *pcp;
2830 struct list_head *list; 2823 struct list_head *list;
2831 bool cold = ((gfp_flags & __GFP_COLD) != 0);
2832 struct page *page; 2824 struct page *page;
2833 unsigned long flags; 2825 unsigned long flags;
2834 2826
2835 local_irq_save(flags); 2827 local_irq_save(flags);
2836 pcp = &this_cpu_ptr(zone->pageset)->pcp; 2828 pcp = &this_cpu_ptr(zone->pageset)->pcp;
2837 list = &pcp->lists[migratetype]; 2829 list = &pcp->lists[migratetype];
2838 page = __rmqueue_pcplist(zone, migratetype, cold, pcp, list); 2830 page = __rmqueue_pcplist(zone, migratetype, pcp, list);
2839 if (page) { 2831 if (page) {
2840 __count_zid_vm_events(PGALLOC, page_zonenum(page), 1 << order); 2832 __count_zid_vm_events(PGALLOC, page_zonenum(page), 1 << order);
2841 zone_statistics(preferred_zone, zone); 2833 zone_statistics(preferred_zone, zone);