|
@@ -3604,6 +3604,17 @@ retry:
|
|
|
*/
|
|
|
alloc_flags = gfp_to_alloc_flags(gfp_mask);
|
|
|
|
|
|
+ /*
|
|
|
+ * Reset the zonelist iterators if memory policies can be ignored.
|
|
|
+ * These allocations are high priority and system rather than user
|
|
|
+ * orientated.
|
|
|
+ */
|
|
|
+ if ((alloc_flags & ALLOC_NO_WATERMARKS) || !(alloc_flags & ALLOC_CPUSET)) {
|
|
|
+ ac->zonelist = node_zonelist(numa_node_id(), gfp_mask);
|
|
|
+ ac->preferred_zoneref = first_zones_zonelist(ac->zonelist,
|
|
|
+ ac->high_zoneidx, ac->nodemask);
|
|
|
+ }
|
|
|
+
|
|
|
/* This is the last chance, in general, before the goto nopage. */
|
|
|
page = get_page_from_freelist(gfp_mask, order,
|
|
|
alloc_flags & ~ALLOC_NO_WATERMARKS, ac);
|
|
@@ -3612,12 +3623,6 @@ retry:
|
|
|
|
|
|
/* Allocate without watermarks if the context allows */
|
|
|
if (alloc_flags & ALLOC_NO_WATERMARKS) {
|
|
|
- /*
|
|
|
- * Ignore mempolicies if ALLOC_NO_WATERMARKS on the grounds
|
|
|
- * the allocation is high priority and these type of
|
|
|
- * allocations are system rather than user orientated
|
|
|
- */
|
|
|
- ac->zonelist = node_zonelist(numa_node_id(), gfp_mask);
|
|
|
page = get_page_from_freelist(gfp_mask, order,
|
|
|
ALLOC_NO_WATERMARKS, ac);
|
|
|
if (page)
|
|
@@ -3816,7 +3821,11 @@ retry_cpuset:
|
|
|
/* Dirty zone balancing only done in the fast path */
|
|
|
ac.spread_dirty_pages = (gfp_mask & __GFP_WRITE);
|
|
|
|
|
|
- /* The preferred zone is used for statistics later */
|
|
|
+ /*
|
|
|
+ * The preferred zone is used for statistics but crucially it is
|
|
|
+ * also used as the starting point for the zonelist iterator. It
|
|
|
+ * may get reset for allocations that ignore memory policies.
|
|
|
+ */
|
|
|
ac.preferred_zoneref = first_zones_zonelist(ac.zonelist,
|
|
|
ac.high_zoneidx, ac.nodemask);
|
|
|
if (!ac.preferred_zoneref) {
|