On Fri, Jul 10, 2026 at 1:30 PM Jonathan Wakely <[email protected]> wrote:

> The result should be zero at infinity.
>
> libstdc++-v3/ChangeLog:
>
>         PR libstdc++/119143
>         * include/tr1/bessel_function.tcc (__cyl_bessel_jn_asymp):
>         Return zero for infinite x.
>         * testsuite/special_functions/08_cyl_bessel_j/check_inf.cc: New
>         test.
>         * testsuite/special_functions/10_cyl_neumann/check_inf.cc: New
>         test.
>         *
> testsuite/tr1/5_numerical_facilities/special_functions/11_cyl_neumann/check_inf.cc:
>         New test.
> ---
>
> Tested x86_64-linux.
>
>  libstdc++-v3/include/tr1/bessel_function.tcc  |  6 +++
>  .../08_cyl_bessel_j/check_inf.cc              | 38 +++++++++++++++++++
>  .../10_cyl_neumann/check_inf.cc               | 38 +++++++++++++++++++
>  .../11_cyl_neumann/check_inf.cc               | 37 ++++++++++++++++++
>  4 files changed, 119 insertions(+)
>  create mode 100644
> libstdc++-v3/testsuite/special_functions/08_cyl_bessel_j/check_inf.cc
>  create mode 100644
> libstdc++-v3/testsuite/special_functions/10_cyl_neumann/check_inf.cc
>  create mode 100644
> libstdc++-v3/testsuite/tr1/5_numerical_facilities/special_functions/11_cyl_neumann/check_inf.cc
>
> diff --git a/libstdc++-v3/include/tr1/bessel_function.tcc
> b/libstdc++-v3/include/tr1/bessel_function.tcc
> index 7e06d98ce3c6..bba792bd89d3 100644
> --- a/libstdc++-v3/include/tr1/bessel_function.tcc
> +++ b/libstdc++-v3/include/tr1/bessel_function.tcc
> @@ -362,6 +362,12 @@ namespace tr1
>      void
>      __cyl_bessel_jn_asymp(_Tp __nu, _Tp __x, _Tp & __Jnu, _Tp & __Nnu)
>      {
> +      if (__builtin_expect(__builtin_isinf(__x), 0))
> +       {
> +         __Jnu = __Nnu = _Tp(0);
> +         return;
> +       }
> +
>        const _Tp __mu = _Tp(4) * __nu * __nu;
>        const _Tp __8x = _Tp(8) * __x;
>
> diff --git
> a/libstdc++-v3/testsuite/special_functions/08_cyl_bessel_j/check_inf.cc
> b/libstdc++-v3/testsuite/special_functions/08_cyl_bessel_j/check_inf.cc
> new file mode 100644
> index 000000000000..50c1f3098297
> --- /dev/null
> +++ b/libstdc++-v3/testsuite/special_functions/08_cyl_bessel_j/check_inf.cc
> @@ -0,0 +1,38 @@
> +// { dg-do run { target c++11 } }
> +// { dg-require-c-std "" }
> +// { dg-options "-D__STDCPP_WANT_MATH_SPEC_FUNCS__" }
> +// { dg-add-options ieee }
> +
> +// ISO/IEC IS 29124 8.1.8 cyl_bessel_j
> +// J_nu(+inf) == 0 for all finite nu >= 0
> +
> +#include <cmath>
> +#include <limits>
> +#include <testsuite_hooks.h>
> +
> +void
> +test01()
>
I would template this on RealType and instantiate it for float and double.
long double instead, but this is also OK.

> +{
> +  float xinf_f = std::numeric_limits<float>::infinity();
> +  double xinf_d = std::numeric_limits<double>::infinity();
> +  long double xinf_l = std::numeric_limits<long double>::infinity();
> +
> +  VERIFY(std::cyl_bessel_j(0.0F, xinf_f) == 0.0F);
> +  VERIFY(std::cyl_bessel_jf(0.0F, xinf_f) == 0.0F);
> +  VERIFY(std::cyl_bessel_j(0.0, xinf_d) == 0.0);
> +  VERIFY(std::cyl_bessel_j(0.0L, xinf_l) == 0.0L);
> +  VERIFY(std::cyl_bessel_jl(0.0L, xinf_l) == 0.0L);
> +
> +  VERIFY(std::cyl_bessel_j(1.0F, xinf_f) == 0.0F);
> +  VERIFY(std::cyl_bessel_j(1.0, xinf_d) == 0.0);
> +  VERIFY(std::cyl_bessel_j(1.0L, xinf_l) == 0.0L);
> +
> +  VERIFY(std::cyl_bessel_j(2.5, xinf_d) == 0.0);
> +}
> +
> +int
> +main()
> +{
> +  test01();
> +  return 0;
> +}
> diff --git
> a/libstdc++-v3/testsuite/special_functions/10_cyl_neumann/check_inf.cc
> b/libstdc++-v3/testsuite/special_functions/10_cyl_neumann/check_inf.cc
> new file mode 100644
> index 000000000000..716dc79b1aab
> --- /dev/null
> +++ b/libstdc++-v3/testsuite/special_functions/10_cyl_neumann/check_inf.cc
> @@ -0,0 +1,38 @@
> +// { dg-do run { target c++11 } }
> +// { dg-require-c-std "" }
> +// { dg-options "-D__STDCPP_WANT_MATH_SPEC_FUNCS__" }
> +// { dg-add-options ieee }
> +
> +// ISO/IEC IS 29124 8.1.10 cyl_neumann
> +// N_nu(+inf) == 0 for all finite nu >= 0
> +
> +#include <cmath>
> +#include <limits>
> +#include <testsuite_hooks.h>
> +
> +void
> +test01()
> +{
> +  float xinf_f = std::numeric_limits<float>::infinity();
> +  double xinf_d = std::numeric_limits<double>::infinity();
> +  long double xinf_l = std::numeric_limits<long double>::infinity();
> +
> +  VERIFY(std::cyl_neumann(0.0F, xinf_f) == 0.0F);
> +  VERIFY(std::cyl_neumannf(0.0F, xinf_f) == 0.0F);
> +  VERIFY(std::cyl_neumann(0.0, xinf_d) == 0.0);
> +  VERIFY(std::cyl_neumann(0.0L, xinf_l) == 0.0L);
> +  VERIFY(std::cyl_neumannl(0.0L, xinf_l) == 0.0L);
> +
> +  VERIFY(std::cyl_neumann(1.0F, xinf_f) == 0.0F);
> +  VERIFY(std::cyl_neumann(1.0, xinf_d) == 0.0);
> +  VERIFY(std::cyl_neumann(1.0L, xinf_l) == 0.0L);
> +
> +  VERIFY(std::cyl_neumann(2.5, xinf_d) == 0.0);
> +}
> +
> +int
> +main()
> +{
> +  test01();
> +  return 0;
> +}
> diff --git
> a/libstdc++-v3/testsuite/tr1/5_numerical_facilities/special_functions/11_cyl_neumann/check_inf.cc
> b/libstdc++-v3/testsuite/tr1/5_numerical_facilities/special_functions/11_cyl_neumann/check_inf.cc
> new file mode 100644
> index 000000000000..9294cab64db0
> --- /dev/null
> +++
> b/libstdc++-v3/testsuite/tr1/5_numerical_facilities/special_functions/11_cyl_neumann/check_inf.cc
> @@ -0,0 +1,37 @@
> +// { dg-require-c-std "" }
> +// { dg-add-options ieee }
> +
> +// TR1 5.2.1.11 cyl_neumann
> +// N_nu(+inf) == 0 for all finite nu >= 0
> +
> +#include <tr1/cmath>
> +#include <limits>
> +#include <testsuite_hooks.h>
> +
> +void
> +test01()
> +{
> +  float xinf_f = std::numeric_limits<float>::infinity();
> +  double xinf_d = std::numeric_limits<double>::infinity();
> +  long double xinf_l = std::numeric_limits<long double>::infinity();
> +
> +  VERIFY(std::tr1::cyl_neumann(0.0F, xinf_f) == 0.0F);
> +  VERIFY(std::tr1::cyl_neumannf(0.0F, xinf_f) == 0.0F);
> +  VERIFY(std::tr1::cyl_neumann(0.0, xinf_d) == 0.0);
> +  VERIFY(std::tr1::cyl_neumann(0.0L, xinf_l) == 0.0L);
> +  VERIFY(std::tr1::cyl_neumannl(0.0L, xinf_l) == 0.0L);
> +
> +  VERIFY(std::tr1::cyl_neumann(1.0F, xinf_f) == 0.0F);
> +  VERIFY(std::tr1::cyl_neumann(1.0, xinf_d) == 0.0);
> +  VERIFY(std::tr1::cyl_neumann(1.0L, xinf_l) == 0.0L);
> +
> +  VERIFY(std::tr1::cyl_neumann(2.5, xinf_d) == 0.0);
> +}
> +
> +int
> +main()
> +{
> +  test01();
> +  return 0;
> +}
> +
> --
> 2.55.0
>
>

Reply via email to