1 // Copyright 2014 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifndef V8_BASE_MACROS_H_
6 #define V8_BASE_MACROS_H_
7
8 #include <limits>
9 #include <type_traits>
10
11 #include "src/base/compiler-specific.h"
12 #include "src/base/logging.h"
13 #include "src/base/platform/wrappers.h"
14
15 // No-op macro which is used to work around MSVC's funky VA_ARGS support.
16 #define EXPAND(x) x
17
18 // This macro does nothing. That's all.
19 #define NOTHING(...)
20
21 #define CONCAT_(a, b) a##b
22 #define CONCAT(a, b) CONCAT_(a, b)
23 // Creates an unique identifier. Useful for scopes to avoid shadowing names.
24 #define UNIQUE_IDENTIFIER(base) CONCAT(base, __COUNTER__)
25
26 // TODO(all) Replace all uses of this macro with C++'s offsetof. To do that, we
27 // have to make sure that only standard-layout types and simple field
28 // designators are used.
29 #define OFFSET_OF(type, field) \
30 (reinterpret_cast<intptr_t>(&(reinterpret_cast<type*>(16)->field)) - 16)
31
32
33 // The arraysize(arr) macro returns the # of elements in an array arr.
34 // The expression is a compile-time constant, and therefore can be
35 // used in defining new arrays, for example. If you use arraysize on
36 // a pointer by mistake, you will get a compile-time error.
37 #define arraysize(array) (sizeof(ArraySizeHelper(array)))
38
39
40 // This template function declaration is used in defining arraysize.
41 // Note that the function doesn't need an implementation, as we only
42 // use its type.
43 template <typename T, size_t N>
44 char (&ArraySizeHelper(T (&array)[N]))[N];
45
46
47 #if !V8_CC_MSVC
48 // That gcc wants both of these prototypes seems mysterious. VC, for
49 // its part, can't decide which to use (another mystery). Matching of
50 // template overloads: the final frontier.
51 template <typename T, size_t N>
52 char (&ArraySizeHelper(const T (&array)[N]))[N];
53 #endif
54
55 // bit_cast<Dest,Source> is a template function that implements the
56 // equivalent of "*reinterpret_cast<Dest*>(&source)". We need this in
57 // very low-level functions like the protobuf library and fast math
58 // support.
59 //
60 // float f = 3.14159265358979;
61 // int i = bit_cast<int32>(f);
62 // // i = 0x40490fdb
63 //
64 // The classical address-casting method is:
65 //
66 // // WRONG
67 // float f = 3.14159265358979; // WRONG
68 // int i = * reinterpret_cast<int*>(&f); // WRONG
69 //
70 // The address-casting method actually produces undefined behavior
71 // according to ISO C++ specification section 3.10 -15 -. Roughly, this
72 // section says: if an object in memory has one type, and a program
73 // accesses it with a different type, then the result is undefined
74 // behavior for most values of "different type".
75 //
76 // This is true for any cast syntax, either *(int*)&f or
77 // *reinterpret_cast<int*>(&f). And it is particularly true for
78 // conversions between integral lvalues and floating-point lvalues.
79 //
80 // The purpose of 3.10 -15- is to allow optimizing compilers to assume
81 // that expressions with different types refer to different memory. gcc
82 // 4.0.1 has an optimizer that takes advantage of this. So a
83 // non-conforming program quietly produces wildly incorrect output.
84 //
85 // The problem is not the use of reinterpret_cast. The problem is type
86 // punning: holding an object in memory of one type and reading its bits
87 // back using a different type.
88 //
89 // The C++ standard is more subtle and complex than this, but that
90 // is the basic idea.
91 //
92 // Anyways ...
93 //
94 // bit_cast<> calls memcpy() which is blessed by the standard,
95 // especially by the example in section 3.9 . Also, of course,
96 // bit_cast<> wraps up the nasty logic in one place.
97 //
98 // Fortunately memcpy() is very fast. In optimized mode, with a
99 // constant size, gcc 2.95.3, gcc 4.0.1, and msvc 7.1 produce inline
100 // code with the minimal amount of data movement. On a 32-bit system,
101 // memcpy(d,s,4) compiles to one load and one store, and memcpy(d,s,8)
102 // compiles to two loads and two stores.
103 //
104 // I tested this code with gcc 2.95.3, gcc 4.0.1, icc 8.1, and msvc 7.1.
105 //
106 // WARNING: if Dest or Source is a non-POD type, the result of the memcpy
107 // is likely to surprise you.
108 template <class Dest, class Source>
bit_cast(Source const & source)109 V8_INLINE Dest bit_cast(Source const& source) {
110 static_assert(sizeof(Dest) == sizeof(Source),
111 "source and dest must be same size");
112 Dest dest;
113 memcpy(&dest, &source, sizeof(dest));
114 return dest;
115 }
116
117 // Explicitly declare the assignment operator as deleted.
118 // Note: This macro is deprecated and will be removed soon. Please explicitly
119 // delete the assignment operator instead.
120 #define DISALLOW_ASSIGN(TypeName) TypeName& operator=(const TypeName&) = delete
121
122 // Explicitly declare all implicit constructors as deleted, namely the
123 // default constructor, copy constructor and operator= functions.
124 // This is especially useful for classes containing only static methods.
125 #define DISALLOW_IMPLICIT_CONSTRUCTORS(TypeName) \
126 TypeName() = delete; \
127 TypeName(const TypeName&) = delete; \
128 DISALLOW_ASSIGN(TypeName)
129
130 // Disallow copying a type, but provide default construction, move construction
131 // and move assignment. Especially useful for move-only structs.
132 #define MOVE_ONLY_WITH_DEFAULT_CONSTRUCTORS(TypeName) \
133 TypeName() = default; \
134 MOVE_ONLY_NO_DEFAULT_CONSTRUCTOR(TypeName)
135
136 // Disallow copying a type, and only provide move construction and move
137 // assignment. Especially useful for move-only structs.
138 #define MOVE_ONLY_NO_DEFAULT_CONSTRUCTOR(TypeName) \
139 TypeName(TypeName&&) V8_NOEXCEPT = default; \
140 TypeName& operator=(TypeName&&) V8_NOEXCEPT = default; \
141 TypeName(const TypeName&) = delete; \
142 DISALLOW_ASSIGN(TypeName)
143
144 // A macro to disallow the dynamic allocation.
145 // This should be used in the private: declarations for a class
146 // Declaring operator new and delete as deleted is not spec compliant.
147 // Extract from 3.2.2 of C++11 spec:
148 // [...] A non-placement deallocation function for a class is
149 // odr-used by the definition of the destructor of that class, [...]
150 #define DISALLOW_NEW_AND_DELETE() \
151 void* operator new(size_t) { v8::base::OS::Abort(); } \
152 void* operator new[](size_t) { v8::base::OS::Abort(); } \
153 void operator delete(void*, size_t) { v8::base::OS::Abort(); } \
154 void operator delete[](void*, size_t) { v8::base::OS::Abort(); }
155
156 // Define V8_USE_ADDRESS_SANITIZER macro.
157 #if defined(__has_feature)
158 #if __has_feature(address_sanitizer)
159 #define V8_USE_ADDRESS_SANITIZER 1
160 #endif
161 #endif
162
163 // Define V8_USE_MEMORY_SANITIZER macro.
164 #if defined(__has_feature)
165 #if __has_feature(memory_sanitizer)
166 #define V8_USE_MEMORY_SANITIZER 1
167 #endif
168 #endif
169
170 // Define V8_USE_UNDEFINED_BEHAVIOR_SANITIZER macro.
171 #if defined(__has_feature)
172 #if __has_feature(undefined_behavior_sanitizer)
173 #define V8_USE_UNDEFINED_BEHAVIOR_SANITIZER 1
174 #endif
175 #endif
176
177 // DISABLE_CFI_PERF -- Disable Control Flow Integrity checks for Perf reasons.
178 #define DISABLE_CFI_PERF V8_CLANG_NO_SANITIZE("cfi")
179
180 // DISABLE_CFI_ICALL -- Disable Control Flow Integrity indirect call checks,
181 // useful because calls into JITed code can not be CFI verified.
182 #ifdef V8_OS_WIN
183 // On Windows, also needs __declspec(guard(nocf)) for CFG.
184 #define DISABLE_CFI_ICALL \
185 V8_CLANG_NO_SANITIZE("cfi-icall") \
186 __declspec(guard(nocf))
187 #else
188 #define DISABLE_CFI_ICALL V8_CLANG_NO_SANITIZE("cfi-icall")
189 #endif
190
191 // A convenience wrapper around static_assert without a string message argument.
192 // Once C++17 becomes the default, this macro can be removed in favor of the
193 // new static_assert(condition) overload.
194 #define STATIC_ASSERT(test) static_assert(test, #test)
195
196 namespace v8 {
197 namespace base {
198
199 // Note that some implementations of std::is_trivially_copyable mandate that at
200 // least one of the copy constructor, move constructor, copy assignment or move
201 // assignment is non-deleted, while others do not. Be aware that also
202 // base::is_trivially_copyable will differ for these cases.
203 template <typename T>
204 struct is_trivially_copyable {
205 #if V8_CC_MSVC
206 // Unfortunately, MSVC 2015 is broken in that std::is_trivially_copyable can
207 // be false even though it should be true according to the standard.
208 // (status at 2018-02-26, observed on the msvc waterfall bot).
209 // Interestingly, the lower-level primitives used below are working as
210 // intended, so we reimplement this according to the standard.
211 // See also https://developercommunity.visualstudio.com/content/problem/
212 // 170883/msvc-type-traits-stdis-trivial-is-bugged.html.
213 static constexpr bool value =
214 // Copy constructor is trivial or deleted.
215 (std::is_trivially_copy_constructible<T>::value ||
216 !std::is_copy_constructible<T>::value) &&
217 // Copy assignment operator is trivial or deleted.
218 (std::is_trivially_copy_assignable<T>::value ||
219 !std::is_copy_assignable<T>::value) &&
220 // Move constructor is trivial or deleted.
221 (std::is_trivially_move_constructible<T>::value ||
222 !std::is_move_constructible<T>::value) &&
223 // Move assignment operator is trivial or deleted.
224 (std::is_trivially_move_assignable<T>::value ||
225 !std::is_move_assignable<T>::value) &&
226 // (Some implementations mandate that one of the above is non-deleted, but
227 // the standard does not, so let's skip this check.)
228 // Trivial non-deleted destructor.
229 std::is_trivially_destructible<T>::value;
230 #else
231 static constexpr bool value = std::is_trivially_copyable<T>::value;
232 #endif
233 };
234 #define ASSERT_TRIVIALLY_COPYABLE(T) \
235 static_assert(::v8::base::is_trivially_copyable<T>::value, \
236 #T " should be trivially copyable")
237 #define ASSERT_NOT_TRIVIALLY_COPYABLE(T) \
238 static_assert(!::v8::base::is_trivially_copyable<T>::value, \
239 #T " should not be trivially copyable")
240
241 // The USE(x, ...) template is used to silence C++ compiler warnings
242 // issued for (yet) unused variables (typically parameters).
243 // The arguments are guaranteed to be evaluated from left to right.
244 struct Use {
245 template <typename T>
UseUse246 Use(T&&) {} // NOLINT(runtime/explicit)
247 };
248 #define USE(...) \
249 do { \
250 ::v8::base::Use unused_tmp_array_for_use_macro[]{__VA_ARGS__}; \
251 (void)unused_tmp_array_for_use_macro; \
252 } while (false)
253
254 } // namespace base
255 } // namespace v8
256
257 // implicit_cast<A>(x) triggers an implicit cast from {x} to type {A}. This is
258 // useful in situations where static_cast<A>(x) would do too much.
259 // Only use this for cheap-to-copy types, or use move semantics explicitly.
260 template <class A>
implicit_cast(A x)261 V8_INLINE A implicit_cast(A x) {
262 return x;
263 }
264
265 // Define our own macros for writing 64-bit constants. This is less fragile
266 // than defining __STDC_CONSTANT_MACROS before including <stdint.h>, and it
267 // works on compilers that don't have it (like MSVC).
268 #if V8_CC_MSVC
269 # if V8_HOST_ARCH_64_BIT
270 # define V8_PTR_PREFIX "ll"
271 # else
272 # define V8_PTR_PREFIX ""
273 # endif // V8_HOST_ARCH_64_BIT
274 #elif V8_CC_MINGW64
275 # define V8_PTR_PREFIX "I64"
276 #elif V8_HOST_ARCH_64_BIT
277 # define V8_PTR_PREFIX "l"
278 #else
279 #if V8_OS_AIX
280 #define V8_PTR_PREFIX "l"
281 #else
282 # define V8_PTR_PREFIX ""
283 #endif
284 #endif
285
286 #define V8PRIxPTR V8_PTR_PREFIX "x"
287 #define V8PRIdPTR V8_PTR_PREFIX "d"
288 #define V8PRIuPTR V8_PTR_PREFIX "u"
289
290 #if V8_TARGET_ARCH_64_BIT
291 #define V8_PTR_HEX_DIGITS 12
292 #define V8PRIxPTR_FMT "0x%012" V8PRIxPTR
293 #else
294 #define V8_PTR_HEX_DIGITS 8
295 #define V8PRIxPTR_FMT "0x%08" V8PRIxPTR
296 #endif
297
298 // ptrdiff_t is 't' according to the standard, but MSVC uses 'I'.
299 #if V8_CC_MSVC
300 #define V8PRIxPTRDIFF "Ix"
301 #define V8PRIdPTRDIFF "Id"
302 #define V8PRIuPTRDIFF "Iu"
303 #else
304 #define V8PRIxPTRDIFF "tx"
305 #define V8PRIdPTRDIFF "td"
306 #define V8PRIuPTRDIFF "tu"
307 #endif
308
309 // Fix for Mac OS X defining uintptr_t as "unsigned long":
310 #if V8_OS_DARWIN
311 #undef V8PRIxPTR
312 #define V8PRIxPTR "lx"
313 #undef V8PRIdPTR
314 #define V8PRIdPTR "ld"
315 #undef V8PRIuPTR
316 #define V8PRIuPTR "lxu"
317 #endif
318
319 // Make a uint64 from two uint32_t halves.
make_uint64(uint32_t high,uint32_t low)320 inline uint64_t make_uint64(uint32_t high, uint32_t low) {
321 return (uint64_t{high} << 32) + low;
322 }
323
324 // Return the largest multiple of m which is <= x.
325 template <typename T>
RoundDown(T x,intptr_t m)326 inline T RoundDown(T x, intptr_t m) {
327 STATIC_ASSERT(std::is_integral<T>::value);
328 // m must be a power of two.
329 DCHECK(m != 0 && ((m & (m - 1)) == 0));
330 return x & static_cast<T>(-m);
331 }
332 template <intptr_t m, typename T>
RoundDown(T x)333 constexpr inline T RoundDown(T x) {
334 STATIC_ASSERT(std::is_integral<T>::value);
335 // m must be a power of two.
336 STATIC_ASSERT(m != 0 && ((m & (m - 1)) == 0));
337 return x & static_cast<T>(-m);
338 }
339
340 // Return the smallest multiple of m which is >= x.
341 template <typename T>
RoundUp(T x,intptr_t m)342 inline T RoundUp(T x, intptr_t m) {
343 STATIC_ASSERT(std::is_integral<T>::value);
344 return RoundDown<T>(static_cast<T>(x + m - 1), m);
345 }
346 template <intptr_t m, typename T>
RoundUp(T x)347 constexpr inline T RoundUp(T x) {
348 STATIC_ASSERT(std::is_integral<T>::value);
349 return RoundDown<m, T>(static_cast<T>(x + (m - 1)));
350 }
351
352 template <typename T, typename U>
IsAligned(T value,U alignment)353 constexpr inline bool IsAligned(T value, U alignment) {
354 return (value & (alignment - 1)) == 0;
355 }
356
AlignedAddress(void * address,size_t alignment)357 inline void* AlignedAddress(void* address, size_t alignment) {
358 // The alignment must be a power of two.
359 DCHECK_EQ(alignment & (alignment - 1), 0u);
360 return reinterpret_cast<void*>(reinterpret_cast<uintptr_t>(address) &
361 ~static_cast<uintptr_t>(alignment - 1));
362 }
363
364 // Bounds checks for float to integer conversions, which does truncation. Hence,
365 // the range of legal values is (min - 1, max + 1).
366 template <typename int_t, typename float_t, typename biggest_int_t = int64_t>
is_inbounds(float_t v)367 bool is_inbounds(float_t v) {
368 static_assert(sizeof(int_t) < sizeof(biggest_int_t),
369 "int_t can't be bounds checked by the compiler");
370 constexpr float_t kLowerBound =
371 static_cast<float_t>(std::numeric_limits<int_t>::min()) - 1;
372 constexpr float_t kUpperBound =
373 static_cast<float_t>(std::numeric_limits<int_t>::max()) + 1;
374 constexpr bool kLowerBoundIsMin =
375 static_cast<biggest_int_t>(kLowerBound) ==
376 static_cast<biggest_int_t>(std::numeric_limits<int_t>::min());
377 constexpr bool kUpperBoundIsMax =
378 static_cast<biggest_int_t>(kUpperBound) ==
379 static_cast<biggest_int_t>(std::numeric_limits<int_t>::max());
380 // Using USE(var) is only a workaround for a GCC 8.1 bug.
381 USE(kLowerBoundIsMin);
382 USE(kUpperBoundIsMax);
383 return (kLowerBoundIsMin ? (kLowerBound <= v) : (kLowerBound < v)) &&
384 (kUpperBoundIsMax ? (v <= kUpperBound) : (v < kUpperBound));
385 }
386
387 #ifdef V8_OS_WIN
388
389 // Setup for Windows shared library export.
390 #ifdef BUILDING_V8_SHARED
391 #define V8_EXPORT_PRIVATE __declspec(dllexport)
392 #elif USING_V8_SHARED
393 #define V8_EXPORT_PRIVATE __declspec(dllimport)
394 #else
395 #define V8_EXPORT_PRIVATE
396 #endif // BUILDING_V8_SHARED
397
398 #else // V8_OS_WIN
399
400 // Setup for Linux shared library export.
401 #if V8_HAS_ATTRIBUTE_VISIBILITY
402 #ifdef BUILDING_V8_SHARED
403 #define V8_EXPORT_PRIVATE __attribute__((visibility("default")))
404 #else
405 #define V8_EXPORT_PRIVATE
406 #endif
407 #else
408 #define V8_EXPORT_PRIVATE
409 #endif
410
411 #endif // V8_OS_WIN
412
413 // Defines IF_WASM, to be used in macro lists for elements that should only be
414 // there if WebAssembly is enabled.
415 #if V8_ENABLE_WEBASSEMBLY
416 // EXPAND is needed to work around MSVC's broken __VA_ARGS__ expansion.
417 #define IF_WASM(V, ...) EXPAND(V(__VA_ARGS__))
418 #else
419 #define IF_WASM(V, ...)
420 #endif // V8_ENABLE_WEBASSEMBLY
421
422 // Defines IF_TSAN, to be used in macro lists for elements that should only be
423 // there if TSAN is enabled.
424 #ifdef V8_IS_TSAN
425 // EXPAND is needed to work around MSVC's broken __VA_ARGS__ expansion.
426 #define IF_TSAN(V, ...) EXPAND(V(__VA_ARGS__))
427 #else
428 #define IF_TSAN(V, ...)
429 #endif // V8_ENABLE_WEBASSEMBLY
430
431 #ifdef GOOGLE3
432 // Disable FRIEND_TEST macro in Google3.
433 #define FRIEND_TEST(test_case_name, test_name)
434 #endif
435
436 #endif // V8_BASE_MACROS_H_
437