1 /* Test file for mpfr_exp10m1.
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_exp10m1
26 #define TEST_RANDOM_EMIN -36
27 #define TEST_RANDOM_EMAX 36
28 #include "tgeneric.c"
29
30 static void
special(void)31 special (void)
32 {
33 mpfr_t x, y;
34 int i;
35
36 mpfr_init2 (x, 2);
37 mpfr_init2 (y, 2);
38
39 mpfr_set_nan (x);
40 mpfr_exp10m1 (y, x, MPFR_RNDN);
41 if (!mpfr_nan_p (y))
42 {
43 printf ("Error for exp10m1(NaN)\n");
44 exit (1);
45 }
46
47 mpfr_set_inf (x, 1);
48 mpfr_exp10m1 (y, x, MPFR_RNDN);
49 if (!mpfr_inf_p (y) || mpfr_sgn (y) < 0)
50 {
51 printf ("Error for exp10m1(+Inf)\n");
52 exit (1);
53 }
54
55 mpfr_set_inf (x, -1);
56 mpfr_exp10m1 (y, x, MPFR_RNDN);
57 if (mpfr_cmp_si (y, -1) != 0)
58 {
59 printf ("Error for exp10m1(-Inf)\n");
60 exit (1);
61 }
62
63 mpfr_set_ui (x, 0, MPFR_RNDN);
64 mpfr_exp10m1 (y, x, MPFR_RNDN);
65 if (MPFR_NOTZERO (y) || MPFR_IS_NEG (y))
66 {
67 printf ("Error for exp10m1(+0)\n");
68 exit (1);
69 }
70
71 mpfr_neg (x, x, MPFR_RNDN);
72 mpfr_exp10m1 (y, x, MPFR_RNDN);
73 if (MPFR_NOTZERO (y) || MPFR_IS_POS (y))
74 {
75 printf ("Error for exp10m1(-0)\n");
76 exit (1);
77 }
78
79 /* Check overflow of exp10m1(x) */
80 mpfr_clear_flags ();
81 mpfr_set_str_binary (x, "1.1E1000000000");
82 i = mpfr_exp10m1 (x, x, MPFR_RNDN);
83 MPFR_ASSERTN (MPFR_IS_INF (x) && MPFR_IS_POS (x));
84 MPFR_ASSERTN (mpfr_overflow_p ());
85 MPFR_ASSERTN (i > 0);
86
87 mpfr_clear_flags ();
88 mpfr_set_str_binary (x, "1.1E1000000000");
89 i = mpfr_exp10m1 (x, x, MPFR_RNDU);
90 MPFR_ASSERTN (MPFR_IS_INF (x) && MPFR_IS_POS (x));
91 MPFR_ASSERTN (mpfr_overflow_p ());
92 MPFR_ASSERTN (i > 0);
93
94 mpfr_clear_flags ();
95 mpfr_set_str_binary (x, "1.1E1000000000");
96 i = mpfr_exp10m1 (x, x, MPFR_RNDD);
97 MPFR_ASSERTN (!MPFR_IS_INF (x) && MPFR_IS_POS (x));
98 MPFR_ASSERTN (mpfr_overflow_p ());
99 MPFR_ASSERTN (i < 0);
100
101 /* Check internal underflow of exp10m1 (x) */
102 mpfr_set_prec (x, 2);
103 mpfr_clear_flags ();
104 mpfr_set_str_binary (x, "-1.1E1000000000");
105 i = mpfr_exp10m1 (x, x, MPFR_RNDN);
106 MPFR_ASSERTN (mpfr_cmp_si (x, -1) == 0);
107 MPFR_ASSERTN (!mpfr_overflow_p () && !mpfr_underflow_p ());
108 MPFR_ASSERTN (i < 0);
109
110 mpfr_set_str_binary (x, "-1.1E1000000000");
111 i = mpfr_exp10m1 (x, x, MPFR_RNDD);
112 MPFR_ASSERTN (mpfr_cmp_si (x, -1) == 0);
113 MPFR_ASSERTN (!mpfr_overflow_p () && !mpfr_underflow_p ());
114 MPFR_ASSERTN (i < 0);
115
116 mpfr_set_str_binary (x, "-1.1E1000000000");
117 i = mpfr_exp10m1 (x, x, MPFR_RNDZ);
118 MPFR_ASSERTN (mpfr_cmp_str (x, "-0.11", 2, MPFR_RNDN) == 0);
119 MPFR_ASSERTN (!mpfr_overflow_p () && !mpfr_underflow_p ());
120 MPFR_ASSERTN (i > 0);
121
122 mpfr_set_str_binary (x, "-1.1E1000000000");
123 i = mpfr_exp10m1 (x, x, MPFR_RNDU);
124 MPFR_ASSERTN (mpfr_cmp_str (x, "-0.11", 2, MPFR_RNDN) == 0);
125 MPFR_ASSERTN (!mpfr_overflow_p () && !mpfr_underflow_p ());
126 MPFR_ASSERTN (i > 0);
127
128 /* hard-coded test */
129 mpfr_set_prec (x, 32);
130 mpfr_set_prec (y, 32);
131 mpfr_set_ui_2exp (x, 1686629713UL, -29, MPFR_RNDN); /* approximates Pi */
132 i = mpfr_exp10m1 (y, x, MPFR_RNDN);
133 MPFR_ASSERTN (mpfr_cmp_ui_2exp (y, 2903414105UL, -21) == 0);
134 MPFR_ASSERTN (i < 0);
135
136 mpfr_clear (x);
137 mpfr_clear (y);
138 }
139
140 /* test integer x, 1 <= x <= 64, where 10^x-1 is exact */
141 static void
test_exact(void)142 test_exact (void)
143 {
144 long k;
145 mpfr_t x, y, z;
146 mpz_t n;
147 mpfr_prec_t p;
148 int i, j, r;
149
150 mpfr_init2 (x, 6); /* enough to represent exactly all integers <= 64 */
151 mpfr_init2 (y, MPFR_PREC_MIN);
152 mpfr_init2 (z, MPFR_PREC_MIN);
153 mpz_init_set_ui (n, 9);
154 for (k = 1; k <= 64; k++)
155 {
156 /* invariant: n = 10^k-1 */
157 /* 10^64 needs 213 bits */
158 for (p = MPFR_PREC_MIN; p <= 213; p++)
159 {
160 mpfr_set_prec (y, p);
161 mpfr_set_prec (z, p);
162 mpfr_set_si (x, k, MPFR_RNDN);
163 /* for RNDF, result may differ */
164 RND_LOOP_NO_RNDF(r)
165 {
166 i = mpfr_exp10m1 (y, x, (mpfr_rnd_t) r);
167 j = mpfr_set_z (z, n, (mpfr_rnd_t) r);
168 if (!mpfr_equal_p (y, z))
169 {
170 printf ("Error for mpfr_exp10m1, x=%ld, rnd=%s\n", k,
171 mpfr_print_rnd_mode ((mpfr_rnd_t) r));
172 printf ("expected "); mpfr_dump (z);
173 printf ("got "); mpfr_dump (y);
174 exit (1);
175 }
176 if ((i == 0 && j != 0) || (i != 0 && j == 0) || (i * j < 0))
177 {
178 printf ("Bar ternary value for mpfr_exp10m1, x=%ld, rnd=%s\n",
179 k, mpfr_print_rnd_mode ((mpfr_rnd_t) r));
180 printf ("expected %d\n", j);
181 printf ("got %d\n", i);
182 exit (1);
183 }
184 }
185 }
186 mpz_mul_ui (n, n, 10);
187 mpz_add_ui (n, n, 9);
188 }
189 mpfr_clear (x);
190 mpfr_clear (y);
191 mpfr_clear (z);
192 mpz_clear (n);
193 }
194
195 int
main(int argc,char * argv[])196 main (int argc, char *argv[])
197 {
198 tests_start_mpfr ();
199
200 special ();
201
202 test_exact ();
203
204 test_generic (MPFR_PREC_MIN, 100, 100);
205
206 tests_end_mpfr ();
207 return 0;
208 }
209