aboutsummaryrefslogtreecommitdiffstats
path: root/mm/migrate.c
diff options
context:
space:
mode:
Diffstat (limited to 'mm/migrate.c')
-rw-r--r--mm/migrate.c30
1 files changed, 17 insertions, 13 deletions
diff --git a/mm/migrate.c b/mm/migrate.c
index c04692774e88..dfc8300ecbb2 100644
--- a/mm/migrate.c
+++ b/mm/migrate.c
@@ -445,6 +445,8 @@ int migrate_huge_page_move_mapping(struct address_space *mapping,
445 */ 445 */
446void migrate_page_copy(struct page *newpage, struct page *page) 446void migrate_page_copy(struct page *newpage, struct page *page)
447{ 447{
448 int cpupid;
449
448 if (PageHuge(page) || PageTransHuge(page)) 450 if (PageHuge(page) || PageTransHuge(page))
449 copy_huge_page(newpage, page); 451 copy_huge_page(newpage, page);
450 else 452 else
@@ -481,6 +483,13 @@ void migrate_page_copy(struct page *newpage, struct page *page)
481 __set_page_dirty_nobuffers(newpage); 483 __set_page_dirty_nobuffers(newpage);
482 } 484 }
483 485
486 /*
487 * Copy NUMA information to the new page, to prevent over-eager
488 * future migrations of this same page.
489 */
490 cpupid = page_cpupid_xchg_last(page, -1);
491 page_cpupid_xchg_last(newpage, cpupid);
492
484 mlock_migrate_page(newpage, page); 493 mlock_migrate_page(newpage, page);
485 ksm_migrate_page(newpage, page); 494 ksm_migrate_page(newpage, page);
486 /* 495 /*
@@ -1500,7 +1509,7 @@ static struct page *alloc_misplaced_dst_page(struct page *page,
1500 __GFP_NOWARN) & 1509 __GFP_NOWARN) &
1501 ~GFP_IOFS, 0); 1510 ~GFP_IOFS, 0);
1502 if (newpage) 1511 if (newpage)
1503 page_nid_xchg_last(newpage, page_nid_last(page)); 1512 page_cpupid_xchg_last(newpage, page_cpupid_last(page));
1504 1513
1505 return newpage; 1514 return newpage;
1506} 1515}
@@ -1601,7 +1610,8 @@ int numamigrate_isolate_page(pg_data_t *pgdat, struct page *page)
1601 * node. Caller is expected to have an elevated reference count on 1610 * node. Caller is expected to have an elevated reference count on
1602 * the page that will be dropped by this function before returning. 1611 * the page that will be dropped by this function before returning.
1603 */ 1612 */
1604int migrate_misplaced_page(struct page *page, int node) 1613int migrate_misplaced_page(struct page *page, struct vm_area_struct *vma,
1614 int node)
1605{ 1615{
1606 pg_data_t *pgdat = NODE_DATA(node); 1616 pg_data_t *pgdat = NODE_DATA(node);
1607 int isolated; 1617 int isolated;
@@ -1609,10 +1619,11 @@ int migrate_misplaced_page(struct page *page, int node)
1609 LIST_HEAD(migratepages); 1619 LIST_HEAD(migratepages);
1610 1620
1611 /* 1621 /*
1612 * Don't migrate pages that are mapped in multiple processes. 1622 * Don't migrate file pages that are mapped in multiple processes
1613 * TODO: Handle false sharing detection instead of this hammer 1623 * with execute permissions as they are probably shared libraries.
1614 */ 1624 */
1615 if (page_mapcount(page) != 1) 1625 if (page_mapcount(page) != 1 && page_is_file_cache(page) &&
1626 (vma->vm_flags & VM_EXEC))
1616 goto out; 1627 goto out;
1617 1628
1618 /* 1629 /*
@@ -1663,13 +1674,6 @@ int migrate_misplaced_transhuge_page(struct mm_struct *mm,
1663 int page_lru = page_is_file_cache(page); 1674 int page_lru = page_is_file_cache(page);
1664 1675
1665 /* 1676 /*
1666 * Don't migrate pages that are mapped in multiple processes.
1667 * TODO: Handle false sharing detection instead of this hammer
1668 */
1669 if (page_mapcount(page) != 1)
1670 goto out_dropref;
1671
1672 /*
1673 * Rate-limit the amount of data that is being migrated to a node. 1677 * Rate-limit the amount of data that is being migrated to a node.
1674 * Optimal placement is no good if the memory bus is saturated and 1678 * Optimal placement is no good if the memory bus is saturated and
1675 * all the time is being spent migrating! 1679 * all the time is being spent migrating!
@@ -1682,7 +1686,7 @@ int migrate_misplaced_transhuge_page(struct mm_struct *mm,
1682 if (!new_page) 1686 if (!new_page)
1683 goto out_fail; 1687 goto out_fail;
1684 1688
1685 page_nid_xchg_last(new_page, page_nid_last(page)); 1689 page_cpupid_xchg_last(new_page, page_cpupid_last(page));
1686 1690
1687 isolated = numamigrate_isolate_page(pgdat, page); 1691 isolated = numamigrate_isolate_page(pgdat, page);
1688 if (!isolated) { 1692 if (!isolated) {