Commit e13fe8695c57fed678877a9f3f8e99fc637ff4fb

Authored by Wen Congyang
Committed by Linus Torvalds
1 parent 76bba1423f

cpu-hotplug,memory-hotplug: clear cpu_to_node() when offlining the node

When the node is offlined, there is no memory/cpu on the node.  If a
sleep task runs on a cpu of this node, it will be migrated to the cpu on
the other node.  So we can clear cpu-to-node mapping.

[akpm@linux-foundation.org: numa_clear_node() and numa_set_node() can no longer be __cpuinit]
Signed-off-by: Wen Congyang <wency@cn.fujitsu.com>
Signed-off-by: Tang Chen <tangchen@cn.fujitsu.com>
Cc: Yasuaki Ishimatsu <isimatu.yasuaki@jp.fujitsu.com>
Cc: David Rientjes <rientjes@google.com>
Cc: Jiang Liu <liuj97@gmail.com>
Cc: Minchan Kim <minchan.kim@gmail.com>
Cc: KOSAKI Motohiro <kosaki.motohiro@jp.fujitsu.com>
Cc: Mel Gorman <mel@csn.ul.ie>
Cc: Thomas Gleixner <tglx@linutronix.de>
Cc: Ingo Molnar <mingo@redhat.com>
Cc: "H. Peter Anvin" <hpa@zytor.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>

Showing 3 changed files with 33 additions and 5 deletions Side-by-side Diff

arch/x86/include/asm/numa.h
... ... @@ -57,8 +57,8 @@
57 57 #endif
58 58  
59 59 #ifdef CONFIG_NUMA
60   -extern void __cpuinit numa_set_node(int cpu, int node);
61   -extern void __cpuinit numa_clear_node(int cpu);
  60 +extern void numa_set_node(int cpu, int node);
  61 +extern void numa_clear_node(int cpu);
62 62 extern void __init init_cpu_to_node(void);
63 63 extern void __cpuinit numa_add_cpu(int cpu);
64 64 extern void __cpuinit numa_remove_cpu(int cpu);
... ... @@ -78,7 +78,7 @@
78 78 DEFINE_EARLY_PER_CPU(int, x86_cpu_to_node_map, NUMA_NO_NODE);
79 79 EXPORT_EARLY_PER_CPU_SYMBOL(x86_cpu_to_node_map);
80 80  
81   -void __cpuinit numa_set_node(int cpu, int node)
  81 +void numa_set_node(int cpu, int node)
82 82 {
83 83 int *cpu_to_node_map = early_per_cpu_ptr(x86_cpu_to_node_map);
84 84  
... ... @@ -101,7 +101,7 @@
101 101 set_cpu_numa_node(cpu, node);
102 102 }
103 103  
104   -void __cpuinit numa_clear_node(int cpu)
  104 +void numa_clear_node(int cpu)
105 105 {
106 106 numa_set_node(cpu, NUMA_NO_NODE);
107 107 }
... ... @@ -1705,6 +1705,34 @@
1705 1705 return 0;
1706 1706 }
1707 1707  
  1708 +static void unmap_cpu_on_node(void *data)
  1709 +{
  1710 +#ifdef CONFIG_ACPI_NUMA
  1711 + struct pglist_data *pgdat = data;
  1712 + int cpu;
  1713 +
  1714 + for_each_possible_cpu(cpu)
  1715 + if (cpu_to_node(cpu) == pgdat->node_id)
  1716 + numa_clear_node(cpu);
  1717 +#endif
  1718 +}
  1719 +
  1720 +static int check_and_unmap_cpu_on_node(void *data)
  1721 +{
  1722 + int ret = check_cpu_on_node(data);
  1723 +
  1724 + if (ret)
  1725 + return ret;
  1726 +
  1727 + /*
  1728 + * the node will be offlined when we come here, so we can clear
  1729 + * the cpu_to_node() now.
  1730 + */
  1731 +
  1732 + unmap_cpu_on_node(data);
  1733 + return 0;
  1734 +}
  1735 +
1708 1736 /* offline the node if all memory sections of this node are removed */
1709 1737 void try_offline_node(int nid)
1710 1738 {
... ... @@ -1731,7 +1759,7 @@
1731 1759 return;
1732 1760 }
1733 1761  
1734   - if (stop_machine(check_cpu_on_node, pgdat, NULL))
  1762 + if (stop_machine(check_and_unmap_cpu_on_node, pgdat, NULL))
1735 1763 return;
1736 1764  
1737 1765 /*