github.com/moontrade/nogc@v0.1.7/sync/CPortability.h (about)

     1  /*
     2   * Copyright (c) Facebook, Inc. and its affiliates.
     3   *
     4   * Licensed under the Apache License, Version 2.0 (the "License");
     5   * you may not use this file except in compliance with the License.
     6   * You may obtain a copy of the License at
     7   *
     8   *     http://www.apache.org/licenses/LICENSE-2.0
     9   *
    10   * Unless required by applicable law or agreed to in writing, software
    11   * distributed under the License is distributed on an "AS IS" BASIS,
    12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13   * See the License for the specific language governing permissions and
    14   * limitations under the License.
    15   */
    16  
    17  #pragma once
    18  
    19  /* These definitions are in a separate file so that they
    20   * may be included from C- as well as C++-based projects. */
    21  
    22  #include "PortabilityConfig.h"
    23  
    24  /**
    25   * Portable version check.
    26   */
    27  #ifndef __GNUC_PREREQ
    28  #if defined __GNUC__ && defined __GNUC_MINOR__
    29  /* nolint */
    30  #define __GNUC_PREREQ(maj, min) \
    31    ((__GNUC__ << 16) + __GNUC_MINOR__ >= ((maj) << 16) + (min))
    32  #else
    33  /* nolint */
    34  #define __GNUC_PREREQ(maj, min) 0
    35  #endif
    36  #endif
    37  
    38  // portable version check for clang
    39  #ifndef __CLANG_PREREQ
    40  #if defined __clang__ && defined __clang_major__ && defined __clang_minor__
    41  /* nolint */
    42  #define __CLANG_PREREQ(maj, min) \
    43    ((__clang_major__ << 16) + __clang_minor__ >= ((maj) << 16) + (min))
    44  #else
    45  /* nolint */
    46  #define __CLANG_PREREQ(maj, min) 0
    47  #endif
    48  #endif
    49  
    50  #if defined(__has_builtin)
    51  #define FOLLY_HAS_BUILTIN(...) __has_builtin(__VA_ARGS__)
    52  #else
    53  #define FOLLY_HAS_BUILTIN(...) 0
    54  #endif
    55  
    56  #if defined(__has_feature)
    57  #define FOLLY_HAS_FEATURE(...) __has_feature(__VA_ARGS__)
    58  #else
    59  #define FOLLY_HAS_FEATURE(...) 0
    60  #endif
    61  
    62  /* FOLLY_SANITIZE_ADDRESS is defined to 1 if the current compilation unit
    63   * is being compiled with ASAN enabled.
    64   *
    65   * Beware when using this macro in a header file: this macro may change values
    66   * across compilation units if some libraries are built with ASAN enabled
    67   * and some built with ASAN disabled.  For instance, this may occur, if folly
    68   * itself was compiled without ASAN but a downstream project that uses folly is
    69   * compiling with ASAN enabled.
    70   *
    71   * Use FOLLY_LIBRARY_SANITIZE_ADDRESS (defined in folly-config.h) to check if
    72   * folly itself was compiled with ASAN enabled.
    73   */
    74  #ifndef FOLLY_SANITIZE_ADDRESS
    75  #if FOLLY_HAS_FEATURE(address_sanitizer) || __SANITIZE_ADDRESS__
    76  #define FOLLY_SANITIZE_ADDRESS 1
    77  #endif
    78  #endif
    79  
    80  /* Define attribute wrapper for function attribute used to disable
    81   * address sanitizer instrumentation. Unfortunately, this attribute
    82   * has issues when inlining is used, so disable that as well. */
    83  #ifdef FOLLY_SANITIZE_ADDRESS
    84  #if defined(__clang__)
    85  #if __has_attribute(__no_sanitize__)
    86  #define FOLLY_DISABLE_ADDRESS_SANITIZER \
    87    __attribute__((__no_sanitize__("address"), __noinline__))
    88  #elif __has_attribute(__no_address_safety_analysis__)
    89  #define FOLLY_DISABLE_ADDRESS_SANITIZER \
    90    __attribute__((__no_address_safety_analysis__, __noinline__))
    91  #elif __has_attribute(__no_sanitize_address__)
    92  #define FOLLY_DISABLE_ADDRESS_SANITIZER \
    93    __attribute__((__no_sanitize_address__, __noinline__))
    94  #endif
    95  #elif defined(__GNUC__)
    96  #define FOLLY_DISABLE_ADDRESS_SANITIZER \
    97    __attribute__((__no_address_safety_analysis__, __noinline__))
    98  #endif
    99  #endif
   100  #ifndef FOLLY_DISABLE_ADDRESS_SANITIZER
   101  #define FOLLY_DISABLE_ADDRESS_SANITIZER
   102  #endif
   103  
   104  /* Define a convenience macro to test when thread sanitizer is being used
   105   * across the different compilers (e.g. clang, gcc) */
   106  #ifndef FOLLY_SANITIZE_THREAD
   107  #if FOLLY_HAS_FEATURE(thread_sanitizer) || __SANITIZE_THREAD__
   108  #define FOLLY_SANITIZE_THREAD 1
   109  #endif
   110  #endif
   111  
   112  #if FOLLY_SANITIZE_THREAD
   113  #define FOLLY_DISABLE_THREAD_SANITIZER \
   114    __attribute__((no_sanitize_thread, noinline))
   115  #else
   116  #define FOLLY_DISABLE_THREAD_SANITIZER
   117  #endif
   118  
   119  /**
   120   * Define a convenience macro to test when memory sanitizer is being used
   121   * across the different compilers (e.g. clang, gcc)
   122   */
   123  #ifndef FOLLY_SANITIZE_MEMORY
   124  #if FOLLY_HAS_FEATURE(memory_sanitizer) || __SANITIZE_MEMORY__
   125  #define FOLLY_SANITIZE_MEMORY 1
   126  #endif
   127  #endif
   128  
   129  #if FOLLY_SANITIZE_MEMORY
   130  #define FOLLY_DISABLE_MEMORY_SANITIZER \
   131    __attribute__((no_sanitize_memory, noinline))
   132  #else
   133  #define FOLLY_DISABLE_MEMORY_SANITIZER
   134  #endif
   135  
   136  /**
   137   * Define a convenience macro to test when ASAN, UBSAN, TSAN or MSAN sanitizer
   138   * are being used
   139   */
   140  #ifndef FOLLY_SANITIZE
   141  #if defined(FOLLY_SANITIZE_ADDRESS) || defined(FOLLY_SANITIZE_THREAD) || \
   142      defined(FOLLY_SANITIZE_MEMORY)
   143  #define FOLLY_SANITIZE 1
   144  #endif
   145  #endif
   146  
   147  #if FOLLY_SANITIZE
   148  #define FOLLY_DISABLE_UNDEFINED_BEHAVIOR_SANITIZER(...) \
   149    __attribute__((no_sanitize(__VA_ARGS__)))
   150  #else
   151  #define FOLLY_DISABLE_UNDEFINED_BEHAVIOR_SANITIZER(...)
   152  #endif // FOLLY_SANITIZE
   153  
   154  #define FOLLY_DISABLE_SANITIZERS                                 \
   155    FOLLY_DISABLE_ADDRESS_SANITIZER FOLLY_DISABLE_THREAD_SANITIZER \
   156        FOLLY_DISABLE_UNDEFINED_BEHAVIOR_SANITIZER("undefined")
   157  
   158  /**
   159   * Macro for marking functions as having public visibility.
   160   */
   161  #if defined(__GNUC__)
   162  #define FOLLY_EXPORT __attribute__((__visibility__("default")))
   163  #else
   164  #define FOLLY_EXPORT
   165  #endif
   166  
   167  // noinline
   168  #ifdef _MSC_VER
   169  #define FOLLY_NOINLINE __declspec(noinline)
   170  #elif defined(__GNUC__)
   171  #define FOLLY_NOINLINE __attribute__((__noinline__))
   172  #else
   173  #define FOLLY_NOINLINE
   174  #endif
   175  
   176  // always inline
   177  #ifdef _MSC_VER
   178  #define FOLLY_ALWAYS_INLINE __forceinline
   179  #elif defined(__GNUC__)
   180  #define FOLLY_ALWAYS_INLINE inline __attribute__((__always_inline__))
   181  #else
   182  #define FOLLY_ALWAYS_INLINE inline
   183  #endif
   184  
   185  // attribute hidden
   186  #if defined(_MSC_VER)
   187  #define FOLLY_ATTR_VISIBILITY_HIDDEN
   188  #elif defined(__GNUC__)
   189  #define FOLLY_ATTR_VISIBILITY_HIDDEN __attribute__((__visibility__("hidden")))
   190  #else
   191  #define FOLLY_ATTR_VISIBILITY_HIDDEN
   192  #endif
   193  
   194  // An attribute for marking symbols as weak, if supported
   195  #if FOLLY_HAVE_WEAK_SYMBOLS
   196  #define FOLLY_ATTR_WEAK __attribute__((__weak__))
   197  #else
   198  #define FOLLY_ATTR_WEAK
   199  #endif
   200  
   201  // Microsoft ABI version (can be overridden manually if necessary)
   202  #ifndef FOLLY_MICROSOFT_ABI_VER
   203  #ifdef _MSC_VER
   204  #define FOLLY_MICROSOFT_ABI_VER _MSC_VER
   205  #endif
   206  #endif
   207  
   208  //  FOLLY_ERASE
   209  //
   210  //  A conceptual attribute/syntax combo for erasing a function from the build
   211  //  artifacts and forcing all call-sites to inline the callee, at least as far
   212  //  as each compiler supports.
   213  //
   214  //  Semantically includes the inline specifier.
   215  #define FOLLY_ERASE FOLLY_ALWAYS_INLINE FOLLY_ATTR_VISIBILITY_HIDDEN
   216  
   217  //  FOLLY_ERASE_HACK_GCC
   218  //
   219  //  Equivalent to FOLLY_ERASE, but without hiding under gcc. Useful when applied
   220  //  to a function which may sometimes be hidden separately, for example by being
   221  //  declared in an anonymous namespace, since in such cases with -Wattributes
   222  //  enabled, gcc would emit: 'visibility' attribute ignored.
   223  //
   224  //  Semantically includes the inline specifier.
   225  #if defined(__GNUC__) && !defined(__clang__)
   226  #define FOLLY_ERASE_HACK_GCC FOLLY_ALWAYS_INLINE
   227  #else
   228  #define FOLLY_ERASE_HACK_GCC FOLLY_ERASE
   229  #endif
   230  
   231  //  FOLLY_ERASE_TRYCATCH
   232  //
   233  //  Equivalent to FOLLY_ERASE, but for code which might contain explicit
   234  //  exception handling. Has the effect of FOLLY_ERASE, except under MSVC which
   235  //  warns about __forceinline when functions contain exception handling.
   236  //
   237  //  Semantically includes the inline specifier.
   238  #ifdef _MSC_VER
   239  #define FOLLY_ERASE_TRYCATCH inline
   240  #else
   241  #define FOLLY_ERASE_TRYCATCH FOLLY_ERASE
   242  #endif