Module: wine Branch: master Commit: bb9f97c4d13151d05ebb6aa24c3e0f6b8cab7bb3 URL: https://source.winehq.org/git/wine.git/?a=commit;h=bb9f97c4d13151d05ebb6aa24...
Author: Piotr Caban piotr@codeweavers.com Date: Sat May 29 19:13:55 2021 +0200
msvcrt: Import tanhf implementation from musl.
Signed-off-by: Piotr Caban piotr@codeweavers.com Signed-off-by: Alexandre Julliard julliard@winehq.org
---
dlls/msvcrt/math.c | 40 +++++++++++++++++++++++++++++++++++++--- dlls/msvcrt/unixlib.c | 9 --------- dlls/msvcrt/unixlib.h | 1 - 3 files changed, 37 insertions(+), 13 deletions(-)
diff --git a/dlls/msvcrt/math.c b/dlls/msvcrt/math.c index 6d60a6fa086..0bace98cd7d 100644 --- a/dlls/msvcrt/math.c +++ b/dlls/msvcrt/math.c @@ -1512,9 +1512,43 @@ float CDECL tanf( float x ) */ float CDECL tanhf( float x ) { - float ret = unix_funcs->tanhf(x); - if (!isfinite(x)) return math_error(_DOMAIN, "tanhf", x, 0, ret); - return ret; + UINT32 ui = *(UINT32*)&x; + int sign; + float t; + + /* x = |x| */ + sign = ui >> 31; + ui &= 0x7fffffff; + x = *(float*)&ui; + + if (ui > 0x3f0c9f54) { + /* |x| > log(3)/2 ~= 0.5493 or nan */ + if (ui > 0x41200000) { +#if _MSVCR_VER < 140 + if (isnan(x)) + return math_error(_DOMAIN, "tanhf", x, 0, x); +#endif + /* |x| > 10 */ + fp_barrierf(x + 0x1p120f); + t = 1 + 0 / x; + } else { + t = __expm1f(2 * x); + t = 1 - 2 / (t + 2); + } + } else if (ui > 0x3e82c578) { + /* |x| > log(5/3)/2 ~= 0.2554 */ + t = __expm1f(2 * x); + t = t / (t + 2); + } else if (ui >= 0x00800000) { + /* |x| >= 0x1p-126 */ + t = __expm1f(-2 * x); + t = -t / (t + 2); + } else { + /* |x| is subnormal */ + fp_barrierf(x * x); + t = x; + } + return sign ? -t : t; }
/********************************************************************* diff --git a/dlls/msvcrt/unixlib.c b/dlls/msvcrt/unixlib.c index ce4a3eed094..d92203c1ab7 100644 --- a/dlls/msvcrt/unixlib.c +++ b/dlls/msvcrt/unixlib.c @@ -268,14 +268,6 @@ static float CDECL unix_powf( float x, float y ) return powf( x, y ); }
-/********************************************************************* - * tanhf - */ -static float CDECL unix_tanhf( float x ) -{ - return tanhf( x ); -} - /********************************************************************* * tgamma */ @@ -327,7 +319,6 @@ static const struct unix_funcs funcs = unix_log2f, unix_pow, unix_powf, - unix_tanhf, unix_tgamma, unix_tgammaf, }; diff --git a/dlls/msvcrt/unixlib.h b/dlls/msvcrt/unixlib.h index a95aae74dea..a01ce285106 100644 --- a/dlls/msvcrt/unixlib.h +++ b/dlls/msvcrt/unixlib.h @@ -46,7 +46,6 @@ struct unix_funcs float (CDECL *log2f)(float x); double (CDECL *pow)(double x, double y); float (CDECL *powf)(float x, float y); - float (CDECL *tanhf)(float x); double (CDECL *tgamma)(double x); float (CDECL *tgammaf)(float x); };