Monado OpenXR Runtime
xrt_compiler.h
Go to the documentation of this file.
1 // Copyright 2019, Collabora, Ltd.
2 // SPDX-License-Identifier: BSL-1.0
3 /*!
4  * @file
5  * @brief Header holding common defines.
6  * @author Jakob Bornecrantz <jakob@collabora.com>
7  * @ingroup xrt_iface
8  */
9 
10 #pragma once
11 
12 
13 /*
14  * C99 is not a high bar to reach.
15  */
16 #include <stddef.h>
17 #include <stdint.h>
18 #include <stdbool.h>
19 
20 #ifdef _MSC_VER
21 #include <intrin.h>
22 // for atomic intrinsics
23 #include "xrt_windows.h"
24 #endif // _MSC_VER
25 
26 /*!
27  * Array size helper.
28  */
29 #define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
30 
31 #if defined(__x86_64__) || defined(_M_X64) || defined(__aarch64__) || defined(_ARCH_PPC64) || defined(__s390x__) || \
32  (defined(__SIZEOF_POINTER__) && __SIZEOF_POINTER__ == 8)
33 #define XRT_64_BIT
34 #else
35 #define XRT_32_BIT
36 #endif
37 
38 /*
39  * Printf helper attribute.
40  */
41 #if defined(__GNUC__)
42 #define XRT_PRINTF_FORMAT(fmt, list) __attribute__((format(printf, fmt, list)))
43 #else
44 #define XRT_PRINTF_FORMAT(fmt, list)
45 #endif
46 
47 
48 /*
49  * To silence unused warnings.
50  */
51 #if defined(__GNUC__)
52 #define XRT_MAYBE_UNUSED __attribute__((unused))
53 #elif defined(_MSC_VER) && defined(__cplusplus)
54 #define XRT_MAYBE_UNUSED [[maybe_unused]]
55 #else
56 #define XRT_MAYBE_UNUSED
57 #endif
58 
59 
60 /*
61  * To make sure return values are checked.
62  */
63 #if defined(__GNUC__) && (__GNUC__ >= 4)
64 #define XRT_CHECK_RESULT __attribute__((warn_unused_result))
65 #elif defined(_MSC_VER) && (_MSC_VER >= 1700)
66 #define XRT_CHECK_RESULT _Check_return_
67 #else
68 #define XRT_CHECK_RESULT
69 #endif
70 
71 
72 /*
73  * To stop inlining.
74  */
75 #if defined(__GNUC__)
76 #define XRT_NO_INLINE __attribute__((noinline))
77 #elif defined(_MSC_VER)
78 #define XRT_NO_INLINE __declspec(noinline)
79 #else
80 #define XRT_NO_INLINE
81 #endif
82 
83 
84 #ifdef XRT_DOXYGEN
85 /*!
86  * To trigger a trap/break in the debugger.
87  *
88  * @ingroup xrt_iface
89  */
90 #define XRT_DEBUGBREAK()
91 #elif defined(__clang__) || defined(__GNUC__)
92 #define XRT_DEBUGBREAK() __builtin_trap()
93 #elif defined(_MSC_VER)
94 #define XRT_DEBUGBREAK() __debugbreak()
95 #else
96 #error "compiler not supported"
97 #endif
98 
99 
100 
101 typedef volatile int32_t xrt_atomic_s32_t;
102 
103 static inline int32_t
104 xrt_atomic_s32_inc_return(xrt_atomic_s32_t *p)
105 {
106 #if defined(__GNUC__)
107  return __sync_add_and_fetch(p, 1);
108 #elif defined(_MSC_VER)
109  return InterlockedIncrement((volatile LONG *)p);
110 #else
111 #error "compiler not supported"
112 #endif
113 }
114 static inline int32_t
115 xrt_atomic_s32_dec_return(xrt_atomic_s32_t *p)
116 {
117 #if defined(__GNUC__)
118  return __sync_sub_and_fetch(p, 1);
119 #elif defined(_MSC_VER)
120  return InterlockedDecrement((volatile LONG *)p);
121 #else
122 #error "compiler not supported"
123 #endif
124 }
125 static inline int32_t
126 xrt_atomic_s32_cmpxchg(xrt_atomic_s32_t *p, int32_t old_, int32_t new_)
127 {
128 #if defined(__GNUC__)
129  return __sync_val_compare_and_swap(p, old_, new_);
130 #elif defined(_MSC_VER)
131  return InterlockedCompareExchange((volatile LONG *)p, old_, new_);
132 #else
133 #error "compiler not supported"
134 #endif
135 }
136 
137 #ifdef _MSC_VER
138 typedef intptr_t ssize_t;
139 #define _SSIZE_T_
140 #define _SSIZE_T_DEFINED
141 #endif
142 
143 /*!
144  * Get the holder from a pointer to a field.
145  *
146  * @ingroup xrt_iface
147  */
148 #define container_of(ptr, type, field) (type *)((char *)ptr - offsetof(type, field))
149 
150 
151 #ifdef XRT_DOXYGEN
152 
153 /*!
154  * Very small default init for structs that works in both C and C++. Helps with
155  * code that needs to be compiled with both C and C++.
156  *
157  * @ingroup xrt_iface
158  */
159 
160 // clang-format off
161 #define XRT_STRUCT_INIT {}
162 // clang-format on
163 
164 #elif defined(__cplusplus)
165 
166 // clang-format off
167 #define XRT_STRUCT_INIT {}
168 // clang-format on
169 
170 #else
171 
172 // clang-format off
173 #define XRT_STRUCT_INIT {0}
174 // clang-format on
175 
176 #endif
A minimal way to include Windows.h.