Commit fda1c745 authored by Dale Curtis's avatar Dale Curtis Committed by Michael Niedermayer

Use gcc/clang builtins for av_sat_(add|sub)_64_c if available.

Signed-off-by: 's avatarDale Curtis <dalecurtis@chromium.org>
Signed-off-by: 's avatarMichael Niedermayer <michael@niedermayer.cc>
parent 61c1df73
...@@ -34,6 +34,12 @@ ...@@ -34,6 +34,12 @@
# define AV_GCC_VERSION_AT_MOST(x,y) 0 # define AV_GCC_VERSION_AT_MOST(x,y) 0
#endif #endif
#ifdef __has_builtin
# define AV_HAS_BUILTIN(x) __has_builtin(x)
#else
# define AV_HAS_BUILTIN(x) false
#endif
#ifndef av_always_inline #ifndef av_always_inline
#if AV_GCC_VERSION_AT_LEAST(3,1) #if AV_GCC_VERSION_AT_LEAST(3,1)
# define av_always_inline __attribute__((always_inline)) inline # define av_always_inline __attribute__((always_inline)) inline
......
...@@ -299,11 +299,16 @@ static av_always_inline int av_sat_dsub32_c(int a, int b) ...@@ -299,11 +299,16 @@ static av_always_inline int av_sat_dsub32_c(int a, int b)
* @return sum with signed saturation * @return sum with signed saturation
*/ */
static av_always_inline int64_t av_sat_add64_c(int64_t a, int64_t b) { static av_always_inline int64_t av_sat_add64_c(int64_t a, int64_t b) {
#if (!defined(__INTEL_COMPILER) && AV_GCC_VERSION_AT_LEAST(5,1)) || AV_HAS_BUILTIN(__builtin_add_overflow)
int64_t tmp;
return !__builtin_add_overflow(a, b, &tmp) ? tmp : (tmp < 0 ? INT64_MAX : INT64_MIN);
#else
if (b >= 0 && a >= INT64_MAX - b) if (b >= 0 && a >= INT64_MAX - b)
return INT64_MAX; return INT64_MAX;
if (b <= 0 && a <= INT64_MIN - b) if (b <= 0 && a <= INT64_MIN - b)
return INT64_MIN; return INT64_MIN;
return a + b; return a + b;
#endif
} }
/** /**
...@@ -314,11 +319,16 @@ static av_always_inline int64_t av_sat_add64_c(int64_t a, int64_t b) { ...@@ -314,11 +319,16 @@ static av_always_inline int64_t av_sat_add64_c(int64_t a, int64_t b) {
* @return difference with signed saturation * @return difference with signed saturation
*/ */
static av_always_inline int64_t av_sat_sub64_c(int64_t a, int64_t b) { static av_always_inline int64_t av_sat_sub64_c(int64_t a, int64_t b) {
#if (!defined(__INTEL_COMPILER) && AV_GCC_VERSION_AT_LEAST(5,1)) || AV_HAS_BUILTIN(__builtin_sub_overflow)
int64_t tmp;
return !__builtin_sub_overflow(a, b, &tmp) ? tmp : (tmp < 0 ? INT64_MAX : INT64_MIN);
#else
if (b <= 0 && a >= INT64_MAX + b) if (b <= 0 && a >= INT64_MAX + b)
return INT64_MAX; return INT64_MAX;
if (b >= 0 && a <= INT64_MIN + b) if (b >= 0 && a <= INT64_MIN + b)
return INT64_MIN; return INT64_MIN;
return a - b; return a - b;
#endif
} }
/** /**
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment