FreeBSD/Linux Kernel Cross Reference
sys/kern/processor.h
1 /*
2 * Mach Operating System
3 * Copyright (c) 1993,1992,1991,1990,1989 Carnegie Mellon University
4 * All Rights Reserved.
5 *
6 * Permission to use, copy, modify and distribute this software and its
7 * documentation is hereby granted, provided that both the copyright
8 * notice and this permission notice appear in all copies of the
9 * software, derivative works or modified versions, and any portions
10 * thereof, and that both notices appear in supporting documentation.
11 *
12 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
13 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
14 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
15 *
16 * Carnegie Mellon requests users of this software to return to
17 *
18 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
19 * School of Computer Science
20 * Carnegie Mellon University
21 * Pittsburgh PA 15213-3890
22 *
23 * any improvements or extensions that they make and grant Carnegie Mellon
24 * the rights to redistribute these changes.
25 */
26 /*
27 * HISTORY
28 * $Log: processor.h,v $
29 * Revision 2.8 93/11/17 17:18:50 dbg
30 * Use runq pointers in processor if NCPUS > 1 - processor_shutdown
31 * does not depend on MACH_HOST.
32 * [93/07/21 dbg]
33 *
34 * Document changed locking hierarchy.
35 * [93/06/01 dbg]
36 *
37 * Remove max_priority. Limits for per-policy scheduling
38 * parameters are in the run queue structures.
39 * [93/05/10 dbg]
40 *
41 * Changed to more flexible run queue structure. It also doubles
42 * as a list of enabled scheduling policies.
43 * [93/04/08 dbg]
44 *
45 * Always enable fixed-priority threads.
46 * [93/03/27 dbg]
47 *
48 * Include kern/run_queues.h for run queue definitions. Include
49 * kern/sched_policy.h for scheduler policy structure. Move
50 * check_processor_set and check_bound_processor macros here.
51 * [93/01/28 dbg]
52 *
53 * Revision 2.7 93/01/14 17:35:59 danner
54 * Removed definitions moved to kern/kern_types.h
55 * [93/01/12 14:50:37 danner]
56 *
57 * Moved actual declarations of struct processor, processor_t,
58 * struct processor_set, processor_set_t to kern/kern_types.h to
59 * permit mutually recursive structure definitions. Finished
60 * adding ANSI function prototypes.
61 * [92/12/28 dbg]
62 * Added separate pset_ref_lock, only governing reference count, to
63 * fix lock ordering to avoid deadlocks. Documented locking hierarchy.
64 * Added prototypes for pset functions.
65 * [92/10/28 dbg]
66 *
67 * Revision 2.6 91/05/14 16:45:38 mrt
68 * Correcting copyright
69 *
70 * Revision 2.5 91/02/05 17:28:34 mrt
71 * Changed to new Mach copyright
72 * [91/02/01 16:16:14 mrt]
73 *
74 * Revision 2.4 90/09/09 14:32:32 rpd
75 * Use decl_simple_lock_data.
76 * [90/08/30 rpd]
77 *
78 * Revision 2.3 90/08/07 17:58:42 rpd
79 * Added processor_set_name_array_t.
80 * [90/08/07 rpd]
81 *
82 * Revision 2.2 90/06/02 14:55:39 rpd
83 * Created for new host/processor technology.
84 * [90/03/26 23:50:00 rpd]
85 *
86 * Merge to X96
87 * [89/08/02 23:01:16 dlb]
88 *
89 * Add quantum_adj_lock to pset structure. Enclose some fields
90 * in NCPUS > 1 conditionals.
91 * [89/06/15 dlb]
92 *
93 * Add all_psets_count declaration.
94 * [89/06/09 dlb]
95 *
96 * Add processor_set_array_t.
97 * [89/06/08 dlb]
98 *
99 * Add max_priority, policies fields to processor_set structure.
100 * [89/05/12 dlb]
101 * Add load factor/average fields to processor set structure.
102 * [89/02/09 dlb]
103 *
104 * Revision 2.5 89/11/20 11:23:50 mja
105 * Put policies field under MACH_FIXPRI conditional.
106 * [89/11/10 dlb]
107 *
108 * Revision 2.4 89/10/15 02:05:13 rpd
109 * Minor cleanups.
110 *
111 * Revision 2.3 89/10/12 21:34:28 dlb
112 * Get ast_check_t from machine/ast_types.h instead of machine/ast.h
113 * [89/10/12 dlb]
114 *
115 * Revision 2.2 89/10/11 14:20:44 dlb
116 * Add remote ast check support for multiprocessors.
117 * Add quantum_adj_lock to pset structure. Enclose some fields
118 * in NCPUS > 1 conditionals.
119 * Add max_priority, policies fields to processor_set structure.
120 * Add load factor/average fields to processor set structure.
121 *
122 * 27-Sep-88 David Black (dlb) at Carnegie-Mellon University
123 * Created.
124 *
125 */
126
127 /*
128 * processor.h: Processor and processor-set definitions.
129 */
130
131 #ifndef _KERN_PROCESSOR_H_
132 #define _KERN_PROCESSOR_H_
133
134 /*
135 * Data structures for managing processors and sets of processors.
136 */
137
138 #include <cpus.h>
139 #include <mach_host.h>
140 #include <mach_io_binding.h>
141
142 #include <mach/boolean.h>
143 #include <mach/kern_return.h>
144 #include <mach/port.h>
145 #include <mach/processor_info.h>
146 #include <kern/cpu_number.h>
147 #include <kern/kern_types.h>
148 #include <kern/lock.h>
149 #include <kern/queue.h>
150 #include <kern/run_queues.h>
151 #include <kern/sched_policy.h>
152 #include <kern/host.h>
153
154 #if NCPUS > 1
155 #include <machine/ast_types.h>
156 #endif /* NCPUS > 1 */
157
158 /*
159 * Scheduler load factor (sched_load) is a scaled fixed-point number.
160 */
161 #define SCHED_SCALE 128
162 #define SCHED_SHIFT 7
163
164 struct processor_set {
165 struct run_queue_head runq; /* runq for this set */
166 #if NCPUS > 1
167 queue_head_t idle_queue; /* idle processors */
168 #endif
169 int idle_count; /* how many ? */
170 decl_simple_lock_data(, idle_lock) /* lock for above */
171 queue_head_t processors; /* all processors here */
172 int processor_count; /* how many ? */
173 boolean_t empty; /* true if no processors */
174 queue_head_t tasks; /* tasks assigned */
175 int task_count; /* how many */
176 queue_head_t threads; /* threads in this set */
177 int thread_count; /* how many */
178 int ref_count; /* structure ref count */
179 decl_simple_lock_data(, ref_lock) /* lock for ref count */
180 queue_chain_t all_psets; /* link for all_psets */
181 boolean_t active; /* is pset in use */
182 decl_simple_lock_data(, lock) /* lock for everything else */
183 struct ipc_port * pset_self; /* port for operations */
184 struct ipc_port * pset_name_self; /* port for information */
185 int set_quantum; /* current default quantum */
186 #if NCPUS > 1
187 int quantum_adj_index; /* runtime quantum adj. */
188 decl_simple_lock_data(, quantum_adj_lock) /* lock for above */
189 int machine_quantum[NCPUS+1]; /* ditto */
190 #endif /* NCPUS > 1 */
191 long mach_factor; /* mach_factor */
192 long load_average; /* load_average */
193 long sched_load; /* load avg for scheduler */
194 };
195
196 extern struct processor_set default_pset;
197
198 struct processor {
199 #if MACH_IO_BINDING
200 struct run_queue_head runq; /* local runq for this processor */
201 #else
202 #if NCPUS > 1
203 struct run_queue_head runq; /* copy of runq pointers for this
204 processor: count and lock are
205 not used */
206 #endif /* NCPUS > 1 */
207 #endif /* MACH_IO_BINDING */
208 queue_chain_t processor_queue; /* idle/assign/shutdown queue link */
209 int state; /* See below */
210 thread_t next_thread; /* next thread to run if dispatched */
211 thread_t idle_thread; /* this processor's idle thread. */
212 int quantum; /* quantum for current thread */
213 boolean_t first_quantum; /* first quantum in succession */
214 int last_quantum; /* last quantum assigned */
215
216 processor_set_t processor_set; /* processor set I belong to */
217 processor_set_t processor_set_next; /* set I will belong to */
218 queue_chain_t processors; /* all processors in set */
219 decl_simple_lock_data(, lock)
220 struct ipc_port *processor_self; /* port for operations */
221 int slot_num; /* machine-indep slot number */
222 #if NCPUS > 1
223 ast_check_t ast_check_data; /* for remote ast_check invocation */
224 #endif /* NCPUS > 1 */
225 /* punt id data temporarily */
226 };
227
228 extern struct processor processor_array[NCPUS];
229
230 /*
231 * Chain of all processor sets.
232 */
233 extern queue_head_t all_psets;
234 extern int all_psets_count;
235 decl_simple_lock_data(extern, all_psets_lock);
236
237 /*
238 * The lock ordering is:
239 *
240 * all_psets_lock task_lock
241 * | |
242 * | +---------------+
243 * | |
244 * | V
245 * | thread_lock
246 * | |
247 * +---------------+
248 * |
249 * V
250 * pset_lock
251 * |
252 * +-----------+---------------+---------------+
253 * | | | |
254 * | | V |
255 * | | pset_self->ip_lock |
256 * | | | |
257 * | | V V
258 * | | pset_ref_lock thread_ref_lock
259 * | |
260 * | V
261 * | thread_sched_lock*
262 * | |
263 * | +-------+
264 * | | |
265 * | | V
266 * | | runq_lock*
267 * V V
268 * processor_lock*
269 * |
270 * V
271 * pset_idle_lock*
272 * |
273 * V
274 * action_lock*
275 *
276 * Locks marked with "*" are taken at splsched.
277 */
278
279 /*
280 * XXX need a pointer to the master processor structure
281 */
282
283 extern processor_t master_processor;
284
285 /*
286 * NOTE: The processor->processor_set link is needed in one of the
287 * scheduler's critical paths. [Figure out where to look for another
288 * thread to run on this processor.] It is accessed without locking.
289 * The following access protocol controls this field.
290 *
291 * Read from own processor - just read.
292 * Read from another processor - lock processor structure during read.
293 * Write from own processor - lock processor structure during write.
294 * Write from another processor - NOT PERMITTED.
295 *
296 */
297
298 /*
299 * Processor state locking:
300 *
301 * Values for the processor state are defined below. If the processor
302 * is off-line or being shutdown, then it is only necessary to lock
303 * the processor to change its state. Otherwise it is only necessary
304 * to lock its processor set's idle_lock. Scheduler code will
305 * typically lock only the idle_lock, but processor manipulation code
306 * will often lock both.
307 */
308
309 #define PROCESSOR_OFF_LINE 0 /* Not in system */
310 #define PROCESSOR_RUNNING 1 /* Running normally */
311 #define PROCESSOR_IDLE 2 /* idle */
312 #define PROCESSOR_DISPATCHING 3 /* dispatching (idle -> running) */
313 #define PROCESSOR_ASSIGN 4 /* Assignment is changing */
314 #define PROCESSOR_SHUTDOWN 5 /* Being shutdown */
315
316 /*
317 * Use processor ptr array to find current processor's data structure.
318 * This replaces a multiplication (index into processor_array) with
319 * an array lookup and a memory reference. It also allows us to save
320 * space if processor numbering gets too sparse.
321 */
322
323 extern processor_t processor_ptr[NCPUS];
324
325 #define cpu_to_processor(i) (processor_ptr[i])
326
327 #define current_processor() (processor_ptr[cpu_number()])
328 #define current_processor_set() (current_processor()->processor_set)
329
330 /* Useful lock macros */
331
332 #define pset_lock(pset) simple_lock(&(pset)->lock)
333 #define pset_unlock(pset) simple_unlock(&(pset)->lock)
334 #define pset_ref_lock(pset) simple_lock(&(pset)->ref_lock)
335 #define pset_ref_unlock(pset) simple_unlock(&(pset)->ref_lock)
336
337 #define processor_lock(pr) simple_lock(&(pr)->lock)
338 #define processor_unlock(pr) simple_unlock(&(pr)->lock)
339
340 typedef mach_port_t *processor_array_t;
341 typedef mach_port_t *processor_set_array_t;
342 typedef mach_port_t *processor_set_name_array_t;
343
344
345 /*
346 * Exported functions
347 */
348
349 /* Initialization */
350
351 extern void pset_sys_bootstrap(void);
352
353 #if MACH_HOST
354 extern void pset_sys_init(void);
355 #endif /* MACH_HOST */
356
357 /* Pset internal functions */
358
359 extern void pset_reference(processor_set_t);
360 extern void pset_deallocate(processor_set_t);
361 extern void pset_remove_processor(processor_set_t, processor_t);
362 extern void pset_add_processor(processor_set_t, processor_t);
363 extern void pset_remove_task(processor_set_t, task_t);
364 extern void pset_add_task(processor_set_t, task_t);
365 extern void pset_remove_thread(processor_set_t, thread_t);
366 extern void pset_add_thread(processor_set_t, thread_t);
367 extern void thread_change_psets(thread_t, processor_set_t, processor_set_t);
368
369 /* Checks that a thread can run on a processor */
370
371 #if MACH_HOST
372 #define check_processor_set(thread) \
373 (current_processor()->processor_set == (thread)->processor_set)
374 #else /* MACH_HOST */
375 #define check_processor_set(thread) TRUE
376 #endif /* MACH_HOST */
377
378 #if NCPUS > 1
379 #define check_bound_processor(thread) \
380 ((thread)->bound_processor == PROCESSOR_NULL || \
381 (thread)->bound_processor == current_processor())
382 #else
383 #define check_bound_processor(thread) TRUE
384 #endif
385
386 /* Processor interface */
387
388 extern kern_return_t processor_get_assignment(
389 processor_t processor,
390 processor_set_t *processor_set);
391
392 extern kern_return_t processor_info(
393 processor_t processor,
394 int flavor,
395 host_t * host,
396 processor_info_t info,
397 natural_t * count);
398
399 extern kern_return_t processor_start(
400 processor_t processor);
401
402 extern kern_return_t processor_exit(
403 processor_t processor);
404
405 extern kern_return_t processor_control(
406 processor_t processor,
407 processor_info_t info,
408 natural_t count);
409
410 /* Pset interface */
411
412 extern kern_return_t processor_set_create(
413 host_t host,
414 processor_set_t *new_set,
415 processor_set_t *new_name);
416
417 extern kern_return_t processor_set_destroy(
418 processor_set_t pset);
419
420 extern kern_return_t processor_set_info(
421 processor_set_t pset,
422 int flavor,
423 host_t *host,
424 processor_set_info_t info,
425 natural_t *count);
426
427 extern kern_return_t processor_set_tasks(
428 processor_set_t pset,
429 task_array_t *task_list,
430 natural_t *count);
431
432 extern kern_return_t processor_set_threads(
433 processor_set_t pset,
434 thread_array_t *thread_list,
435 natural_t *count);
436
437 extern kern_return_t processor_set_policy_add(
438 processor_set_t pset,
439 int policy,
440 policy_param_t limit,
441 natural_t count);
442
443 extern kern_return_t processor_set_policy_remove(
444 processor_set_t pset,
445 int policy);
446
447 extern kern_return_t processor_set_policy_limit(
448 processor_set_t pset,
449 int policy,
450 policy_param_t limit,
451 natural_t count,
452 boolean_t change_threads);
453
454 /*
455 * Obsolete routines
456 */
457 extern kern_return_t processor_set_max_priority(
458 processor_set_t pset,
459 int max_priority,
460 boolean_t change_threads);
461
462 extern kern_return_t processor_set_policy_enable(
463 processor_set_t pset,
464 int policy);
465
466 extern kern_return_t processor_set_policy_disable(
467 processor_set_t pset,
468 int policy,
469 boolean_t change_threads);
470
471 #endif /* _KERN_PROCESSOR_H_ */
Cache object: c518e6cd44036f0e90f8d42adff4fb28
|