(root)/
mpfr-4.2.1/
tests/
ttanh.c
       1  /* Test file for mpfr_tanh.
       2  
       3  Copyright 2001-2023 Free Software Foundation, Inc.
       4  Contributed by the AriC and Caramba projects, INRIA.
       5  
       6  This file is part of the GNU MPFR Library.
       7  
       8  The GNU MPFR Library is free software; you can redistribute it and/or modify
       9  it under the terms of the GNU Lesser General Public License as published by
      10  the Free Software Foundation; either version 3 of the License, or (at your
      11  option) any later version.
      12  
      13  The GNU MPFR Library is distributed in the hope that it will be useful, but
      14  WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
      15  or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public
      16  License for more details.
      17  
      18  You should have received a copy of the GNU Lesser General Public License
      19  along with the GNU MPFR Library; see the file COPYING.LESSER.  If not, see
      20  https://www.gnu.org/licenses/ or write to the Free Software Foundation, Inc.,
      21  51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. */
      22  
      23  #include "mpfr-test.h"
      24  
      25  #define TEST_FUNCTION mpfr_tanh
      26  #define TEST_RANDOM_EMIN -36
      27  #define TEST_RANDOM_EMAX 36
      28  #include "tgeneric.c"
      29  
      30  static void
      31  special (void)
      32  {
      33    mpfr_t x;
      34  
      35    mpfr_init (x);
      36  
      37    mpfr_set_nan (x);
      38    mpfr_tanh (x, x, MPFR_RNDN);
      39    MPFR_ASSERTN(mpfr_nan_p (x));
      40  
      41    mpfr_set_inf (x, 1);
      42    mpfr_tanh (x, x, MPFR_RNDN);
      43    MPFR_ASSERTN(mpfr_cmp_ui (x, 1) == 0);
      44  
      45    mpfr_set_inf (x, -1);
      46    mpfr_tanh (x, x, MPFR_RNDN);
      47    MPFR_ASSERTN(mpfr_cmp_si (x, -1) == 0);
      48  
      49    mpfr_set_prec (x, 10);
      50    mpfr_set_str_binary (x, "-0.1001011001");
      51    mpfr_tanh (x, x, MPFR_RNDN);
      52    MPFR_ASSERTN(mpfr_cmp_si_2exp (x, -135, -8) == 0);
      53  
      54    mpfr_clear (x);
      55  }
      56  
      57  static void
      58  special_overflow (void)
      59  {
      60    mpfr_t x, y;
      61    int i;
      62    mpfr_exp_t emin, emax;
      63  
      64    emin = mpfr_get_emin ();
      65    emax = mpfr_get_emax ();
      66  
      67    mpfr_clear_overflow ();
      68    set_emin (-125);
      69    set_emax (128);
      70    mpfr_init2 (x, 24);
      71    mpfr_init2 (y, 24);
      72  
      73    mpfr_set_str_binary (x, "0.101100100000000000110100E7");
      74    i = mpfr_tanh (y, x, MPFR_RNDN);
      75    if (mpfr_cmp_ui (y, 1) || i != 1)
      76      {
      77        printf("Overflow error (1). i=%d\ny=", i);
      78        mpfr_dump (y);
      79        exit (1);
      80      }
      81    MPFR_ASSERTN (!mpfr_overflow_p ());
      82  
      83    i = mpfr_tanh (y, x, MPFR_RNDZ);
      84    if (mpfr_cmp_str (y, "0.111111111111111111111111E0", 2, MPFR_RNDN)
      85        || i != -1)
      86      {
      87        printf("Overflow error (2).i=%d\ny=", i);
      88        mpfr_dump (y);
      89        exit (1);
      90      }
      91    MPFR_ASSERTN (!mpfr_overflow_p ());
      92  
      93    set_emin (emin);
      94    set_emax (emax);
      95  
      96    mpfr_set_str_binary (x, "0.1E1000000000");
      97    i = mpfr_tanh (y, x, MPFR_RNDN);
      98    if (mpfr_cmp_ui (y, 1) || i != 1)
      99      {
     100        printf("Overflow error (3). i=%d\ny=", i);
     101        mpfr_dump (y);
     102        exit (1);
     103      }
     104    MPFR_ASSERTN (!mpfr_overflow_p ());
     105    mpfr_set_str_binary (x, "-0.1E1000000000");
     106    i = mpfr_tanh (y, x, MPFR_RNDU);
     107    if (mpfr_cmp_str (y, "-0.111111111111111111111111E0", 2, MPFR_RNDN)
     108        || i != 1)
     109      {
     110        printf("Overflow error (4). i=%d\ny=", i);
     111        mpfr_dump (y);
     112        exit (1);
     113      }
     114  
     115    mpfr_clear (y);
     116    mpfr_clear (x);
     117  }
     118  
     119  /* This test was generated from bad_cases, with input y=-7.778@-1 = -3823/8192.
     120     For the x value below, we have atanh(y) < x, thus since tanh() is increasing,
     121     y < tanh(x), and thus tanh(x) rounded toward zero should give -3822/8192. */
     122  static void
     123  bug20171218 (void)
     124  {
     125    mpfr_t x, y, z;
     126    mpfr_init2 (x, 813);
     127    mpfr_init2 (y, 12);
     128    mpfr_init2 (z, 12);
     129    mpfr_set_str (x, "-8.17cd20bfc17ae00935dc3abad8e17ab43d3ef7740c320798eefb93191f4a62dba9a2daa5efb6eace21130abd87e3ee2eadd2ad8ddae883d2f2db5dee1ac7ce3c59d16eca09e2ca3f21dc2a0386c037a0d3972e62d5b6e82446032020705553c566b1df24f40@-1", 16, MPFR_RNDN);
     130    mpfr_tanh (y, x, MPFR_RNDZ);
     131    mpfr_set_str (z, "-7.770@-1", 16, MPFR_RNDN);
     132    MPFR_ASSERTN(mpfr_equal_p (y, z));
     133    mpfr_clear (x);
     134    mpfr_clear (y);
     135    mpfr_clear (z);
     136  }
     137  
     138  int
     139  main (int argc, char *argv[])
     140  {
     141    tests_start_mpfr ();
     142  
     143    bug20171218 ();
     144    special_overflow ();
     145    special ();
     146  
     147    test_generic (MPFR_PREC_MIN, 100, 100);
     148  
     149    data_check ("data/tanh", mpfr_tanh, "mpfr_tanh");
     150    bad_cases (mpfr_tanh, mpfr_atanh, "mpfr_tanh", 256, -128, 0,
     151               4, 128, 800, 100);
     152  
     153    tests_end_mpfr ();
     154    return 0;
     155  }