aboutsummaryrefslogtreecommitdiffstats
path: root/include/linux/compiler_attributes.h
diff options
context:
space:
mode:
authorMiguel Ojeda <miguel.ojeda.sandonis@gmail.com>2018-08-30 14:36:59 -0400
committerMiguel Ojeda <miguel.ojeda.sandonis@gmail.com>2018-09-30 14:14:03 -0400
commita3f8a30f3f0079c7edfc72e329eee8594fb3e3cb (patch)
tree8855bb09c0335640b625080fe266e668d9225c16 /include/linux/compiler_attributes.h
parent66dbeef915f275dad6c8656b31667ef9640f5639 (diff)
Compiler Attributes: use feature checks instead of version checks
Instead of using version checks per-compiler to define (or not) each attribute, use __has_attribute to test for them, following the cleanup started with commit 815f0ddb346c ("include/linux/compiler*.h: make compiler-*.h mutually exclusive"), which is supported on gcc >= 5, clang >= 2.9 and icc >= 17. In the meantime, to support 4.6 <= gcc < 5, we implement __has_attribute by hand. All the attributes that can be unconditionally defined and directly map to compiler attribute(s) (even if optional) have been moved to a new file include/linux/compiler_attributes.h In an effort to make the file as regular as possible, comments stating the purpose of attributes have been removed. Instead, links to the compiler docs have been added (i.e. to gcc and, if available, to clang as well). In addition, they have been sorted. Finally, if an attribute is optional (i.e. if it is guarded by __has_attribute), the reason has been stated for future reference. Tested-by: Sedat Dilek <sedat.dilek@gmail.com> # on top of v4.19-rc5, clang 7 Reviewed-by: Nick Desaulniers <ndesaulniers@google.com> Reviewed-by: Luc Van Oostenryck <luc.vanoostenryck@gmail.com> Signed-off-by: Miguel Ojeda <miguel.ojeda.sandonis@gmail.com>
Diffstat (limited to 'include/linux/compiler_attributes.h')
-rw-r--r--include/linux/compiler_attributes.h244
1 files changed, 244 insertions, 0 deletions
diff --git a/include/linux/compiler_attributes.h b/include/linux/compiler_attributes.h
new file mode 100644
index 000000000000..f0f9fc398440
--- /dev/null
+++ b/include/linux/compiler_attributes.h
@@ -0,0 +1,244 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2#ifndef __LINUX_COMPILER_ATTRIBUTES_H
3#define __LINUX_COMPILER_ATTRIBUTES_H
4
5/*
6 * The attributes in this file are unconditionally defined and they directly
7 * map to compiler attribute(s) -- except those that are optional.
8 *
9 * Any other "attributes" (i.e. those that depend on a configuration option,
10 * on a compiler, on an architecture, on plugins, on other attributes...)
11 * should be defined elsewhere (e.g. compiler_types.h or compiler-*.h).
12 *
13 * This file is meant to be sorted (by actual attribute name,
14 * not by #define identifier). Use the __attribute__((__name__)) syntax
15 * (i.e. with underscores) to avoid future collisions with other macros.
16 * If an attribute is optional, state the reason in the comment.
17 */
18
19/*
20 * To check for optional attributes, we use __has_attribute, which is supported
21 * on gcc >= 5, clang >= 2.9 and icc >= 17. In the meantime, to support
22 * 4.6 <= gcc < 5, we implement __has_attribute by hand.
23 *
24 * sparse does not support __has_attribute (yet) and defines __GNUC_MINOR__
25 * depending on the compiler used to build it; however, these attributes have
26 * no semantic effects for sparse, so it does not matter. Also note that,
27 * in order to avoid sparse's warnings, even the unsupported ones must be
28 * defined to 0.
29 */
30#ifndef __has_attribute
31# define __has_attribute(x) __GCC4_has_attribute_##x
32# define __GCC4_has_attribute___assume_aligned__ (__GNUC_MINOR__ >= 9)
33# define __GCC4_has_attribute___designated_init__ 0
34# define __GCC4_has_attribute___externally_visible__ 1
35# define __GCC4_has_attribute___noclone__ 1
36# define __GCC4_has_attribute___optimize__ 1
37# define __GCC4_has_attribute___no_sanitize_address__ (__GNUC_MINOR__ >= 8)
38#endif
39
40/*
41 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-alias-function-attribute
42 */
43#define __alias(symbol) __attribute__((__alias__(#symbol)))
44
45/*
46 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-aligned-function-attribute
47 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Type-Attributes.html#index-aligned-type-attribute
48 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-aligned-variable-attribute
49 */
50#define __aligned(x) __attribute__((__aligned__(x)))
51#define __aligned_largest __attribute__((__aligned__))
52
53/*
54 * Note: users of __always_inline currently do not write "inline" themselves,
55 * which seems to be required by gcc to apply the attribute according
56 * to its docs (and also "warning: always_inline function might not be
57 * inlinable [-Wattributes]" is emitted).
58 *
59 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-always_005finline-function-attribute
60 * clang: mentioned
61 */
62#define __always_inline inline __attribute__((__always_inline__))
63
64/*
65 * The second argument is optional (default 0), so we use a variadic macro
66 * to make the shorthand.
67 *
68 * Beware: Do not apply this to functions which may return
69 * ERR_PTRs. Also, it is probably unwise to apply it to functions
70 * returning extra information in the low bits (but in that case the
71 * compiler should see some alignment anyway, when the return value is
72 * massaged by 'flags = ptr & 3; ptr &= ~3;').
73 *
74 * Optional: only supported since gcc >= 4.9
75 * Optional: not supported by icc
76 *
77 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-assume_005faligned-function-attribute
78 * clang: https://clang.llvm.org/docs/AttributeReference.html#assume-aligned
79 */
80#if __has_attribute(__assume_aligned__)
81# define __assume_aligned(a, ...) __attribute__((__assume_aligned__(a, ## __VA_ARGS__)))
82#else
83# define __assume_aligned(a, ...)
84#endif
85
86/*
87 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-cold-function-attribute
88 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Label-Attributes.html#index-cold-label-attribute
89 */
90#define __cold __attribute__((__cold__))
91
92/*
93 * Note the long name.
94 *
95 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-const-function-attribute
96 */
97#define __attribute_const__ __attribute__((__const__))
98
99/*
100 * Don't. Just don't. See commit 771c035372a0 ("deprecate the '__deprecated'
101 * attribute warnings entirely and for good") for more information.
102 *
103 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-deprecated-function-attribute
104 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Type-Attributes.html#index-deprecated-type-attribute
105 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-deprecated-variable-attribute
106 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Enumerator-Attributes.html#index-deprecated-enumerator-attribute
107 * clang: https://clang.llvm.org/docs/AttributeReference.html#deprecated
108 */
109#define __deprecated
110
111/*
112 * Optional: only supported since gcc >= 5.1
113 * Optional: not supported by clang
114 * Optional: not supported by icc
115 *
116 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Type-Attributes.html#index-designated_005finit-type-attribute
117 */
118#if __has_attribute(__designated_init__)
119# define __designated_init __attribute__((__designated_init__))
120#else
121# define __designated_init
122#endif
123
124/*
125 * Optional: not supported by clang
126 *
127 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-externally_005fvisible-function-attribute
128 */
129#if __has_attribute(__externally_visible__)
130# define __visible __attribute__((__externally_visible__))
131#else
132# define __visible
133#endif
134
135/*
136 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-format-function-attribute
137 * clang: https://clang.llvm.org/docs/AttributeReference.html#format
138 */
139#define __printf(a, b) __attribute__((__format__(printf, a, b)))
140#define __scanf(a, b) __attribute__((__format__(scanf, a, b)))
141
142/*
143 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-gnu_005finline-function-attribute
144 * clang: https://clang.llvm.org/docs/AttributeReference.html#gnu-inline
145 */
146#define __gnu_inline __attribute__((__gnu_inline__))
147
148/*
149 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-malloc-function-attribute
150 */
151#define __malloc __attribute__((__malloc__))
152
153/*
154 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Type-Attributes.html#index-mode-type-attribute
155 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-mode-variable-attribute
156 */
157#define __mode(x) __attribute__((__mode__(x)))
158
159/*
160 * Optional: not supported by clang
161 * Note: icc does not recognize gcc's no-tracer
162 *
163 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-noclone-function-attribute
164 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-optimize-function-attribute
165 */
166#if __has_attribute(__noclone__)
167# if __has_attribute(__optimize__)
168# define __noclone __attribute__((__noclone__, __optimize__("no-tracer")))
169# else
170# define __noclone __attribute__((__noclone__))
171# endif
172#else
173# define __noclone
174#endif
175
176/*
177 * Note the missing underscores.
178 *
179 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-noinline-function-attribute
180 * clang: mentioned
181 */
182#define noinline __attribute__((__noinline__))
183
184/*
185 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-noreturn-function-attribute
186 * clang: https://clang.llvm.org/docs/AttributeReference.html#noreturn
187 * clang: https://clang.llvm.org/docs/AttributeReference.html#id1
188 */
189#define __noreturn __attribute__((__noreturn__))
190
191/*
192 * Optional: only supported since gcc >= 4.8
193 * Optional: not supported by icc
194 *
195 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-no_005fsanitize_005faddress-function-attribute
196 * clang: https://clang.llvm.org/docs/AttributeReference.html#no-sanitize-address-no-address-safety-analysis
197 */
198#if __has_attribute(__no_sanitize_address__)
199# define __no_sanitize_address __attribute__((__no_sanitize_address__))
200#else
201# define __no_sanitize_address
202#endif
203
204/*
205 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Type-Attributes.html#index-packed-type-attribute
206 * clang: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-packed-variable-attribute
207 */
208#define __packed __attribute__((__packed__))
209
210/*
211 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-pure-function-attribute
212 */
213#define __pure __attribute__((__pure__))
214
215/*
216 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-section-function-attribute
217 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-section-variable-attribute
218 * clang: https://clang.llvm.org/docs/AttributeReference.html#section-declspec-allocate
219 */
220#define __section(S) __attribute__((__section__(#S)))
221
222/*
223 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-unused-function-attribute
224 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Type-Attributes.html#index-unused-type-attribute
225 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-unused-variable-attribute
226 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Label-Attributes.html#index-unused-label-attribute
227 * clang: https://clang.llvm.org/docs/AttributeReference.html#maybe-unused-unused
228 */
229#define __always_unused __attribute__((__unused__))
230#define __maybe_unused __attribute__((__unused__))
231
232/*
233 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-used-function-attribute
234 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-used-variable-attribute
235 */
236#define __used __attribute__((__used__))
237
238/*
239 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#index-weak-function-attribute
240 * gcc: https://gcc.gnu.org/onlinedocs/gcc/Common-Variable-Attributes.html#index-weak-variable-attribute
241 */
242#define __weak __attribute__((__weak__))
243
244#endif /* __LINUX_COMPILER_ATTRIBUTES_H */