1 #ifndef MY_COMPILER_INCLUDED
2 #define MY_COMPILER_INCLUDED
3
4 /* Copyright (c) 2010, 2016, Oracle and/or its affiliates. All rights reserved.
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License, version 2.0,
8 as published by the Free Software Foundation.
9
10 This program is also distributed with certain software (including
11 but not limited to OpenSSL) that is licensed under separate terms,
12 as designated in a particular file or component or in included license
13 documentation. The authors of MySQL hereby grant you an additional
14 permission to link the program and your derivative works with the
15 separately licensed software that they have included with MySQL.
16
17 Without limiting anything contained in the foregoing, this file,
18 which is part of C Driver for MySQL (Connector/C), is also subject to the
19 Universal FOSS Exception, version 1.0, a copy of which can be found at
20 http://oss.oracle.com/licenses/universal-foss-exception.
21
22 This program is distributed in the hope that it will be useful,
23 but WITHOUT ANY WARRANTY; without even the implied warranty of
24 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
25 GNU General Public License, version 2.0, for more details.
26
27 You should have received a copy of the GNU General Public License
28 along with this program; if not, write to the Free Software
29 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
30
31 /**
32 Header for compiler-dependent features.
33
34 Intended to contain a set of reusable wrappers for preprocessor
35 macros, attributes, pragmas, and any other features that are
36 specific to a target compiler.
37 */
38
39 #include <stddef.h> /* size_t */
40
41 #if defined __GNUC__
42 /*
43 Convenience macro to test the minimum required GCC version.
44 These should be used with care as Clang also sets __GNUC__ and
45 __GNUC_MINOR__ (currently to 4.2). Prefer using feature specific
46 CMake checks in configure.cmake instead.
47 */
48 # define MY_GNUC_PREREQ(maj, min) \
49 ((__GNUC__ << 16) + __GNUC_MINOR__ >= ((maj) << 16) + (min))
50 # define GCC_VERSION (__GNUC__ * 1000 + __GNUC_MINOR__)
51 #else
52 # define MY_GNUC_PREREQ(maj, min) (0)
53 #endif
54
55 /*
56 The macros below are borrowed from include/linux/compiler.h in the
57 Linux kernel. Use them to indicate the likelyhood of the truthfulness
58 of a condition. This serves two purposes - newer versions of gcc will be
59 able to optimize for branch predication, which could yield siginficant
60 performance gains in frequently executed sections of the code, and the
61 other reason to use them is for documentation
62 */
63 #ifdef HAVE_BUILTIN_EXPECT
64
65 // likely/unlikely are likely to clash with other symbols, do not #define
66 #if defined(__cplusplus)
likely(bool expr)67 inline bool likely(bool expr)
68 {
69 return __builtin_expect(expr, true);
70 }
unlikely(bool expr)71 inline bool unlikely(bool expr)
72 {
73 return __builtin_expect(expr, false);
74 }
75 #else
76 # define likely(x) __builtin_expect((x),1)
77 # define unlikely(x) __builtin_expect((x),0)
78 #endif
79
80 #else /* HAVE_BUILTIN_EXPECT */
81
82 #if defined(__cplusplus)
likely(bool expr)83 inline bool likely(bool expr)
84 {
85 return expr;
86 }
unlikely(bool expr)87 inline bool unlikely(bool expr)
88 {
89 return expr;
90 }
91 #else
92 # define likely(x) (x)
93 # define unlikely(x) (x)
94 #endif
95
96 #endif /* HAVE_BUILTIN_EXPECT */
97
98 /* Comunicate to the compiler the unreachability of the code. */
99 #ifdef HAVE_BUILTIN_UNREACHABLE
100 # define MY_ASSERT_UNREACHABLE() __builtin_unreachable()
101 #else
102 # define MY_ASSERT_UNREACHABLE() do { assert(0); } while (0)
103 #endif
104
105 #if defined __GNUC__ || defined __SUNPRO_C || defined __SUNPRO_CC
106 /* Specifies the minimum alignment of a type. */
107 # define MY_ALIGNOF(type) __alignof__(type)
108 /* Determine the alignment requirement of a type. */
109 # define MY_ALIGNED(n) __attribute__((__aligned__((n))))
110 /* Microsoft Visual C++ */
111 #elif defined _MSC_VER
112 # define MY_ALIGNOF(type) __alignof(type)
113 # define MY_ALIGNED(n) __declspec(align(n))
114 #else /* Make sure they are defined for other compilers. */
115 # define MY_ALIGNOF(type)
116 # define MY_ALIGNED(size)
117 #endif
118
119 /* Visual Studio requires '__inline' for C code */
120 #if !defined(__cplusplus) && defined(_MSC_VER)
121 # define inline __inline
122 #endif
123
124 /* Provide __func__ macro definition for Visual Studio. */
125 #if defined(_MSC_VER)
126 # define __func__ __FUNCTION__
127 #endif
128
129 /**
130 C++ Type Traits
131 */
132 #ifdef __cplusplus
133
134 /**
135 Opaque storage with a particular alignment.
136 Partial specialization used due to MSVC++.
137 */
138 template<size_t alignment> struct my_alignment_imp;
139 template<> struct MY_ALIGNED(1) my_alignment_imp<1> {};
140 template<> struct MY_ALIGNED(2) my_alignment_imp<2> {};
141 template<> struct MY_ALIGNED(4) my_alignment_imp<4> {};
142 template<> struct MY_ALIGNED(8) my_alignment_imp<8> {};
143 template<> struct MY_ALIGNED(16) my_alignment_imp<16> {};
144
145 /**
146 A POD type with a given size and alignment.
147
148 @remark If the compiler does not support a alignment attribute
149 (MY_ALIGN macro), the default alignment of a double is
150 used instead.
151
152 @tparam size The minimum size.
153 @tparam alignment The desired alignment: 1, 2, 4, 8 or 16.
154 */
155 template <size_t size, size_t alignment>
156 struct my_aligned_storage
157 {
158 union
159 {
160 char data[size];
161 my_alignment_imp<alignment> align;
162 };
163 };
164
165 #endif /* __cplusplus */
166
167 /*
168 Disable MY_ATTRIBUTE for Sun Studio and Visual Studio.
169 Note that Sun Studio supports some __attribute__ variants,
170 but not format or unused which we use quite a lot.
171 */
172 #ifndef MY_ATTRIBUTE
173 #if defined(__GNUC__)
174 # define MY_ATTRIBUTE(A) __attribute__(A)
175 #else
176 # define MY_ATTRIBUTE(A)
177 #endif
178 #endif
179
180 #ifndef __has_attribute
181 # define __has_attribute(x) 0
182 #endif
183
184 #if __has_attribute(no_sanitize_undefined)
185 # define SUPPRESS_UBSAN __attribute__((no_sanitize_undefined))
186 #else
187 # define SUPPRESS_UBSAN
188 #endif
189
190 #endif /* MY_COMPILER_INCLUDED */
191