Home | History | Annotate | Download | only in support
      1 // -*- C++ -*-
      2 //===---------------------------- test_macros.h ---------------------------===//
      3 //
      4 //                     The LLVM Compiler Infrastructure
      5 //
      6 // This file is dual licensed under the MIT and the University of Illinois Open
      7 // Source Licenses. See LICENSE.TXT for details.
      8 //
      9 //===----------------------------------------------------------------------===//
     10 
     11 #ifndef SUPPORT_TEST_MACROS_HPP
     12 #define SUPPORT_TEST_MACROS_HPP
     13 
     14 #include <ciso646> // Get STL specific macros like _LIBCPP_VERSION
     15 
     16 #if defined(__GNUC__)
     17 #pragma GCC diagnostic push
     18 #pragma GCC diagnostic ignored "-Wvariadic-macros"
     19 #endif
     20 
     21 #define TEST_CONCAT1(X, Y) X##Y
     22 #define TEST_CONCAT(X, Y) TEST_CONCAT1(X, Y)
     23 
     24 #ifdef __has_feature
     25 #define TEST_HAS_FEATURE(X) __has_feature(X)
     26 #else
     27 #define TEST_HAS_FEATURE(X) 0
     28 #endif
     29 
     30 #ifndef __has_include
     31 #define __has_include(...) 0
     32 #endif
     33 
     34 #ifdef __has_extension
     35 #define TEST_HAS_EXTENSION(X) __has_extension(X)
     36 #else
     37 #define TEST_HAS_EXTENSION(X) 0
     38 #endif
     39 
     40 #ifdef __has_builtin
     41 #define TEST_HAS_BUILTIN(X) __has_builtin(X)
     42 #else
     43 #define TEST_HAS_BUILTIN(X) 0
     44 #endif
     45 #ifdef __is_identifier
     46 // '__is_identifier' returns '0' if '__x' is a reserved identifier provided by
     47 // the compiler and '1' otherwise.
     48 #define TEST_HAS_BUILTIN_IDENTIFIER(X) !__is_identifier(X)
     49 #else
     50 #define TEST_HAS_BUILTIN_IDENTIFIER(X) 0
     51 #endif
     52 
     53 #if defined(__EDG__)
     54 # define TEST_COMPILER_EDG
     55 #elif defined(__clang__)
     56 # define TEST_COMPILER_CLANG
     57 # if defined(__apple_build_version__)
     58 #  define TEST_COMPILER_APPLE_CLANG
     59 # endif
     60 #elif defined(_MSC_VER)
     61 # define TEST_COMPILER_C1XX
     62 #elif defined(__GNUC__)
     63 # define TEST_COMPILER_GCC
     64 #endif
     65 
     66 #if defined(__apple_build_version__)
     67 #define TEST_APPLE_CLANG_VER (__clang_major__ * 100) + __clang_minor__
     68 #elif defined(__clang_major__)
     69 #define TEST_CLANG_VER (__clang_major__ * 100) + __clang_minor__
     70 #elif defined(__GNUC__)
     71 #define TEST_GCC_VER (__GNUC__ * 100 + __GNUC_MINOR__)
     72 #endif
     73 
     74 /* Make a nice name for the standard version */
     75 #ifndef TEST_STD_VER
     76 #if  __cplusplus <= 199711L
     77 # define TEST_STD_VER 3
     78 #elif __cplusplus <= 201103L
     79 # define TEST_STD_VER 11
     80 #elif __cplusplus <= 201402L
     81 # define TEST_STD_VER 14
     82 #elif __cplusplus <= 201703L
     83 # define TEST_STD_VER 17
     84 #else
     85 # define TEST_STD_VER 99    // greater than current standard
     86 // This is deliberately different than _LIBCPP_STD_VER to discourage matching them up.
     87 #endif
     88 #endif
     89 
     90 // Attempt to deduce the GLIBC version
     91 #if (defined(__has_include) && __has_include(<features.h>)) || \
     92     defined(__linux__)
     93 #include <features.h>
     94 #if defined(__GLIBC_PREREQ)
     95 #define TEST_HAS_GLIBC
     96 #define TEST_GLIBC_PREREQ(major, minor) __GLIBC_PREREQ(major, minor)
     97 #endif
     98 #endif
     99 
    100 #if TEST_STD_VER >= 11
    101 #define TEST_ALIGNOF(...) alignof(__VA_ARGS__)
    102 #define TEST_ALIGNAS(...) alignas(__VA_ARGS__)
    103 #define TEST_CONSTEXPR constexpr
    104 #define TEST_NOEXCEPT noexcept
    105 #define TEST_NOEXCEPT_FALSE noexcept(false)
    106 #define TEST_NOEXCEPT_COND(...) noexcept(__VA_ARGS__)
    107 # if TEST_STD_VER >= 14
    108 #   define TEST_CONSTEXPR_CXX14 constexpr
    109 # else
    110 #   define TEST_CONSTEXPR_CXX14
    111 # endif
    112 # if TEST_STD_VER > 14
    113 #   define TEST_THROW_SPEC(...)
    114 # else
    115 #   define TEST_THROW_SPEC(...) throw(__VA_ARGS__)
    116 # endif
    117 #else
    118 #define TEST_ALIGNOF(...) __alignof(__VA_ARGS__)
    119 #define TEST_ALIGNAS(...) __attribute__((__aligned__(__VA_ARGS__)))
    120 #define TEST_CONSTEXPR
    121 #define TEST_CONSTEXPR_CXX14
    122 #define TEST_NOEXCEPT throw()
    123 #define TEST_NOEXCEPT_FALSE
    124 #define TEST_NOEXCEPT_COND(...)
    125 #define TEST_THROW_SPEC(...) throw(__VA_ARGS__)
    126 #endif
    127 
    128 // Sniff out to see if the underling C library has C11 features
    129 // Note that at this time (July 2018), MacOS X and iOS do NOT.
    130 // This is cribbed from __config; but lives here as well because we can't assume libc++
    131 #if __ISO_C_VISIBLE >= 2011 || TEST_STD_VER >= 11
    132 #  if defined(__FreeBSD__)
    133 //  Specifically, FreeBSD does NOT have timespec_get, even though they have all
    134 //  the rest of C11 - this is PR#38495
    135 #    define TEST_HAS_C11_FEATURES
    136 #  elif defined(__Fuchsia__)
    137 #    define TEST_HAS_C11_FEATURES
    138 #    define TEST_HAS_TIMESPEC_GET
    139 #  elif defined(__linux__)
    140 // This block preserves the old behavior used by include/__config:
    141 // _LIBCPP_GLIBC_PREREQ would be defined to 0 if __GLIBC_PREREQ was not
    142 // available. The configuration here may be too vague though, as Bionic, uClibc,
    143 // newlib, etc may all support these features but need to be configured.
    144 #    if defined(TEST_GLIBC_PREREQ)
    145 #      if TEST_GLIBC_PREREQ(2, 17)
    146 #        define TEST_HAS_TIMESPEC_GET
    147 #        define TEST_HAS_C11_FEATURES
    148 #      endif
    149 #    elif defined(_LIBCPP_HAS_MUSL_LIBC)
    150 #      define TEST_HAS_C11_FEATURES
    151 #      define TEST_HAS_TIMESPEC_GET
    152 #    endif
    153 #  elif defined(_WIN32)
    154 #    if defined(_MSC_VER) && !defined(__MINGW32__)
    155 #      define TEST_HAS_C11_FEATURES // Using Microsoft's C Runtime library
    156 #      define TEST_HAS_TIMESPEC_GET
    157 #    endif
    158 #  endif
    159 #endif
    160 
    161 /* Features that were introduced in C++14 */
    162 #if TEST_STD_VER >= 14
    163 #define TEST_HAS_EXTENDED_CONSTEXPR
    164 #define TEST_HAS_VARIABLE_TEMPLATES
    165 #endif
    166 
    167 /* Features that were introduced in C++17 */
    168 #if TEST_STD_VER >= 17
    169 #endif
    170 
    171 /* Features that were introduced after C++17 */
    172 #if TEST_STD_VER > 17
    173 #endif
    174 
    175 
    176 #define TEST_ALIGNAS_TYPE(...) TEST_ALIGNAS(TEST_ALIGNOF(__VA_ARGS__))
    177 
    178 #if !TEST_HAS_FEATURE(cxx_rtti) && !defined(__cpp_rtti) \
    179     && !defined(__GXX_RTTI)
    180 #define TEST_HAS_NO_RTTI
    181 #endif
    182 
    183 #if !TEST_HAS_FEATURE(cxx_exceptions) && !defined(__cpp_exceptions) \
    184      && !defined(__EXCEPTIONS)
    185 #define TEST_HAS_NO_EXCEPTIONS
    186 #endif
    187 
    188 #if TEST_HAS_FEATURE(address_sanitizer) || TEST_HAS_FEATURE(memory_sanitizer) || \
    189     TEST_HAS_FEATURE(thread_sanitizer)
    190 #define TEST_HAS_SANITIZERS
    191 #endif
    192 
    193 #if defined(_LIBCPP_NORETURN)
    194 #define TEST_NORETURN _LIBCPP_NORETURN
    195 #else
    196 #define TEST_NORETURN [[noreturn]]
    197 #endif
    198 
    199 #if defined(_LIBCPP_HAS_NO_ALIGNED_ALLOCATION) || \
    200   (!(TEST_STD_VER > 14 || \
    201     (defined(__cpp_aligned_new) && __cpp_aligned_new >= 201606L)))
    202 #define TEST_HAS_NO_ALIGNED_ALLOCATION
    203 #endif
    204 
    205 #if defined(_LIBCPP_SAFE_STATIC)
    206 #define TEST_SAFE_STATIC _LIBCPP_SAFE_STATIC
    207 #else
    208 #define TEST_SAFE_STATIC
    209 #endif
    210 
    211 // FIXME: Fix this feature check when either (A) a compiler provides a complete
    212 // implementation, or (b) a feature check macro is specified
    213 #define TEST_HAS_NO_SPACESHIP_OPERATOR
    214 
    215 
    216 #if TEST_STD_VER < 11
    217 #define ASSERT_NOEXCEPT(...)
    218 #define ASSERT_NOT_NOEXCEPT(...)
    219 #else
    220 #define ASSERT_NOEXCEPT(...) \
    221     static_assert(noexcept(__VA_ARGS__), "Operation must be noexcept")
    222 
    223 #define ASSERT_NOT_NOEXCEPT(...) \
    224     static_assert(!noexcept(__VA_ARGS__), "Operation must NOT be noexcept")
    225 #endif
    226 
    227 /* Macros for testing libc++ specific behavior and extensions */
    228 #if defined(_LIBCPP_VERSION)
    229 #define LIBCPP_ASSERT(...) assert(__VA_ARGS__)
    230 #define LIBCPP_STATIC_ASSERT(...) static_assert(__VA_ARGS__)
    231 #define LIBCPP_ASSERT_NOEXCEPT(...) ASSERT_NOEXCEPT(__VA_ARGS__)
    232 #define LIBCPP_ASSERT_NOT_NOEXCEPT(...) ASSERT_NOT_NOEXCEPT(__VA_ARGS__)
    233 #define LIBCPP_ONLY(...) __VA_ARGS__
    234 #else
    235 #define LIBCPP_ASSERT(...) ((void)0)
    236 #define LIBCPP_STATIC_ASSERT(...) ((void)0)
    237 #define LIBCPP_ASSERT_NOEXCEPT(...) ((void)0)
    238 #define LIBCPP_ASSERT_NOT_NOEXCEPT(...) ((void)0)
    239 #define LIBCPP_ONLY(...) ((void)0)
    240 #endif
    241 
    242 #define TEST_IGNORE_NODISCARD (void)
    243 
    244 namespace test_macros_detail {
    245 template <class T, class U>
    246 struct is_same { enum { value = 0};} ;
    247 template <class T>
    248 struct is_same<T, T> { enum {value = 1}; };
    249 } // namespace test_macros_detail
    250 
    251 #define ASSERT_SAME_TYPE(...) \
    252     static_assert((test_macros_detail::is_same<__VA_ARGS__>::value), \
    253                  "Types differ unexpectedly")
    254 
    255 #ifndef TEST_HAS_NO_EXCEPTIONS
    256 #define TEST_THROW(...) throw __VA_ARGS__
    257 #else
    258 #if defined(__GNUC__)
    259 #define TEST_THROW(...) __builtin_abort()
    260 #else
    261 #include <stdlib.h>
    262 #define TEST_THROW(...) ::abort()
    263 #endif
    264 #endif
    265 
    266 #if defined(__GNUC__) || defined(__clang__)
    267 template <class Tp>
    268 inline
    269 void DoNotOptimize(Tp const& value) {
    270     asm volatile("" : : "r,m"(value) : "memory");
    271 }
    272 
    273 template <class Tp>
    274 inline void DoNotOptimize(Tp& value) {
    275 #if defined(__clang__)
    276   asm volatile("" : "+r,m"(value) : : "memory");
    277 #else
    278   asm volatile("" : "+m,r"(value) : : "memory");
    279 #endif
    280 }
    281 #else
    282 #include <intrin.h>
    283 template <class Tp>
    284 inline void DoNotOptimize(Tp const& value) {
    285   const volatile void* volatile unused = __builtin_addressof(value);
    286   static_cast<void>(unused);
    287   _ReadWriteBarrier();
    288 }
    289 #endif
    290 
    291 #if defined(__GNUC__)
    292 #define TEST_ALWAYS_INLINE __attribute__((always_inline))
    293 #define TEST_NOINLINE __attribute__((noinline))
    294 #elif defined(_MSC_VER)
    295 #define TEST_ALWAYS_INLINE __forceinline
    296 #define TEST_NOINLINE __declspec(noinline)
    297 #else
    298 #define TEST_ALWAYS_INLINE
    299 #define TEST_NOINLINE
    300 #endif
    301 
    302 #if defined(__GNUC__)
    303 #pragma GCC diagnostic pop
    304 #endif
    305 
    306 #endif // SUPPORT_TEST_MACROS_HPP
    307