From 744dddb3fdf0a93c8efb355903f0b3b7d40755b8 Mon Sep 17 00:00:00 2001 From: Lv Meng Date: Mon, 23 Dec 2013 12:09:13 +0800 Subject: [PATCH] GBE: improve precision of atanh Signed-off-by: Lv Meng Tested-by: "Song, Ruiling" --- backend/src/ocl_stdlib.tmpl.h | 20 +++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) diff --git a/backend/src/ocl_stdlib.tmpl.h b/backend/src/ocl_stdlib.tmpl.h index c2373e1..03044c4 100755 --- a/backend/src/ocl_stdlib.tmpl.h +++ b/backend/src/ocl_stdlib.tmpl.h @@ -1806,9 +1806,6 @@ INLINE_OVERLOADABLE float __gen_ocl_internal_atan(float x) { INLINE_OVERLOADABLE float __gen_ocl_internal_atanpi(float x) { return __gen_ocl_internal_atan(x) / M_PI_F; } -INLINE_OVERLOADABLE float __gen_ocl_internal_atanh(float x) { - return 0.5f * native_sqrt((1 + x) / (1 - x)); -} INLINE_OVERLOADABLE float __gen_ocl_internal_erf(float x) { return M_2_SQRTPI_F * (x - __gen_ocl_pow(x, 3) / 3 + __gen_ocl_pow(x, 5) / 10 - __gen_ocl_pow(x, 7) / 42 + __gen_ocl_pow(x, 9) / 216); } @@ -2365,6 +2362,23 @@ INLINE_OVERLOADABLE float __gen_ocl_internal_ldexp(float x, int n) { return x; } +INLINE_OVERLOADABLE float __gen_ocl_internal_atanh(float x) { + //return 0.5f * native_sqrt((1 + x) / (1 - x)); + float xa = __gen_ocl_fabs (x); + float t; + if (isless (xa, 0.5f)){ + if (xa < 0x1.0p-28f) return x; + t = xa + xa; + t = 0.5f * log1p (t + t * xa / (1.0f - xa)); + } else if (isless (xa, 1.0f)){ + t = 0.5f * log1p ((xa + xa) / (1.0f - xa)); + } else{ + if (isgreater (xa, 1.0f)) return (x - x) / (x - x); + return x / 0.0f; + } + return __gen_ocl_internal_copysign(t, x); +} + // TODO use llvm intrinsics definitions #define cos native_cos #define cospi __gen_ocl_internal_cospi -- 2.7.4