diff --git a/include/linux/mm_types.h b/include/linux/mm_types.h index 48d72db9d86d..ed9df33228a6 100644 --- a/include/linux/mm_types.h +++ b/include/linux/mm_types.h @@ -83,12 +83,18 @@ struct page { */ union { struct { /* Page cache and anonymous pages */ - /** - * @lru: Pageout list, eg. active_list protected by - * pgdat->lru_lock. Sometimes used as a generic list - * by the page owner. - */ - struct list_head lru; + union { + /** + * @lru: Pageout list, eg. active_list protected by + * pgdat->lru_lock. Sometimes used as a generic list + * by the page owner. + */ + struct list_head lru; + + /* Or, free page */ + struct list_head buddy_list; + struct list_head pcp_list; + }; /* See page-flags.h for PAGE_MAPPING_FLAGS */ struct address_space *mapping; pgoff_t index; /* Our offset within mapping. */ diff --git a/mm/page_alloc.c b/mm/page_alloc.c index be4117d9ff2f..d34a86a20adf 100644 --- a/mm/page_alloc.c +++ b/mm/page_alloc.c @@ -747,7 +747,7 @@ static inline bool set_page_guard(struct zone *zone, struct page *page, return false; __SetPageGuard(page); - INIT_LIST_HEAD(&page->lru); + INIT_LIST_HEAD(&page->buddy_list); set_page_private(page, order); /* Guard pages are not available for any usage */ __mod_zone_freepage_state(zone, -(1 << order), migratetype); @@ -921,7 +921,7 @@ static inline void add_to_free_list(struct page *page, struct zone *zone, { struct free_area *area = &zone->free_area[order]; - list_add(&page->lru, &area->free_list[migratetype]); + list_add(&page->buddy_list, &area->free_list[migratetype]); area->nr_free++; } @@ -931,7 +931,7 @@ static inline void add_to_free_list_tail(struct page *page, struct zone *zone, { struct free_area *area = &zone->free_area[order]; - list_add_tail(&page->lru, &area->free_list[migratetype]); + list_add_tail(&page->buddy_list, &area->free_list[migratetype]); area->nr_free++; } @@ -945,7 +945,7 @@ static inline void move_to_free_list(struct page *page, struct zone *zone, { struct free_area *area = &zone->free_area[order]; - list_move_tail(&page->lru, &area->free_list[migratetype]); + list_move_tail(&page->buddy_list, &area->free_list[migratetype]); } static inline void del_page_from_free_list(struct page *page, struct zone *zone, @@ -955,7 +955,7 @@ static inline void del_page_from_free_list(struct page *page, struct zone *zone, if (page_reported(page)) __ClearPageReported(page); - list_del(&page->lru); + list_del(&page->buddy_list); __ClearPageBuddy(page); set_page_private(page, 0); zone->free_area[order].nr_free--; @@ -1461,7 +1461,7 @@ static void free_pcppages_bulk(struct zone *zone, int count, do { page = list_last_entry(list, struct page, lru); /* must delete to avoid corrupting pcp list */ - list_del(&page->lru); + list_del(&page->pcp_list); pcp->count--; if (bulkfree_pcp_prepare(page)) @@ -3061,7 +3061,7 @@ static int rmqueue_bulk(struct zone *zone, unsigned int order, * for IO devices that can merge IO requests if the physical * pages are ordered properly. */ - list_add_tail(&page->lru, list); + list_add_tail(&page->pcp_list, list); alloced++; if (is_migrate_cma(get_pcppage_migratetype(page))) __mod_zone_page_state(zone, NR_FREE_CMA_PAGES, @@ -3349,7 +3349,7 @@ static void free_unref_page_commit(struct page *page, int migratetype) __count_vm_event(PGFREE); pcp = &this_cpu_ptr(zone->pageset)->pcp; - list_add(&page->lru, &pcp->lists[migratetype]); + list_add(&page->pcp_list, &pcp->lists[migratetype]); pcp->count++; if (pcp->count >= pcp->high) { unsigned long batch = READ_ONCE(pcp->batch); @@ -3596,7 +3596,7 @@ static struct page *__rmqueue_pcplist(struct zone *zone, int migratetype, } page = list_first_entry(list, struct page, lru); - list_del(&page->lru); + list_del(&page->pcp_list); pcp->count--; } while (check_new_pcp(page));