diff options
Diffstat (limited to 'boost/config/compiler/clang.hpp')
-rw-r--r-- | boost/config/compiler/clang.hpp | 149 |
1 files changed, 143 insertions, 6 deletions
diff --git a/boost/config/compiler/clang.hpp b/boost/config/compiler/clang.hpp index aab3c610c9..95ddcbefc7 100644 --- a/boost/config/compiler/clang.hpp +++ b/boost/config/compiler/clang.hpp @@ -1,13 +1,28 @@ // (C) Copyright Douglas Gregor 2010 // -// Use, modification and distribution are subject to the -// Boost Software License, Version 1.0. (See accompanying file +// Use, modification and distribution are subject to the +// Boost Software License, Version 1.0. (See accompanying file // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) // See http://www.boost.org for most recent version. // Clang compiler setup. +#define BOOST_HAS_PRAGMA_ONCE + +// Detecting `-fms-extension` compiler flag assuming that _MSC_VER defined when that flag is used. +#if defined (_MSC_VER) && (__clang_major__ > 3 || (__clang_major__ == 3 && __clang_minor__ >= 4)) +# define BOOST_HAS_PRAGMA_DETECT_MISMATCH +#endif + +// When compiling with clang before __has_extension was defined, +// even if one writes 'defined(__has_extension) && __has_extension(xxx)', +// clang reports a compiler error. So the only workaround found is: + +#ifndef __has_extension +#define __has_extension __has_feature +#endif + #if !__has_feature(cxx_exceptions) && !defined(BOOST_NO_EXCEPTIONS) # define BOOST_NO_EXCEPTIONS #endif @@ -20,21 +35,64 @@ # define BOOST_NO_TYPEID #endif -#if defined(__int64) +#if defined(__int64) && !defined(__GNUC__) # define BOOST_HAS_MS_INT64 #endif #define BOOST_HAS_NRVO +// Branch prediction hints +#if defined(__has_builtin) +#if __has_builtin(__builtin_expect) +#define BOOST_LIKELY(x) __builtin_expect(x, 1) +#define BOOST_UNLIKELY(x) __builtin_expect(x, 0) +#endif +#endif + // Clang supports "long long" in all compilation modes. #define BOOST_HAS_LONG_LONG +// +// We disable this if the compiler is really nvcc as it +// doesn't actually support __int128 as of CUDA_VERSION=5000 +// even though it defines __SIZEOF_INT128__. +// See https://svn.boost.org/trac/boost/ticket/10418 +// Only re-enable this for nvcc if you're absolutely sure +// of the circumstances under which it's supported: +// +#if defined(__SIZEOF_INT128__) && !defined(__CUDACC__) +# define BOOST_HAS_INT128 +#endif + + +// +// Dynamic shared object (DSO) and dynamic-link library (DLL) support +// +#if !defined(_WIN32) && !defined(__WIN32__) && !defined(WIN32) +# define BOOST_SYMBOL_EXPORT __attribute__((__visibility__("default"))) +# define BOOST_SYMBOL_IMPORT +# define BOOST_SYMBOL_VISIBLE __attribute__((__visibility__("default"))) +#endif + +// +// The BOOST_FALLTHROUGH macro can be used to annotate implicit fall-through +// between switch labels. +// +#if __cplusplus >= 201103L && defined(__has_warning) +# if __has_feature(cxx_attributes) && __has_warning("-Wimplicit-fallthrough") +# define BOOST_FALLTHROUGH [[clang::fallthrough]] +# endif +#endif + #if !__has_feature(cxx_auto_type) # define BOOST_NO_CXX11_AUTO_DECLARATIONS # define BOOST_NO_CXX11_AUTO_MULTIDECLARATIONS #endif -#if !(defined(__GXX_EXPERIMENTAL_CXX0X__) || __cplusplus >= 201103L) +// +// Currently clang on Windows using VC++ RTL does not support C++11's char16_t or char32_t +// +#if defined(_MSC_VER) || !(defined(__GXX_EXPERIMENTAL_CXX0X__) || __cplusplus >= 201103L) # define BOOST_NO_CXX11_CHAR16_T # define BOOST_NO_CXX11_CHAR32_T #endif @@ -95,6 +153,10 @@ # define BOOST_NO_CXX11_RAW_LITERALS #endif +#if !__has_feature(cxx_reference_qualified_functions) +# define BOOST_NO_CXX11_REF_QUALIFIERS +#endif + #if !__has_feature(cxx_generalized_initializers) # define BOOST_NO_CXX11_UNIFIED_INITIALIZATION_SYNTAX #endif @@ -123,8 +185,83 @@ # define BOOST_NO_CXX11_VARIADIC_TEMPLATES #endif -// Clang always supports variadic macros -// Clang always supports extern templates +#if !__has_feature(cxx_user_literals) +# define BOOST_NO_CXX11_USER_DEFINED_LITERALS +#endif + +#if !(__has_feature(cxx_alignas) || __has_extension(cxx_alignas)) +# define BOOST_NO_CXX11_ALIGNAS +#endif + +#if !__has_feature(cxx_trailing_return) +# define BOOST_NO_CXX11_TRAILING_RESULT_TYPES +#endif + +#if !__has_feature(cxx_inline_namespaces) +# define BOOST_NO_CXX11_INLINE_NAMESPACES +#endif + +#if !__has_feature(cxx_override_control) +# define BOOST_NO_CXX11_FINAL +#endif + +#if !(__has_feature(cxx_binary_literals) || __has_extension(cxx_binary_literals)) +# define BOOST_NO_CXX14_BINARY_LITERALS +#endif + +#if !(__has_feature(cxx_decltype_auto) || __has_extension(cxx_decltype_auto)) +# define BOOST_NO_CXX14_DECLTYPE_AUTO +#endif + +#if !(__has_feature(cxx_aggregate_nsdmi) || __has_extension(cxx_aggregate_nsdmi)) +# define BOOST_NO_CXX14_AGGREGATE_NSDMI +#endif + +#if !(__has_feature(cxx_init_captures) || __has_extension(cxx_init_captures)) +# define BOOST_NO_CXX14_INITIALIZED_LAMBDA_CAPTURES +#endif + +#if !(__has_feature(cxx_generic_lambdas) || __has_extension(cxx_generic_lambdas)) +# define BOOST_NO_CXX14_GENERIC_LAMBDAS +#endif + +// clang < 3.5 has a defect with dependent type, like following. +// +// template <class T> +// constexpr typename enable_if<pred<T> >::type foo(T &) +// { } // error: no return statement in constexpr function +// +// This issue also affects C++11 mode, but C++11 constexpr requires return stmt. +// Therefore we don't care such case. +// +// Note that we can't check Clang version directly as the numbering system changes depending who's +// creating the Clang release (see https://github.com/boostorg/config/pull/39#issuecomment-59927873) +// so instead verify that we have a feature that was introduced at the same time as working C++14 +// constexpr (generic lambda's in this case): +// +#if !__has_feature(cxx_generic_lambdas) \ + || !(__has_feature(cxx_relaxed_constexpr) || __has_extension(cxx_relaxed_constexpr)) +# define BOOST_NO_CXX14_CONSTEXPR +#endif + +#if !(__has_feature(cxx_return_type_deduction) || __has_extension(cxx_return_type_deduction)) +# define BOOST_NO_CXX14_RETURN_TYPE_DEDUCTION +#endif + +#if !(__has_feature(cxx_variable_templates) || __has_extension(cxx_variable_templates)) +# define BOOST_NO_CXX14_VARIABLE_TEMPLATES +#endif + +#if __cplusplus < 201400 +// All versions with __cplusplus above this value seem to support this: +# define BOOST_NO_CXX14_DIGIT_SEPARATORS +#endif + + +// Unused attribute: +#if defined(__GNUC__) && (__GNUC__ >= 4) +# define BOOST_ATTRIBUTE_UNUSED __attribute__((unused)) +#endif #ifndef BOOST_COMPILER # define BOOST_COMPILER "Clang version " __clang_version__ |