diff options
Diffstat (limited to 'mm/migrate.c')
-rw-r--r-- | mm/migrate.c | 11 |
1 files changed, 9 insertions, 2 deletions
diff --git a/mm/migrate.c b/mm/migrate.c index 37c73b902008..e2fdbce1874b 100644 --- a/mm/migrate.c +++ b/mm/migrate.c | |||
@@ -611,6 +611,7 @@ static int unmap_and_move(new_page_t get_new_page, unsigned long private, | |||
611 | int rc = 0; | 611 | int rc = 0; |
612 | int *result = NULL; | 612 | int *result = NULL; |
613 | struct page *newpage = get_new_page(page, private, &result); | 613 | struct page *newpage = get_new_page(page, private, &result); |
614 | int rcu_locked = 0; | ||
614 | 615 | ||
615 | if (!newpage) | 616 | if (!newpage) |
616 | return -ENOMEM; | 617 | return -ENOMEM; |
@@ -636,8 +637,13 @@ static int unmap_and_move(new_page_t get_new_page, unsigned long private, | |||
636 | * we cannot notice that anon_vma is freed while we migrates a page. | 637 | * we cannot notice that anon_vma is freed while we migrates a page. |
637 | * This rcu_read_lock() delays freeing anon_vma pointer until the end | 638 | * This rcu_read_lock() delays freeing anon_vma pointer until the end |
638 | * of migration. File cache pages are no problem because of page_lock() | 639 | * of migration. File cache pages are no problem because of page_lock() |
640 | * File Caches may use write_page() or lock_page() in migration, then, | ||
641 | * just care Anon page here. | ||
639 | */ | 642 | */ |
640 | rcu_read_lock(); | 643 | if (PageAnon(page)) { |
644 | rcu_read_lock(); | ||
645 | rcu_locked = 1; | ||
646 | } | ||
641 | /* | 647 | /* |
642 | * This is a corner case handling. | 648 | * This is a corner case handling. |
643 | * When a new swap-cache is read into, it is linked to LRU | 649 | * When a new swap-cache is read into, it is linked to LRU |
@@ -656,7 +662,8 @@ static int unmap_and_move(new_page_t get_new_page, unsigned long private, | |||
656 | if (rc) | 662 | if (rc) |
657 | remove_migration_ptes(page, page); | 663 | remove_migration_ptes(page, page); |
658 | rcu_unlock: | 664 | rcu_unlock: |
659 | rcu_read_unlock(); | 665 | if (rcu_locked) |
666 | rcu_read_unlock(); | ||
660 | 667 | ||
661 | unlock: | 668 | unlock: |
662 | 669 | ||