Skip to content

Commit 9e79c52

Browse files
committed
Merge branch 'smp-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip
Pull cpu/SMT fix from Ingo Molnar: "Fix a build bug on CONFIG_HOTPLUG_SMT=y && !CONFIG_SYSFS kernels" * 'smp-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip: cpu/SMT: Fix x86 link error without CONFIG_SYSFS
2 parents a186c11 + dc8d37e commit 9e79c52

File tree

1 file changed

+72
-71
lines changed

1 file changed

+72
-71
lines changed

kernel/cpu.c

Lines changed: 72 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -1909,6 +1909,78 @@ void __cpuhp_remove_state(enum cpuhp_state state, bool invoke)
19091909
}
19101910
EXPORT_SYMBOL(__cpuhp_remove_state);
19111911

1912+
#ifdef CONFIG_HOTPLUG_SMT
1913+
static void cpuhp_offline_cpu_device(unsigned int cpu)
1914+
{
1915+
struct device *dev = get_cpu_device(cpu);
1916+
1917+
dev->offline = true;
1918+
/* Tell user space about the state change */
1919+
kobject_uevent(&dev->kobj, KOBJ_OFFLINE);
1920+
}
1921+
1922+
static void cpuhp_online_cpu_device(unsigned int cpu)
1923+
{
1924+
struct device *dev = get_cpu_device(cpu);
1925+
1926+
dev->offline = false;
1927+
/* Tell user space about the state change */
1928+
kobject_uevent(&dev->kobj, KOBJ_ONLINE);
1929+
}
1930+
1931+
int cpuhp_smt_disable(enum cpuhp_smt_control ctrlval)
1932+
{
1933+
int cpu, ret = 0;
1934+
1935+
cpu_maps_update_begin();
1936+
for_each_online_cpu(cpu) {
1937+
if (topology_is_primary_thread(cpu))
1938+
continue;
1939+
ret = cpu_down_maps_locked(cpu, CPUHP_OFFLINE);
1940+
if (ret)
1941+
break;
1942+
/*
1943+
* As this needs to hold the cpu maps lock it's impossible
1944+
* to call device_offline() because that ends up calling
1945+
* cpu_down() which takes cpu maps lock. cpu maps lock
1946+
* needs to be held as this might race against in kernel
1947+
* abusers of the hotplug machinery (thermal management).
1948+
*
1949+
* So nothing would update device:offline state. That would
1950+
* leave the sysfs entry stale and prevent onlining after
1951+
* smt control has been changed to 'off' again. This is
1952+
* called under the sysfs hotplug lock, so it is properly
1953+
* serialized against the regular offline usage.
1954+
*/
1955+
cpuhp_offline_cpu_device(cpu);
1956+
}
1957+
if (!ret)
1958+
cpu_smt_control = ctrlval;
1959+
cpu_maps_update_done();
1960+
return ret;
1961+
}
1962+
1963+
int cpuhp_smt_enable(void)
1964+
{
1965+
int cpu, ret = 0;
1966+
1967+
cpu_maps_update_begin();
1968+
cpu_smt_control = CPU_SMT_ENABLED;
1969+
for_each_present_cpu(cpu) {
1970+
/* Skip online CPUs and CPUs on offline nodes */
1971+
if (cpu_online(cpu) || !node_online(cpu_to_node(cpu)))
1972+
continue;
1973+
ret = _cpu_up(cpu, 0, CPUHP_ONLINE);
1974+
if (ret)
1975+
break;
1976+
/* See comment in cpuhp_smt_disable() */
1977+
cpuhp_online_cpu_device(cpu);
1978+
}
1979+
cpu_maps_update_done();
1980+
return ret;
1981+
}
1982+
#endif
1983+
19121984
#if defined(CONFIG_SYSFS) && defined(CONFIG_HOTPLUG_CPU)
19131985
static ssize_t show_cpuhp_state(struct device *dev,
19141986
struct device_attribute *attr, char *buf)
@@ -2063,77 +2135,6 @@ static const struct attribute_group cpuhp_cpu_root_attr_group = {
20632135

20642136
#ifdef CONFIG_HOTPLUG_SMT
20652137

2066-
static void cpuhp_offline_cpu_device(unsigned int cpu)
2067-
{
2068-
struct device *dev = get_cpu_device(cpu);
2069-
2070-
dev->offline = true;
2071-
/* Tell user space about the state change */
2072-
kobject_uevent(&dev->kobj, KOBJ_OFFLINE);
2073-
}
2074-
2075-
static void cpuhp_online_cpu_device(unsigned int cpu)
2076-
{
2077-
struct device *dev = get_cpu_device(cpu);
2078-
2079-
dev->offline = false;
2080-
/* Tell user space about the state change */
2081-
kobject_uevent(&dev->kobj, KOBJ_ONLINE);
2082-
}
2083-
2084-
int cpuhp_smt_disable(enum cpuhp_smt_control ctrlval)
2085-
{
2086-
int cpu, ret = 0;
2087-
2088-
cpu_maps_update_begin();
2089-
for_each_online_cpu(cpu) {
2090-
if (topology_is_primary_thread(cpu))
2091-
continue;
2092-
ret = cpu_down_maps_locked(cpu, CPUHP_OFFLINE);
2093-
if (ret)
2094-
break;
2095-
/*
2096-
* As this needs to hold the cpu maps lock it's impossible
2097-
* to call device_offline() because that ends up calling
2098-
* cpu_down() which takes cpu maps lock. cpu maps lock
2099-
* needs to be held as this might race against in kernel
2100-
* abusers of the hotplug machinery (thermal management).
2101-
*
2102-
* So nothing would update device:offline state. That would
2103-
* leave the sysfs entry stale and prevent onlining after
2104-
* smt control has been changed to 'off' again. This is
2105-
* called under the sysfs hotplug lock, so it is properly
2106-
* serialized against the regular offline usage.
2107-
*/
2108-
cpuhp_offline_cpu_device(cpu);
2109-
}
2110-
if (!ret)
2111-
cpu_smt_control = ctrlval;
2112-
cpu_maps_update_done();
2113-
return ret;
2114-
}
2115-
2116-
int cpuhp_smt_enable(void)
2117-
{
2118-
int cpu, ret = 0;
2119-
2120-
cpu_maps_update_begin();
2121-
cpu_smt_control = CPU_SMT_ENABLED;
2122-
for_each_present_cpu(cpu) {
2123-
/* Skip online CPUs and CPUs on offline nodes */
2124-
if (cpu_online(cpu) || !node_online(cpu_to_node(cpu)))
2125-
continue;
2126-
ret = _cpu_up(cpu, 0, CPUHP_ONLINE);
2127-
if (ret)
2128-
break;
2129-
/* See comment in cpuhp_smt_disable() */
2130-
cpuhp_online_cpu_device(cpu);
2131-
}
2132-
cpu_maps_update_done();
2133-
return ret;
2134-
}
2135-
2136-
21372138
static ssize_t
21382139
__store_smt_control(struct device *dev, struct device_attribute *attr,
21392140
const char *buf, size_t count)

0 commit comments

Comments
 (0)