[PATCH 0/4] math: Fix inaccurate sin/cos/tan for large arguments (BZ 34376)

Adhemerval Zanella <[email protected]>
Newsgroups gmane.comp.lib.glibc.alpha
Message-ID <[email protected]>
For arguments extremely close to a multiple of pi/2, the Payne-Hanek
range reducer __branred delivers the reduced argument with insufficient
precision (about 93 significant bits, while the reduced argument can be
as small as 2^-61), making sin/cos/tan wrong by up to ~143000 ulp.
This is a regression from commit 649095838b8 ("sin/cos slow paths:
remove slow paths from huge range reduction") and commit 476d692e8a8
("math: Remove slow paths in tan [BZ #15267]"), which removed the
multiple-precision fallbacks that used to hide the inaccuracy.

The fix restores the fdlibm e_rem_pio2.c (removed as unused by commit
ca3aac57efa), trimmed to its huge-argument path since the callers
reduce smaller arguments themselves, and uses __ieee754_rem_pio2,
whose kernel computes the reduction to full precision, instead of
__branred.

The first three patches restructure the sin/cos/tan benchmark inputs
into path-oriented workloads (fast/moderate/slow) so the impact on the
huge-argument path can be measured.  Results on x86_64-v3 (minimum of
5 runs, in cycles, lower is better):

                        master             fixed
                    rthruput latency  rthruput latency   rthruput
  sin workload-slow  211.66   222.24   318.99   351.20    +51%
  cos workload-slow  217.03   226.98   319.43   350.14    +47%
  tan workload-slow  241.18   248.52   346.93   368.89    +44%

The fast and moderate workloads are unchanged (within noise).  The
slowdown is confined to the huge-argument path (|x| > 1e8), which now
produces correctly reduced results.

Adhemerval Zanella (4):
  benchtests: Add path-oriented workloads to cos
  benchtests: Add path-oriented workloads to sin
  benchtests: Add path-oriented workloads to tan
  math: Fix inaccurate sin/cos/tan for large arguments (BZ 34376)

 benchtests/cos-inputs                | 5411 ++++++++++--------
 benchtests/sin-inputs                | 7917 ++++++++++----------------
 benchtests/tan-inputs                | 5450 +++++++-----------
 math/Makefile                        |    2 +-
 math/auto-libm-test-in               |   17 +
 math/auto-libm-test-out-cos          |  252 +
 math/auto-libm-test-out-sin          |  228 +
 math/auto-libm-test-out-tan          |  183 +
 sysdeps/generic/math_private.h       |    1 -
 sysdeps/ieee754/dbl-64/Makefile      |    2 -
 sysdeps/ieee754/dbl-64/branred.c     |  143 -
 sysdeps/ieee754/dbl-64/branred.h     |   79 -
 sysdeps/ieee754/dbl-64/e_rem_pio2.c  |   76 +
 sysdeps/ieee754/dbl-64/s_sin.c       |   14 +-
 sysdeps/ieee754/dbl-64/s_sincos.c    |   10 +-
 sysdeps/ieee754/dbl-64/s_tan.c       |   11 +-
 sysdeps/m68k/m680x0/fpu/e_rem_pio2.c |    1 +
 sysdeps/x86_64/fpu/Makefile          |   12 -
 18 files changed, 8796 insertions(+), 11013 deletions(-)
 delete mode 100644 sysdeps/ieee754/dbl-64/branred.c
 delete mode 100644 sysdeps/ieee754/dbl-64/branred.h
 create mode 100644 sysdeps/ieee754/dbl-64/e_rem_pio2.c
 create mode 100644 sysdeps/m68k/m680x0/fpu/e_rem_pio2.c

-- 
2.43.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.