1 /**
2 * \file
3 * Common constants.
4 * \ingroup l4_api
5 */
6 /*
7 * (c) 2008-2009 Adam Lackorzynski <adam@os.inf.tu-dresden.de>,
8 * Alexander Warg <warg@os.inf.tu-dresden.de>,
9 * Björn Döbel <doebel@os.inf.tu-dresden.de>,
10 * Torsten Frenzel <frenzel@os.inf.tu-dresden.de>
11 * economic rights: Technische Universität Dresden (Germany)
12 *
13 * This file is part of TUD:OS and distributed under the terms of the
14 * GNU General Public License 2.
15 * Please see the COPYING-GPL-2 file for details.
16 *
17 * As a special exception, you may use this file as part of a free software
18 * library without restriction. Specifically, if other files instantiate
19 * templates or use macros or inline functions from this file, or you compile
20 * this file and link it with other files to produce an executable, this
21 * file does not by itself cause the resulting executable to be covered by
22 * the GNU General Public License. This exception does not however
23 * invalidate any other reasons why the executable file might be covered by
24 * the GNU General Public License.
25 */
26 #ifndef __L4_SYS__INCLUDE__CONSTS_H__
27 #define __L4_SYS__INCLUDE__CONSTS_H__
28
29 #include <l4/sys/compiler.h>
30 #include <l4/sys/l4int.h>
31
32 /**
33 * Capability selector flags.
34 * \ingroup l4_ipc_api
35 *
36 * These flags determine the concrete operation when a kernel object
37 * is invoked.
38 */
39 enum l4_syscall_flags_t
40 {
41 /**
42 * Default flags (call to a kernel object).
43 * \hideinitializer
44 *
45 * Using this value as flags in the capability selector for an
46 * invocation indicates a call (send and wait for a reply).
47 */
48 L4_SYSF_NONE = 0x00,
49
50 /**
51 * Send-phase flag.
52 * \hideinitializer
53 *
54 * Setting this flag in a capability selector induces a send phase,
55 * this means a message is sent to the object denoted by the capability.
56 * For receive phase see #L4_SYSF_RECV.
57 */
58 L4_SYSF_SEND = 0x01,
59
60 /**
61 * Receive-phase flag.
62 * \hideinitializer
63 *
64 * Setting this flag in a capability selector induces a receive phase,
65 * this means the invoking thread waits for a message from the object
66 * denoted by the capability.
67 * For a send phase see #L4_SYSF_SEND.
68 */
69 L4_SYSF_RECV = 0x02,
70
71 /**
72 * Open-wait flag.
73 * \hideinitializer
74 *
75 * This flag indicates that the receive operation (see #L4_SYSF_RECV)
76 * shall be an \em open \em wait. \em Open \em wait means that the invoking
77 * thread shall wait for a message from any possible sender and \em not from
78 * the sender denoted by the capability.
79 */
80 L4_SYSF_OPEN_WAIT = 0x04,
81
82 /**
83 * Reply flag.
84 * \hideinitializer
85 *
86 * This flag indicates that the send phase shall use the in-kernel reply
87 * capability instead of the capability denoted by the selector index.
88 */
89 L4_SYSF_REPLY = 0x08,
90
91 /**
92 * Call flags (combines send and receive).
93 * \hideinitializer
94 *
95 * Combines #L4_SYSF_SEND and L4_SYSF_RECV.
96 */
97 L4_SYSF_CALL = L4_SYSF_SEND | L4_SYSF_RECV,
98
99 /**
100 * Wait flags (combines receive and open wait).
101 * \hideinitializer
102 *
103 * Combines #L4_SYSF_RECV and #L4_SYSF_OPEN_WAIT.
104 */
105 L4_SYSF_WAIT = L4_SYSF_OPEN_WAIT | L4_SYSF_RECV,
106
107 /**
108 * Send-and-wait flags.
109 * \hideinitializer
110 *
111 * Combines #L4_SYSF_SEND and #L4_SYSF_WAIT.
112 */
113 L4_SYSF_SEND_AND_WAIT = L4_SYSF_OPEN_WAIT | L4_SYSF_CALL,
114
115 /**
116 * Reply-and-wait flags.
117 * \hideinitializer
118 *
119 * Combines #L4_SYSF_SEND, #L4_SYSF_REPLY, and #L4_SYSF_WAIT.
120 */
121 L4_SYSF_REPLY_AND_WAIT = L4_SYSF_WAIT | L4_SYSF_SEND | L4_SYSF_REPLY
122 };
123
124 /**
125 * Constants related to capability selectors.
126 * \ingroup l4_cap_api
127 */
128 enum l4_cap_consts_t
129 {
130 /** Capability index shift. \hideinitializer */
131 L4_CAP_SHIFT = 12UL,
132 /** Offset of two consecutive capability selectors. \hideinitializer */
133 L4_CAP_SIZE = 1UL << L4_CAP_SHIFT,
134 L4_CAP_OFFSET = 1UL << L4_CAP_SHIFT,
135 /**
136 * Mask to get only the relevant bits of an l4_cap_idx_t.
137 * \hideinitializer
138 */
139 L4_CAP_MASK = ~0UL << (L4_CAP_SHIFT - 1),
140 /** Invalid capability selector. \hideinitializer */
141 L4_INVALID_CAP = ~0UL << (L4_CAP_SHIFT - 1),
142
143 L4_INVALID_CAP_BIT = 1UL << (L4_CAP_SHIFT - 1),
144 };
145
146 enum l4_sched_consts_t
147 {
148 L4_SCHED_MIN_PRIO = 0,
149 L4_SCHED_MAX_PRIO = 255,
150 };
151
152 /**
153 * Flags for the unmap operation.
154 * \ingroup l4_task_api
155 * \see L4::Task::unmap() and l4_task_unmap()
156 */
157 enum l4_unmap_flags_t
158 {
159 /**
160 * Flag to tell the unmap operation to unmap all child mappings including the
161 * mapping in the invoked task.
162 *
163 * \note Object capabilities are not hierarchical -- they have no children.
164 * The result of the map operation on an object capability is a copy of
165 * that capability in the object space of the destination task. An
166 * unmap operation on object capabilities is a no-op if this flag is
167 * not specified.
168 * \hideinitializer
169 * \see L4::Task::unmap() l4_task_unmap()
170 */
171 L4_FP_ALL_SPACES = 0x80000000UL,
172
173 /**
174 * Flag that indicates that an unmap operation on object capabilities shall
175 * try to delete the corresponding objects.
176 * \hideinitializer
177 * \see L4::Task::unmap() l4_task_unmap()
178 */
179 L4_FP_DELETE_OBJ = 0xc0000000UL,
180
181 /**
182 * Counterpart to #L4_FP_ALL_SPACES, unmap only child mappings.
183 * \hideinitializer
184 * \see L4::Task::unmap() l4_task_unmap()
185 */
186 L4_FP_OTHER_SPACES = 0x0UL
187 };
188
189 /**
190 * Constants for message items.
191 * \ingroup l4_msgitem_api
192 */
193 enum l4_msg_item_consts_t
194 {
195 L4_ITEM_MAP = 8, ///< Identify a message item as \em map \em item.
196
197 /**
198 * Denote that the following item shall be put into the same receive item as
199 * this one.
200 */
201 L4_ITEM_CONT = 1,
202
203 // send
204 L4_MAP_ITEM_GRANT = 2, ///< Flag as \em grant instead of \em map operation.
205 L4_MAP_ITEM_MAP = 0, ///< Flag as usual \em map operation.
206
207 // receive
208 /**
209 * Mark the receive buffer to be a small receive item that describes a buffer
210 * for a single capability.
211 */
212 L4_RCV_ITEM_SINGLE_CAP = L4_ITEM_MAP | 2,
213
214 /**
215 * The receiver requests to receive a local ID instead of a mapping whenever
216 * possible.
217 */
218 L4_RCV_ITEM_LOCAL_ID = 4,
219 };
220
221 /**
222 * Constants for buffer descriptors.
223 * \ingroup l4_utcb_br_api
224 */
225 enum l4_buffer_desc_consts_t
226 {
227 L4_BDR_MEM_SHIFT = 0, ///< Bit offset for the memory-buffer index
228 L4_BDR_IO_SHIFT = 5, ///< Bit offset for the IO-buffer index
229 L4_BDR_OBJ_SHIFT = 10, ///< Bit offset for the capability-buffer index
230 L4_BDR_OFFSET_MASK = (1UL << 20) - 1,
231 };
232
233 /**
234 * \ingroup l4_cap_api
235 * Default capabilities setup for the initial tasks.
236 *
237 * These capability selectors are setup per default by the micro kernel
238 * for the two initial tasks, the Root-Pager (Sigma0) and the Root-Task
239 * (Moe).
240 *
241 * \attention These constants do not have any particular meaning for
242 * applications started by Moe, see \ref api_l4re_env for
243 * this kind of information.
244 * \see \ref api_l4re_env for information useful for normal user applications.
245 */
246 enum l4_default_caps_t
247 {
248 /// Capability selector for the current task. \hideinitializer
249 L4_BASE_TASK_CAP = 1UL << L4_CAP_SHIFT,
250 /// Capability selector for the factory. \hideinitializer
251 L4_BASE_FACTORY_CAP = 2UL << L4_CAP_SHIFT,
252 /// Capability selector for the first thread. \hideinitializer
253 L4_BASE_THREAD_CAP = 3UL << L4_CAP_SHIFT,
254 /**
255 * Capability selector for the pager gate.
256 *
257 * \hideinitializer
258 * For Sigma0, the pager is not present since it never raises page faults.
259 * For Moe, the pager is set to Sigma0.
260 */
261 L4_BASE_PAGER_CAP = 4UL << L4_CAP_SHIFT,
262 /**
263 * Capability selector for the log object.
264 *
265 * \hideinitializer
266 * Present if the corresponding feature is turned on in the microkernel
267 * configuration.
268 */
269 L4_BASE_LOG_CAP = 5UL << L4_CAP_SHIFT,
270 /// Capability selector for the base icu object. \hideinitializer
271 L4_BASE_ICU_CAP = 6UL << L4_CAP_SHIFT,
272 /// Capability selector for the scheduler cap. \hideinitializer
273 L4_BASE_SCHEDULER_CAP = 7UL << L4_CAP_SHIFT,
274 /**
275 * Capability selector for the IO-MMU cap.
276 *
277 * \hideinitializer
278 * Present if the microkernel detected an IO-MMU.
279 */
280 L4_BASE_IOMMU_CAP = 8UL << L4_CAP_SHIFT,
281 /**
282 * Capability selector for the debugger cap.
283 *
284 * \hideinitializer
285 * Present if the corresponding feature is turned on in the microkernel
286 * configuration.
287 */
288 L4_BASE_DEBUGGER_CAP = 10UL << L4_CAP_SHIFT,
289 /** Capability selector for the ARM SMCCC cap.
290 *
291 * \hideinitializer
292 * Present if the microkernel detected an ARM SMC capable trusted execution
293 * environment.
294 */
295 L4_BASE_ARM_SMCCC_CAP = 11UL << L4_CAP_SHIFT,
296
297 /// \internal helper must be last before L4_BASE_CAPS_LAST
298 L4_BASE_CAPS_LAST_P1,
299 /// Last capability index used for base capabilities
300 L4_BASE_CAPS_LAST = L4_BASE_CAPS_LAST_P1 - 1
301 };
302
303 /**
304 * \defgroup l4_memory_api Memory related
305 * Memory related constants, data types and functions.
306 * \ingroup l4_api
307 */
308 /**
309 * Minimal page size (in bytes).
310 * \ingroup l4_memory_api
311 * \hideinitializer
312 */
313 #define L4_PAGESIZE (1UL << L4_PAGESHIFT)
314
315 /**
316 * Mask for the page number.
317 * \ingroup l4_memory_api
318 * \hideinitializer
319 *
320 * \note The most significant bits are set.
321 */
322 #define L4_PAGEMASK (~(L4_PAGESIZE - 1))
323
324 /**
325 * Number of bits used for page offset.
326 * \ingroup l4_memory_api
327 * \hideinitializer
328 *
329 * Size of page in log2.
330 */
331 #define L4_LOG2_PAGESIZE L4_PAGESHIFT
332
333 /**
334 * Size of a large page.
335 * \ingroup l4_memory_api
336 * \hideinitializer
337 *
338 * A large page is a \em super \em page on IA32 or a \em section on ARM.
339 */
340 #define L4_SUPERPAGESIZE (1UL << L4_SUPERPAGESHIFT)
341
342 /**
343 * Mask for the number of a large page.
344 * \ingroup l4_memory_api
345 * \hideinitializer
346 *
347 * \note The most significant bits are set.
348 */
349 #define L4_SUPERPAGEMASK (~(L4_SUPERPAGESIZE - 1))
350
351 /**
352 * Number of bits used as offset for a large page.
353 * \ingroup l4_memory_api
354 * \hideinitializer
355 * Size of large page in log2
356 */
357 #define L4_LOG2_SUPERPAGESIZE L4_SUPERPAGESHIFT
358
359 /**
360 * Round an address down to the next lower page boundary.
361 * \ingroup l4_memory_api
362 *
363 * The address is rounded down to the next lower minimal page boundary. On
364 * most architectures this is a 4k page. Check #L4_PAGESIZE for the minimal
365 * page size.
366 *
367 * \param address The address to round.
368 */
369 L4_INLINE l4_addr_t l4_trunc_page(l4_addr_t address) L4_NOTHROW;
l4_trunc_page(l4_addr_t address)370 L4_INLINE l4_addr_t l4_trunc_page(l4_addr_t address) L4_NOTHROW
371 { return address & L4_PAGEMASK; }
372
373 /**
374 * Round an address down to the next lower flex page with size \a bits.
375 * \ingroup l4_memory_api
376 *
377 * \param address The address to round.
378 * \param bits The size of the flex page (log2).
379 */
380 L4_INLINE l4_addr_t l4_trunc_size(l4_addr_t address, unsigned char bits) L4_NOTHROW;
l4_trunc_size(l4_addr_t address,unsigned char bits)381 L4_INLINE l4_addr_t l4_trunc_size(l4_addr_t address, unsigned char bits) L4_NOTHROW
382 { return address & (~0UL << bits); }
383
384 /**
385 * Round address up to the next page.
386 * \ingroup l4_memory_api
387 *
388 * The address is rounded up to the next minimal page boundary. On most
389 * architectures this is a 4k page. Check #L4_PAGESIZE for the minimal page
390 * size.
391 *
392 * \param address The address to round up.
393 */
394 L4_INLINE l4_addr_t l4_round_page(l4_addr_t address) L4_NOTHROW;
l4_round_page(l4_addr_t address)395 L4_INLINE l4_addr_t l4_round_page(l4_addr_t address) L4_NOTHROW
396 { return (address + L4_PAGESIZE - 1) & L4_PAGEMASK; }
397
398 /**
399 * Round value up to the next alignment with \a bits size.
400 * \ingroup l4_memory_api
401 *
402 * \param value The value to round up to the next size-alignment.
403 * \param bits The size of the alignment (log2).
404 */
405 L4_INLINE l4_addr_t l4_round_size(l4_addr_t value, unsigned char bits) L4_NOTHROW;
l4_round_size(l4_addr_t value,unsigned char bits)406 L4_INLINE l4_addr_t l4_round_size(l4_addr_t value, unsigned char bits) L4_NOTHROW
407 { return (value + (1UL << bits) - 1) & (~0UL << bits); }
408
409 /**
410 * Determine how many machine words (l4_umword_t) are required to store a
411 * buffer of 'size' bytes.
412 *
413 * \ingroup l4_memory_api
414 *
415 * \param bytes The number of bytes to be translated into machine words.
416 */
417 L4_INLINE unsigned l4_bytes_to_mwords(unsigned size) L4_NOTHROW;
l4_bytes_to_mwords(unsigned size)418 L4_INLINE unsigned l4_bytes_to_mwords(unsigned size) L4_NOTHROW
419 { return (size + sizeof(l4_umword_t) - 1) / sizeof(l4_umword_t); }
420
421 /**
422 * Address related constants.
423 * \ingroup l4_memory_api
424 */
425 enum l4_addr_consts_t {
426 /// Invalid address.
427 L4_INVALID_ADDR = ~0UL
428 };
429
430 /**
431 * Invalid address as pointer type.
432 * \ingroup l4_memory_api
433 */
434 #define L4_INVALID_PTR ((void *)L4_INVALID_ADDR)
435
436 #ifndef NULL
437 #ifndef __cplusplus
438 # define NULL ((void *)0) /**< \ingroup l4sys_defines
439 ** \hideinitializer
440 ** NULL
441 **/
442 #else
443 # define NULL 0
444 #endif
445 #endif
446
447 #endif /* ! __L4_SYS__INCLUDE__CONSTS_H__ */
448