1 // Copyright 2019 The Pigweed Authors
3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not
4 // use this file except in compliance with the License. You may obtain a copy of
7 // https://www.apache.org/licenses/LICENSE-2.0
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12 // License for the specific language governing permissions and limitations under
15 // Preprocessor macros that wrap compiler-specific features.
16 // This file is used by both C++ and C code.
19 // Marks a struct or class as packed.
20 #define PW_PACKED(declaration) declaration __attribute__((packed))
22 // Marks a function or object as used, ensuring code for it is generated.
23 #define PW_USED __attribute__((used))
25 // Prevents generation of a prologue or epilogue for a function. This is
26 // helpful when implementing the function in assembly.
27 #define PW_NO_PROLOGUE __attribute__((naked))
29 // Marks that a function declaration takes a printf-style format string and
30 // variadic arguments. This allows the compiler to perform check the validity of
31 // the format string and arguments. This macro must only be on the function
32 // declaration, not the definition.
34 // The format_index is index of the format string parameter and parameter_index
35 // is the starting index of the variadic arguments. Indices start at 1. For C++
36 // class member functions, add one to the index to account for the implicit this
39 // This example shows a function where the format string is argument 2 and the
40 // varargs start at argument 3.
42 // int PrintfStyleFunction(char* buffer,
43 // const char* fmt, ...) PW_PRINTF_FORMAT(2,3);
45 // int PrintfStyleFunction(char* buffer, const char* fmt, ...) {
46 // ... implementation here ...
50 // When compiling for host using MinGW, use gnu_printf() rather than printf()
51 // to support %z format specifiers.
52 #ifdef __USE_MINGW_ANSI_STDIO
53 #define _PW_PRINTF_FORMAT_TYPE gnu_printf
55 #define _PW_PRINTF_FORMAT_TYPE printf
56 #endif // __USE_MINGW_ANSI_STDIO
58 #define PW_PRINTF_FORMAT(format_index, parameter_index) \
59 __attribute__((format(_PW_PRINTF_FORMAT_TYPE, format_index, parameter_index)))
61 // Places a variable in the specified linker section and directs the compiler
62 // to keep the variable, even if it is not used. Depending on the linker
63 // options, the linker may still remove this section if it is not declared in
64 // the linker script and marked KEEP.
66 #define PW_KEEP_IN_SECTION(name) __attribute__((section("__DATA," name), used))
68 #define PW_KEEP_IN_SECTION(name) __attribute__((section(name), used))
71 // Indicate to the compiler that the annotated function won't return. Example:
73 // PW_NO_RETURN void HandleAssertFailure(ErrorCode error_code);
75 #define PW_NO_RETURN __attribute__((noreturn))
77 // Prevents the compiler from inlining a fuction.
78 #define PW_NO_INLINE __attribute__((noinline))
80 // Indicate to the compiler that the given section of code will not be reached.
85 // vendor_StartScheduler(); // Note: vendor forgot noreturn attribute.
89 #define PW_UNREACHABLE __builtin_unreachable()
91 // Indicate to a sanitizer compiler runtime to skip the named check in the
92 // associated function.
95 // uint32_t djb2(const void* buf, size_t len)
96 // PW_NO_SANITIZE("unsigned-integer-overflow"){
97 // uint32_t hash = 5381;
98 // const uint8_t* u8 = static_cast<const uint8_t*>(buf);
99 // for (size_t i = 0; i < len; ++i) {
100 // hash = (hash * 33) + u8[i]; /* hash * 33 + c */
105 #define PW_NO_SANITIZE(check) __attribute__((no_sanitize(check)))
107 #define PW_NO_SANITIZE(check)