diff options
Diffstat (limited to 'kernel/cpuset.c')
-rw-r--r-- | kernel/cpuset.c | 42 |
1 files changed, 32 insertions, 10 deletions
diff --git a/kernel/cpuset.c b/kernel/cpuset.c index 86ea9e34e326..798b3ab054eb 100644 --- a/kernel/cpuset.c +++ b/kernel/cpuset.c | |||
@@ -797,8 +797,10 @@ static int update_cpumask(struct cpuset *cs, char *buf) | |||
797 | retval = cpulist_parse(buf, trialcs.cpus_allowed); | 797 | retval = cpulist_parse(buf, trialcs.cpus_allowed); |
798 | if (retval < 0) | 798 | if (retval < 0) |
799 | return retval; | 799 | return retval; |
800 | |||
801 | if (!cpus_subset(trialcs.cpus_allowed, cpu_online_map)) | ||
802 | return -EINVAL; | ||
800 | } | 803 | } |
801 | cpus_and(trialcs.cpus_allowed, trialcs.cpus_allowed, cpu_online_map); | ||
802 | retval = validate_change(cs, &trialcs); | 804 | retval = validate_change(cs, &trialcs); |
803 | if (retval < 0) | 805 | if (retval < 0) |
804 | return retval; | 806 | return retval; |
@@ -932,9 +934,11 @@ static int update_nodemask(struct cpuset *cs, char *buf) | |||
932 | retval = nodelist_parse(buf, trialcs.mems_allowed); | 934 | retval = nodelist_parse(buf, trialcs.mems_allowed); |
933 | if (retval < 0) | 935 | if (retval < 0) |
934 | goto done; | 936 | goto done; |
937 | |||
938 | if (!nodes_subset(trialcs.mems_allowed, | ||
939 | node_states[N_HIGH_MEMORY])) | ||
940 | return -EINVAL; | ||
935 | } | 941 | } |
936 | nodes_and(trialcs.mems_allowed, trialcs.mems_allowed, | ||
937 | node_states[N_HIGH_MEMORY]); | ||
938 | oldmem = cs->mems_allowed; | 942 | oldmem = cs->mems_allowed; |
939 | if (nodes_equal(oldmem, trialcs.mems_allowed)) { | 943 | if (nodes_equal(oldmem, trialcs.mems_allowed)) { |
940 | retval = 0; /* Too easy - nothing to do */ | 944 | retval = 0; /* Too easy - nothing to do */ |
@@ -1033,8 +1037,8 @@ int current_cpuset_is_being_rebound(void) | |||
1033 | 1037 | ||
1034 | static int update_relax_domain_level(struct cpuset *cs, s64 val) | 1038 | static int update_relax_domain_level(struct cpuset *cs, s64 val) |
1035 | { | 1039 | { |
1036 | if ((int)val < 0) | 1040 | if (val < -1 || val >= SD_LV_MAX) |
1037 | val = -1; | 1041 | return -EINVAL; |
1038 | 1042 | ||
1039 | if (val != cs->relax_domain_level) { | 1043 | if (val != cs->relax_domain_level) { |
1040 | cs->relax_domain_level = val; | 1044 | cs->relax_domain_level = val; |
@@ -1878,7 +1882,7 @@ static void scan_for_empty_cpusets(const struct cpuset *root) | |||
1878 | * in order to minimize text size. | 1882 | * in order to minimize text size. |
1879 | */ | 1883 | */ |
1880 | 1884 | ||
1881 | static void common_cpu_mem_hotplug_unplug(void) | 1885 | static void common_cpu_mem_hotplug_unplug(int rebuild_sd) |
1882 | { | 1886 | { |
1883 | cgroup_lock(); | 1887 | cgroup_lock(); |
1884 | 1888 | ||
@@ -1886,6 +1890,13 @@ static void common_cpu_mem_hotplug_unplug(void) | |||
1886 | top_cpuset.mems_allowed = node_states[N_HIGH_MEMORY]; | 1890 | top_cpuset.mems_allowed = node_states[N_HIGH_MEMORY]; |
1887 | scan_for_empty_cpusets(&top_cpuset); | 1891 | scan_for_empty_cpusets(&top_cpuset); |
1888 | 1892 | ||
1893 | /* | ||
1894 | * Scheduler destroys domains on hotplug events. | ||
1895 | * Rebuild them based on the current settings. | ||
1896 | */ | ||
1897 | if (rebuild_sd) | ||
1898 | rebuild_sched_domains(); | ||
1899 | |||
1889 | cgroup_unlock(); | 1900 | cgroup_unlock(); |
1890 | } | 1901 | } |
1891 | 1902 | ||
@@ -1902,11 +1913,22 @@ static void common_cpu_mem_hotplug_unplug(void) | |||
1902 | static int cpuset_handle_cpuhp(struct notifier_block *unused_nb, | 1913 | static int cpuset_handle_cpuhp(struct notifier_block *unused_nb, |
1903 | unsigned long phase, void *unused_cpu) | 1914 | unsigned long phase, void *unused_cpu) |
1904 | { | 1915 | { |
1905 | if (phase == CPU_DYING || phase == CPU_DYING_FROZEN) | 1916 | switch (phase) { |
1917 | case CPU_UP_CANCELED: | ||
1918 | case CPU_UP_CANCELED_FROZEN: | ||
1919 | case CPU_DOWN_FAILED: | ||
1920 | case CPU_DOWN_FAILED_FROZEN: | ||
1921 | case CPU_ONLINE: | ||
1922 | case CPU_ONLINE_FROZEN: | ||
1923 | case CPU_DEAD: | ||
1924 | case CPU_DEAD_FROZEN: | ||
1925 | common_cpu_mem_hotplug_unplug(1); | ||
1926 | break; | ||
1927 | default: | ||
1906 | return NOTIFY_DONE; | 1928 | return NOTIFY_DONE; |
1929 | } | ||
1907 | 1930 | ||
1908 | common_cpu_mem_hotplug_unplug(); | 1931 | return NOTIFY_OK; |
1909 | return 0; | ||
1910 | } | 1932 | } |
1911 | 1933 | ||
1912 | #ifdef CONFIG_MEMORY_HOTPLUG | 1934 | #ifdef CONFIG_MEMORY_HOTPLUG |
@@ -1919,7 +1941,7 @@ static int cpuset_handle_cpuhp(struct notifier_block *unused_nb, | |||
1919 | 1941 | ||
1920 | void cpuset_track_online_nodes(void) | 1942 | void cpuset_track_online_nodes(void) |
1921 | { | 1943 | { |
1922 | common_cpu_mem_hotplug_unplug(); | 1944 | common_cpu_mem_hotplug_unplug(0); |
1923 | } | 1945 | } |
1924 | #endif | 1946 | #endif |
1925 | 1947 | ||