diff --git a/ndk/platforms/android-9/arch-x86/include/fenv.h b/ndk/platforms/android-9/arch-x86/include/fenv.h index 5fe64e2d8..710494c00 100644 --- a/ndk/platforms/android-9/arch-x86/include/fenv.h +++ b/ndk/platforms/android-9/arch-x86/include/fenv.h @@ -45,13 +45,6 @@ typedef struct { char __other[16]; } fenv_t; -#define __get_mxcsr(env) (((env).__mxcsr_hi << 16) | \ - ((env).__mxcsr_lo)) -#define __set_mxcsr(env, x) do { \ - (env).__mxcsr_hi = (__uint32_t)(x) >> 16; \ - (env).__mxcsr_lo = (__uint16_t)(x); \ -} while (0) - typedef __uint16_t fexcept_t; /* Exception flags */ @@ -72,168 +65,35 @@ typedef __uint16_t fexcept_t; #define _ROUND_MASK (FE_TONEAREST | FE_DOWNWARD | \ FE_UPWARD | FE_TOWARDZERO) -/* - * As compared to the x87 control word, the SSE unit's control word - * has the rounding control bits offset by 3 and the exception mask - * bits offset by 7. - */ -#define _SSE_ROUND_SHIFT 3 -#define _SSE_EMASK_SHIFT 7 - -/* After testing for SSE support once, we cache the result in __has_sse. */ -enum __sse_support { __SSE_YES, __SSE_NO, __SSE_UNK }; -extern enum __sse_support __has_sse; -int __test_sse(void); -#ifdef __SSE__ -#define __HAS_SSE() 1 -#else -#define __HAS_SSE() (__has_sse == __SSE_YES || \ - (__has_sse == __SSE_UNK && __test_sse())) -#endif - __BEGIN_DECLS /* Default floating-point environment */ extern const fenv_t __fe_dfl_env; #define FE_DFL_ENV (&__fe_dfl_env) -#define __fldcw(__cw) __asm __volatile("fldcw %0" : : "m" (__cw)) -#define __fldenv(__env) __asm __volatile("fldenv %0" : : "m" (__env)) -#define __fnclex() __asm __volatile("fnclex") -#define __fnstenv(__env) __asm __volatile("fnstenv %0" : "=m" (*(__env))) -#define __fnstcw(__cw) __asm __volatile("fnstcw %0" : "=m" (*(__cw))) -#define __fnstsw(__sw) __asm __volatile("fnstsw %0" : "=a" (*(__sw))) -#define __fwait() __asm __volatile("fwait") -#define __ldmxcsr(__csr) __asm __volatile("ldmxcsr %0" : : "m" (__csr)) -#define __stmxcsr(__csr) __asm __volatile("stmxcsr %0" : "=m" (*(__csr))) +/* C99 floating-point exception functions */ +int feclearexcept(int excepts); +int fegetexceptflag(fexcept_t *flagp, int excepts); +int fesetexceptflag(const fexcept_t *flagp, int excepts); +/* feraiseexcept does not set the inexact flag on overflow/underflow */ +int feraiseexcept(int excepts); +int fetestexcept(int excepts); -static __inline int -feclearexcept(int __excepts) -{ - fenv_t __env; - int __mxcsr; - - if (__excepts == FE_ALL_EXCEPT) { - __fnclex(); - } else { - __fnstenv(&__env); - __env.__status &= ~__excepts; - __fldenv(__env); - } - if (__HAS_SSE()) { - __stmxcsr(&__mxcsr); - __mxcsr &= ~__excepts; - __ldmxcsr(__mxcsr); - } - return (0); -} - -static __inline int -fegetexceptflag(fexcept_t *__flagp, int __excepts) -{ - int __mxcsr; - short __status; - - __fnstsw(&__status); - if (__HAS_SSE()) - __stmxcsr(&__mxcsr); - else - __mxcsr = 0; - *__flagp = (__mxcsr | __status) & __excepts; - return (0); -} - -int fesetexceptflag(const fexcept_t *__flagp, int __excepts); -int feraiseexcept(int __excepts); - -static __inline int -fetestexcept(int __excepts) -{ - int __mxcsr; - short __status; - - __fnstsw(&__status); - if (__HAS_SSE()) - __stmxcsr(&__mxcsr); - else - __mxcsr = 0; - return ((__status | __mxcsr) & __excepts); -} - -static __inline int -fegetround(void) -{ - int __control; - - /* - * We assume that the x87 and the SSE unit agree on the - * rounding mode. Reading the control word on the x87 turns - * out to be about 5 times faster than reading it on the SSE - * unit on an Opteron 244. - */ - __fnstcw(&__control); - return (__control & _ROUND_MASK); -} - -static __inline int -fesetround(int __round) -{ - int __mxcsr, __control; - - if (__round & ~_ROUND_MASK) - return (-1); - - __fnstcw(&__control); - __control &= ~_ROUND_MASK; - __control |= __round; - __fldcw(__control); - - if (__HAS_SSE()) { - __stmxcsr(&__mxcsr); - __mxcsr &= ~(_ROUND_MASK << _SSE_ROUND_SHIFT); - __mxcsr |= __round << _SSE_ROUND_SHIFT; - __ldmxcsr(__mxcsr); - } - - return (0); -} +/* C99 rounding control functions */ +int fegetround(void); +int fesetround(int round); +/* C99 floating-point environment functions */ int fegetenv(fenv_t *__envp); int feholdexcept(fenv_t *__envp); - -static __inline int -fesetenv(const fenv_t *__envp) -{ - fenv_t __env = *__envp; - int __mxcsr; - - __mxcsr = __get_mxcsr(__env); - __set_mxcsr(__env, 0xffffffff); - __fldenv(__env); - if (__HAS_SSE()) - __ldmxcsr(__mxcsr); - return (0); -} - +int fesetenv(const fenv_t *envp); int feupdateenv(const fenv_t *__envp); #if __BSD_VISIBLE - +/* Additional support functions to set/query floating point traps */ int feenableexcept(int __mask); int fedisableexcept(int __mask); - -static __inline int -fegetexcept(void) -{ - int __control; - - /* - * We assume that the masks for the x87 and the SSE unit are - * the same. - */ - __fnstcw(&__control); - return (~__control & FE_ALL_EXCEPT); -} +int fegetexcept(void); #endif /* __BSD_VISIBLE */ diff --git a/ndk/platforms/android-9/arch-x86/symbols/libm.so.functions.txt b/ndk/platforms/android-9/arch-x86/symbols/libm.so.functions.txt index 2899b4235..53affc074 100644 --- a/ndk/platforms/android-9/arch-x86/symbols/libm.so.functions.txt +++ b/ndk/platforms/android-9/arch-x86/symbols/libm.so.functions.txt @@ -1,6 +1,4 @@ __exp__D -__fedisableexcept -__feenableexcept __fpclassifyd __fpclassifyf __fpclassifyl @@ -27,7 +25,7 @@ __log__D __signbit __signbitf __signbitl -__test_sse +_scan_nan acos acosf acosh @@ -72,10 +70,19 @@ fabsl fdim fdimf fdiml +feclearexcept +fedisableexcept +feenableexcept fegetenv +fegetexcept +fegetexceptflag +fegetround feholdexcept feraiseexcept +fesetenv fesetexceptflag +fesetround +fetestexcept feupdateenv finite finitef @@ -137,6 +144,8 @@ lroundf lroundl modf modff +nan +nanf nearbyint nearbyintf nextafter @@ -174,6 +183,7 @@ tanf tanh tanhf tgamma +tgammaf trunc truncf truncl