Software APIs
macros.h
Go to the documentation of this file.
1// Copyright lowRISC contributors (OpenTitan project).
2// Licensed under the Apache License, Version 2.0, see LICENSE for details.
3// SPDX-License-Identifier: Apache-2.0
4
5#ifndef OPENTITAN_SW_DEVICE_LIB_BASE_MACROS_H_
6#define OPENTITAN_SW_DEVICE_LIB_BASE_MACROS_H_
7
8// This file may be used in .S files, in which case standard library includes
9// should be elided.
10#if !defined(__ASSEMBLER__) && !defined(NOSTDINC)
11#include <assert.h>
12#include <stddef.h>
13#include <stdint.h>
14
15#ifdef __cplusplus
16// The <type_traits> header is required for the C++-only `SignConverter` class.
17// See `SignConverter` for an explanation of this `extern "C++"` block.
18extern "C++" {
19#include <type_traits>
20}
21#endif
22#endif
23
24/**
25 * @file
26 * @brief Generic preprocessor macros that don't really fit anywhere else.
27 */
28
29/**
30 * Computes the number of elements in the given array.
31 *
32 * Note that this can only determine the length of *fixed-size* arrays. Due to
33 * limitations of C, it will incorrectly compute the size of an array passed as
34 * a function argument, because those automatically decay into pointers. This
35 * function can only be used correctly with:
36 * - Arrays declared as stack variables.
37 * - Arrays declared at global scope.
38 * - Arrays that are members of a struct or union.
39 *
40 * @param array The array expression to measure.
41 * @return The number of elements in the array, as a `size_t`.
42 */
43// This is a sufficiently well-known macro that we don't really need to bother
44// with a prefix like the others, and a rename will cause churn.
45#define ARRAYSIZE(array) (sizeof(array) / sizeof(array[0]))
46
47/**
48 * An annotation that a switch/case fallthrough is the intended behavior.
49 */
50#define OT_FALLTHROUGH_INTENDED __attribute__((fallthrough))
51
52/**
53 * A directive to force the compiler to inline a function.
54 */
55#define OT_ALWAYS_INLINE __attribute__((always_inline)) inline
56
57/**
58 * The `restrict` keyword is C specific, so we provide a C++-portable wrapper
59 * that uses the GCC name.
60 *
61 * It only needs to be used in headers; .c files can use `restrict` directly.
62 */
63#define OT_RESTRICT __restrict__
64
65/**
66 * An argument stringification macro.
67 */
68#define OT_STRINGIFY(a) OT_STRINGIFY_(a)
69#define OT_STRINGIFY_(a) #a
70
71/**
72 * A variable-argument macro that expands to the number of arguments passed into
73 * it, between 0 and 31 arguments.
74 *
75 * This macro is based off of a well-known preprocessor trick. This
76 * StackOverflow post expains the trick in detail:
77 * https://stackoverflow.com/questions/2308243/macro-returning-the-number-of-arguments-it-is-given-in-c
78 * TODO #2026: a dummy token is required for this to work correctly.
79 *
80 * @param dummy a dummy token that is required to be passed for the calculation
81 * to work correctly.
82 * @param ... the variable args list.
83 */
84#define OT_VA_ARGS_COUNT(dummy, ...) \
85 OT_SHIFT_N_VARIABLE_ARGS_(dummy, ##__VA_ARGS__, 31, 30, 29, 28, 27, 26, 25, \
86 24, 23, 22, 21, 20, 19, 18, 17, 16, 15, 14, 13, \
87 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0)
88
89// Implementation details for `OT_VA_ARGS_COUNT()`.
90#define OT_SHIFT_N_VARIABLE_ARGS_(...) OT_GET_NTH_VARIABLE_ARG_(__VA_ARGS__)
91#define OT_GET_NTH_VARIABLE_ARG_(x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x10, \
92 x11, x12, x13, x14, x15, x16, x17, x18, x19, \
93 x20, x21, x22, x23, x24, x25, x26, x27, x28, \
94 x29, x30, x31, n, ...) \
95 n
96
97/**
98 * An argument concatenation macro.
99 *
100 * Because the `##` operator inhibits expansion, we use a level of indirection
101 * to create a macro which concatenates without inhibition.
102 */
103#define OT_CAT(a, ...) OT_PRIMITIVE_CAT(a, __VA_ARGS__)
104#define OT_PRIMITIVE_CAT(a, ...) a##__VA_ARGS__
105
106/**
107 * A macro which gets the nth arg from a __VA_LIST__
108 */
109#define OT_GET_ARG(n, ...) OT_CAT(OT_CAT(OT_GET_ARG_, n), _)(__VA_ARGS__)
110
111/**
112 * A macro which gets the last arg from a __VA_LIST__
113 *
114 * Note: we leave out the dummy argument because we want count to
115 * give us the number of args minus one so that the created
116 * OT_GET_ARG_n token will contain the correct integer.
117 */
118#define OT_GET_LAST_ARG(...) \
119 OT_GET_ARG(OT_VA_ARGS_COUNT(__VA_ARGS__), ##__VA_ARGS__)
120
121/**
122 * The following collection of `OT_GET_ARG` macros are used to construct the
123 * generic "get nth arg" macro.
124 */
125#define OT_GET_ARG_0_(x0, ...) x0
126#define OT_GET_ARG_1_(x1, x0, ...) x0
127#define OT_GET_ARG_2_(x2, x1, x0, ...) x0
128#define OT_GET_ARG_3_(x3, x2, x1, x0, ...) x0
129#define OT_GET_ARG_4_(x4, x3, x2, x1, x0, ...) x0
130#define OT_GET_ARG_5_(x5, x4, x3, x2, x1, x0, ...) x0
131#define OT_GET_ARG_6_(x6, x5, x4, x3, x2, x1, x0, ...) x0
132#define OT_GET_ARG_7_(x7, x6, x5, x4, x3, x2, x1, x0, ...) x0
133#define OT_GET_ARG_8_(x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) x0
134#define OT_GET_ARG_9_(x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) x0
135#define OT_GET_ARG_10_(x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) x0
136#define OT_GET_ARG_11_(x11, x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) x0
137#define OT_GET_ARG_12_(x12, x11, x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, \
138 ...) \
139 x0
140#define OT_GET_ARG_13_(x13, x12, x11, x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, \
141 x0, ...) \
142 x0
143#define OT_GET_ARG_14_(x14, x13, x12, x11, x10, x9, x8, x7, x6, x5, x4, x3, \
144 x2, x1, x0, ...) \
145 x0
146#define OT_GET_ARG_15_(x15, x14, x13, x12, x11, x10, x9, x8, x7, x6, x5, x4, \
147 x3, x2, x1, x0, ...) \
148 x0
149#define OT_GET_ARG_16_(x16, x15, x14, x13, x12, x11, x10, x9, x8, x7, x6, x5, \
150 x4, x3, x2, x1, x0, ...) \
151 x0
152#define OT_GET_ARG_17_(x17, x16, x15, x14, x13, x12, x11, x10, x9, x8, x7, x6, \
153 x5, x4, x3, x2, x1, x0, ...) \
154 x0
155#define OT_GET_ARG_18_(x18, x17, x16, x15, x14, x13, x12, x11, x10, x9, x8, \
156 x7, x6, x5, x4, x3, x2, x1, x0, ...) \
157 x0
158#define OT_GET_ARG_19_(x19, x18, x17, x16, x15, x14, x13, x12, x11, x10, x9, \
159 x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) \
160 x0
161#define OT_GET_ARG_20_(x20, x19, x18, x17, x16, x15, x14, x13, x12, x11, x10, \
162 x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) \
163 x0
164#define OT_GET_ARG_21_(x21, x20, x19, x18, x17, x16, x15, x14, x13, x12, x11, \
165 x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) \
166 x0
167#define OT_GET_ARG_22_(x22, x21, x20, x19, x18, x17, x16, x15, x14, x13, x12, \
168 x11, x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) \
169 x0
170#define OT_GET_ARG_23_(x23, x22, x21, x20, x19, x18, x17, x16, x15, x14, x13, \
171 x12, x11, x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, \
172 ...) \
173 x0
174#define OT_GET_ARG_24_(x24, x23, x22, x21, x20, x19, x18, x17, x16, x15, x14, \
175 x13, x12, x11, x10, x9, x8, x7, x6, x5, x4, x3, x2, x1, \
176 x0, ...) \
177 x0
178#define OT_GET_ARG_25_(x25, x24, x23, x22, x21, x20, x19, x18, x17, x16, x15, \
179 x14, x13, x12, x11, x10, x9, x8, x7, x6, x5, x4, x3, \
180 x2, x1, x0, ...) \
181 x0
182#define OT_GET_ARG_26_(x26, x25, x24, x23, x22, x21, x20, x19, x18, x17, x16, \
183 x15, x14, x13, x12, x11, x10, x9, x8, x7, x6, x5, x4, \
184 x3, x2, x1, x0, ...) \
185 x0
186#define OT_GET_ARG_27_(x27, x26, x25, x24, x23, x22, x21, x20, x19, x18, x17, \
187 x16, x15, x14, x13, x12, x11, x10, x9, x8, x7, x6, x5, \
188 x4, x3, x2, x1, x0, ...) \
189 x0
190#define OT_GET_ARG_28_(x28, x27, x26, x25, x24, x23, x22, x21, x20, x19, x18, \
191 x17, x16, x15, x14, x13, x12, x11, x10, x9, x8, x7, x6, \
192 x5, x4, x3, x2, x1, x0, ...) \
193 x0
194#define OT_GET_ARG_29_(x29, x28, x27, x26, x25, x24, x23, x22, x21, x20, x19, \
195 x18, x17, x16, x15, x14, x13, x12, x11, x10, x9, x8, \
196 x7, x6, x5, x4, x3, x2, x1, x0, ...) \
197 x0
198#define OT_GET_ARG_30_(x30, x29, x28, x27, x26, x25, x24, x23, x22, x21, x20, \
199 x19, x18, x17, x16, x15, x14, x13, x12, x11, x10, x9, \
200 x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) \
201 x0
202#define OT_GET_ARG_31_(x31, x30, x29, x28, x27, x26, x25, x24, x23, x22, x21, \
203 x20, x19, x18, x17, x16, x15, x14, x13, x12, x11, x10, \
204 x9, x8, x7, x6, x5, x4, x3, x2, x1, x0, ...) \
205 x0
206
207/**
208 * A macro that expands to an assertion for the offset of a struct member.
209 *
210 * @param type A struct type.
211 * @param member A member of the struct.
212 * @param offset Expected offset of the member.
213 */
214#define OT_ASSERT_MEMBER_OFFSET(type, member, offset) \
215 static_assert(offsetof(type, member) == UINT32_C(offset), \
216 "Unexpected offset for " #type "." #member)
217
218/**
219 * A macro that expands to an assertion for the offset of a struct member.
220 *
221 * @param type A struct type.
222 * @param member A member of the struct.
223 * @param enum_offset Expected offset of the member as an enum constant.
224 */
225#define OT_ASSERT_MEMBER_OFFSET_AS_ENUM(type, member, enum_offset) \
226 static_assert(offsetof(type, member) == enum_offset, \
227 "Unexpected offset for " #type "." #member)
228
229/**
230 * A macro that expands to an assertion for the size of a struct member.
231 *
232 * @param type A struct type.
233 * @param member A member of the struct.
234 * @param size Expected size of the type.
235 */
236#define OT_ASSERT_MEMBER_SIZE(type, member, size) \
237 static_assert(sizeof(((type){0}).member) == UINT32_C(size), \
238 "Unexpected size for " #type)
239
240/**
241 * A macro that expands to an assertion for the size of a struct member.
242 *
243 * Identical to `OT_ASSERT_MEMBER_SIZE`, except the size parameter is provided
244 * as an enum constant.
245 *
246 * @param type A struct type.
247 * @param member A member of the struct.
248 * @param enum_size Expected size of the type as an enum constant.
249 */
250#define OT_ASSERT_MEMBER_SIZE_AS_ENUM(type, member, enum_size) \
251 static_assert(sizeof(((type){0}).member) == enum_size, \
252 "Unexpected size for " #type)
253
254/**
255 * A macro that expands to an assertion for the size of a type.
256 *
257 * @param type A type.
258 * @param size Expected size of the type.
259 */
260#define OT_ASSERT_SIZE(type, size) \
261 static_assert(sizeof(type) == UINT32_C(size), "Unexpected size for " #type)
262
263/**
264 * A macro that expands to an assertion for an expected enum value.
265 *
266 * @param var An enum entry.
267 * @param expected_value Expected enum value.
268 */
269#define OT_ASSERT_ENUM_VALUE(var, expected_value) \
270 static_assert(var == expected_value, "Unexpected value for " #var)
271
272/**
273 * A variable-argument macro that expands to the number of arguments passed into
274 * it, between 1 and 32 arguments (1 action and 0-31 others).
275 *
276 * This macro accepts a macro name and a variable list of items, and will then
277 * expand to sequentially call the macro with each provided item in order. This
278 * can be useful for performing compile-time checks on arguments in variadic
279 * functions defined via macros.
280 *
281 * For example, OT_VAR_FOR_EACH(TEST, 5, 19, 32, 1, 4) would expand to be
282 * `do {TEST(5); TEST(19); TEST(32); TEST(1); TEST(4);} while (false)`
283 *
284 * @param action The name of the macro to invoke with each item individually.
285 * @param ... The variable args list to call the macro on.
286 */
287#define OT_VA_FOR_EACH(action, ...) \
288 do { \
289 OT_CAT(OT_CAT(OT_VA_FOR_EACH_, OT_VA_ARGS_COUNT(0, ##__VA_ARGS__)), _) \
290 (action, ##__VA_ARGS__) \
291 } while (false)
292
293/**
294 * The following collection of `OT_VA_FOR_EACH` macros are used to construct
295 * the generic "for each" `OT_VA_FOR_EACH` macro.
296 */
297#define OT_VA_FOR_EACH_0_(action)
298#define OT_VA_FOR_EACH_1_(action, item, ...) \
299 action(item); \
300 OT_VA_FOR_EACH_0_(action, ##__VA_ARGS__)
301#define OT_VA_FOR_EACH_2_(action, item, ...) \
302 action(item); \
303 OT_VA_FOR_EACH_1_(action, ##__VA_ARGS__)
304#define OT_VA_FOR_EACH_3_(action, item, ...) \
305 action(item); \
306 OT_VA_FOR_EACH_2_(action, ##__VA_ARGS__)
307#define OT_VA_FOR_EACH_4_(action, item, ...) \
308 action(item); \
309 OT_VA_FOR_EACH_3_(action, ##__VA_ARGS__)
310#define OT_VA_FOR_EACH_5_(action, item, ...) \
311 action(item); \
312 OT_VA_FOR_EACH_4_(action, ##__VA_ARGS__)
313#define OT_VA_FOR_EACH_6_(action, item, ...) \
314 action(item); \
315 OT_VA_FOR_EACH_5_(action, ##__VA_ARGS__)
316#define OT_VA_FOR_EACH_7_(action, item, ...) \
317 action(item); \
318 OT_VA_FOR_EACH_6_(action, ##__VA_ARGS__)
319#define OT_VA_FOR_EACH_8_(action, item, ...) \
320 action(item); \
321 OT_VA_FOR_EACH_7_(action, ##__VA_ARGS__)
322#define OT_VA_FOR_EACH_9_(action, item, ...) \
323 action(item); \
324 OT_VA_FOR_EACH_8_(action, ##__VA_ARGS__)
325#define OT_VA_FOR_EACH_10_(action, item, ...) \
326 action(item); \
327 OT_VA_FOR_EACH_9_(action, ##__VA_ARGS__)
328#define OT_VA_FOR_EACH_11_(action, item, ...) \
329 action(item); \
330 OT_VA_FOR_EACH_10_(action, ##__VA_ARGS__)
331#define OT_VA_FOR_EACH_12_(action, item, ...) \
332 action(item); \
333 OT_VA_FOR_EACH_11_(action, ##__VA_ARGS__)
334#define OT_VA_FOR_EACH_13_(action, item, ...) \
335 action(item); \
336 OT_VA_FOR_EACH_12_(action, ##__VA_ARGS__)
337#define OT_VA_FOR_EACH_14_(action, item, ...) \
338 action(item); \
339 OT_VA_FOR_EACH_13_(action, ##__VA_ARGS__)
340#define OT_VA_FOR_EACH_15_(action, item, ...) \
341 action(item); \
342 OT_VA_FOR_EACH_14_(action, ##__VA_ARGS__)
343#define OT_VA_FOR_EACH_16_(action, item, ...) \
344 action(item); \
345 OT_VA_FOR_EACH_15_(action, ##__VA_ARGS__)
346#define OT_VA_FOR_EACH_17_(action, item, ...) \
347 action(item); \
348 OT_VA_FOR_EACH_16_(action, ##__VA_ARGS__)
349#define OT_VA_FOR_EACH_18_(action, item, ...) \
350 action(item); \
351 OT_VA_FOR_EACH_17_(action, ##__VA_ARGS__)
352#define OT_VA_FOR_EACH_19_(action, item, ...) \
353 action(item); \
354 OT_VA_FOR_EACH_18_(action, ##__VA_ARGS__)
355#define OT_VA_FOR_EACH_20_(action, item, ...) \
356 action(item); \
357 OT_VA_FOR_EACH_19_(action, ##__VA_ARGS__)
358#define OT_VA_FOR_EACH_21_(action, item, ...) \
359 action(item); \
360 OT_VA_FOR_EACH_20_(action, ##__VA_ARGS__)
361#define OT_VA_FOR_EACH_22_(action, item, ...) \
362 action(item); \
363 OT_VA_FOR_EACH_21_(action, ##__VA_ARGS__)
364#define OT_VA_FOR_EACH_23_(action, item, ...) \
365 action(item); \
366 OT_VA_FOR_EACH_22_(action, ##__VA_ARGS__)
367#define OT_VA_FOR_EACH_24_(action, item, ...) \
368 action(item); \
369 OT_VA_FOR_EACH_23_(action, ##__VA_ARGS__)
370#define OT_VA_FOR_EACH_25_(action, item, ...) \
371 action(item); \
372 OT_VA_FOR_EACH_24_(action, ##__VA_ARGS__)
373#define OT_VA_FOR_EACH_26_(action, item, ...) \
374 action(item); \
375 OT_VA_FOR_EACH_25_(action, ##__VA_ARGS__)
376#define OT_VA_FOR_EACH_27_(action, item, ...) \
377 action(item); \
378 OT_VA_FOR_EACH_26_(action, ##__VA_ARGS__)
379#define OT_VA_FOR_EACH_28_(action, item, ...) \
380 action(item); \
381 OT_VA_FOR_EACH_27_(action, ##__VA_ARGS__)
382#define OT_VA_FOR_EACH_29_(action, item, ...) \
383 action(item); \
384 OT_VA_FOR_EACH_28_(action, ##__VA_ARGS__)
385#define OT_VA_FOR_EACH_30_(action, item, ...) \
386 action(item); \
387 OT_VA_FOR_EACH_29_(action, ##__VA_ARGS__)
388#define OT_VA_FOR_EACH_31_(action, item, ...) \
389 action(item); \
390 OT_VA_FOR_EACH_30_(action, ##__VA_ARGS__)
391
392/**
393 * A macro that checks whether a specified argument is not a standard C integer
394 * type with a width of 64 bits. Useful when assuming that variable arguments
395 * are 32 bits integers.
396 *
397 * @param arg An argument/expression
398 */
399#define OT_CHECK_NOT_INT64(arg) \
400 _Generic((arg), int64_t: false, uint64_t: false, default: true)
401
402/**
403 * A macro that expands to an assertion that wraps the `OT_CHECK_NOT_INT64`
404 * macro, failing with a relevant error message if the provided argument is a
405 * standard C integer type with a width of 64 bits.
406 *
407 * @param arg An argument/expression to check
408 * @param func_name The name of the macro/functionality being invoked, to be
409 * printed in a relevant error if the assertion fails.
410 */
411#define OT_FAIL_IF_64_BIT(arg, func_name) \
412 do { \
413 static_assert(OT_CHECK_NOT_INT64(arg), \
414 "Argument '" #arg "' passed to the " #func_name \
415 " function must be no wider than 32 bits. " \
416 "Hint: maybe cast with '(uint32_t) " #arg "'?"); \
417 } while (0)
418
419/**
420 * A macro representing the OpenTitan execution platform.
421 */
422#if __riscv_xlen == 32
423#define OT_PLATFORM_RV32 1
424#endif
425
426/**
427 * A macro indicating whether software should assume reduced hardware
428 * support (for the `top_englishbreakafst` toplevel).
429 */
430#ifdef OT_IS_ENGLISH_BREAKFAST_REDUCED_SUPPORT_FOR_INTERNAL_USE_ONLY_
431#define OT_IS_ENGLISH_BREAKFAST 1
432#endif
433
434/**
435 * Attribute for functions which return errors that must be acknowledged.
436 *
437 * This attribute must be used to mark all DIFs which return an error value of
438 * some kind, to ensure that callers do not accidentally drop the error on the
439 * ground.
440 *
441 * Normally, the standard way to drop such a value on the ground explicitly is
442 * with the syntax `(void)expr;`, in analogy with the behavior of C++'s
443 * `[[nodiscard]]` attribute.
444 * However, GCC does not implement this, so the idiom `if (expr) {}` should be
445 * used instead, for the time being.
446 * See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=25509.
447 */
448#define OT_WARN_UNUSED_RESULT __attribute__((warn_unused_result))
449
450/**
451 * Attribute for weak functions that can be overridden, e.g., ISRs.
452 */
453#define OT_WEAK __attribute__((weak))
454
455/**
456 * Attribute to construct functions without prologue/epilogue sequences.
457 *
458 * Only basic asm statements can be safely included in naked functions.
459 *
460 * See https://gcc.gnu.org/onlinedocs/gcc/RISC-V-Function-Attributes.html
461 * #RISC-V-Function-Attributes
462 */
463#define OT_NAKED __attribute__((naked))
464
465/**
466 * Attribute to place symbols into particular sections.
467 *
468 * See https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html
469 * #Common-Function-Attributes
470 */
471#define OT_SECTION(name) __attribute__((section(name)))
472
473/**
474 * Pragma meant to place symbols into a NOBITS section with a specified name.
475 *
476 * This should only be used for zero-initialized globals (including
477 * implicitly zero-initialized ones, when the initializer is missing). The
478 * pragma won't affect variables that do not go into the bss section.
479 *
480 * Example:
481 *
482 * OT_SET_BSS_SECTION(".foo",
483 * uint32_t x; // emitted in section .foo instead of .bss
484 * uint32_t y = 42; // emitted in regular .data section (but don't do this)
485 * )
486 */
487#define OT_SET_BSS_SECTION(name, ...) \
488 OT_SET_BSS_SECTION_(clang section bss = name) \
489 __VA_ARGS__ \
490 _Pragma("clang section bss = \"\"")
491#define OT_SET_BSS_SECTION_(section) _Pragma(#section)
492
493/**
494 * Attribute to suppress the inlining of a function at its call sites.
495 *
496 * See https://clang.llvm.org/docs/AttributeReference.html#noinline.
497 */
498#define OT_NOINLINE __attribute__((noinline))
499
500/**
501 * Returns the address of the current function stack frame.
502 *
503 * See https://gcc.gnu.org/onlinedocs/gcc/Return-Address.html.
504 */
505#define OT_FRAME_ADDR() __builtin_frame_address(0)
506
507/**
508 * Hints to the compiler that some point is not reachable.
509 *
510 * One use case could be a function that never returns.
511 *
512 * Please not that if the control flow reaches the point of the
513 * __builtin_unreachable, the program is undefined.
514 *
515 * See https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html.
516 */
517#define OT_UNREACHABLE() __builtin_unreachable()
518
519/**
520 * Attribute for weak alias that can be overridden, e.g., Mock overrides in
521 * DIFs.
522 */
523#define OT_ALIAS(name) __attribute__((alias(name)))
524
525/**
526 * Defines a local symbol named `kName_` whose address resolves to the
527 * program counter value an inline assembly block at this location would
528 * see.
529 *
530 * The primary intention of this macro is to allow for peripheral tests to be
531 * written that want to assert that a specific program counter reported by the
532 * hardware corresponds to actual code that executed.
533 *
534 * For example, suppose that we're waiting for an interrupt to fire, and want
535 * to verify that it fired in a specific region. We have two volatile globals:
536 * `irq_happened`, which the ISR sets before returning, and `irq_pc`, which
537 * the ISR sets to whatever PC the hardware reports it came from. The
538 * code below tests that the reported PC matches expectations.
539 *
540 * ```
541 * OT_ADDRESSABLE_LABEL(kIrqWaitStart);
542 * enable_interrupts();
543 * while(!irq_happened) {
544 * wait_for_interrupt();
545 * }
546 * OT_ADDRESSABLE_LABEL(kIrqWaitEnd);
547 *
548 * CHECK(irq_pc >= &kIrqWaitStart && irq_pc < &IrqWaitEnd);
549 * ```
550 *
551 * Note that this only works if all functions called between the two labels
552 * are actually inlined; if the interrupt fires inside of one of those two
553 * functions, it will appear to not have the right PC, even though it is
554 * logically inside the pair of labels.
555 *
556 * # Volatile Semantics
557 *
558 * This has the same semantics as a `volatile` inline assembly block: it
559 * may be reordered with respect to all operations except other volatile
560 * operations (i.e. volatile assembly and volatile read/write, such as
561 * MMIO). For example, in the following code, `kBefore` and `kAfter` can
562 * wind up having the same address:
563 *
564 * ```
565 * OT_ADDRESSABLE_LABEL(kBefore);
566 * x += 5;
567 * OT_ADDRESSABLE_LABEL(kAfter);
568 * ```
569 *
570 * Because it can be reordered and the compiler is free to emit whatever
571 * instructions it likes, comparing a program counter value obtained from
572 * the hardware with a symbol emitted by this macro is brittle (and,
573 * ultimately, futile). Instead, it should be used in pairs to create a
574 * range of addresses that a value can be checked for being within.
575 *
576 * For this primitive to work correctly there must be something that counts as
577 * a volatile operation between the two labels. These include:
578 *
579 * - Direct reads or writes to MMIO registers or CSRs.
580 * - A volatile assembly block with at least one instruction.
581 * - Any DIF or driver call that may touch an MMIO register or a CSR.
582 * - `LOG`ging, `printf`ing, or `CHECK`ing.
583 * - `wait_for_interrupt()`.
584 * - `barrier32()`, but NOT `launder32()`.
585 *
586 * This macro should not be used on the host side. It will compile, but will
587 * probably not provide any meaningful values. In the future, it may start
588 * producing a garbage value on the host side.
589 *
590 * # Symbol Access
591 *
592 * The symbol reference `kName_` will only be scoped to the current block
593 * in a function, but it can be redeclared in the same file with
594 *
595 * ```
596 * extern const char kName_[];
597 * ```
598 *
599 * if needed elsewhere (although this should be avoided for readability's sake).
600 * The name of the constant is global to the current `.c` file only.
601 *
602 * # Example Uses
603 */
604#define OT_ADDRESSABLE_LABEL(kName_) \
605 extern const char kName_[]; \
606 asm volatile(".local " #kName_ "; " #kName_ ":;"); \
607 /* Force this to be at function scope. It could go at global scope, but it \
608 * would give a garbage value dependent on the whims of the linker. */ \
609 do { \
610 } while (false)
611
612/**
613 * Evaluates and discards `expr_`.
614 *
615 * This is needed because ‘(void)expr;` does not work for gcc.
616 */
617#define OT_DISCARD(expr_) \
618 if (expr_) { \
619 }
620
621/**
622 * An attribute used for static variables indicating that they should be
623 * retained in the object file, even if they are seemingly unreferenced.
624 */
625#define OT_USED __attribute__((used))
626
627/**
628 * OT_BUILD_FOR_STATIC_ANALYZER indicates whether we are compiling for the
629 * purpose of static analysis. Currently, this macro only detects
630 * Clang-Analyzer, which is used as a backend by Clang-Tidy.
631 */
632#ifdef __clang_analyzer__
633#define OT_BUILD_FOR_STATIC_ANALYZER 1
634#else
635#define OT_BUILD_FOR_STATIC_ANALYZER 0
636#endif
637
638/**
639 * This macro is used to align an offset to point to a 32b value.
640 */
641#define OT_ALIGN_MEM(x) (uint32_t)(4 + (((uintptr_t)(x)-1) & ~3u))
642
643#if !defined(__ASSEMBLER__) && !defined(NOSTDINC) && \
644 !defined(RUST_PREPROCESSOR_EMIT)
645#ifndef __cplusplus
647 char err;
648};
649
650/**
651 * This macro converts a given unsigned integer value to its signed counterpart.
652 */
653#define OT_SIGNED(value) \
654 _Generic((value), \
655 uint8_t: (int8_t)(value), \
656 uint16_t: (int16_t)(value), \
657 uint32_t: (int32_t)(value), \
658 uint64_t: (int64_t)(value), \
659 default: (struct OtSignConversionUnsupportedType){.err = 1})
660
661/**
662 * This macro converts a given signed integer value to its unsigned counterpart.
663 */
664#define OT_UNSIGNED(value) \
665 _Generic((value), \
666 int8_t: (uint8_t)(value), \
667 int16_t: (uint16_t)(value), \
668 int32_t: (uint32_t)(value), \
669 int64_t: (uint64_t)(value), \
670 default: (struct OtSignConversionUnsupportedType){.err = 1})
671#else // __cplusplus
672// Templates require "C++" linkage. Even though this block is only reachable
673// when __cplusplus is defined, it's possible that we are in the middle of an
674// `extern "C"` block. In case that is true, we explicitly set the linkage to
675// "C++" for the coming C++ templates.
676extern "C++" {
677namespace {
678template <typename T>
679class SignConverter {
680 public:
681 using SignedT = typename std::make_signed<T>::type;
682 using UnsignedT = typename std::make_unsigned<T>::type;
683 static constexpr SignedT as_signed(T value) {
684 return static_cast<SignedT>(value);
685 }
686 static constexpr UnsignedT as_unsigned(T value) {
687 return static_cast<UnsignedT>(value);
688 }
689};
690} // namespace
691}
692#define OT_SIGNED(value) (SignConverter<__typeof__(value)>::as_signed((value)))
693#define OT_UNSIGNED(value) \
694 (SignConverter<__typeof__(value)>::as_unsigned((value)))
695#endif // __cplusplus
696#endif // !defined(__ASSEMBLER__) && !defined(NOSTDINC) &&
697 // !defined(RUST_PREPROCESSOR_EMIT)
698
699// This routine makes sure that a condition that can be changed by IRQs
700// is evaluated inside a critical session. It executes a `wfi` between
701// evaluations.
702#define ATOMIC_WAIT_FOR_INTERRUPT(_volatile_condition) \
703 while (true) { \
704 irq_global_ctrl(false); \
705 if ((_volatile_condition)) { \
706 break; \
707 } \
708 wait_for_interrupt(); \
709 irq_global_ctrl(true); \
710 } \
711 irq_global_ctrl(true)
712
713/**
714 * Macros for implementing OT ISRs.
715 */
716#define OT_WORD_SIZE 4
717#define OT_HALF_WORD_SIZE (OT_WORD_SIZE / 2)
718// The ISR context size is 30 words. There are 32 cpu registers; 30 of them
719// need to be saved. The two that do not are `sp` and `gp` (x2 and x3).
720#define OT_CONTEXT_SIZE (OT_WORD_SIZE * 30)
721
722#endif // OPENTITAN_SW_DEVICE_LIB_BASE_MACROS_H_