nuclear@0: /************************************************************************************ nuclear@0: nuclear@0: PublicHeader: OVR.h nuclear@0: Filename : OVR_Compiler.h nuclear@0: Content : Compiler-specific feature identification and utilities nuclear@0: Created : June 19, 2014 nuclear@0: Notes : nuclear@0: nuclear@0: Copyright : Copyright 2014 Oculus VR, LLC All Rights reserved. nuclear@0: nuclear@0: Licensed under the Oculus VR Rift SDK License Version 3.2 (the "License"); nuclear@0: you may not use the Oculus VR Rift SDK except in compliance with the License, nuclear@0: which is provided at the time of installation or download, or which nuclear@0: otherwise accompanies this software in either electronic or hard copy form. nuclear@0: nuclear@0: You may obtain a copy of the License at nuclear@0: nuclear@0: http://www.oculusvr.com/licenses/LICENSE-3.2 nuclear@0: nuclear@0: Unless required by applicable law or agreed to in writing, the Oculus VR SDK nuclear@0: distributed under the License is distributed on an "AS IS" BASIS, nuclear@0: WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. nuclear@0: See the License for the specific language governing permissions and nuclear@0: limitations under the License. nuclear@0: nuclear@0: ************************************************************************************/ nuclear@0: nuclear@0: nuclear@0: #ifndef OVR_Compiler_h nuclear@0: #define OVR_Compiler_h nuclear@0: nuclear@0: #pragma once nuclear@0: nuclear@0: nuclear@0: // References nuclear@0: // https://gcc.gnu.org/projects/cxx0x.html nuclear@0: // https://gcc.gnu.org/projects/cxx1y.html nuclear@0: // http://clang.llvm.org/cxx_status.html nuclear@0: // http://msdn.microsoft.com/en-us/library/hh567368.aspx nuclear@0: // https://docs.google.com/spreadsheet/pub?key=0AoBblDsbooe4dHZuVTRoSTFBejk5eFBfVk1GWlE5UlE&output=html nuclear@0: // http://nadeausoftware.com/articles/2012/10/c_c_tip_how_detect_compiler_name_and_version_using_compiler_predefined_macros nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** Compiler nuclear@0: // nuclear@0: // The following compilers are defined: (OVR_CC_x) nuclear@0: // nuclear@0: // MSVC - Microsoft Visual C/C++ nuclear@0: // INTEL - Intel C++ for Linux / Windows nuclear@0: // GNU - GNU C++ nuclear@0: // ARM - ARM C/C++ nuclear@0: nuclear@0: #if defined(__INTEL_COMPILER) nuclear@0: // Intel 4.0 = 400 nuclear@0: // Intel 5.0 = 500 nuclear@0: // Intel 6.0 = 600 nuclear@0: // Intel 8.0 = 800 nuclear@0: // Intel 9.0 = 900 nuclear@0: # define OVR_CC_INTEL __INTEL_COMPILER nuclear@0: nuclear@0: #elif defined(_MSC_VER) nuclear@0: // MSVC 5.0 = 1100 nuclear@0: // MSVC 6.0 = 1200 nuclear@0: // MSVC 7.0 (VC2002) = 1300 nuclear@0: // MSVC 7.1 (VC2003) = 1310 nuclear@0: // MSVC 8.0 (VC2005) = 1400 nuclear@0: // MSVC 9.0 (VC2008) = 1500 nuclear@0: // MSVC 10.0 (VC2010) = 1600 nuclear@0: // MSVC 11.0 (VC2012) = 1700 nuclear@0: // MSVC 12.0 (VC2013) = 1800 nuclear@0: # define OVR_CC_MSVC _MSC_VER nuclear@0: nuclear@0: #if _MSC_VER == 0x1600 nuclear@0: # if _MSC_FULL_VER < 160040219 nuclear@0: # error "Oculus does not support VS2010 without SP1 installed." nuclear@0: # endif nuclear@0: #endif nuclear@0: nuclear@0: #elif defined(__GNUC__) nuclear@0: # define OVR_CC_GNU nuclear@0: nuclear@0: #elif defined(__clang__) nuclear@0: # define OVR_CC_CLANG nuclear@0: nuclear@0: #elif defined(__CC_ARM) nuclear@0: # define OVR_CC_ARM nuclear@0: nuclear@0: #else nuclear@0: # error "Oculus does not support this Compiler" nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CC_VERSION nuclear@0: // nuclear@0: // M = major version nuclear@0: // m = minor version nuclear@0: // p = patch release nuclear@0: // b = build number nuclear@0: // nuclear@0: // Compiler Format Example nuclear@0: // ---------------------------- nuclear@0: // OVR_CC_GNU Mmm 408 means GCC 4.8 nuclear@0: // OVR_CC_CLANG Mmm 305 means clang 3.5 nuclear@0: // OVR_CC_MSVC MMMM 1700 means VS2012 nuclear@0: // OVR_CC_ARM Mmpbbb 401677 means 4.0, patch 1, build 677 nuclear@0: // OVR_CC_INTEL MMmm 1210 means 12.10 nuclear@0: // OVR_CC_EDG Mmm 407 means EDG 4.7 nuclear@0: // nuclear@0: #if defined(OVR_CC_GNU) nuclear@0: #define OVR_CC_VERSION ((__GNUC__ * 100) + __GNUC_MINOR__) nuclear@0: #elif defined(OVR_CC_CLANG) nuclear@0: #define OVR_CC_VERSION ((__clang_major__ * 100) + __clang_minor__) nuclear@0: #elif defined(OVR_CC_MSVC) nuclear@0: #define OVR_CC_VERSION _MSC_VER // Question: Should we recognize _MSC_FULL_VER? nuclear@0: #elif defined(OVR_CC_ARM) nuclear@0: #define OVR_CC_VERSION __ARMCC_VERSION nuclear@0: #elif defined(OVR_CC_INTEL) nuclear@0: #if defined(__INTEL_COMPILER) nuclear@0: #define OVR_CC_VERSION __INTEL_COMPILER nuclear@0: #elif defined(__ICL) nuclear@0: #define OVR_CC_VERSION __ICL nuclear@0: #elif defined(__ICC) nuclear@0: #define OVR_CC_VERSION __ICC nuclear@0: #elif defined(__ECC) nuclear@0: #define OVR_CC_VERSION __ECC nuclear@0: #endif nuclear@0: #elif defined(OVR_CC_EDG) nuclear@0: #define OVR_CC_VERSION __EDG_VERSION__ // This is a generic fallback for EDG-based compilers which aren't specified above (e.g. as OVR_CC_ARM) nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_DISABLE_OPTIMIZATION / OVR_RESTORE_OPTIMIZATION nuclear@0: // nuclear@0: // Allows for the dynamic disabling and restoring of compiler optimizations in code. nuclear@0: // This is useful for helping deal with potential compiler code generation problems. nuclear@0: // With VC++ the usage must be outside of function bodies. This can be used only to nuclear@0: // temporarily disable optimization for a block of code and not to temporarily enable nuclear@0: // optimization for a block of code. nuclear@0: // nuclear@0: // Clang doesn't support this as of June 2014, though function __attribute__((optimize(0)) nuclear@0: // is supposedly supported by clang in addition to GCC. To consider: Make a wrapper for nuclear@0: // this attribute-based functionality. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_DISABLE_OPTIMIZATION() nuclear@0: // void Test() { ... } nuclear@0: // OVR_RESTORE_OPTIMIZATION() nuclear@0: // nuclear@0: #if !defined(OVR_DISABLE_OPTIMIZATION) nuclear@0: #if defined(OVR_CC_GNU) && (OVR_CC_VERSION > 404) && (defined(OVR_CPU_X86) || defined(OVR_CPU_X86_64)) nuclear@0: #define OVR_DISABLE_OPTIMIZATION() \ nuclear@0: _Pragma("GCC push_options") \ nuclear@0: _Pragma("GCC optimize 0") nuclear@0: #elif defined(OVR_CC_MSVC) nuclear@0: #define OVR_DISABLE_OPTIMIZATION() __pragma(optimize("", off)) nuclear@0: #else nuclear@0: #define OVR_DISABLE_OPTIMIZATION() nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_RESTORE_OPTIMIZATION) nuclear@0: #if defined(OVR_CC_GNU) && (OVR_CC_VERSION > 404) && (defined(OVR_CPU_X86) || defined(OVR_CPU_X86_64)) nuclear@0: #define OVR_RESTORE_OPTIMIZATION() _Pragma("GCC pop_options") nuclear@0: #elif defined(OVR_CC_MSVC) nuclear@0: #define OVR_RESTORE_OPTIMIZATION() __pragma(optimize("", on)) nuclear@0: #else nuclear@0: #define OVR_RESTORE_OPTIMIZATION() nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_DISABLE_GNU_WARNING / OVR_RESTORE_GNU_WARNING nuclear@0: // nuclear@0: // Portable wrapper for disabling GCC compiler warnings, one at a time. See example nuclear@0: // usage for usage by example. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_DISABLE_GNU_WARNING(-Wmissing-braces) // Only one warning per usage. nuclear@0: // OVR_DISABLE_GNU_WARNING(-Wunused-variable) nuclear@0: // nuclear@0: // OVR_RESTORE_GNU_WARNINGS() nuclear@0: // OVR_RESTORE_GNU_WARNINGS() // Must match each disable with a restore. nuclear@0: // nuclear@0: #if !defined(OVR_DISABLE_GNU_WARNING) nuclear@0: #if defined(OVR_CC_GNU) nuclear@0: #define ODGW1(x) #x nuclear@0: #define ODGW2(x) ODGW1(GCC diagnostic ignored x) nuclear@0: #define ODGW3(x) ODGW2(#x) nuclear@0: #endif nuclear@0: nuclear@0: #if defined(OVR_CC_GNU) && (OVR_CC_VERSION >= 406) nuclear@0: #define OVR_DISABLE_GNU_WARNING(w) \ nuclear@0: _Pragma("GCC diagnostic push") \ nuclear@0: _Pragma(ODGW3(w)) nuclear@0: #elif defined(OVR_CC_GNU) && (OVR_CC_VERSION >= 404) // GCC 4.4 doesn't support diagnostic push, but supports disabling warnings. nuclear@0: #define OVR_DISABLE_GNU_WARNING(w) \ nuclear@0: _Pragma(ODGW3(w)) nuclear@0: #else nuclear@0: #define OVR_DISABLE_GNU_WARNING(w) nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_RESTORE_GNU_WARNING) nuclear@0: #if defined(OVR_CC_GNU) && (OVR_CC_VERSION >= 4006) nuclear@0: #define OVR_RESTORE_GNU_WARNINGS() \ nuclear@0: _Pragma("GCC diagnostic pop") nuclear@0: #else nuclear@0: #define OVR_RESTORE_GNU_WARNING() nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_DISABLE_CLANG_WARNING / OVR_RESTORE_CLANG_WARNING nuclear@0: // nuclear@0: // Portable wrapper for disabling GCC compiler warnings, one at a time. See example nuclear@0: // usage for usage by example. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_DISABLE_CLANG_WARNING(-Wmissing-braces) // Only one warning per usage. nuclear@0: // OVR_DISABLE_CLANG_WARNING(-Wunused-variable) nuclear@0: // nuclear@0: // OVR_RESTORE_CLANG_WARNINGS() nuclear@0: // OVR_RESTORE_CLANG_WARNINGS() // Must match each disable with a restore. nuclear@0: // nuclear@0: // nuclear@0: #if !defined(OVR_DISABLE_CLANG_WARNING) nuclear@0: #if defined(OVR_CC_CLANG) nuclear@0: #define ODCW1(x) #x nuclear@0: #define ODCW2(x) ODCW1(clang diagnostic ignored x) nuclear@0: #define ODCW3(x) ODCW2(#x) nuclear@0: nuclear@0: #define OVR_DISABLE_CLANG_WARNING(w) \ nuclear@0: _Pragma("clang diagnostic push") \ nuclear@0: _Pragma(ODCW3(w)) nuclear@0: #else nuclear@0: #define OVR_DISABLE_CLANG_WARNING(w) nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_RESTORE_CLANG_WARNING) nuclear@0: #if defined(OVR_CC_CLANG) nuclear@0: #define OVR_RESTORE_CLANG_WARNING() \ nuclear@0: _Pragma("clang diagnostic pop") nuclear@0: #else nuclear@0: #define OVR_RESTORE_CLANG_WARNING() nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_DISABLE_MSVC_WARNING / OVR_RESTORE_MSVC_WARNING nuclear@0: // nuclear@0: // Portable wrapper for disabling VC++ compiler warnings. See example usage for usage nuclear@0: // by example. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_DISABLE_MSVC_WARNING(4556 4782 4422) nuclear@0: // nuclear@0: // OVR_RESTORE_MSVC_WARNING() nuclear@0: // nuclear@0: #if !defined(OVR_DISABLE_MSVC_WARNING) nuclear@0: #if defined(OVR_CC_MSVC) nuclear@0: #define OVR_DISABLE_MSVC_WARNING(w) \ nuclear@0: __pragma(warning(push)) \ nuclear@0: __pragma(warning(disable:w)) nuclear@0: #else nuclear@0: #define OVR_DISABLE_MSVC_WARNING(w) nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_RESTORE_MSVC_WARNING) nuclear@0: #if defined(OVR_CC_MSVC) nuclear@0: #define OVR_RESTORE_MSVC_WARNING() \ nuclear@0: __pragma(warning(pop)) nuclear@0: #else nuclear@0: #define OVR_RESTORE_MSVC_WARNING() nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_DISABLE_ALL_MSVC_WARNINGS / OVR_RESTORE_ALL_MSVC_WARNINGS nuclear@0: // nuclear@0: // Portable wrapper for disabling all VC++ compiler warnings. nuclear@0: // OVR_RESTORE_ALL_MSVC_WARNINGS restores warnings that were disabled by nuclear@0: // OVR_DISABLE_ALL_MSVC_WARNINGS. Any previously enabled warnings will still be nuclear@0: // enabled after OVR_RESTORE_ALL_MSVC_WARNINGS. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_DISABLE_ALL_MSVC_WARNINGS() nuclear@0: // nuclear@0: // OVR_RESTORE_ALL_MSVC_WARNINGS() nuclear@0: nuclear@0: #if !defined(OVR_DISABLE_ALL_MSVC_WARNINGS) nuclear@0: #if defined(OVR_CC_MSVC) nuclear@0: #define OVR_DISABLE_ALL_MSVC_WARNINGS() \ nuclear@0: __pragma(warning(push, 0)) nuclear@0: #else nuclear@0: #define OVR_DISABLE_ALL_MSVC_WARNINGS() nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_RESTORE_ALL_MSVC_WARNINGS) nuclear@0: #if defined(OVR_CC_MSVC) nuclear@0: #define OVR_RESTORE_ALL_MSVC_WARNINGS() \ nuclear@0: __pragma(warning(pop)) nuclear@0: #else nuclear@0: #define OVR_RESTORE_ALL_MSVC_WARNINGS() nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CC_HAS_FEATURE nuclear@0: // nuclear@0: // This is a portable way to use compile-time feature identification available nuclear@0: // with some compilers in a clean way. Direct usage of __has_feature in preprocessing nuclear@0: // statements of non-supporting compilers results in a preprocessing error. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // #if OVR_CC_HAS_FEATURE(is_pod) nuclear@0: // if(__is_pod(T)) // If the type is plain data then we can safely memcpy it. nuclear@0: // memcpy(&destObject, &srcObject, sizeof(object)); nuclear@0: // #endif nuclear@0: // nuclear@0: #if !defined(OVR_CC_HAS_FEATURE) nuclear@0: #if defined(__clang__) // http://clang.llvm.org/docs/LanguageExtensions.html#id2 nuclear@0: #define OVR_CC_HAS_FEATURE(x) __has_feature(x) nuclear@0: #else nuclear@0: #define OVR_CC_HAS_FEATURE(x) 0 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CC_HAS_BUILTIN nuclear@0: // nuclear@0: // nuclear@0: // This is a portable way to use compile-time builtin identification available nuclear@0: // with some compilers in a clean way. Direct usage of __has_builtin in preprocessing nuclear@0: // statements of non-supporting compilers results in a preprocessing error. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // #if OVR_CC_HAS_BUILTIN(__builtin_trap) nuclear@0: // #define DEBUG_BREAK __builtin_trap nuclear@0: // #endif nuclear@0: // nuclear@0: #if !defined(OVR_CC_HAS_BUILTIN) nuclear@0: #if defined(__clang__) nuclear@0: #define OVR_CC_HAS_BUILTIN(x) __has_builtin(x) // http://clang.llvm.org/docs/LanguageExtensions.html#id2 nuclear@0: #else nuclear@0: #define OVR_CC_HAS_BUILTIN(x) 0 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP11_ENABLED / OVR_CPP_CPP14_ENABLED nuclear@0: // nuclear@0: // Defined as 1 if the compiler has its available C++11 support enabled, else undefined. nuclear@0: // This does not mean that all of C++11 or any particular feature of C++11 is supported nuclear@0: // by the compiler. It means that whatever C++11 support the compiler has is enabled. nuclear@0: // This also includes existing and older compilers that still identify C++11 as C++0x. nuclear@0: // nuclear@0: #if !defined(OVR_CPP11_ENABLED) && defined(__cplusplus) nuclear@0: #if defined(__GNUC__) && defined(__GXX_EXPERIMENTAL_CXX0X__) nuclear@0: #define OVR_CPP11_ENABLED 1 nuclear@0: #elif defined(_MSC_VER) && (_MSC_VER >= 1500) // VS2010+, the first version with any significant C++11 support. nuclear@0: #define OVR_CPP11_ENABLED 1 nuclear@0: #elif (__cplusplus >= 201103L) // 201103 is the first C++11 version. nuclear@0: #define OVR_CPP11_ENABLED 1 nuclear@0: #else nuclear@0: // Leave undefined nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_CPP_CPP14_ENABLED) && defined(__cplusplus) nuclear@0: #if defined(_MSC_VER) && (_MSC_VER >= 1800) // VS2013+, the first version with any significant C++14 support. nuclear@0: #define OVR_CPP_CPP14_ENABLED 1 nuclear@0: #elif (__cplusplus > 201103L) nuclear@0: #define OVR_CPP_CPP14_ENABLED 1 nuclear@0: #else nuclear@0: // Leave undefined nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_EXCEPTIONS / OVR_CPP_NO_UNWIND nuclear@0: // nuclear@0: // OVR_CPP_NO_EXCEPTIONS is defined as 1 if the compiler doesn't support C++ nuclear@0: // exceptions or is configured to disable support for them. Else not defined. nuclear@0: // If OVR_CPP_NO_EXCEPTIONS is defined then attempts to use try/catch nuclear@0: // related C++ statements result in a compilation error with many nuclear@0: // compilers. nuclear@0: // nuclear@0: // OVR_CPP_NO_UNWIND is defined as 1 if the compiler supports exceptions but nuclear@0: // doesn't support stack unwinding in the presence of an exception. Else not defined. nuclear@0: // For the Microsoft compiler, disabling exceptions means disabling stack unwinding nuclear@0: // and not disabling exceptions themselves. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // void Test() { nuclear@0: // #if !defined(OVR_CPP_NO_EXCEPTIONS) nuclear@0: // try { nuclear@0: // #endif nuclear@0: // void* ptr = new Object; nuclear@0: // #if !defined(OVR_CPP_NO_EXCEPTIONS) nuclear@0: // catch(...) { ... } nuclear@0: // #endif nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_EXCEPTIONS) nuclear@0: #if defined(OVR_CPP_GNUC) && defined(_NO_EX) nuclear@0: #define OVR_CPP_NO_EXCEPTIONS 1 nuclear@0: #elif (defined(OVR_CC_GNU) || defined(OVR_CC_CLANG) || defined(OVR_CC_INTEL) || defined(OVR_CC_ARM)) && !defined(__EXCEPTIONS) nuclear@0: #define OVR_CPP_NO_EXCEPTIONS 1 nuclear@0: #elif defined(OVR_CC_MSVC) && !defined(_CPPUNWIND) nuclear@0: #define OVR_CPP_NO_UNWIND 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_RTTI nuclear@0: // nuclear@0: // Defined as 1 if C++ run-time type information support is unavailable or disabled nuclear@0: // by the compiler. Else undefined. Allows you to write portable code in the face nuclear@0: // of the possibility that RTTI is disabled. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // #if !OVR_CPP_NO_RTTI nuclear@0: // #include nuclear@0: // int x = std::dynamic_cast(3.4f); nuclear@0: // #endif nuclear@0: nuclear@0: #if defined(__clang__) && !OVR_CC_HAS_FEATURE(cxx_rtti) nuclear@0: #define OVR_CPP_NO_RTTI 1 nuclear@0: #elif defined(__GNUC__) && !defined(__GXX_RTTI) nuclear@0: #define OVR_CPP_NO_RTTI 1 nuclear@0: #elif defined(_MSC_VER) && !defined(_CPPRTTI) nuclear@0: #define OVR_CPP_NO_RTTI 1 nuclear@0: #elif defined(__CC_ARM) && defined(__TARGET_CPU_MPCORE) && !defined(__RTTI) nuclear@0: #define OVR_CPP_NO_RTTI 1 nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_STATIC_ASSERT nuclear@0: // nuclear@0: // Defined as 1 if C++ run-time type information support is available and enabled nuclear@0: // by the compiler. Else undefined. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // #if OVR_CPP_NO_STATIC_ASSERT nuclear@0: // #define MY_ASSERT(x) { int zero = 0; switch(zero) {case 0: case (x):;} } nuclear@0: // #else nuclear@0: // #define MY_ASSERT(x) static_assert((x), #x) nuclear@0: // #endif nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_STATIC_ASSERT) nuclear@0: #if !(defined(__GNUC__) && (defined(__GXX_EXPERIMENTAL_CXX0X__) || (defined(__cplusplus) && (__cplusplus >= 201103L)))) && \ nuclear@0: !(defined(__clang__) && defined(__cplusplus) && OVR_CC_HAS_FEATURE(cxx_static_assert)) && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600) && defined(__cplusplus)) && /* VS2010+ */ \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401) && defined(OVR_CPP11_ENABLED)) /* EDG 4.1+ */ nuclear@0: #define OVR_CPP_NO_STATIC_ASSERT 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_NULLPTR nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 nullptr built in type. nuclear@0: // Otherwise undefined. Does not identify if the standard library defines nuclear@0: // std::nullptr_t, as some standard libraries are further behind in standardization nuclear@0: // than the compilers using them (e.g. Apple clang with the supplied libstdc++). nuclear@0: // nuclear@0: // OVR_Nullptr.h provides a portable nullptr and std::nullptr_t for when the nuclear@0: // compiler or standard library do not. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_NULLPTR) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_nullptr)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 406)) /* GCC 4.6+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 403))) /* EDG 4.3+ */ nuclear@0: #define OVR_CPP_NO_NULLPTR 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_RVALUE_REFERENCES nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 rvalue references and move semantics. nuclear@0: // Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_RVALUE_REFERENCES) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_rvalue_references)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 405)) /* GCC 4.5+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 403))) /* EDG 4.3+ */ nuclear@0: #define OVR_CPP_NO_RVALUE_REFERENCES 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_AUTO nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 auto keyword. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_AUTO) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_auto_type)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 309))) /* EDG 3.9+ */ nuclear@0: #define OVR_CPP_NO_AUTO 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_RANGE_BASED_FOR_LOOP nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 range-based for loops. nuclear@0: // Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_RANGE_BASED_FOR_LOOP) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_range_for)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 406)) /* GCC 4.6+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1700)) /* VS2012+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 405))) /* EDG 4.5+ */ nuclear@0: #define OVR_CPP_NO_RANGE_BASED_FOR_LOOP 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_CONSTEXPR / OVR_CPP_NO_RELAXED_CONSTEXPR nuclear@0: // nuclear@0: // OVR_CPP_NO_CONSTEXPR is defined as 1 if the compiler doesn't support C++11 constexpr. nuclear@0: // OVR_CPP_NO_RELAXED_CONSTEXPR is defined as 1 if the compiler doesn't support C++14 constexpr. nuclear@0: // Otherwise undefined. nuclear@0: // See the OVR_CONSTEXPR / OVR_CONSTEXPR_OR_CONST macros for portable wrappers of this functionality. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_CONSTEXPR) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_constexpr)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 406)) /* GCC 4.6+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 406))) /* EDG 4.6+ */ nuclear@0: // Not supported by VC++ through at least VS2013. nuclear@0: #define OVR_CPP_NO_CONSTEXPR 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_RELAXED_CONSTEXPR) nuclear@0: #if !defined(OVR_CPP14_ENABLED) || \ nuclear@0: !(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_relaxed_constexpr)) /* clang */ nuclear@0: // Supported only by clang as of this writing. nuclear@0: #define OVR_CPP_NO_RELAXED_CONSTEXPR 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_LAMBDA_EXPRESSIONS nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 lambda expressions. Otherwise undefined. nuclear@0: // Some compilers have slightly crippled versions of this. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_LAMBDA_EXPRESSIONS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_lambdas)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401))) /* EDG 4.1+ */ nuclear@0: // Conversion of lambdas to function pointers is not supported until EDG 4.5. nuclear@0: #define OVR_CPP_NO_LAMBDA_EXPRESSIONS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_ALIGNOF nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 alignof. Otherwise undefined. nuclear@0: // Some compilers support __alignof__ instead of alignof, so for portability you nuclear@0: // should use OVR_ALIGNOF instead of directly using C++11 alignof. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_ALIGNOF) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 300)) /* Apple clang 3.0+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 401)) /* GCC 4.1+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1900)) /* VS2014+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 400))) /* EDG 4.0+ */ nuclear@0: #define OVR_CPP_NO_ALIGNOF 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_ALIGNAS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 alignas. Otherwise undefined. nuclear@0: // See the OVR_ALIGNAS for a portable wrapper for alignas functionality. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_ALIGNAS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 300)) /* clang 3.0+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 408)) /* GCC 4.8+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1900)) /* VS2014+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 408))) /* EDG 4.8+ */ nuclear@0: #define OVR_CPP_NO_ALIGNAS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_OVERRIDE nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 override. Otherwise undefined. nuclear@0: // See the OVR_OVERRIDE and OVR_FINALOVERRIDE macros for a portable wrapper. nuclear@0: nuclear@0: #if !defined(OOVR_CPP_NO_OVERRIDE) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 400)) /* Apple clang 4.0+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 407)) /* GCC 4.7+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1500)) /* VS2008+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 408))) /* EDG 4.8+ */ nuclear@0: #define OVR_CPP_NO_OVERRIDE 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_FINAL nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 final attribute. Otherwise undefined. nuclear@0: // See the OVR_FINAL and OVR_FINALOVERRIDE macros for a portable wrapper. nuclear@0: nuclear@0: #if !defined(OOVR_CPP_NO_FINAL) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 400)) /* Apple clang 4.0+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 407)) /* GCC 4.7+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1500)) /* VS2008+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 408))) /* EDG 4.8+ */ nuclear@0: #define OVR_CPP_NO_FINAL 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_EXTERN_TEMPLATE nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 extern template. nuclear@0: // Otherwise undefined. See OVR_EXTERN_TEMPLATE for wrapper macro. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_EXTERN_TEMPLATE) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 406)) /* GCC 4.6+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1700)) /* VS2012+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401))) /* EDG 4.1+ */ nuclear@0: #define OVR_CPP_NO_EXTERN_TEMPLATE 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_VARIADIC_TEMPLATES nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 variadic templates. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_VARIADIC_TEMPLATES) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_variadic_templates)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 403))) /* EDG 4.3+ */ nuclear@0: #define OVR_CPP_NO_VARIADIC_TEMPLATES 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_NOEXCEPT nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 noexcept. Otherwise undefined. nuclear@0: // http://en.cppreference.com/w/cpp/language/noexcept nuclear@0: // See OVR_NOEXCEPT / OVR_NOEXCEPT_IF / OVR_NOEXCEPT_EXPR for a portable wrapper nuclear@0: // for noexcept functionality. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_NOEXCEPT) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_noexcept)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 406)) /* GCC 4.6+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1900)) /* VS2014+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 405))) /* EDG 4.5+ */ nuclear@0: #define OVR_CPP_NO_NOEXCEPT 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_DECLTYPE nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 decltype. Otherwise undefined. nuclear@0: // Some compilers (e.g. VS2012) support most uses of decltype but don't support nuclear@0: // decltype with incomplete types (which is an uncommon usage seen usually in nuclear@0: // template metaprogramming). We don't include this support as a requirement for nuclear@0: // our definition of decltype support here. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_DECLTYPE) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_decltype)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 403)) /* GCC 4.3+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 402))) /* EDG 4.2+ */ nuclear@0: // VC++ fails to support decltype for incomplete types until VS2013. nuclear@0: // EDG fails to support decltype for incomplete types until v4.8. nuclear@0: #define OVR_CPP_NO_DECLTYPE 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_DEFAULTED_FUNCTIONS nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 defaulted functions. Otherwise undefined. nuclear@0: // Some compilers have slightly crippled versions of this. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_DEFAULTED_FUNCTIONS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_defaulted_functions))/* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401))) /* EDG 4.1+ */ nuclear@0: // Up through at least VS2013 it's unsupported for defaulted move constructors and move assignment operators. nuclear@0: // Until EDG 4.8 it's unsupported for defaulted move constructors and move assigment operators. nuclear@0: #define OVR_CPP_NO_DEFAULTED_FUNCTIONS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_DELETED_FUNCTIONS nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 deleted functions. Otherwise undefined. nuclear@0: // Some compilers have slightly crippled versions of this. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_DELETED_FUNCTIONS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_defaulted_functions)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401))) /* EDG 4.1+ */ nuclear@0: // Up through at least VS2013 it's unsupported for defaulted move constructors and move assignment operators. nuclear@0: // Until EDG 4.8 it's unsupported for defaulted move constructors and move assigment operators. nuclear@0: #define OVR_CPP_NO_DELETED_FUNCTIONS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_STANDARD_LAYOUT_TYPES nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 standard layout (relaxed POD). Otherwise undefined. nuclear@0: // http://en.cppreference.com/w/cpp/types/is_standard_layout nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_STANDARD_LAYOUT_TYPES) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 300)) /* clang 3.0+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 405)) /* GCC 4.5+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1700)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 406))) /* EDG 4.6+ */ nuclear@0: #define OVR_CPP_NO_STANDARD_LAYOUT_TYPES 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_FORWARD_DECLARED_ENUMS nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 forward declared enums. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_FORWARD_DECLARED_ENUMS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 301)) /* clang 3.1+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 406)) /* GCC 4.6+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1700)) /* VS2012+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 405))) /* EDG 4.5+ */ nuclear@0: #define OVR_CPP_NO_FORWARD_DECLARED_ENUMS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_STRONGLY_TYPED_ENUMS nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 strongly typed enums. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_STRONGLY_TYPED_ENUMS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_strong_enums)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1700)) /* VS2012+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 400))) /* EDG 4.0+ */ nuclear@0: #define OVR_CPP_NO_STRONGLY_TYPED_ENUMS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_TRAILING_RETURN_TYPES nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 trailing return types. Otherwise undefined. nuclear@0: // http://en.wikipedia.org/wiki/C%2B%2B11#Alternative_function_syntax nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_TRAILING_RETURN_TYPES) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_trailing_return)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401))) /* EDG 4.1+ */ nuclear@0: #define OVR_CPP_NO_TRAILING_RETURN_TYPES 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_TEMPLATE_ALIASES nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 template aliases. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_TEMPLATE_ALIASES) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_alias_templates)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 407)) /* GCC 4.7+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 402))) /* EDG 4.2+ */ nuclear@0: #define OVR_CPP_NO_TEMPLATE_ALIASES 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_INITIALIZER_LISTS nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 initializer lists. Otherwise undefined. nuclear@0: // This refers to the compiler support for this and not the Standard Library support for std::initializer_list, nuclear@0: // as a new compiler with an old standard library (e.g. Apple clang with libstdc++) may not support std::initializer_list. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_INITIALIZER_LISTS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_generalized_initializers)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 405))) /* EDG 4.5+ */ nuclear@0: #define OVR_CPP_NO_INITIALIZER_LISTS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_NORETURN nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support the C++11 noreturn attribute. Otherwise undefined. nuclear@0: // http://en.cppreference.com/w/cpp/language/attributes nuclear@0: // nuclear@0: #if !defined(OVR_CPP_NO_NORETURN) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 301)) /* clang 3.1+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 408)) /* GCC 4.8+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1500)) /* VS2008+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 402))) /* EDG 4.2+ */ nuclear@0: // Supported with VC++ only via __declspec(noreturn) (see OVR_NORETURN). nuclear@0: #define OVR_CPP_NO_NORETURN 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_NONSTATIC_MEMBER_INITIALIZERS nuclear@0: // nuclear@0: // Defined as 1 if the compiler doesn't support C++11 in-class non-static member initializers. Otherwise undefined. nuclear@0: // http://en.cppreference.com/w/cpp/language/data_members nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_NONSTATIC_MEMBER_INITIALIZERS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 301)) /* clang 3.1+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 407)) /* GCC 4.7+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 406))) /* EDG 4.6+ */ nuclear@0: #define OVR_CPP_NO_NONSTATIC_MEMBER_INITIALIZERS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_DOUBLE_TEMPLATE_BRACKETS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports nested template declarations with >>, nuclear@0: // as supported by C++11. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_DOUBLE_TEMPLATE_ANGLE_BRACKETS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 400)) /* Apple clang 4.0+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 403)) /* GCC 4.3+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401))) /* EDG 4.1+ */ nuclear@0: #define OVR_CPP_NO_DOUBLE_TEMPLATE_BRACKETS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_INHERITING_CONSTRUCTORS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 inheriting constructors. Otherwise undefined. nuclear@0: // Example usage: nuclear@0: // struct A { explicit A(int x){} }; nuclear@0: // struct B : public A { using A::A; }; // As if B redeclared A::A(int). nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_INHERITING_CONSTRUCTORS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_inheriting_constructors)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 408)) /* GCC 4.8+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1900)) /* VS2014+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 408))) /* EDG 4.8+ */ nuclear@0: #define OVR_CPP_NO_INHERITING_CONSTRUCTORS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_DELEGATING_CONSTRUCTORS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 delegating constructors. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_DELEGATING_CONSTRUCTORS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 300)) /* clang 3.0+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 407)) /* GCC 4.7+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 407))) /* EDG 4.7+ */ nuclear@0: #define OVR_CPP_NO_DELEGATING_CONSTRUCTORS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_FUNCTION_TEMPLATE_DEFAULT_ARGS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 function template default arguments. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_FUNCTION_TEMPLATE_DEFAULT_ARGS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.0+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 403)) /* GCC 4.3+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 403))) /* EDG 4.3+ */ nuclear@0: #define OVR_CPP_NO_FUNCTION_TEMPLATE_DEFAULT_ARGS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_UNRESTRICTED_UNIONS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 unrestricted unions. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_UNRESTRICTED_UNIONS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 301)) /* clang 3.1+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 406)) /* GCC 4.6+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 406))) /* EDG 4.6+ */ nuclear@0: // Not supported by VC++ as of VS2013. nuclear@0: #define OVR_CPP_NO_UNRESTRICTED_UNIONS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_EXTENDED_SIZEOF nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 class sizeof extensions (e.g. sizeof SomeClass::someMember). nuclear@0: // Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_EXTENDED_SIZEOF) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 301)) /* clang 3.1+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 405)) /* GCC 4.5+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1900)) /* VS2014+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 405))) /* EDG 4.5+ */ nuclear@0: #define OVR_CPP_NO_EXTENDED_SIZEOF 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_INLINE_NAMESPACES nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 inlined namespaces. Otherwise undefined. nuclear@0: // http://en.cppreference.com/w/cpp/language/namespace#Inline_namespaces nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_INLINE_NAMESPACES) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 400)) /* Apple clang 4.0+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 405))) /* EDG 4.5+ */ nuclear@0: // Not supported by VC++ as of VS2013. nuclear@0: #define OVR_CPP_NO_INLINE_NAMESPACES 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_EXPLICIT_CONVERSION_OPERATORS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 explicit conversion operators. Otherwise undefined. nuclear@0: // http://en.cppreference.com/w/cpp/language/explicit nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_EXPLICIT_CONVERSION_OPERATORS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_explicit_conversions)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 405)) /* GCC 4.5+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 404))) /* EDG 4.4+ */ nuclear@0: #define OVR_CPP_NO_EXPLICIT_CONVERSION_OPERATORS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_LOCAL_CLASS_TEMPLATE_PARAMETERS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 local class template parameters. Otherwise undefined. nuclear@0: // Example: nuclear@0: // void Test() { nuclear@0: // struct LocalClass{ }; nuclear@0: // SomeTemplateClass t; // Allowed only in C++11 nuclear@0: // } nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_LOCAL_CLASS_TEMPLATE_PARAMETERS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_local_type_template_args)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 405)) /* GCC 4.5+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 402))) /* EDG 4.2+ */ nuclear@0: #define OVR_CPP_NO_LOCAL_CLASS_TEMPLATE_PARAMETERS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_NEW_CHARACTER_TYPES nuclear@0: // nuclear@0: // Defined as 1 if the compiler natively supports C++11 char16_t and char32_t. Otherwise undefined. nuclear@0: // VC++ through at least VS2013 defines char16_t as unsigned short in its standard library, nuclear@0: // but it is not a native type or unique type, nor can you for a string literal with it. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_NEW_CHARACTER_TYPES) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_unicode_literals)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 407))) /* EDG 4.7+ */ nuclear@0: // Not supported by VC++ as of VS2013. nuclear@0: #define OVR_CPP_NO_NEW_CHARACTER_TYPES 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_UNICODE_CHAR_NAME_LITERALS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 \u and \U character literals for nuclear@0: // native char16_t and char32_t types. nuclear@0: // nuclear@0: #if !defined(OVR_CPP_NO_UNICODE_CHAR_NAME_LITERALS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 301)) /* clang 3.1+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 405)) /* GCC 4.5+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 408))) /* EDG 4.8+ */ nuclear@0: // Not supported by VC++ as of VS2013. VC++'s existing \U and \u are non-conforming. nuclear@0: #define OVR_CPP_NO_UNICODE_CHAR_NAME_LITERALS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_USER_DEFINED_LITERALS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 user-defined literals. Otherwise undefined. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_USER_DEFINED_LITERALS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 301)) /* clang 3.1+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 401)) /* Apple clang 4.1+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 407)) /* GCC 4.7+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 408))) /* EDG 4.8+ */ nuclear@0: // Not supported by VC++ as of VS2013. nuclear@0: #define OVR_CPP_NO_USER_DEFINED_LITERALS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_UNICODE_STRING_LITERALS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 Unicode string literals. Otherwise undefined. nuclear@0: // http://en.wikipedia.org/wiki/C%2B%2B11#New_string_literals nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_UNICODE_STRING_LITERALS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_unicode_literals)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 407))) /* EDG 4.7+ */ nuclear@0: // Not supported by VC++ as of VS2013. nuclear@0: #define OVR_CPP_NO_UNICODE_STRING_LITERALS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_RAW_STRING_LITERALS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 raw literals. Otherwise undefined. nuclear@0: // http://en.wikipedia.org/wiki/C%2B%2B11#New_string_literals nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_RAW_STRING_LITERALS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_raw_string_literals)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 405)) /* GCC 4.5+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 407))) /* EDG 4.7+ */ nuclear@0: // Not supported by VC++ as of VS2013. nuclear@0: #define OVR_CPP_NO_RAW_STRING_LITERALS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_UNIFIED_INITIALIZATION_SYNTAX nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 unified initialization. nuclear@0: // http://en.wikipedia.org/wiki/C%2B%2B11#Uniform_initialization nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_UNIFIED_INITIALIZATION_SYNTAX) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_generalized_initializers)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 404)) /* GCC 4.4+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1800)) /* VS2013+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 406))) /* EDG 4.6+ */ nuclear@0: #define OVR_CPP_NO_UNIFIED_INITIALIZATION_SYNTAX 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_EXTENDED_FRIEND_DECLARATIONS nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 extended friends. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_EXTENDED_FRIEND_DECLARATIONS) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && !defined(__APPLE__) && (__clang__ >= 209)) /* clang 2.9+ */ && \ nuclear@0: !(defined(__clang__) && defined(__APPLE__) && (__clang__ >= 400)) /* Apple clang 4.0+ */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 407)) /* GCC 4.7+ */ && \ nuclear@0: !(defined(_MSC_VER) && (_MSC_VER >= 1600)) /* VS2010+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 401))) /* EDG 4.1+ */ nuclear@0: #define OVR_CPP_NO_EXTENDED_FRIEND_DECLARATIONS 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: //----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CPP_NO_THREAD_LOCAL nuclear@0: // nuclear@0: // Defined as 1 if the compiler supports C++11 thread_local. Else undefined. Does not nuclear@0: // indicate if the compiler supports C thread-local compiler extensions such as __thread nuclear@0: // and declspec(thread). Use OVR_THREAD_LOCAL if you want to declare a thread-local nuclear@0: // variable that supports C++11 thread_local when available but the C extension when nuclear@0: // it's available. The primary difference between C++11 thread_local and C extensions is nuclear@0: // that C++11 thread_local supports non-PODs and calls their constructors and destructors. nuclear@0: // nuclear@0: // Note that thread_local requires both compiler and linker support, and so it's possible nuclear@0: // that the compiler may support thread_local but the linker does not. nuclear@0: nuclear@0: #if !defined(OVR_CPP_NO_THREAD_LOCAL) nuclear@0: #if !defined(OVR_CPP11_ENABLED) || \ nuclear@0: (!(defined(__clang__) && OVR_CC_HAS_FEATURE(cxx_thread_local)) /* clang */ && \ nuclear@0: !(defined(__GNUC__) && (OVR_CC_VERSION >= 408)) /* GCC 4.8+ */ && \ nuclear@0: !(defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 408))) /* EDG 4.8+ */ nuclear@0: #define OVR_CPP_NO_THREAD_LOCAL 1 nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_ALIGNAS / OVR_ALIGNOF nuclear@0: // nuclear@0: // OVR_ALIGNAS(n) // Specifies a size_t power of two alignment for a type or instance. nuclear@0: // OVR_ALIGNOF(type) // Returns the size_t alignment of a type or instance. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_ALIGNAS(8) char c = 'c'; // Specifies that the instance c be aligned to an 8 byte boundary. nuclear@0: // typedef OVR_ALIGNAS(8) char C; // Specifies that the type C be aligned to an 8 byte boundary. nuclear@0: // struct OVR_ALIGNAS(64) S{ char array[16]; }; // Specfies that the struct S have a natural alignment of 64. nuclear@0: // OVR_ALIGNAS(32) S s; // Specifies that the instance s of struct S be aligned to an 32 byte boundary. nuclear@0: // OVR_ALIGNAS(32) struct T{ char array[16]; } t; // Specfies that the instance t of struct T have a natural alignment of 32. nuclear@0: // struct OVR_ALIGNAS(T) U{}; // Specifes that U be aligned the same as T. Supported only by C++11 compilers (see OVR_CPP_NO_ALIGNAS). nuclear@0: // nuclear@0: // size_t a = OVR_ALIGNOF(double); // Returns the natural alignment of the double type. nuclear@0: // size_t a = OVR_ALIGNOF(S); // Returns the natural alignment of the struct S type. nuclear@0: // nuclear@0: // Note: If C++11 alignas is supported, then alignas/OVR_ALIGNAS may take a const expression in addition to a constant. nuclear@0: // Note: The C11 Standard species the _Alignas keyword and alignas as a macro for it in nuclear@0: nuclear@0: #if !defined(OVR_ALIGNAS) nuclear@0: #if defined(OVR_CC_GNU) && !defined(OVR_CPP_NO_ALIGNAS) // If C++11 alignas is supported... nuclear@0: #define OVR_ALIGNAS(n) alignas(n) nuclear@0: #elif defined(__clang__) && !defined(OVR_CPP_NO_ALIGNAS) nuclear@0: #define OVR_ALIGNAS(n) alignas(n) nuclear@0: #elif defined(OVR_CC_GNU) || defined(__clang__) nuclear@0: #define OVR_ALIGNAS(n) __attribute__((aligned(n))) nuclear@0: #elif defined(OVR_CC_MSVC) || defined(OVR_CC_INTEL) nuclear@0: #define OVR_ALIGNAS(n) __declspec(align(n)) // For Microsoft the alignment must be a literal integer. nuclear@0: #elif defined(OVR_CC_ARM) nuclear@0: #define OVR_ALIGNAS(n) __align(n) nuclear@0: #else nuclear@0: #error Need to define OVR_ALIGNAS nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_ALIGNOF) nuclear@0: #if defined(OVR_CC_GNU) && !defined(OVR_CPP_NO_ALIGNOF) // If C++11 alignof is supported... nuclear@0: #define OVR_ALIGNOF(type) alignof(type) nuclear@0: #elif defined(__clang__) && !defined(OVR_CPP_NO_ALIGNOF) nuclear@0: #define OVR_ALIGNOF(type) alignof(type) nuclear@0: #elif defined(OVR_CC_GNU) || defined(__clang__) nuclear@0: #define OVR_ALIGNOF(type) ((size_t)__alignof__(type)) nuclear@0: #elif defined(OVR_CC_MSVC) || defined(OVR_CC_INTEL) nuclear@0: #define OVR_ALIGNOF(type) ((size_t)__alignof(type)) nuclear@0: #elif defined(OVR_CC_ARM) nuclear@0: #define OVR_ALIGNOF(type) ((size_t)__ALIGNOF__(type)) nuclear@0: #else nuclear@0: #error Need to define OVR_ALIGNOF nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_ASSUME / OVR_ANALYSIS_ASSUME nuclear@0: // nuclear@0: // This is a portable wrapper for VC++'s __assume and __analysis_assume. nuclear@0: // __analysis_assume is typically used to quell VC++ static analysis warnings. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // void Test(char c){ nuclear@0: // switch(c){ nuclear@0: // case 'a': nuclear@0: // case 'b': nuclear@0: // case 'c': nuclear@0: // case 'd': nuclear@0: // break; nuclear@0: // default: nuclear@0: // OVR_ASSUME(0); // Unreachable code. nuclear@0: // } nuclear@0: // } nuclear@0: // nuclear@0: // size_t Test(char* str){ nuclear@0: // OVR_ANALYSIS_ASSUME(str != nullptr); nuclear@0: // return strlen(str); nuclear@0: // } nuclear@0: nuclear@0: #if !defined(OVR_ASSUME) nuclear@0: #if defined(OVR_CC_MSVC) nuclear@0: #define OVR_ASSUME(x) __assume(x) nuclear@0: #define OVR_ANALYSIS_ASSUME(x) __analysis_assume(!!(x)) nuclear@0: #else nuclear@0: #define OVR_ASSUME(x) nuclear@0: #define OVR_ANALYSIS_ASSUME(x) nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_RESTRICT nuclear@0: // nuclear@0: // Wraps the C99 restrict keyword in a portable way. nuclear@0: // C++11 and C++14 don't have restrict but this functionality is supported by nuclear@0: // all C++ compilers. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // void* memcpy(void* OVR_RESTRICT s1, const void* OVR_RESTRICT s2, size_t n); nuclear@0: nuclear@0: #if !defined(OVR_RESTRICT) nuclear@0: #define OVR_RESTRICT __restrict // Currently supported by all compilers of significance to us. nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_NOEXCEPT / OVR_NOEXCEPT_IF(predicate) / OVR_NOEXCEPT_EXPR(expression) nuclear@0: // nuclear@0: // Implements a portable wrapper for C++11 noexcept. nuclear@0: // http://en.cppreference.com/w/cpp/language/noexcept nuclear@0: // nuclear@0: // Example usage: nuclear@0: // void Test() OVR_NOEXCEPT {} // This function doesn't throw. nuclear@0: // nuclear@0: // template nuclear@0: // void DoNothing() OVR_NOEXCEPT_IF(OVR_NOEXCEPT_EXPR(T())) // Throws an if and only if T::T(int) throws. nuclear@0: // { T t(3); } nuclear@0: // nuclear@0: #if !defined(OVR_NOEXCEPT) nuclear@0: #if defined(OVR_CPP_NOEXCEPT) nuclear@0: #define OVR_NOEXCEPT nuclear@0: #define OVR_NOEXCEPT_IF(predicate) nuclear@0: #define OVR_NOEXCEPT_EXPR(expression) false nuclear@0: #else nuclear@0: #define OVR_NOEXCEPT noexcept nuclear@0: #define OVR_NOEXCEPT_IF(predicate) noexcept((predicate)) nuclear@0: #define OVR_NOEXCEPT_EXPR(expression) noexcept((expression)) nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_FINAL nuclear@0: // nuclear@0: // Wraps the C++11 final keyword in a portable way. nuclear@0: // http://en.cppreference.com/w/cpp/language/final nuclear@0: // nuclear@0: // Example usage: nuclear@0: // struct Test { virtual int GetValue() OVR_FINAL; }; nuclear@0: nuclear@0: #if !defined(OVR_FINAL) nuclear@0: #if defined(OVR_CC_MSVC) && (OVR_CC_VERSION < 1700) // VC++ 2012 and earlier nuclear@0: #define OVR_FINAL sealed nuclear@0: #elif defined(OVR_CPP_INHERITANCE_FINAL) nuclear@0: #define OVR_FINAL nuclear@0: #else nuclear@0: #define OVR_FINAL final nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_OVERRIDE nuclear@0: // nuclear@0: // Wraps the C++11 override keyword in a portable way. nuclear@0: // http://en.cppreference.com/w/cpp/language/override nuclear@0: // nuclear@0: // Example usage: nuclear@0: // struct Parent { virtual void Func(int); }; nuclear@0: // struct Child : public Parent { void Func(int) OVR_OVERRIDE; }; nuclear@0: nuclear@0: #if !defined(OVR_CPP11_ENABLED) nuclear@0: #define OVR_OVERRIDE nuclear@0: #elif !defined(OVR_OVERRIDE) nuclear@0: #if defined(OVR_CPP_OVERRIDE) nuclear@0: #define OVR_OVERRIDE nuclear@0: #else nuclear@0: #if (defined(_MSC_VER) && (_MSC_VER <= 1600)) nuclear@0: #pragma warning(disable : 4481) nuclear@0: #endif nuclear@0: #define OVR_OVERRIDE override nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_FINAL_OVERRIDE nuclear@0: // nuclear@0: // Wraps the C++11 final+override keywords (a common combination) in a portable way. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // struct Parent { virtual void Func(); }; nuclear@0: // struct Child : public Parent { virtual void Func() OVR_FINAL_OVERRIDE; }; nuclear@0: nuclear@0: #if !defined(OVR_FINAL_OVERRIDE) nuclear@0: #define OVR_FINAL_OVERRIDE OVR_FINAL OVR_OVERRIDE nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_EXTERN_TEMPLATE nuclear@0: // nuclear@0: // Portable wrapper for C++11 extern template. This tells the compiler to not instantiate nuclear@0: // the template in the current translation unit, which can significantly speed up nuclear@0: // compilation and avoid problems due to two translation units compiling code with nuclear@0: // different settings. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_EXTERN_TEMPLATE(class basic_string); // Nothing to do for non-C++11 compilers. nuclear@0: nuclear@0: #if !defined(OVR_EXTERN_TEMPLATE) nuclear@0: #if defined(OVR_CPP_EXTERN_TEMPLATE) nuclear@0: #define OVR_EXTERN_TEMPLATE(decl) nuclear@0: #else nuclear@0: #define OVR_EXTERN_TEMPLATE(decl) extern template decl nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_CONSTEXPR / OVR_CONSTEXPR_OR_CONST nuclear@0: // nuclear@0: // Portable wrapper for C++11 constexpr. Doesn't include C++14 relaxed constexpr, nuclear@0: // for which a different wrapper name is reserved. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // OVR_CONSTEXPR int Test() { return 15; } // This can be optimized better by a C++11 compiler that supports constexpr. nuclear@0: // OVR_CONSTEXPR_OR_CONST float x = 3.14159f; // This can be optimized better by a C++11 compiler, but if not then at least make it const. nuclear@0: nuclear@0: #if !defined(OVR_CONSTEXPR) nuclear@0: #if defined(OVR_CPP_NO_CONSTEXPR) nuclear@0: #define OVR_CONSTEXPR nuclear@0: #else nuclear@0: #define OVR_CONSTEXPR constexpr nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: #if !defined(OVR_CONSTEXPR_OR_CONST) nuclear@0: #if defined(OVR_CPP_NO_CONSTEXPR) nuclear@0: #define OVR_CONSTEXPR_OR_CONST const nuclear@0: #else nuclear@0: #define OVR_CONSTEXPR_OR_CONST constexpr nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_FUNCTION_DELETE / OVR_FUNCTION_DEFAULT nuclear@0: // nuclear@0: // Wraps the C++11 delete and default keywords in a way that allows for cleaner code nuclear@0: // while making for a better version of uncallable or default functions. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // struct Test{ nuclear@0: // Test() OVR_FUNCTION_DEFAULT; // Non-C++11 compilers will require a separate definition for Test(). nuclear@0: // private: // Users should put OVR_FUNCTION_DELETE usage in a private nuclear@0: // void Uncallable() OVR_FUNCTION_DELETE; // area for compatibility with pre-C++11 compilers. nuclear@0: // }; nuclear@0: nuclear@0: #if defined(OVR_CPP_NO_DELETED_FUNCTIONS) nuclear@0: #define OVR_FUNCTION_DELETE nuclear@0: #else nuclear@0: #define OVR_FUNCTION_DELETE = delete nuclear@0: #endif nuclear@0: nuclear@0: #if defined(OVR_CPP_NO_DEFAULTED_FUNCTIONS) nuclear@0: #define OVR_FUNCTION_DEFAULT nuclear@0: #else nuclear@0: #define OVR_FUNCTION_DEFAULT = default nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: nuclear@0: // ----------------------------------------------------------------------------------- nuclear@0: // ***** OVR_NON_COPYABLE nuclear@0: // nuclear@0: // Allows you to specify a class as being neither copy-constructible nor assignable, nuclear@0: // which is a commonly needed pattern in C++ programming. Classes with this declaration nuclear@0: // are required to be default constructible (as are most classes). For pre-C++11 nuclear@0: // compilers this macro declares a private section for the class, which will be nuclear@0: // inherited by whatever code is directly below the macro invocation by default. nuclear@0: // nuclear@0: // Example usage: nuclear@0: // struct Test { nuclear@0: // Test(); nuclear@0: // ... nuclear@0: // OVR_NON_COPYABLE(Test) nuclear@0: // }; nuclear@0: nuclear@0: #if !defined(OVR_NON_COPYABLE) nuclear@0: #if defined(OVR_CPP_NO_DELETED_FUNCTIONS) nuclear@0: #define OVR_NON_COPYABLE(Type) \ nuclear@0: private: \ nuclear@0: Type(const Type&); \ nuclear@0: void operator=(const Type&); nuclear@0: #else nuclear@0: #define OVR_NON_COPYABLE(Type) \ nuclear@0: Type(const Type&) = delete; \ nuclear@0: void operator=(const Type&) = delete; nuclear@0: #endif nuclear@0: #endif nuclear@0: nuclear@0: nuclear@0: nuclear@0: #endif // header include guard nuclear@0: nuclear@0: nuclear@0: nuclear@0: