(root)/
m4-1.4.19/
tests/
test-printf-frexpl.c
       1  /* Test of splitting a 'long double' into fraction and mantissa.
       2     Copyright (C) 2007-2021 Free Software Foundation, Inc.
       3  
       4     This program is free software: you can redistribute it and/or modify
       5     it under the terms of the GNU General Public License as published by
       6     the Free Software Foundation; either version 3 of the License, or
       7     (at your option) any later version.
       8  
       9     This program is distributed in the hope that it will be useful,
      10     but WITHOUT ANY WARRANTY; without even the implied warranty of
      11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      12     GNU General Public License for more details.
      13  
      14     You should have received a copy of the GNU General Public License
      15     along with this program.  If not, see <https://www.gnu.org/licenses/>.  */
      16  
      17  /* Written by Bruno Haible <bruno@clisp.org>, 2007.  */
      18  
      19  #include <config.h>
      20  
      21  #include "printf-frexpl.h"
      22  
      23  #include <float.h>
      24  
      25  #include "fpucw.h"
      26  #include "macros.h"
      27  
      28  /* On MIPS IRIX machines, LDBL_MIN_EXP is -1021, but the smallest reliable
      29     exponent for 'long double' is -964.  Similarly, on PowerPC machines,
      30     LDBL_MIN_EXP is -1021, but the smallest reliable exponent for 'long double'
      31     is -968.  For exponents below that, the precision may be truncated to the
      32     precision used for 'double'.  */
      33  #ifdef __sgi
      34  # define MIN_NORMAL_EXP (LDBL_MIN_EXP + 57)
      35  # define MIN_SUBNORMAL_EXP MIN_NORMAL_EXP
      36  #elif defined __ppc || defined __ppc__ || defined __powerpc || defined __powerpc__
      37  # define MIN_NORMAL_EXP (LDBL_MIN_EXP + 53)
      38  # define MIN_SUBNORMAL_EXP MIN_NORMAL_EXP
      39  #else
      40  # define MIN_NORMAL_EXP LDBL_MIN_EXP
      41  # define MIN_SUBNORMAL_EXP (LDBL_MIN_EXP - 100)
      42  #endif
      43  
      44  static long double
      45  my_ldexp (long double x, int d)
      46  {
      47    for (; d > 0; d--)
      48      x *= 2.0L;
      49    for (; d < 0; d++)
      50      x *= 0.5L;
      51    return x;
      52  }
      53  
      54  int
      55  main ()
      56  {
      57    int i;
      58    long double x;
      59    DECL_LONG_DOUBLE_ROUNDING
      60  
      61    BEGIN_LONG_DOUBLE_ROUNDING ();
      62  
      63    for (i = 1, x = 1.0L; i <= LDBL_MAX_EXP; i++, x *= 2.0L)
      64      {
      65        int exp = -9999;
      66        long double mantissa = printf_frexpl (x, &exp);
      67        ASSERT (exp == i - 1);
      68        ASSERT (mantissa == 1.0L);
      69      }
      70    for (i = 1, x = 1.0L; i >= MIN_NORMAL_EXP; i--, x *= 0.5L)
      71      {
      72        int exp = -9999;
      73        long double mantissa = printf_frexpl (x, &exp);
      74        ASSERT (exp == i - 1);
      75        ASSERT (mantissa == 1.0L);
      76      }
      77    for (; i >= MIN_SUBNORMAL_EXP && x > 0.0L; i--, x *= 0.5L)
      78      {
      79        int exp = -9999;
      80        long double mantissa = printf_frexpl (x, &exp);
      81        ASSERT (exp == LDBL_MIN_EXP - 1);
      82        ASSERT (mantissa == my_ldexp (1.0L, i - LDBL_MIN_EXP));
      83      }
      84  
      85    for (i = 1, x = 1.01L; i <= LDBL_MAX_EXP; i++, x *= 2.0L)
      86      {
      87        int exp = -9999;
      88        long double mantissa = printf_frexpl (x, &exp);
      89        ASSERT (exp == i - 1);
      90        ASSERT (mantissa == 1.01L);
      91      }
      92    for (i = 1, x = 1.01L; i >= MIN_NORMAL_EXP; i--, x *= 0.5L)
      93      {
      94        int exp = -9999;
      95        long double mantissa = printf_frexpl (x, &exp);
      96        ASSERT (exp == i - 1);
      97        ASSERT (mantissa == 1.01L);
      98      }
      99    for (; i >= MIN_SUBNORMAL_EXP && x > 0.0L; i--, x *= 0.5L)
     100      {
     101        int exp = -9999;
     102        long double mantissa = printf_frexpl (x, &exp);
     103        ASSERT (exp == LDBL_MIN_EXP - 1);
     104        ASSERT (mantissa >= my_ldexp (1.0L, i - LDBL_MIN_EXP));
     105        ASSERT (mantissa <= my_ldexp (2.0L, i - LDBL_MIN_EXP));
     106        ASSERT (mantissa == my_ldexp (x, - exp));
     107      }
     108  
     109    for (i = 1, x = 1.73205L; i <= LDBL_MAX_EXP; i++, x *= 2.0L)
     110      {
     111        int exp = -9999;
     112        long double mantissa = printf_frexpl (x, &exp);
     113        ASSERT (exp == i - 1);
     114        ASSERT (mantissa == 1.73205L);
     115      }
     116    for (i = 1, x = 1.73205L; i >= MIN_NORMAL_EXP; i--, x *= 0.5L)
     117      {
     118        int exp = -9999;
     119        long double mantissa = printf_frexpl (x, &exp);
     120        ASSERT (exp == i - 1);
     121        ASSERT (mantissa == 1.73205L);
     122      }
     123    for (; i >= MIN_SUBNORMAL_EXP && x > 0.0L; i--, x *= 0.5L)
     124      {
     125        int exp = -9999;
     126        long double mantissa = printf_frexpl (x, &exp);
     127        ASSERT (exp == LDBL_MIN_EXP - 1);
     128        ASSERT (mantissa >= my_ldexp (1.0L, i - LDBL_MIN_EXP));
     129        ASSERT (mantissa <= my_ldexp (2.0L, i - LDBL_MIN_EXP));
     130        ASSERT (mantissa == my_ldexp (x, - exp));
     131      }
     132  
     133    return 0;
     134  }