aboutsummaryrefslogtreecommitdiffstats
path: root/mm/memory_hotplug.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2015-04-14 19:49:17 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2015-04-14 19:49:17 -0400
commit1dcf58d6e6e6eb7ec10e9abc56887b040205b06f (patch)
treec03e7a25ef13eea62f1547914a76e5c68f3f4c28 /mm/memory_hotplug.c
parent80dcc31fbe55932ac9204daee5f2ebc0c49b6da3 (diff)
parente4b0db72be2487bae0e3251c22f82c104f7c1cfd (diff)
Merge branch 'akpm' (patches from Andrew)
Merge first patchbomb from Andrew Morton: - arch/sh updates - ocfs2 updates - kernel/watchdog feature - about half of mm/ * emailed patches from Andrew Morton <akpm@linux-foundation.org>: (122 commits) Documentation: update arch list in the 'memtest' entry Kconfig: memtest: update number of test patterns up to 17 arm: add support for memtest arm64: add support for memtest memtest: use phys_addr_t for physical addresses mm: move memtest under mm mm, hugetlb: abort __get_user_pages if current has been oom killed mm, mempool: do not allow atomic resizing memcg: print cgroup information when system panics due to panic_on_oom mm: numa: remove migrate_ratelimited mm: fold arch_randomize_brk into ARCH_HAS_ELF_RANDOMIZE mm: split ET_DYN ASLR from mmap ASLR s390: redefine randomize_et_dyn for ELF_ET_DYN_BASE mm: expose arch_mmap_rnd when available s390: standardize mmap_rnd() usage powerpc: standardize mmap_rnd() usage mips: extract logic for mmap_rnd() arm64: standardize mmap_rnd() usage x86: standardize mmap_rnd() usage arm: factor out mmap ASLR into mmap_rnd ...
Diffstat (limited to 'mm/memory_hotplug.c')
-rw-r--r--mm/memory_hotplug.c35
1 files changed, 13 insertions, 22 deletions
diff --git a/mm/memory_hotplug.c b/mm/memory_hotplug.c
index 65842d688b7c..e2e8014fb755 100644
--- a/mm/memory_hotplug.c
+++ b/mm/memory_hotplug.c
@@ -104,7 +104,7 @@ void put_online_mems(void)
104 104
105} 105}
106 106
107static void mem_hotplug_begin(void) 107void mem_hotplug_begin(void)
108{ 108{
109 mem_hotplug.active_writer = current; 109 mem_hotplug.active_writer = current;
110 110
@@ -119,7 +119,7 @@ static void mem_hotplug_begin(void)
119 } 119 }
120} 120}
121 121
122static void mem_hotplug_done(void) 122void mem_hotplug_done(void)
123{ 123{
124 mem_hotplug.active_writer = NULL; 124 mem_hotplug.active_writer = NULL;
125 mutex_unlock(&mem_hotplug.lock); 125 mutex_unlock(&mem_hotplug.lock);
@@ -502,7 +502,7 @@ int __ref __add_pages(int nid, struct zone *zone, unsigned long phys_start_pfn,
502 end_sec = pfn_to_section_nr(phys_start_pfn + nr_pages - 1); 502 end_sec = pfn_to_section_nr(phys_start_pfn + nr_pages - 1);
503 503
504 for (i = start_sec; i <= end_sec; i++) { 504 for (i = start_sec; i <= end_sec; i++) {
505 err = __add_section(nid, zone, i << PFN_SECTION_SHIFT); 505 err = __add_section(nid, zone, section_nr_to_pfn(i));
506 506
507 /* 507 /*
508 * EEXIST is finally dealt with by ioresource collision 508 * EEXIST is finally dealt with by ioresource collision
@@ -959,6 +959,7 @@ static void node_states_set_node(int node, struct memory_notify *arg)
959} 959}
960 960
961 961
962/* Must be protected by mem_hotplug_begin() */
962int __ref online_pages(unsigned long pfn, unsigned long nr_pages, int online_type) 963int __ref online_pages(unsigned long pfn, unsigned long nr_pages, int online_type)
963{ 964{
964 unsigned long flags; 965 unsigned long flags;
@@ -969,7 +970,6 @@ int __ref online_pages(unsigned long pfn, unsigned long nr_pages, int online_typ
969 int ret; 970 int ret;
970 struct memory_notify arg; 971 struct memory_notify arg;
971 972
972 mem_hotplug_begin();
973 /* 973 /*
974 * This doesn't need a lock to do pfn_to_page(). 974 * This doesn't need a lock to do pfn_to_page().
975 * The section can't be removed here because of the 975 * The section can't be removed here because of the
@@ -977,21 +977,20 @@ int __ref online_pages(unsigned long pfn, unsigned long nr_pages, int online_typ
977 */ 977 */
978 zone = page_zone(pfn_to_page(pfn)); 978 zone = page_zone(pfn_to_page(pfn));
979 979
980 ret = -EINVAL;
981 if ((zone_idx(zone) > ZONE_NORMAL || 980 if ((zone_idx(zone) > ZONE_NORMAL ||
982 online_type == MMOP_ONLINE_MOVABLE) && 981 online_type == MMOP_ONLINE_MOVABLE) &&
983 !can_online_high_movable(zone)) 982 !can_online_high_movable(zone))
984 goto out; 983 return -EINVAL;
985 984
986 if (online_type == MMOP_ONLINE_KERNEL && 985 if (online_type == MMOP_ONLINE_KERNEL &&
987 zone_idx(zone) == ZONE_MOVABLE) { 986 zone_idx(zone) == ZONE_MOVABLE) {
988 if (move_pfn_range_left(zone - 1, zone, pfn, pfn + nr_pages)) 987 if (move_pfn_range_left(zone - 1, zone, pfn, pfn + nr_pages))
989 goto out; 988 return -EINVAL;
990 } 989 }
991 if (online_type == MMOP_ONLINE_MOVABLE && 990 if (online_type == MMOP_ONLINE_MOVABLE &&
992 zone_idx(zone) == ZONE_MOVABLE - 1) { 991 zone_idx(zone) == ZONE_MOVABLE - 1) {
993 if (move_pfn_range_right(zone, zone + 1, pfn, pfn + nr_pages)) 992 if (move_pfn_range_right(zone, zone + 1, pfn, pfn + nr_pages))
994 goto out; 993 return -EINVAL;
995 } 994 }
996 995
997 /* Previous code may changed the zone of the pfn range */ 996 /* Previous code may changed the zone of the pfn range */
@@ -1007,7 +1006,7 @@ int __ref online_pages(unsigned long pfn, unsigned long nr_pages, int online_typ
1007 ret = notifier_to_errno(ret); 1006 ret = notifier_to_errno(ret);
1008 if (ret) { 1007 if (ret) {
1009 memory_notify(MEM_CANCEL_ONLINE, &arg); 1008 memory_notify(MEM_CANCEL_ONLINE, &arg);
1010 goto out; 1009 return ret;
1011 } 1010 }
1012 /* 1011 /*
1013 * If this zone is not populated, then it is not in zonelist. 1012 * If this zone is not populated, then it is not in zonelist.
@@ -1031,7 +1030,7 @@ int __ref online_pages(unsigned long pfn, unsigned long nr_pages, int online_typ
1031 (((unsigned long long) pfn + nr_pages) 1030 (((unsigned long long) pfn + nr_pages)
1032 << PAGE_SHIFT) - 1); 1031 << PAGE_SHIFT) - 1);
1033 memory_notify(MEM_CANCEL_ONLINE, &arg); 1032 memory_notify(MEM_CANCEL_ONLINE, &arg);
1034 goto out; 1033 return ret;
1035 } 1034 }
1036 1035
1037 zone->present_pages += onlined_pages; 1036 zone->present_pages += onlined_pages;
@@ -1061,9 +1060,7 @@ int __ref online_pages(unsigned long pfn, unsigned long nr_pages, int online_typ
1061 1060
1062 if (onlined_pages) 1061 if (onlined_pages)
1063 memory_notify(MEM_ONLINE, &arg); 1062 memory_notify(MEM_ONLINE, &arg);
1064out: 1063 return 0;
1065 mem_hotplug_done();
1066 return ret;
1067} 1064}
1068#endif /* CONFIG_MEMORY_HOTPLUG_SPARSE */ 1065#endif /* CONFIG_MEMORY_HOTPLUG_SPARSE */
1069 1066
@@ -1688,21 +1685,18 @@ static int __ref __offline_pages(unsigned long start_pfn,
1688 if (!test_pages_in_a_zone(start_pfn, end_pfn)) 1685 if (!test_pages_in_a_zone(start_pfn, end_pfn))
1689 return -EINVAL; 1686 return -EINVAL;
1690 1687
1691 mem_hotplug_begin();
1692
1693 zone = page_zone(pfn_to_page(start_pfn)); 1688 zone = page_zone(pfn_to_page(start_pfn));
1694 node = zone_to_nid(zone); 1689 node = zone_to_nid(zone);
1695 nr_pages = end_pfn - start_pfn; 1690 nr_pages = end_pfn - start_pfn;
1696 1691
1697 ret = -EINVAL;
1698 if (zone_idx(zone) <= ZONE_NORMAL && !can_offline_normal(zone, nr_pages)) 1692 if (zone_idx(zone) <= ZONE_NORMAL && !can_offline_normal(zone, nr_pages))
1699 goto out; 1693 return -EINVAL;
1700 1694
1701 /* set above range as isolated */ 1695 /* set above range as isolated */
1702 ret = start_isolate_page_range(start_pfn, end_pfn, 1696 ret = start_isolate_page_range(start_pfn, end_pfn,
1703 MIGRATE_MOVABLE, true); 1697 MIGRATE_MOVABLE, true);
1704 if (ret) 1698 if (ret)
1705 goto out; 1699 return ret;
1706 1700
1707 arg.start_pfn = start_pfn; 1701 arg.start_pfn = start_pfn;
1708 arg.nr_pages = nr_pages; 1702 arg.nr_pages = nr_pages;
@@ -1795,7 +1789,6 @@ repeat:
1795 writeback_set_ratelimit(); 1789 writeback_set_ratelimit();
1796 1790
1797 memory_notify(MEM_OFFLINE, &arg); 1791 memory_notify(MEM_OFFLINE, &arg);
1798 mem_hotplug_done();
1799 return 0; 1792 return 0;
1800 1793
1801failed_removal: 1794failed_removal:
@@ -1805,12 +1798,10 @@ failed_removal:
1805 memory_notify(MEM_CANCEL_OFFLINE, &arg); 1798 memory_notify(MEM_CANCEL_OFFLINE, &arg);
1806 /* pushback to free area */ 1799 /* pushback to free area */
1807 undo_isolate_page_range(start_pfn, end_pfn, MIGRATE_MOVABLE); 1800 undo_isolate_page_range(start_pfn, end_pfn, MIGRATE_MOVABLE);
1808
1809out:
1810 mem_hotplug_done();
1811 return ret; 1801 return ret;
1812} 1802}
1813 1803
1804/* Must be protected by mem_hotplug_begin() */
1814int offline_pages(unsigned long start_pfn, unsigned long nr_pages) 1805int offline_pages(unsigned long start_pfn, unsigned long nr_pages)
1815{ 1806{
1816 return __offline_pages(start_pfn, start_pfn + nr_pages, 120 * HZ); 1807 return __offline_pages(start_pfn, start_pfn + nr_pages, 120 * HZ);