OpenVDB 11.0.0
Loading...
Searching...
No Matches
Platform.h
Go to the documentation of this file.
1// Copyright Contributors to the OpenVDB Project
2// SPDX-License-Identifier: MPL-2.0
3///
4/// @file Platform.h
5
6#ifndef OPENVDB_PLATFORM_HAS_BEEN_INCLUDED
7#define OPENVDB_PLATFORM_HAS_BEEN_INCLUDED
8
9#define PRAGMA(x) _Pragma(#x)
10
11/// @name Utilities
12/// @{
13/// @cond OPENVDB_DOCS_INTERNAL
14#define OPENVDB_PREPROC_STRINGIFY_(x) #x
15/// @endcond
16/// @brief Return @a x as a string literal. If @a x is a macro,
17/// return its value as a string literal.
18/// @hideinitializer
19#define OPENVDB_PREPROC_STRINGIFY(x) OPENVDB_PREPROC_STRINGIFY_(x)
20
21/// @cond OPENVDB_DOCS_INTERNAL
22#define OPENVDB_PREPROC_CONCAT_(x, y) x ## y
23/// @endcond
24/// @brief Form a new token by concatenating two existing tokens.
25/// If either token is a macro, concatenate its value.
26/// @hideinitializer
27#define OPENVDB_PREPROC_CONCAT(x, y) OPENVDB_PREPROC_CONCAT_(x, y)
28/// @}
29
30/// Macro for determining if GCC version is >= than X.Y
31#if defined(__GNUC__)
32 #define OPENVDB_CHECK_GCC(MAJOR, MINOR) \
33 (__GNUC__ > MAJOR || (__GNUC__ == MAJOR && __GNUC_MINOR__ >= MINOR))
34#else
35 #define OPENVDB_CHECK_GCC(MAJOR, MINOR) 0
36#endif
37
38/// OpenVDB now requires C++17
39#define OPENVDB_HAS_CXX11 1 // kept for backward compatibility
40
41#if __cplusplus >= 202002L
42 #define OPENVDB_HAS_CXX20
43#endif
44
45/// SIMD Intrinsic Headers
46#if defined(OPENVDB_USE_SSE42) || defined(OPENVDB_USE_AVX)
47 #if defined(_WIN32)
48 #include <intrin.h>
49 #elif defined(__GNUC__)
50 #if defined(__x86_64__) || defined(__i386__)
51 #include <x86intrin.h>
52 #elif defined(__ARM_NEON__)
53 #include <arm_neon.h>
54 #endif
55 #endif
56#endif
57
58/// Windows defines
59#ifdef _WIN32
60 ///Disable the non-portable Windows definitions of min() and max() macros
61 #ifndef NOMINMAX
62 #define NOMINMAX
63 #endif
64
65 // By default, assume we're building OpenVDB as a DLL if we're dynamically
66 // linking in the CRT, unless OPENVDB_STATICLIB is defined.
67 #if defined(_DLL) && !defined(OPENVDB_STATICLIB) && !defined(OPENVDB_DLL)
68 #define OPENVDB_DLL
69 #endif
70#endif
71
72/// Macros to suppress undefined behaviour sanitizer warnings. Should be used
73/// sparingly, primarily to suppress issues in upstream dependencies.
74#if defined(__clang__)
75#define OPENVDB_UBSAN_SUPPRESS(X) __attribute__((no_sanitize(X)))
76#else
77#define OPENVDB_UBSAN_SUPPRESS(X)
78#endif
79
80/// Macros to alias to compiler builtins which hint at critical edge selection
81/// during conditional statements.
82#if defined(__GNUC__) || defined(__clang__) || defined(__INTEL_COMPILER)
83#ifdef __cplusplus
84#define OPENVDB_LIKELY(x) (__builtin_expect(static_cast<bool>(x), true))
85#define OPENVDB_UNLIKELY(x) (__builtin_expect(static_cast<bool>(x), false))
86#else
87#define OPENVDB_LIKELY(x) (__builtin_expect((x), 1))
88#define OPENVDB_UNLIKELY(x) (__builtin_expect((x), 0))
89#endif
90#else
91#define OPENVDB_LIKELY(x) (x)
92#define OPENVDB_UNLIKELY(x) (x)
93#endif
94
95/// Force inline function macros. These macros do not necessary guarantee that
96/// the decorated function will be inlined, but provide the strongest vendor
97/// annotations to that end.
98#if defined(__GNUC__)
99#define OPENVDB_FORCE_INLINE __attribute__((always_inline)) inline
100#elif defined(_MSC_VER)
101#define OPENVDB_FORCE_INLINE __forceinline
102#else
103#define OPENVDB_FORCE_INLINE inline
104#endif
105
106/// Bracket code with OPENVDB_NO_UNREACHABLE_CODE_WARNING_BEGIN/_END,
107/// as in the following example, to inhibit ICC remarks about unreachable code:
108/// @code
109/// template<typename NodeType>
110/// void processNode(NodeType& node)
111/// {
112/// OPENVDB_NO_UNREACHABLE_CODE_WARNING_BEGIN
113/// if (NodeType::LEVEL == 0) return; // ignore leaf nodes
114/// int i = 0;
115/// ...
116/// OPENVDB_NO_UNREACHABLE_CODE_WARNING_END
117/// }
118/// @endcode
119/// In the above, <tt>NodeType::LEVEL == 0</tt> is a compile-time constant expression,
120/// so for some template instantiations, the line below it is unreachable.
121#if defined(__INTEL_COMPILER)
122 // Disable ICC remarks 111 ("statement is unreachable"), 128 ("loop is not reachable"),
123 // 185 ("dynamic initialization in unreachable code"), and 280 ("selector expression
124 // is constant").
125 #define OPENVDB_NO_UNREACHABLE_CODE_WARNING_BEGIN \
126 _Pragma("warning (push)") \
127 _Pragma("warning (disable:111)") \
128 _Pragma("warning (disable:128)") \
129 _Pragma("warning (disable:185)") \
130 _Pragma("warning (disable:280)")
131 #define OPENVDB_NO_UNREACHABLE_CODE_WARNING_END \
132 _Pragma("warning (pop)")
133#elif defined(__clang__)
134 #define OPENVDB_NO_UNREACHABLE_CODE_WARNING_BEGIN \
135 PRAGMA(clang diagnostic push) \
136 PRAGMA(clang diagnostic ignored "-Wunreachable-code")
137 #define OPENVDB_NO_UNREACHABLE_CODE_WARNING_END \
138 PRAGMA(clang diagnostic pop)
139#else
140 #define OPENVDB_NO_UNREACHABLE_CODE_WARNING_BEGIN
141 #define OPENVDB_NO_UNREACHABLE_CODE_WARNING_END
142#endif
143
144/// Deprecation macros. Define OPENVDB_NO_DEPRECATION_WARNINGS to disable all
145/// deprecation warnings in OpenVDB.
146#ifndef OPENVDB_NO_DEPRECATION_WARNINGS
147#define OPENVDB_DEPRECATED [[deprecated]]
148#define OPENVDB_DEPRECATED_MESSAGE(msg) [[deprecated(msg)]]
149#else
150#define OPENVDB_DEPRECATED
151#define OPENVDB_DEPRECATED_MESSAGE(msg)
152#endif
153
154/// @brief Bracket code with OPENVDB_NO_DEPRECATION_WARNING_BEGIN/_END,
155/// to inhibit warnings about deprecated code.
156/// @note Only intended to be used internally whilst parent code is being
157/// deprecated
158/// @details Example:
159/// @code
160/// OPENVDB_DEPRECATED void myDeprecatedFunction() {}
161///
162/// {
163/// OPENVDB_NO_DEPRECATION_WARNING_BEGIN
164/// myDeprecatedFunction();
165/// OPENVDB_NO_DEPRECATION_WARNING_END
166/// }
167/// @endcode
168#if defined __INTEL_COMPILER
169 #define OPENVDB_NO_DEPRECATION_WARNING_BEGIN \
170 _Pragma("warning (push)") \
171 _Pragma("warning (disable:1478)")
172 #define OPENVDB_NO_DEPRECATION_WARNING_END \
173 _Pragma("warning (pop)")
174#elif defined __clang__
175 #define OPENVDB_NO_DEPRECATION_WARNING_BEGIN \
176 _Pragma("clang diagnostic push") \
177 _Pragma("clang diagnostic ignored \"-Wdeprecated-declarations\"")
178 // note: no #pragma message, since Clang treats them as warnings
179 #define OPENVDB_NO_DEPRECATION_WARNING_END \
180 _Pragma("clang diagnostic pop")
181#elif defined __GNUC__
182 #define OPENVDB_NO_DEPRECATION_WARNING_BEGIN \
183 _Pragma("GCC diagnostic push") \
184 _Pragma("GCC diagnostic ignored \"-Wdeprecated-declarations\"")
185 #define OPENVDB_NO_DEPRECATION_WARNING_END \
186 _Pragma("GCC diagnostic pop")
187#elif defined _MSC_VER
188 #define OPENVDB_NO_DEPRECATION_WARNING_BEGIN \
189 __pragma(warning(push)) \
190 __pragma(warning(disable : 4996))
191 #define OPENVDB_NO_DEPRECATION_WARNING_END \
192 __pragma(warning(pop))
193#else
194 #define OPENVDB_NO_DEPRECATION_WARNING_BEGIN
195 #define OPENVDB_NO_DEPRECATION_WARNING_END
196#endif
197
198
199/// @brief Bracket code with OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN/_END,
200/// to inhibit warnings about type conversion.
201/// @note Use this sparingly. Use static casts and explicit type conversion if at all possible.
202/// @details Example:
203/// @code
204/// float value = 0.1f;
205/// OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
206/// int valueAsInt = value;
207/// OPENVDB_NO_TYPE_CONVERSION_WARNING_END
208/// @endcode
209#if defined __INTEL_COMPILER
210 #define OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
211 #define OPENVDB_NO_TYPE_CONVERSION_WARNING_END
212#elif defined __GNUC__
213 // -Wfloat-conversion was only introduced in GCC 4.9
214 #if OPENVDB_CHECK_GCC(4, 9)
215 #define OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN \
216 _Pragma("GCC diagnostic push") \
217 _Pragma("GCC diagnostic ignored \"-Wconversion\"") \
218 _Pragma("GCC diagnostic ignored \"-Wfloat-conversion\"")
219 #else
220 #define OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN \
221 _Pragma("GCC diagnostic push") \
222 _Pragma("GCC diagnostic ignored \"-Wconversion\"")
223 #endif
224 #define OPENVDB_NO_TYPE_CONVERSION_WARNING_END \
225 _Pragma("GCC diagnostic pop")
226#else
227 #define OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
228 #define OPENVDB_NO_TYPE_CONVERSION_WARNING_END
229#endif
230
231/// Helper macros for defining library symbol visibility
232#ifdef OPENVDB_EXPORT
233#undef OPENVDB_EXPORT
234#endif
235#ifdef OPENVDB_IMPORT
236#undef OPENVDB_IMPORT
237#endif
238#ifdef _WIN32
239 #ifdef OPENVDB_DLL
240 #define OPENVDB_EXPORT __declspec(dllexport)
241 #define OPENVDB_IMPORT __declspec(dllimport)
242 #else
243 #define OPENVDB_EXPORT
244 #define OPENVDB_IMPORT
245 #endif
246#elif defined(__GNUC__)
247 #define OPENVDB_EXPORT __attribute__((visibility("default")))
248 #define OPENVDB_IMPORT __attribute__((visibility("default")))
249#endif
250
251/// Helper macros for explicit template instantiation
252#if defined(_WIN32) && defined(OPENVDB_DLL)
253 #ifdef OPENVDB_PRIVATE
254 #define OPENVDB_TEMPLATE_EXPORT OPENVDB_EXPORT
255 #define OPENVDB_TEMPLATE_IMPORT
256 #else
257 #define OPENVDB_TEMPLATE_EXPORT
258 #define OPENVDB_TEMPLATE_IMPORT OPENVDB_IMPORT
259 #endif
260#else
261 #define OPENVDB_TEMPLATE_IMPORT
262 #define OPENVDB_TEMPLATE_EXPORT
263#endif
264
265/// All classes and public free standing functions must be explicitly marked
266/// as <lib>_API to be exported. The <lib>_PRIVATE macros are defined when
267/// building that particular library.
268#ifdef OPENVDB_API
269#undef OPENVDB_API
270#endif
271#ifdef OPENVDB_PRIVATE
272 #define OPENVDB_API OPENVDB_EXPORT
273#else
274 #define OPENVDB_API OPENVDB_IMPORT
275#endif
276#ifdef OPENVDB_HOUDINI_API
277#undef OPENVDB_HOUDINI_API
278#endif
279#ifdef OPENVDB_HOUDINI_PRIVATE
280 #define OPENVDB_HOUDINI_API OPENVDB_EXPORT
281#else
282 #define OPENVDB_HOUDINI_API OPENVDB_IMPORT
283#endif
284
285#ifdef OPENVDB_AX_DLL
286#ifdef OPENVDB_AX_API
287#undef OPENVDB_AX_API
288#endif
289#ifdef OPENVDB_AX_PRIVATE
290 #define OPENVDB_AX_API OPENVDB_EXPORT
291#else
292 #define OPENVDB_AX_API OPENVDB_IMPORT
293#endif
294#else
295#define OPENVDB_AX_API
296#endif // OPENVDB_AX_DLL
297
298#if defined(__ICC)
299
300// Use these defines to bracket a region of code that has safe static accesses.
301// Keep the region as small as possible.
302#define OPENVDB_START_THREADSAFE_STATIC_REFERENCE __pragma(warning(disable:1710))
303#define OPENVDB_FINISH_THREADSAFE_STATIC_REFERENCE __pragma(warning(default:1710))
304#define OPENVDB_START_THREADSAFE_STATIC_WRITE __pragma(warning(disable:1711))
305#define OPENVDB_FINISH_THREADSAFE_STATIC_WRITE __pragma(warning(default:1711))
306#define OPENVDB_START_THREADSAFE_STATIC_ADDRESS __pragma(warning(disable:1712))
307#define OPENVDB_FINISH_THREADSAFE_STATIC_ADDRESS __pragma(warning(default:1712))
308
309// Use these defines to bracket a region of code that has unsafe static accesses.
310// Keep the region as small as possible.
311#define OPENVDB_START_NON_THREADSAFE_STATIC_REFERENCE __pragma(warning(disable:1710))
312#define OPENVDB_FINISH_NON_THREADSAFE_STATIC_REFERENCE __pragma(warning(default:1710))
313#define OPENVDB_START_NON_THREADSAFE_STATIC_WRITE __pragma(warning(disable:1711))
314#define OPENVDB_FINISH_NON_THREADSAFE_STATIC_WRITE __pragma(warning(default:1711))
315#define OPENVDB_START_NON_THREADSAFE_STATIC_ADDRESS __pragma(warning(disable:1712))
316#define OPENVDB_FINISH_NON_THREADSAFE_STATIC_ADDRESS __pragma(warning(default:1712))
317
318// Simpler version for one-line cases
319#define OPENVDB_THREADSAFE_STATIC_REFERENCE(CODE) \
320 __pragma(warning(disable:1710)); CODE; __pragma(warning(default:1710))
321#define OPENVDB_THREADSAFE_STATIC_WRITE(CODE) \
322 __pragma(warning(disable:1711)); CODE; __pragma(warning(default:1711))
323#define OPENVDB_THREADSAFE_STATIC_ADDRESS(CODE) \
324 __pragma(warning(disable:1712)); CODE; __pragma(warning(default:1712))
325
326#else // GCC does not support these compiler warnings
327
328#define OPENVDB_START_THREADSAFE_STATIC_REFERENCE
329#define OPENVDB_FINISH_THREADSAFE_STATIC_REFERENCE
330#define OPENVDB_START_THREADSAFE_STATIC_WRITE
331#define OPENVDB_FINISH_THREADSAFE_STATIC_WRITE
332#define OPENVDB_START_THREADSAFE_STATIC_ADDRESS
333#define OPENVDB_FINISH_THREADSAFE_STATIC_ADDRESS
334
335#define OPENVDB_START_NON_THREADSAFE_STATIC_REFERENCE
336#define OPENVDB_FINISH_NON_THREADSAFE_STATIC_REFERENCE
337#define OPENVDB_START_NON_THREADSAFE_STATIC_WRITE
338#define OPENVDB_FINISH_NON_THREADSAFE_STATIC_WRITE
339#define OPENVDB_START_NON_THREADSAFE_STATIC_ADDRESS
340#define OPENVDB_FINISH_NON_THREADSAFE_STATIC_ADDRESS
341
342#define OPENVDB_THREADSAFE_STATIC_REFERENCE(CODE) CODE
343#define OPENVDB_THREADSAFE_STATIC_WRITE(CODE) CODE
344#define OPENVDB_THREADSAFE_STATIC_ADDRESS(CODE) CODE
345
346#endif // defined(__ICC)
347
348#endif // OPENVDB_PLATFORM_HAS_BEEN_INCLUDED