/*
- * Copyright 2015 Facebook, Inc.
+ * Copyright 2016 Facebook, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* limitations under the License.
*/
-#ifndef FOLLY_PORTABILITY_H_
-#define FOLLY_PORTABILITY_H_
+#pragma once
#include <string.h>
#include <cstddef>
-#ifndef FOLLY_NO_CONFIG
-#include <folly/folly-config.h>
-#endif
-
-#ifdef FOLLY_PLATFORM_CONFIG
-#include FOLLY_PLATFORM_CONFIG
-#endif
-
-#if FOLLY_HAVE_FEATURES_H
-#include <features.h>
-#endif
+#include <folly/portability/Config.h>
#include <folly/CPortability.h>
-#ifdef __APPLE__
-# include <malloc/malloc.h>
-#endif
-
#if FOLLY_HAVE_SCHED_H
#include <sched.h>
- #ifndef FOLLY_HAVE_PTHREAD_YIELD
- #define pthread_yield sched_yield
- #endif
#endif
-// A change in folly/MemoryMapping.cpp uses MAP_ANONYMOUS, which is named
-// MAP_ANON on OSX/BSD.
-#if defined(__APPLE__) || defined(__FreeBSD__)
- #include <sys/mman.h>
- #ifndef MAP_ANONYMOUS
- #ifdef MAP_ANON
- #define MAP_ANONYMOUS MAP_ANON
- #endif
- #endif
+// Unaligned loads and stores
+namespace folly {
+#if FOLLY_HAVE_UNALIGNED_ACCESS
+constexpr bool kHasUnalignedAccess = true;
+#else
+constexpr bool kHasUnalignedAccess = false;
#endif
+}
// compiler specific attribute translation
// msvc should come first, so if clang is in msvc mode it gets the right defines
# define FOLLY_DEPRECATED(msg)
#endif
-// noreturn
-#if defined(_MSC_VER)
-# define FOLLY_NORETURN __declspec(noreturn)
-#elif defined(__clang__) || defined(__GNUC__)
-# define FOLLY_NORETURN __attribute__((__noreturn__))
-#else
-# define FOLLY_NORETURN
-#endif
-
// noinline
#ifdef _MSC_VER
# define FOLLY_NOINLINE __declspec(noinline)
# define FOLLY_ALWAYS_INLINE inline
#endif
+// target
+#ifdef _MSC_VER
+# define FOLLY_TARGET_ATTRIBUTE(target)
+#else
+# define FOLLY_TARGET_ATTRIBUTE(target) __attribute__((__target__(target)))
+#endif
+
// detection for 64 bit
#if defined(__x86_64__) || defined(_M_X64)
# define FOLLY_X64 1
# define FOLLY_PACK_POP /**/
#endif
+// Generalize warning push/pop.
+#if defined(_MSC_VER)
+# define FOLLY_PUSH_WARNING __pragma(warning(push))
+# define FOLLY_POP_WARNING __pragma(warning(pop))
+// Disable the GCC warnings.
+# define FOLLY_GCC_DISABLE_WARNING(warningName)
+# define FOLLY_MSVC_DISABLE_WARNING(warningNumber) __pragma(warning(disable: warningNumber))
+#elif defined(__clang__) || defined(__GNUC__)
+# define FOLLY_PUSH_WARNING _Pragma("GCC diagnostic push")
+# define FOLLY_POP_WARNING _Pragma("GCC diagnostic pop")
+#define FOLLY_GCC_DISABLE_WARNING_INTERNAL3(warningName) #warningName
+#define FOLLY_GCC_DISABLE_WARNING_INTERNAL2(warningName) \
+ FOLLY_GCC_DISABLE_WARNING_INTERNAL3(warningName)
+#define FOLLY_GCC_DISABLE_WARNING(warningName) \
+ _Pragma(FOLLY_GCC_DISABLE_WARNING_INTERNAL2(GCC diagnostic ignored \
+ FOLLY_GCC_DISABLE_WARNING_INTERNAL3(-W##warningName)))
+// Disable the MSVC warnings.
+# define FOLLY_MSVC_DISABLE_WARNING(warningNumber)
+#else
+# define FOLLY_PUSH_WARNING
+# define FOLLY_POP_WARNING
+# define FOLLY_GCC_DISABLE_WARNING(warningName)
+# define FOLLY_MSVC_DISABLE_WARNING(warningNumber)
+#endif
+
// portable version check
#ifndef __GNUC_PREREQ
# if defined __GNUC__ && defined __GNUC_MINOR__
# error cannot define platform specific thread local storage
#endif
-// Define to 1 if you have the `preadv' and `pwritev' functions, respectively
-#if !defined(FOLLY_HAVE_PREADV) && !defined(FOLLY_HAVE_PWRITEV)
-# if defined(__GLIBC_PREREQ)
-# if __GLIBC_PREREQ(2, 10)
-# define FOLLY_HAVE_PREADV 1
-# define FOLLY_HAVE_PWRITEV 1
-# endif
-# endif
+#if FOLLY_MOBILE
+#undef FOLLY_TLS
#endif
// It turns out that GNU libstdc++ and LLVM libc++ differ on how they implement
-// the 'std' namespace; the latter uses inline namepsaces. Wrap this decision
+// the 'std' namespace; the latter uses inline namespaces. Wrap this decision
// up in a macro to make forward-declarations easier.
#if FOLLY_USE_LIBCPP
#include <__config>
# define FOLLY_GLIBCXX_NAMESPACE_CXX11_END
#endif
-// Some platforms lack clock_gettime(2) and clock_getres(2). Inject our own
-// versions of these into the global namespace.
-#if FOLLY_HAVE_CLOCK_GETTIME
-#include <time.h>
-#else
-#include <folly/detail/Clock.h>
-#endif
-
// Provide our own std::__throw_* wrappers for platforms that don't have them
#if FOLLY_HAVE_BITS_FUNCTEXCEPT_H
#include <bits/functexcept.h>
// MSVC specific defines
// mainly for posix compat
#ifdef _MSC_VER
-
-// this definition is in a really silly place with a silly name
-// and ifdefing it every time we want it is painful
-#include <basetsd.h>
-typedef SSIZE_T ssize_t;
-
-// sprintf semantics are not exactly identical
-// but current usage is not a problem
-# define snprintf _snprintf
-
-// semantics here are identical
-# define strerror_r(errno,buf,len) strerror_s(buf,len,errno)
+#include <folly/portability/SysTypes.h>
// compiler specific to compiler specific
// nolint
// Hide a GCC specific thing that breaks MSVC if left alone.
# define __extension__
-#ifdef _M_IX86_FP
-# define FOLLY_SSE _M_IX86_FP
-# define FOLLY_SSE_MINOR 0
+// We have compiler support for the newest of the new, but
+// MSVC doesn't tell us that.
+#define __SSE4_2__ 1
+
#endif
+// Debug
+namespace folly {
+#ifdef NDEBUG
+constexpr auto kIsDebug = false;
+#else
+constexpr auto kIsDebug = true;
#endif
+}
+
+// Endianness
+namespace folly {
+#ifdef _MSC_VER
+// It's MSVC, so we just have to guess ... and allow an override
+#ifdef FOLLY_ENDIAN_BE
+constexpr auto kIsLittleEndian = false;
+#else
+constexpr auto kIsLittleEndian = true;
+#endif
+#else
+constexpr auto kIsLittleEndian = __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__;
+#endif
+constexpr auto kIsBigEndian = !kIsLittleEndian;
+}
#ifndef FOLLY_SSE
# if defined(__SSE4_2__)
#include <TargetConditionals.h>
#endif
-// MacOS doesn't have malloc_usable_size()
-#if defined(__APPLE__) && !defined(FOLLY_HAVE_MALLOC_USABLE_SIZE)
-inline size_t malloc_usable_size(void* ptr) {
- return malloc_size(ptr);
-}
-#endif
-
// RTTI may not be enabled for this compilation unit.
#if defined(__GXX_RTTI) || defined(__cpp_rtti) || \
(defined(_MSC_VER) && defined(_CPPRTTI))
# define FOLLY_HAS_RTTI 1
#endif
-#ifdef _MSC_VER
-# include <intrin.h>
+#if defined(__APPLE__) || defined(_MSC_VER)
+#define FOLLY_STATIC_CTOR_PRIORITY_MAX
+#else
+// 101 is the highest priority allowed by the init_priority attribute.
+// This priority is already used by JEMalloc and other memory allocators so
+// we will take the next one.
+#define FOLLY_STATIC_CTOR_PRIORITY_MAX __attribute__((__init_priority__(102)))
#endif
namespace folly {
-inline void asm_volatile_memory() {
-#if defined(__clang__) || defined(__GNUC__)
- asm volatile("" : : : "memory");
-#elif defined(_MSC_VER)
- ::_ReadWriteBarrier();
-#endif
-}
-
-inline void asm_volatile_pause() {
-#if defined(_MSC_VER) && (defined(_M_IX86) || defined(_M_X64))
- ::_mm_pause();
-#elif defined(__i386__) || FOLLY_X64
- asm volatile ("pause");
-#elif FOLLY_A64
- asm volatile ("wfe");
-#elif FOLLY_PPC64
- asm volatile("or 27,27,27");
-#endif
-}
-inline void asm_pause() {
-#if defined(_MSC_VER) && (defined(_M_IX86) || defined(_M_X64))
- ::_mm_pause();
-#elif defined(__i386__) || FOLLY_X64
- asm ("pause");
-#elif FOLLY_A64
- asm ("wfe");
-#elif FOLLY_PPC64
- asm ("or 31,31,31");
-#endif
-}
-
-constexpr size_t constexpr_strlen(const char* s) {
-#if defined(__clang__)
- return __builtin_strlen(s);
+#ifdef __linux__
+constexpr auto kIsLinux = true;
#else
- return strlen(s);
+constexpr auto kIsLinux = false;
#endif
}
-
-} // namespace folly
-#endif // FOLLY_PORTABILITY_H_