1/*
2 * Copyright 2019-2025 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the Apache License 2.0 (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#ifndef OPENSSL_MACROS_H
11#define OPENSSL_MACROS_H
12#pragma once
13
14#include <openssl/opensslconf.h>
15#include <openssl/opensslv.h>
16
17/* Helper macros for CPP string composition */
18#define OPENSSL_MSTR_HELPER(x) #x
19#define OPENSSL_MSTR(x) OPENSSL_MSTR_HELPER(x)
20
21/*
22 * Sometimes OPENSSL_NO_xxx ends up with an empty file and some compilers
23 * don't like that. This will hopefully silence them.
24 */
25#define NON_EMPTY_TRANSLATION_UNIT static void *dummy = &dummy;
26
27/*
28 * Generic deprecation macro
29 *
30 * If OPENSSL_SUPPRESS_DEPRECATED is defined, then OSSL_DEPRECATED and
31 * OSSL_DEPRECATED_FOR become no-ops
32 */
33#ifndef OSSL_DEPRECATED
34#undef OSSL_DEPRECATED_FOR
35#ifndef OPENSSL_SUPPRESS_DEPRECATED
36#if defined(_MSC_VER)
37/*
38 * MSVC supports __declspec(deprecated) since MSVC 2003 (13.10),
39 * and __declspec(deprecated(message)) since MSVC 2005 (14.00)
40 */
41#if _MSC_VER >= 1400
42#define OSSL_DEPRECATED(since) \
43 __declspec(deprecated("Since OpenSSL " #since))
44#define OSSL_DEPRECATED_FOR(since, message) \
45 __declspec(deprecated("Since OpenSSL " #since ";" message))
46#elif _MSC_VER >= 1310
47#define OSSL_DEPRECATED(since) __declspec(deprecated)
48#define OSSL_DEPRECATED_FOR(since, message) __declspec(deprecated)
49#endif
50#elif defined(__GNUC__)
51/*
52 * According to GCC documentation, deprecations with message appeared in
53 * GCC 4.5.0
54 */
55#if __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5)
56#define OSSL_DEPRECATED(since) \
57 __attribute__((deprecated("Since OpenSSL " #since)))
58#define OSSL_DEPRECATED_FOR(since, message) \
59 __attribute__((deprecated("Since OpenSSL " #since ";" message)))
60#elif __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 0)
61#define OSSL_DEPRECATED(since) __attribute__((deprecated))
62#define OSSL_DEPRECATED_FOR(since, message) __attribute__((deprecated))
63#endif
64#elif defined(__SUNPRO_C)
65#if (__SUNPRO_C >= 0x5130)
66#define OSSL_DEPRECATED(since) __attribute__((deprecated))
67#define OSSL_DEPRECATED_FOR(since, message) __attribute__((deprecated))
68#endif
69#endif
70#endif
71#endif
72
73/*
74 * Still not defined? Then define no-op macros. This means these macros
75 * are unsuitable for use in a typedef.
76 */
77#ifndef OSSL_DEPRECATED
78#define OSSL_DEPRECATED(since) extern
79#define OSSL_DEPRECATED_FOR(since, message) extern
80#endif
81
82/*
83 * Applications should use -DOPENSSL_API_COMPAT=<version> to suppress the
84 * declarations of functions deprecated in or before <version>. If this is
85 * undefined, the value of the macro OPENSSL_CONFIGURED_API (defined in
86 * <openssl/opensslconf.h>) is the default.
87 *
88 * For any version number up until version 1.1.x, <version> is expected to be
89 * the calculated version number 0xMNNFFPPSL.
90 * For version numbers 3.0 and on, <version> is expected to be a computation
91 * of the major and minor numbers in decimal using this formula:
92 *
93 * MAJOR * 10000 + MINOR * 100
94 *
95 * So version 3.0 becomes 30000, version 3.2 becomes 30200, etc.
96 */
97
98/*
99 * We use the OPENSSL_API_COMPAT value to define API level macros. These
100 * macros are used to enable or disable features at that API version boundary.
101 */
102
103#ifdef OPENSSL_API_LEVEL
104#error "OPENSSL_API_LEVEL must not be defined by application"
105#endif
106
107/*
108 * We figure out what API level was intended by simple numeric comparison.
109 * The lowest old style number we recognise is 0x00908000L, so we take some
110 * safety margin and assume that anything below 0x00900000L is a new style
111 * number. This allows new versions up to and including v943.71.83.
112 */
113#ifdef OPENSSL_API_COMPAT
114#if OPENSSL_API_COMPAT < 0x900000L
115#define OPENSSL_API_LEVEL (OPENSSL_API_COMPAT)
116#else
117#define OPENSSL_API_LEVEL \
118 (((OPENSSL_API_COMPAT >> 28) & 0xF) * 10000 \
119 + ((OPENSSL_API_COMPAT >> 20) & 0xFF) * 100 \
120 + ((OPENSSL_API_COMPAT >> 12) & 0xFF))
121#endif
122#endif
123
124/*
125 * If OPENSSL_API_COMPAT wasn't given, we use default numbers to set
126 * the API compatibility level.
127 */
128#ifndef OPENSSL_API_LEVEL
129#if OPENSSL_CONFIGURED_API > 0
130#define OPENSSL_API_LEVEL (OPENSSL_CONFIGURED_API)
131#else
132#define OPENSSL_API_LEVEL \
133 (OPENSSL_VERSION_MAJOR * 10000 + OPENSSL_VERSION_MINOR * 100)
134#endif
135#endif
136
137#if OPENSSL_API_LEVEL > OPENSSL_CONFIGURED_API
138#error "The requested API level higher than the configured API compatibility level"
139#endif
140
141/*
142 * Check of sane values.
143 */
144/* Can't go higher than the current version. */
145#if OPENSSL_API_LEVEL > (OPENSSL_VERSION_MAJOR * 10000 + OPENSSL_VERSION_MINOR * 100)
146#error "OPENSSL_API_COMPAT expresses an impossible API compatibility level"
147#endif
148/* OpenSSL will have no version 2.y.z */
149#if OPENSSL_API_LEVEL < 30000 && OPENSSL_API_LEVEL >= 20000
150#error "OPENSSL_API_COMPAT expresses an impossible API compatibility level"
151#endif
152/* Below 0.9.8 is unacceptably low */
153#if OPENSSL_API_LEVEL < 908
154#error "OPENSSL_API_COMPAT expresses an impossible API compatibility level"
155#endif
156
157/*
158 * Define macros for deprecation and simulated removal purposes.
159 *
160 * The macros OSSL_DEPRECATEDIN_{major}_{minor} are always defined for
161 * all OpenSSL versions we care for. They can be used as attributes
162 * in function declarations where appropriate.
163 *
164 * The macros OPENSSL_NO_DEPRECATED_{major}_{minor} are defined for
165 * all OpenSSL versions up to or equal to the version given with
166 * OPENSSL_API_COMPAT. They are used as guards around anything that's
167 * deprecated up to that version, as an effect of the developer option
168 * 'no-deprecated'.
169 */
170
171#undef OPENSSL_NO_DEPRECATED_3_6
172#undef OPENSSL_NO_DEPRECATED_3_4
173#undef OPENSSL_NO_DEPRECATED_3_1
174#undef OPENSSL_NO_DEPRECATED_3_0
175#undef OPENSSL_NO_DEPRECATED_1_1_1
176#undef OPENSSL_NO_DEPRECATED_1_1_0
177#undef OPENSSL_NO_DEPRECATED_1_0_2
178#undef OPENSSL_NO_DEPRECATED_1_0_1
179#undef OPENSSL_NO_DEPRECATED_1_0_0
180#undef OPENSSL_NO_DEPRECATED_0_9_8
181
182#if OPENSSL_API_LEVEL >= 30600
183#ifndef OPENSSL_NO_DEPRECATED
184#define OSSL_DEPRECATEDIN_3_6 OSSL_DEPRECATED(3.6)
185#define OSSL_DEPRECATEDIN_3_6_FOR(msg) OSSL_DEPRECATED_FOR(3.6, msg)
186#else
187#define OPENSSL_NO_DEPRECATED_3_6
188#endif
189#else
190#define OSSL_DEPRECATEDIN_3_6
191#define OSSL_DEPRECATEDIN_3_6_FOR(msg)
192#endif
193#if OPENSSL_API_LEVEL >= 30500
194#ifndef OPENSSL_NO_DEPRECATED
195#define OSSL_DEPRECATEDIN_3_5 OSSL_DEPRECATED(3.5)
196#define OSSL_DEPRECATEDIN_3_5_FOR(msg) OSSL_DEPRECATED_FOR(3.5, msg)
197#else
198#define OPENSSL_NO_DEPRECATED_3_5
199#endif
200#else
201#define OSSL_DEPRECATEDIN_3_5
202#define OSSL_DEPRECATEDIN_3_5_FOR(msg)
203#endif
204#if OPENSSL_API_LEVEL >= 30400
205#ifndef OPENSSL_NO_DEPRECATED
206#define OSSL_DEPRECATEDIN_3_4 OSSL_DEPRECATED(3.4)
207#define OSSL_DEPRECATEDIN_3_4_FOR(msg) OSSL_DEPRECATED_FOR(3.4, msg)
208#else
209#define OPENSSL_NO_DEPRECATED_3_4
210#endif
211#else
212#define OSSL_DEPRECATEDIN_3_4
213#define OSSL_DEPRECATEDIN_3_4_FOR(msg)
214#endif
215#if OPENSSL_API_LEVEL >= 30100
216#ifndef OPENSSL_NO_DEPRECATED
217#define OSSL_DEPRECATEDIN_3_1 OSSL_DEPRECATED(3.1)
218#define OSSL_DEPRECATEDIN_3_1_FOR(msg) OSSL_DEPRECATED_FOR(3.1, msg)
219#else
220#define OPENSSL_NO_DEPRECATED_3_1
221#endif
222#else
223#define OSSL_DEPRECATEDIN_3_1
224#define OSSL_DEPRECATEDIN_3_1_FOR(msg)
225#endif
226#if OPENSSL_API_LEVEL >= 30000
227#ifndef OPENSSL_NO_DEPRECATED
228#define OSSL_DEPRECATEDIN_3_0 OSSL_DEPRECATED(3.0)
229#define OSSL_DEPRECATEDIN_3_0_FOR(msg) OSSL_DEPRECATED_FOR(3.0, msg)
230#else
231#define OPENSSL_NO_DEPRECATED_3_0
232#endif
233#else
234#define OSSL_DEPRECATEDIN_3_0
235#define OSSL_DEPRECATEDIN_3_0_FOR(msg)
236#endif
237#if OPENSSL_API_LEVEL >= 10101
238#ifndef OPENSSL_NO_DEPRECATED
239#define OSSL_DEPRECATEDIN_1_1_1 OSSL_DEPRECATED(1.1.1)
240#define OSSL_DEPRECATEDIN_1_1_1_FOR(msg) OSSL_DEPRECATED_FOR(1.1.1, msg)
241#else
242#define OPENSSL_NO_DEPRECATED_1_1_1
243#endif
244#else
245#define OSSL_DEPRECATEDIN_1_1_1
246#define OSSL_DEPRECATEDIN_1_1_1_FOR(msg)
247#endif
248#if OPENSSL_API_LEVEL >= 10100
249#ifndef OPENSSL_NO_DEPRECATED
250#define OSSL_DEPRECATEDIN_1_1_0 OSSL_DEPRECATED(1.1.0)
251#define OSSL_DEPRECATEDIN_1_1_0_FOR(msg) OSSL_DEPRECATED_FOR(1.1.0, msg)
252#else
253#define OPENSSL_NO_DEPRECATED_1_1_0
254#endif
255#else
256#define OSSL_DEPRECATEDIN_1_1_0
257#define OSSL_DEPRECATEDIN_1_1_0_FOR(msg)
258#endif
259#if OPENSSL_API_LEVEL >= 10002
260#ifndef OPENSSL_NO_DEPRECATED
261#define OSSL_DEPRECATEDIN_1_0_2 OSSL_DEPRECATED(1.0.2)
262#define OSSL_DEPRECATEDIN_1_0_2_FOR(msg) OSSL_DEPRECATED_FOR(1.0.2, msg)
263#else
264#define OPENSSL_NO_DEPRECATED_1_0_2
265#endif
266#else
267#define OSSL_DEPRECATEDIN_1_0_2
268#define OSSL_DEPRECATEDIN_1_0_2_FOR(msg)
269#endif
270#if OPENSSL_API_LEVEL >= 10001
271#ifndef OPENSSL_NO_DEPRECATED
272#define OSSL_DEPRECATEDIN_1_0_1 OSSL_DEPRECATED(1.0.1)
273#define OSSL_DEPRECATEDIN_1_0_1_FOR(msg) OSSL_DEPRECATED_FOR(1.0.1, msg)
274#else
275#define OPENSSL_NO_DEPRECATED_1_0_1
276#endif
277#else
278#define OSSL_DEPRECATEDIN_1_0_1
279#define OSSL_DEPRECATEDIN_1_0_1_FOR(msg)
280#endif
281#if OPENSSL_API_LEVEL >= 10000
282#ifndef OPENSSL_NO_DEPRECATED
283#define OSSL_DEPRECATEDIN_1_0_0 OSSL_DEPRECATED(1.0.0)
284#define OSSL_DEPRECATEDIN_1_0_0_FOR(msg) OSSL_DEPRECATED_FOR(1.0.0, msg)
285#else
286#define OPENSSL_NO_DEPRECATED_1_0_0
287#endif
288#else
289#define OSSL_DEPRECATEDIN_1_0_0
290#define OSSL_DEPRECATEDIN_1_0_0_FOR(msg)
291#endif
292#if OPENSSL_API_LEVEL >= 908
293#ifndef OPENSSL_NO_DEPRECATED
294#define OSSL_DEPRECATEDIN_0_9_8 OSSL_DEPRECATED(0.9.8)
295#define OSSL_DEPRECATEDIN_0_9_8_FOR(msg) OSSL_DEPRECATED_FOR(0.9.8, msg)
296#else
297#define OPENSSL_NO_DEPRECATED_0_9_8
298#endif
299#else
300#define OSSL_DEPRECATEDIN_0_9_8
301#define OSSL_DEPRECATEDIN_0_9_8_FOR(msg)
302#endif
303
304/*
305 * Make our own variants of __FILE__ and __LINE__, depending on configuration
306 */
307
308#ifndef OPENSSL_FILE
309#ifdef OPENSSL_NO_FILENAMES
310#define OPENSSL_FILE ""
311#define OPENSSL_LINE 0
312#else
313#define OPENSSL_FILE __FILE__
314#define OPENSSL_LINE __LINE__
315#endif
316#endif
317
318/*
319 * __func__ was standardized in C99, so for any compiler that claims
320 * to implement that language level or newer, we assume we can safely
321 * use that symbol.
322 *
323 * GNU C also provides __FUNCTION__ since version 2, which predates
324 * C99. We can, however, only use this if __STDC_VERSION__ exists,
325 * as it's otherwise not allowed according to ISO C standards (C90).
326 * (compiling with GNU C's -pedantic tells us so)
327 *
328 * If none of the above applies, we check if the compiler is MSVC,
329 * and use __FUNCTION__ if that's the case.
330 */
331#ifndef OPENSSL_FUNC
332#if defined(__STDC_VERSION__)
333#if __STDC_VERSION__ >= 199901L
334#define OPENSSL_FUNC __func__
335#elif defined(__GNUC__) && __GNUC__ >= 2
336#define OPENSSL_FUNC __FUNCTION__
337#endif
338#elif defined(_MSC_VER)
339#define OPENSSL_FUNC __FUNCTION__
340#endif
341/*
342 * If all these possibilities are exhausted, we give up and use a
343 * static string.
344 */
345#ifndef OPENSSL_FUNC
346#define OPENSSL_FUNC "(unknown function)"
347#endif
348#endif
349
350#ifndef OSSL_CRYPTO_ALLOC
351#if defined(__GNUC__)
352#define OSSL_CRYPTO_ALLOC __attribute__((__malloc__))
353#elif defined(_MSC_VER)
354#define OSSL_CRYPTO_ALLOC __declspec(restrict)
355#else
356#define OSSL_CRYPTO_ALLOC
357#endif
358#endif
359
360#endif /* OPENSSL_MACROS_H */
361