aboutsummaryrefslogtreecommitdiffstats
path: root/mm/memory.c
diff options
context:
space:
mode:
authorMel Gorman <mgorman@suse.de>2012-11-20 20:18:23 -0500
committerMel Gorman <mgorman@suse.de>2012-12-11 09:42:55 -0500
commitb8593bfda1652755136333cdd362de125b283a9c (patch)
treec0395d9cf775fd9225e81b055fc8f5540a14333a /mm/memory.c
parente42c8ff2999de1239a57d434bfbd8e9f2a56e814 (diff)
mm: sched: Adapt the scanning rate if a NUMA hinting fault does not migrate
The PTE scanning rate and fault rates are two of the biggest sources of system CPU overhead with automatic NUMA placement. Ideally a proper policy would detect if a workload was properly placed, schedule and adjust the PTE scanning rate accordingly. We do not track the necessary information to do that but we at least know if we migrated or not. This patch scans slower if a page was not migrated as the result of a NUMA hinting fault up to sysctl_numa_balancing_scan_period_max which is now higher than the previous default. Once every minute it will reset the scanner in case of phase changes. This is hilariously crude and the numbers are arbitrary. Workloads will converge quite slowly in comparison to what a proper policy should be able to do. On the plus side, we will chew up less CPU for workloads that have no need for automatic balancing. Signed-off-by: Mel Gorman <mgorman@suse.de>
Diffstat (limited to 'mm/memory.c')
-rw-r--r--mm/memory.c12
1 files changed, 8 insertions, 4 deletions
diff --git a/mm/memory.c b/mm/memory.c
index 84c6d9eab182..39edb11b63dc 100644
--- a/mm/memory.c
+++ b/mm/memory.c
@@ -3468,6 +3468,7 @@ int do_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
3468 spinlock_t *ptl; 3468 spinlock_t *ptl;
3469 int current_nid = -1; 3469 int current_nid = -1;
3470 int target_nid; 3470 int target_nid;
3471 bool migrated = false;
3471 3472
3472 /* 3473 /*
3473 * The "pte" at this point cannot be used safely without 3474 * The "pte" at this point cannot be used safely without
@@ -3509,12 +3510,13 @@ int do_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
3509 } 3510 }
3510 3511
3511 /* Migrate to the requested node */ 3512 /* Migrate to the requested node */
3512 if (migrate_misplaced_page(page, target_nid)) 3513 migrated = migrate_misplaced_page(page, target_nid);
3514 if (migrated)
3513 current_nid = target_nid; 3515 current_nid = target_nid;
3514 3516
3515out: 3517out:
3516 if (current_nid != -1) 3518 if (current_nid != -1)
3517 task_numa_fault(current_nid, 1); 3519 task_numa_fault(current_nid, 1, migrated);
3518 return 0; 3520 return 0;
3519} 3521}
3520 3522
@@ -3554,6 +3556,7 @@ static int do_pmd_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
3554 struct page *page; 3556 struct page *page;
3555 int curr_nid = local_nid; 3557 int curr_nid = local_nid;
3556 int target_nid; 3558 int target_nid;
3559 bool migrated;
3557 if (!pte_present(pteval)) 3560 if (!pte_present(pteval))
3558 continue; 3561 continue;
3559 if (!pte_numa(pteval)) 3562 if (!pte_numa(pteval))
@@ -3590,9 +3593,10 @@ static int do_pmd_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
3590 3593
3591 /* Migrate to the requested node */ 3594 /* Migrate to the requested node */
3592 pte_unmap_unlock(pte, ptl); 3595 pte_unmap_unlock(pte, ptl);
3593 if (migrate_misplaced_page(page, target_nid)) 3596 migrated = migrate_misplaced_page(page, target_nid);
3597 if (migrated)
3594 curr_nid = target_nid; 3598 curr_nid = target_nid;
3595 task_numa_fault(curr_nid, 1); 3599 task_numa_fault(curr_nid, 1, migrated);
3596 3600
3597 pte = pte_offset_map_lock(mm, pmdp, addr, &ptl); 3601 pte = pte_offset_map_lock(mm, pmdp, addr, &ptl);
3598 } 3602 }