mm: initialize MAX_ORDER_NR_PAGES at a time instead of doing larger sections

Add yet another iterator, for_each_free_mem_range_in_zone_from, and then
use it to support initializing and freeing pages in groups no larger than
MAX_ORDER_NR_PAGES.  By doing this we can greatly improve the cache
locality of the pages while we do several loops over them in the init and
freeing process.

We are able to tighten the loops further as a result of the "from"
iterator as we can perform the initial checks for first_init_pfn in our
first call to the iterator, and continue without the need for those checks
via the "from" iterator.  I have added this functionality in the function
called deferred_init_mem_pfn_range_in_zone that primes the iterator and
causes us to exit if we encounter any failure.

On my x86_64 test system with 384GB of memory per node I saw a reduction
in initialization time from 1.85s to 1.38s as a result of this patch.

Signed-off-by: Alexander Duyck <>
Reviewed-by: Pavel Tatashin <>
Cc: Mike Rapoport <>
Cc: Michal Hocko <>
Cc: Dave Jiang <>
Cc: Matthew Wilcox <>
Cc: Ingo Molnar <>
Cc: <>
Cc: Khalid Aziz <>
Cc: Mike Rapoport <>
Cc: Vlastimil Babka <>
Cc: Dan Williams <>
Cc: Laurent Dufour <>
Cc: Mel Gorman <>
Cc: David S. Miller <>
Cc: "Kirill A. Shutemov" <>
Cc: Pavel Tatashin <>
Signed-off-by: Andrew Morton <>
Signed-off-by: Linus Torvalds <>
2 files changed