aboutsummaryrefslogtreecommitdiffstats
path: root/include/linux
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2016-10-03 22:43:08 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2016-10-03 22:43:08 -0400
commit597f03f9d133e9837d00965016170271d4f87dcf (patch)
tree33bdb5c1104d5b466387f4ae98748c5f4ddd29bb /include/linux
parent999dcbe2414e15e19cdc1f91497d01f262c6e1cf (diff)
parent0bf71e4d02ffec8ab9a6adecca61d3eed74fc99d (diff)
Merge branch 'smp-hotplug-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip
Pull CPU hotplug updates from Thomas Gleixner: "Yet another batch of cpu hotplug core updates and conversions: - Provide core infrastructure for multi instance drivers so the drivers do not have to keep custom lists. - Convert custom lists to the new infrastructure. The block-mq custom list conversion comes through the block tree and makes the diffstat tip over to more lines removed than added. - Handle unbalanced hotplug enable/disable calls more gracefully. - Remove the obsolete CPU_STARTING/DYING notifier support. - Convert another batch of notifier users. The relayfs changes which conflicted with the conversion have been shipped to me by Andrew. The remaining lot is targeted for 4.10 so that we finally can remove the rest of the notifiers" * 'smp-hotplug-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip: (46 commits) cpufreq: Fix up conversion to hotplug state machine blk/mq: Reserve hotplug states for block multiqueue x86/apic/uv: Convert to hotplug state machine s390/mm/pfault: Convert to hotplug state machine mips/loongson/smp: Convert to hotplug state machine mips/octeon/smp: Convert to hotplug state machine fault-injection/cpu: Convert to hotplug state machine padata: Convert to hotplug state machine cpufreq: Convert to hotplug state machine ACPI/processor: Convert to hotplug state machine virtio scsi: Convert to hotplug state machine oprofile/timer: Convert to hotplug state machine block/softirq: Convert to hotplug state machine lib/irq_poll: Convert to hotplug state machine x86/microcode: Convert to hotplug state machine sh/SH-X3 SMP: Convert to hotplug state machine ia64/mca: Convert to hotplug state machine ARM/OMAP/wakeupgen: Convert to hotplug state machine ARM/shmobile: Convert to hotplug state machine arm64/FP/SIMD: Convert to hotplug state machine ...
Diffstat (limited to 'include/linux')
-rw-r--r--include/linux/cpu.h12
-rw-r--r--include/linux/cpuhotplug.h136
-rw-r--r--include/linux/padata.h2
-rw-r--r--include/linux/perf/arm_pmu.h2
-rw-r--r--include/linux/relay.h23
-rw-r--r--include/linux/slab.h8
6 files changed, 158 insertions, 25 deletions
diff --git a/include/linux/cpu.h b/include/linux/cpu.h
index ad4f1f33a74e..7572d9e9dced 100644
--- a/include/linux/cpu.h
+++ b/include/linux/cpu.h
@@ -61,17 +61,8 @@ struct notifier_block;
61#define CPU_DOWN_PREPARE 0x0005 /* CPU (unsigned)v going down */ 61#define CPU_DOWN_PREPARE 0x0005 /* CPU (unsigned)v going down */
62#define CPU_DOWN_FAILED 0x0006 /* CPU (unsigned)v NOT going down */ 62#define CPU_DOWN_FAILED 0x0006 /* CPU (unsigned)v NOT going down */
63#define CPU_DEAD 0x0007 /* CPU (unsigned)v dead */ 63#define CPU_DEAD 0x0007 /* CPU (unsigned)v dead */
64#define CPU_DYING 0x0008 /* CPU (unsigned)v not running any task,
65 * not handling interrupts, soon dead.
66 * Called on the dying cpu, interrupts
67 * are already disabled. Must not
68 * sleep, must not fail */
69#define CPU_POST_DEAD 0x0009 /* CPU (unsigned)v dead, cpu_hotplug 64#define CPU_POST_DEAD 0x0009 /* CPU (unsigned)v dead, cpu_hotplug
70 * lock is dropped */ 65 * lock is dropped */
71#define CPU_STARTING 0x000A /* CPU (unsigned)v soon running.
72 * Called on the new cpu, just before
73 * enabling interrupts. Must not sleep,
74 * must not fail */
75#define CPU_BROKEN 0x000B /* CPU (unsigned)v did not die properly, 66#define CPU_BROKEN 0x000B /* CPU (unsigned)v did not die properly,
76 * perhaps due to preemption. */ 67 * perhaps due to preemption. */
77 68
@@ -86,9 +77,6 @@ struct notifier_block;
86#define CPU_DOWN_PREPARE_FROZEN (CPU_DOWN_PREPARE | CPU_TASKS_FROZEN) 77#define CPU_DOWN_PREPARE_FROZEN (CPU_DOWN_PREPARE | CPU_TASKS_FROZEN)
87#define CPU_DOWN_FAILED_FROZEN (CPU_DOWN_FAILED | CPU_TASKS_FROZEN) 78#define CPU_DOWN_FAILED_FROZEN (CPU_DOWN_FAILED | CPU_TASKS_FROZEN)
88#define CPU_DEAD_FROZEN (CPU_DEAD | CPU_TASKS_FROZEN) 79#define CPU_DEAD_FROZEN (CPU_DEAD | CPU_TASKS_FROZEN)
89#define CPU_DYING_FROZEN (CPU_DYING | CPU_TASKS_FROZEN)
90#define CPU_STARTING_FROZEN (CPU_STARTING | CPU_TASKS_FROZEN)
91
92 80
93#ifdef CONFIG_SMP 81#ifdef CONFIG_SMP
94extern bool cpuhp_tasks_frozen; 82extern bool cpuhp_tasks_frozen;
diff --git a/include/linux/cpuhotplug.h b/include/linux/cpuhotplug.h
index eb445a4e2a83..7b6c446ee17f 100644
--- a/include/linux/cpuhotplug.h
+++ b/include/linux/cpuhotplug.h
@@ -16,15 +16,40 @@ enum cpuhp_state {
16 CPUHP_PERF_SUPERH, 16 CPUHP_PERF_SUPERH,
17 CPUHP_X86_HPET_DEAD, 17 CPUHP_X86_HPET_DEAD,
18 CPUHP_X86_APB_DEAD, 18 CPUHP_X86_APB_DEAD,
19 CPUHP_VIRT_NET_DEAD,
20 CPUHP_SLUB_DEAD,
21 CPUHP_MM_WRITEBACK_DEAD,
22 CPUHP_SOFTIRQ_DEAD,
23 CPUHP_NET_MVNETA_DEAD,
24 CPUHP_CPUIDLE_DEAD,
25 CPUHP_ARM64_FPSIMD_DEAD,
26 CPUHP_ARM_OMAP_WAKE_DEAD,
27 CPUHP_IRQ_POLL_DEAD,
28 CPUHP_BLOCK_SOFTIRQ_DEAD,
29 CPUHP_VIRT_SCSI_DEAD,
30 CPUHP_ACPI_CPUDRV_DEAD,
31 CPUHP_S390_PFAULT_DEAD,
32 CPUHP_BLK_MQ_DEAD,
19 CPUHP_WORKQUEUE_PREP, 33 CPUHP_WORKQUEUE_PREP,
20 CPUHP_POWER_NUMA_PREPARE, 34 CPUHP_POWER_NUMA_PREPARE,
21 CPUHP_HRTIMERS_PREPARE, 35 CPUHP_HRTIMERS_PREPARE,
22 CPUHP_PROFILE_PREPARE, 36 CPUHP_PROFILE_PREPARE,
23 CPUHP_X2APIC_PREPARE, 37 CPUHP_X2APIC_PREPARE,
24 CPUHP_SMPCFD_PREPARE, 38 CPUHP_SMPCFD_PREPARE,
39 CPUHP_RELAY_PREPARE,
40 CPUHP_SLAB_PREPARE,
41 CPUHP_MD_RAID5_PREPARE,
25 CPUHP_RCUTREE_PREP, 42 CPUHP_RCUTREE_PREP,
43 CPUHP_CPUIDLE_COUPLED_PREPARE,
44 CPUHP_POWERPC_PMAC_PREPARE,
45 CPUHP_POWERPC_MMU_CTX_PREPARE,
26 CPUHP_NOTIFY_PREPARE, 46 CPUHP_NOTIFY_PREPARE,
47 CPUHP_ARM_SHMOBILE_SCU_PREPARE,
48 CPUHP_SH_SH3X_PREPARE,
49 CPUHP_BLK_MQ_PREPARE,
27 CPUHP_TIMERS_DEAD, 50 CPUHP_TIMERS_DEAD,
51 CPUHP_NOTF_ERR_INJ_PREPARE,
52 CPUHP_MIPS_SOC_PREPARE,
28 CPUHP_BRINGUP_CPU, 53 CPUHP_BRINGUP_CPU,
29 CPUHP_AP_IDLE_DEAD, 54 CPUHP_AP_IDLE_DEAD,
30 CPUHP_AP_OFFLINE, 55 CPUHP_AP_OFFLINE,
@@ -72,7 +97,6 @@ enum cpuhp_state {
72 CPUHP_AP_ARM64_ISNDEP_STARTING, 97 CPUHP_AP_ARM64_ISNDEP_STARTING,
73 CPUHP_AP_SMPCFD_DYING, 98 CPUHP_AP_SMPCFD_DYING,
74 CPUHP_AP_X86_TBOOT_DYING, 99 CPUHP_AP_X86_TBOOT_DYING,
75 CPUHP_AP_NOTIFY_STARTING,
76 CPUHP_AP_ONLINE, 100 CPUHP_AP_ONLINE,
77 CPUHP_TEARDOWN_CPU, 101 CPUHP_TEARDOWN_CPU,
78 CPUHP_AP_ONLINE_IDLE, 102 CPUHP_AP_ONLINE_IDLE,
@@ -103,7 +127,7 @@ enum cpuhp_state {
103 127
104int __cpuhp_setup_state(enum cpuhp_state state, const char *name, bool invoke, 128int __cpuhp_setup_state(enum cpuhp_state state, const char *name, bool invoke,
105 int (*startup)(unsigned int cpu), 129 int (*startup)(unsigned int cpu),
106 int (*teardown)(unsigned int cpu)); 130 int (*teardown)(unsigned int cpu), bool multi_instance);
107 131
108/** 132/**
109 * cpuhp_setup_state - Setup hotplug state callbacks with calling the callbacks 133 * cpuhp_setup_state - Setup hotplug state callbacks with calling the callbacks
@@ -120,7 +144,7 @@ static inline int cpuhp_setup_state(enum cpuhp_state state,
120 int (*startup)(unsigned int cpu), 144 int (*startup)(unsigned int cpu),
121 int (*teardown)(unsigned int cpu)) 145 int (*teardown)(unsigned int cpu))
122{ 146{
123 return __cpuhp_setup_state(state, name, true, startup, teardown); 147 return __cpuhp_setup_state(state, name, true, startup, teardown, false);
124} 148}
125 149
126/** 150/**
@@ -139,7 +163,66 @@ static inline int cpuhp_setup_state_nocalls(enum cpuhp_state state,
139 int (*startup)(unsigned int cpu), 163 int (*startup)(unsigned int cpu),
140 int (*teardown)(unsigned int cpu)) 164 int (*teardown)(unsigned int cpu))
141{ 165{
142 return __cpuhp_setup_state(state, name, false, startup, teardown); 166 return __cpuhp_setup_state(state, name, false, startup, teardown,
167 false);
168}
169
170/**
171 * cpuhp_setup_state_multi - Add callbacks for multi state
172 * @state: The state for which the calls are installed
173 * @name: Name of the callback.
174 * @startup: startup callback function
175 * @teardown: teardown callback function
176 *
177 * Sets the internal multi_instance flag and prepares a state to work as a multi
178 * instance callback. No callbacks are invoked at this point. The callbacks are
179 * invoked once an instance for this state are registered via
180 * @cpuhp_state_add_instance or @cpuhp_state_add_instance_nocalls.
181 */
182static inline int cpuhp_setup_state_multi(enum cpuhp_state state,
183 const char *name,
184 int (*startup)(unsigned int cpu,
185 struct hlist_node *node),
186 int (*teardown)(unsigned int cpu,
187 struct hlist_node *node))
188{
189 return __cpuhp_setup_state(state, name, false,
190 (void *) startup,
191 (void *) teardown, true);
192}
193
194int __cpuhp_state_add_instance(enum cpuhp_state state, struct hlist_node *node,
195 bool invoke);
196
197/**
198 * cpuhp_state_add_instance - Add an instance for a state and invoke startup
199 * callback.
200 * @state: The state for which the instance is installed
201 * @node: The node for this individual state.
202 *
203 * Installs the instance for the @state and invokes the startup callback on
204 * the present cpus which have already reached the @state. The @state must have
205 * been earlier marked as multi-instance by @cpuhp_setup_state_multi.
206 */
207static inline int cpuhp_state_add_instance(enum cpuhp_state state,
208 struct hlist_node *node)
209{
210 return __cpuhp_state_add_instance(state, node, true);
211}
212
213/**
214 * cpuhp_state_add_instance_nocalls - Add an instance for a state without
215 * invoking the startup callback.
216 * @state: The state for which the instance is installed
217 * @node: The node for this individual state.
218 *
219 * Installs the instance for the @state The @state must have been earlier
220 * marked as multi-instance by @cpuhp_setup_state_multi.
221 */
222static inline int cpuhp_state_add_instance_nocalls(enum cpuhp_state state,
223 struct hlist_node *node)
224{
225 return __cpuhp_state_add_instance(state, node, false);
143} 226}
144 227
145void __cpuhp_remove_state(enum cpuhp_state state, bool invoke); 228void __cpuhp_remove_state(enum cpuhp_state state, bool invoke);
@@ -166,6 +249,51 @@ static inline void cpuhp_remove_state_nocalls(enum cpuhp_state state)
166 __cpuhp_remove_state(state, false); 249 __cpuhp_remove_state(state, false);
167} 250}
168 251
252/**
253 * cpuhp_remove_multi_state - Remove hotplug multi state callback
254 * @state: The state for which the calls are removed
255 *
256 * Removes the callback functions from a multi state. This is the reverse of
257 * cpuhp_setup_state_multi(). All instances should have been removed before
258 * invoking this function.
259 */
260static inline void cpuhp_remove_multi_state(enum cpuhp_state state)
261{
262 __cpuhp_remove_state(state, false);
263}
264
265int __cpuhp_state_remove_instance(enum cpuhp_state state,
266 struct hlist_node *node, bool invoke);
267
268/**
269 * cpuhp_state_remove_instance - Remove hotplug instance from state and invoke
270 * the teardown callback
271 * @state: The state from which the instance is removed
272 * @node: The node for this individual state.
273 *
274 * Removes the instance and invokes the teardown callback on the present cpus
275 * which have already reached the @state.
276 */
277static inline int cpuhp_state_remove_instance(enum cpuhp_state state,
278 struct hlist_node *node)
279{
280 return __cpuhp_state_remove_instance(state, node, true);
281}
282
283/**
284 * cpuhp_state_remove_instance_nocalls - Remove hotplug instance from state
285 * without invoking the reatdown callback
286 * @state: The state from which the instance is removed
287 * @node: The node for this individual state.
288 *
289 * Removes the instance without invoking the teardown callback.
290 */
291static inline int cpuhp_state_remove_instance_nocalls(enum cpuhp_state state,
292 struct hlist_node *node)
293{
294 return __cpuhp_state_remove_instance(state, node, false);
295}
296
169#ifdef CONFIG_SMP 297#ifdef CONFIG_SMP
170void cpuhp_online_idle(enum cpuhp_state state); 298void cpuhp_online_idle(enum cpuhp_state state);
171#else 299#else
diff --git a/include/linux/padata.h b/include/linux/padata.h
index 113ee626a4dc..0f9e567d5e15 100644
--- a/include/linux/padata.h
+++ b/include/linux/padata.h
@@ -151,7 +151,7 @@ struct parallel_data {
151 * @flags: padata flags. 151 * @flags: padata flags.
152 */ 152 */
153struct padata_instance { 153struct padata_instance {
154 struct notifier_block cpu_notifier; 154 struct hlist_node node;
155 struct workqueue_struct *wq; 155 struct workqueue_struct *wq;
156 struct parallel_data *pd; 156 struct parallel_data *pd;
157 struct padata_cpumask cpumask; 157 struct padata_cpumask cpumask;
diff --git a/include/linux/perf/arm_pmu.h b/include/linux/perf/arm_pmu.h
index 9ff07d3fc8de..8462da266089 100644
--- a/include/linux/perf/arm_pmu.h
+++ b/include/linux/perf/arm_pmu.h
@@ -116,7 +116,7 @@ struct arm_pmu {
116 DECLARE_BITMAP(pmceid_bitmap, ARMV8_PMUV3_MAX_COMMON_EVENTS); 116 DECLARE_BITMAP(pmceid_bitmap, ARMV8_PMUV3_MAX_COMMON_EVENTS);
117 struct platform_device *plat_device; 117 struct platform_device *plat_device;
118 struct pmu_hw_events __percpu *hw_events; 118 struct pmu_hw_events __percpu *hw_events;
119 struct list_head entry; 119 struct hlist_node node;
120 struct notifier_block cpu_pm_nb; 120 struct notifier_block cpu_pm_nb;
121 /* the attr_groups array must be NULL-terminated */ 121 /* the attr_groups array must be NULL-terminated */
122 const struct attribute_group *attr_groups[ARMPMU_NR_ATTR_GROUPS + 1]; 122 const struct attribute_group *attr_groups[ARMPMU_NR_ATTR_GROUPS + 1];
diff --git a/include/linux/relay.h b/include/linux/relay.h
index d7c8359693c6..ecbb34a382b8 100644
--- a/include/linux/relay.h
+++ b/include/linux/relay.h
@@ -19,6 +19,7 @@
19#include <linux/fs.h> 19#include <linux/fs.h>
20#include <linux/poll.h> 20#include <linux/poll.h>
21#include <linux/kref.h> 21#include <linux/kref.h>
22#include <linux/percpu.h>
22 23
23/* 24/*
24 * Tracks changes to rchan/rchan_buf structs 25 * Tracks changes to rchan/rchan_buf structs
@@ -63,7 +64,7 @@ struct rchan
63 struct kref kref; /* channel refcount */ 64 struct kref kref; /* channel refcount */
64 void *private_data; /* for user-defined data */ 65 void *private_data; /* for user-defined data */
65 size_t last_toobig; /* tried to log event > subbuf size */ 66 size_t last_toobig; /* tried to log event > subbuf size */
66 struct rchan_buf *buf[NR_CPUS]; /* per-cpu channel buffers */ 67 struct rchan_buf ** __percpu buf; /* per-cpu channel buffers */
67 int is_global; /* One global buffer ? */ 68 int is_global; /* One global buffer ? */
68 struct list_head list; /* for channel list */ 69 struct list_head list; /* for channel list */
69 struct dentry *parent; /* parent dentry passed to open */ 70 struct dentry *parent; /* parent dentry passed to open */
@@ -204,7 +205,7 @@ static inline void relay_write(struct rchan *chan,
204 struct rchan_buf *buf; 205 struct rchan_buf *buf;
205 206
206 local_irq_save(flags); 207 local_irq_save(flags);
207 buf = chan->buf[smp_processor_id()]; 208 buf = *this_cpu_ptr(chan->buf);
208 if (unlikely(buf->offset + length > chan->subbuf_size)) 209 if (unlikely(buf->offset + length > chan->subbuf_size))
209 length = relay_switch_subbuf(buf, length); 210 length = relay_switch_subbuf(buf, length);
210 memcpy(buf->data + buf->offset, data, length); 211 memcpy(buf->data + buf->offset, data, length);
@@ -230,12 +231,12 @@ static inline void __relay_write(struct rchan *chan,
230{ 231{
231 struct rchan_buf *buf; 232 struct rchan_buf *buf;
232 233
233 buf = chan->buf[get_cpu()]; 234 buf = *get_cpu_ptr(chan->buf);
234 if (unlikely(buf->offset + length > buf->chan->subbuf_size)) 235 if (unlikely(buf->offset + length > buf->chan->subbuf_size))
235 length = relay_switch_subbuf(buf, length); 236 length = relay_switch_subbuf(buf, length);
236 memcpy(buf->data + buf->offset, data, length); 237 memcpy(buf->data + buf->offset, data, length);
237 buf->offset += length; 238 buf->offset += length;
238 put_cpu(); 239 put_cpu_ptr(chan->buf);
239} 240}
240 241
241/** 242/**
@@ -251,17 +252,19 @@ static inline void __relay_write(struct rchan *chan,
251 */ 252 */
252static inline void *relay_reserve(struct rchan *chan, size_t length) 253static inline void *relay_reserve(struct rchan *chan, size_t length)
253{ 254{
254 void *reserved; 255 void *reserved = NULL;
255 struct rchan_buf *buf = chan->buf[smp_processor_id()]; 256 struct rchan_buf *buf = *get_cpu_ptr(chan->buf);
256 257
257 if (unlikely(buf->offset + length > buf->chan->subbuf_size)) { 258 if (unlikely(buf->offset + length > buf->chan->subbuf_size)) {
258 length = relay_switch_subbuf(buf, length); 259 length = relay_switch_subbuf(buf, length);
259 if (!length) 260 if (!length)
260 return NULL; 261 goto end;
261 } 262 }
262 reserved = buf->data + buf->offset; 263 reserved = buf->data + buf->offset;
263 buf->offset += length; 264 buf->offset += length;
264 265
266end:
267 put_cpu_ptr(chan->buf);
265 return reserved; 268 return reserved;
266} 269}
267 270
@@ -285,5 +288,11 @@ static inline void subbuf_start_reserve(struct rchan_buf *buf,
285 */ 288 */
286extern const struct file_operations relay_file_operations; 289extern const struct file_operations relay_file_operations;
287 290
291#ifdef CONFIG_RELAY
292int relay_prepare_cpu(unsigned int cpu);
293#else
294#define relay_prepare_cpu NULL
295#endif
296
288#endif /* _LINUX_RELAY_H */ 297#endif /* _LINUX_RELAY_H */
289 298
diff --git a/include/linux/slab.h b/include/linux/slab.h
index 4293808d8cfb..084b12bad198 100644
--- a/include/linux/slab.h
+++ b/include/linux/slab.h
@@ -650,4 +650,12 @@ static inline void *kzalloc_node(size_t size, gfp_t flags, int node)
650unsigned int kmem_cache_size(struct kmem_cache *s); 650unsigned int kmem_cache_size(struct kmem_cache *s);
651void __init kmem_cache_init_late(void); 651void __init kmem_cache_init_late(void);
652 652
653#if defined(CONFIG_SMP) && defined(CONFIG_SLAB)
654int slab_prepare_cpu(unsigned int cpu);
655int slab_dead_cpu(unsigned int cpu);
656#else
657#define slab_prepare_cpu NULL
658#define slab_dead_cpu NULL
659#endif
660
653#endif /* _LINUX_SLAB_H */ 661#endif /* _LINUX_SLAB_H */