1
2#ifndef __LINUX_SMP_H
3#define __LINUX_SMP_H
4
5
6
7
8
9
10#include <linux/errno.h>
11#include <linux/types.h>
12#include <linux/list.h>
13#include <linux/cpumask.h>
14#include <linux/init.h>
15#include <linux/smp_types.h>
16
17typedef void (*smp_call_func_t)(void *info);
18typedef bool (*smp_cond_func_t)(int cpu, void *info);
19
20
21
22
23struct __call_single_data {
24 struct __call_single_node node;
25 smp_call_func_t func;
26 void *info;
27};
28
29#define CSD_INIT(_func, _info) \
30 (struct __call_single_data){ .func = (_func), .info = (_info), }
31
32
33typedef struct __call_single_data call_single_data_t
34 __aligned(sizeof(struct __call_single_data));
35
36#define INIT_CSD(_csd, _func, _info) \
37do { \
38 *(_csd) = CSD_INIT((_func), (_info)); \
39} while (0)
40
41
42
43
44
45extern void __smp_call_single_queue(int cpu, struct llist_node *node);
46
47
48extern unsigned int total_cpus;
49
50int smp_call_function_single(int cpuid, smp_call_func_t func, void *info,
51 int wait);
52
53void on_each_cpu_cond_mask(smp_cond_func_t cond_func, smp_call_func_t func,
54 void *info, bool wait, const struct cpumask *mask);
55
56int smp_call_function_single_async(int cpu, struct __call_single_data *csd);
57
58
59
60
61
62void panic_smp_self_stop(void);
63void nmi_panic_self_stop(struct pt_regs *regs);
64void crash_smp_send_stop(void);
65
66
67
68
69static inline void on_each_cpu(smp_call_func_t func, void *info, int wait)
70{
71 on_each_cpu_cond_mask(NULL, func, info, wait, cpu_online_mask);
72}
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90static inline void on_each_cpu_mask(const struct cpumask *mask,
91 smp_call_func_t func, void *info, bool wait)
92{
93 on_each_cpu_cond_mask(NULL, func, info, wait, mask);
94}
95
96
97
98
99
100
101
102static inline void on_each_cpu_cond(smp_cond_func_t cond_func,
103 smp_call_func_t func, void *info, bool wait)
104{
105 on_each_cpu_cond_mask(cond_func, func, info, wait, cpu_online_mask);
106}
107
108#ifdef CONFIG_SMP
109
110#include <linux/preempt.h>
111#include <linux/kernel.h>
112#include <linux/compiler.h>
113#include <linux/thread_info.h>
114#include <asm/smp.h>
115
116
117
118
119
120
121
122
123
124extern void smp_send_stop(void);
125
126
127
128
129extern void smp_send_reschedule(int cpu);
130
131
132
133
134
135extern void smp_prepare_cpus(unsigned int max_cpus);
136
137
138
139
140extern int __cpu_up(unsigned int cpunum, struct task_struct *tidle);
141
142
143
144
145extern void smp_cpus_done(unsigned int max_cpus);
146
147
148
149
150void smp_call_function(smp_call_func_t func, void *info, int wait);
151void smp_call_function_many(const struct cpumask *mask,
152 smp_call_func_t func, void *info, bool wait);
153
154int smp_call_function_any(const struct cpumask *mask,
155 smp_call_func_t func, void *info, int wait);
156
157void kick_all_cpus_sync(void);
158void wake_up_all_idle_cpus(void);
159
160
161
162
163void __init call_function_init(void);
164void generic_smp_call_function_single_interrupt(void);
165#define generic_smp_call_function_interrupt \
166 generic_smp_call_function_single_interrupt
167
168
169
170
171
172void smp_prepare_boot_cpu(void);
173
174extern unsigned int setup_max_cpus;
175extern void __init setup_nr_cpu_ids(void);
176extern void __init smp_init(void);
177
178extern int __boot_cpu_id;
179
180static inline int get_boot_cpu_id(void)
181{
182 return __boot_cpu_id;
183}
184
185#else
186
187static inline void smp_send_stop(void) { }
188
189
190
191
192#define raw_smp_processor_id() 0
193static inline void up_smp_call_function(smp_call_func_t func, void *info)
194{
195}
196#define smp_call_function(func, info, wait) \
197 (up_smp_call_function(func, info))
198
199static inline void smp_send_reschedule(int cpu) { }
200#define smp_prepare_boot_cpu() do {} while (0)
201#define smp_call_function_many(mask, func, info, wait) \
202 (up_smp_call_function(func, info))
203static inline void call_function_init(void) { }
204
205static inline int
206smp_call_function_any(const struct cpumask *mask, smp_call_func_t func,
207 void *info, int wait)
208{
209 return smp_call_function_single(0, func, info, wait);
210}
211
212static inline void kick_all_cpus_sync(void) { }
213static inline void wake_up_all_idle_cpus(void) { }
214
215#ifdef CONFIG_UP_LATE_INIT
216extern void __init up_late_init(void);
217static inline void smp_init(void) { up_late_init(); }
218#else
219static inline void smp_init(void) { }
220#endif
221
222static inline int get_boot_cpu_id(void)
223{
224 return 0;
225}
226
227#endif
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257#ifndef __smp_processor_id
258#define __smp_processor_id(x) raw_smp_processor_id(x)
259#endif
260
261#ifdef CONFIG_DEBUG_PREEMPT
262 extern unsigned int debug_smp_processor_id(void);
263# define smp_processor_id() debug_smp_processor_id()
264#else
265# define smp_processor_id() __smp_processor_id()
266#endif
267
268#define get_cpu() ({ preempt_disable(); __smp_processor_id(); })
269#define put_cpu() preempt_enable()
270
271
272
273
274
275extern void arch_disable_smp_support(void);
276
277extern void arch_thaw_secondary_cpus_begin(void);
278extern void arch_thaw_secondary_cpus_end(void);
279
280void smp_setup_processor_id(void);
281
282int smp_call_on_cpu(unsigned int cpu, int (*func)(void *), void *par,
283 bool phys);
284
285
286int smpcfd_prepare_cpu(unsigned int cpu);
287int smpcfd_dead_cpu(unsigned int cpu);
288int smpcfd_dying_cpu(unsigned int cpu);
289
290#endif
291