Merge "configure: check for __builtin_bswapXX()"

This commit is contained in:
James Zern 2014-07-05 13:43:43 -07:00 committed by Gerrit Code Review
commit 5a1a7264fc
2 changed files with 50 additions and 11 deletions

View File

@ -127,6 +127,26 @@ AC_DEFUN([LIBCHECK_EPILOGUE],
CPPFLAGS=$SAVED_CPPFLAGS CPPFLAGS=$SAVED_CPPFLAGS
LIBS=$SAVED_LIBS]) LIBS=$SAVED_LIBS])
dnl === Check for gcc builtins
dnl === CHECK_FOR_BUILTIN([builtin], [param], [define])
dnl === links a C AC_LANG_PROGRAM, with <builtin>(<param>)
dnl === AC_DEFINE'ing <define> if successful.
AC_DEFUN([CHECK_FOR_BUILTIN],
[AC_LANG_PUSH([C])
AC_MSG_CHECKING([for $1])
AC_LINK_IFELSE([AC_LANG_PROGRAM([], [$1($2)])],
[AC_MSG_RESULT([yes])
AC_DEFINE([$3], [1],
[Set to 1 if $1 is available])],
[AC_MSG_RESULT([no])]),
AC_LANG_POP])
dnl AC_CHECK_FUNC doesn't work with builtin's.
CHECK_FOR_BUILTIN([__builtin_bswap16], [1u << 15], [HAVE_BUILTIN_BSWAP16])
CHECK_FOR_BUILTIN([__builtin_bswap32], [1u << 31], [HAVE_BUILTIN_BSWAP32])
CHECK_FOR_BUILTIN([__builtin_bswap64], [1ull << 63], [HAVE_BUILTIN_BSWAP64])
dnl === Check for pthread support dnl === Check for pthread support
AC_ARG_ENABLE([threading], AC_ARG_ENABLE([threading],
AS_HELP_STRING([--disable-threading], AS_HELP_STRING([--disable-threading],

View File

@ -33,24 +33,43 @@
#define HToLE16(x) (x) #define HToLE16(x) (x)
#endif #endif
// gcc 4.3 has builtin functions for swap32/swap64 #if !defined(HAVE_CONFIG_H)
// TODO(jzern): this should have a corresponding autoconf check. #ifdef __GNUC__
#if defined(__GNUC__) && \ # define LOCAL_GCC_VERSION ((__GNUC__ << 8) | __GNUC_MINOR__)
(__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 3)) #else
#define HAVE_BUILTIN_BSWAP # define LOCAL_GCC_VERSION 0
#endif // __GNUC__
#ifdef __clang__
# define LOCAL_CLANG_VERSION ((__clang_major__ << 8) | __clang_minor__)
#else
# define LOCAL_CLANG_VERSION 0
#endif // __clang__
// clang-3.3 and gcc-4.3 have builtin functions for swap32/swap64
#if LOCAL_GCC_VERSION >= 0x403 || LOCAL_CLANG_VERSION >= 0x303
#define HAVE_BUILTIN_BSWAP32
#define HAVE_BUILTIN_BSWAP64
#endif #endif
// clang-3.3 and gcc-4.8 have a builtin function for swap16
#if LOCAL_GCC_VERSION >= 0x408 || LOCAL_CLANG_VERSION >= 0x303
#define HAVE_BUILTIN_BSWAP16
#endif
#endif // !HAVE_CONFIG_H
static WEBP_INLINE uint16_t BSwap16(uint16_t x) { static WEBP_INLINE uint16_t BSwap16(uint16_t x) {
#if defined(_MSC_VER) #if defined(HAVE_BUILTIN_BSWAP16)
return __builtin_bswap16(x);
#elif defined(_MSC_VER)
return _byteswap_ushort(x); return _byteswap_ushort(x);
#else #else
// gcc will recognize a 'rorw $8, ...' here: // gcc will recognize a 'rorw $8, ...' here:
return (x >> 8) | ((x & 0xff) << 8); return (x >> 8) | ((x & 0xff) << 8);
#endif // _MSC_VER #endif // HAVE_BUILTIN_BSWAP16
} }
static WEBP_INLINE uint32_t BSwap32(uint32_t x) { static WEBP_INLINE uint32_t BSwap32(uint32_t x) {
#if defined(HAVE_BUILTIN_BSWAP) #if defined(HAVE_BUILTIN_BSWAP32)
return __builtin_bswap32(x); return __builtin_bswap32(x);
#elif defined(__i386__) || defined(__x86_64__) #elif defined(__i386__) || defined(__x86_64__)
uint32_t swapped_bytes; uint32_t swapped_bytes;
@ -60,11 +79,11 @@ static WEBP_INLINE uint32_t BSwap32(uint32_t x) {
return (uint32_t)_byteswap_ulong(x); return (uint32_t)_byteswap_ulong(x);
#else #else
return (x >> 24) | ((x >> 8) & 0xff00) | ((x << 8) & 0xff0000) | (x << 24); return (x >> 24) | ((x >> 8) & 0xff00) | ((x << 8) & 0xff0000) | (x << 24);
#endif // HAVE_BUILTIN_BSWAP #endif // HAVE_BUILTIN_BSWAP32
} }
static WEBP_INLINE uint64_t BSwap64(uint64_t x) { static WEBP_INLINE uint64_t BSwap64(uint64_t x) {
#if defined(HAVE_BUILTIN_BSWAP) #if defined(HAVE_BUILTIN_BSWAP64)
return __builtin_bswap64(x); return __builtin_bswap64(x);
#elif defined(__x86_64__) #elif defined(__x86_64__)
uint64_t swapped_bytes; uint64_t swapped_bytes;
@ -77,7 +96,7 @@ static WEBP_INLINE uint64_t BSwap64(uint64_t x) {
x = ((x & 0xffff0000ffff0000ull) >> 16) | ((x & 0x0000ffff0000ffffull) << 16); x = ((x & 0xffff0000ffff0000ull) >> 16) | ((x & 0x0000ffff0000ffffull) << 16);
x = ((x & 0xff00ff00ff00ff00ull) >> 8) | ((x & 0x00ff00ff00ff00ffull) << 8); x = ((x & 0xff00ff00ff00ff00ull) >> 8) | ((x & 0x00ff00ff00ff00ffull) << 8);
return x; return x;
#endif // HAVE_BUILTIN_BSWAP #endif // HAVE_BUILTIN_BSWAP64
} }
#endif // WEBP_UTILS_ENDIAN_INL_H_ #endif // WEBP_UTILS_ENDIAN_INL_H_