1 /* Test file for mpfr_round_nearest_away.
2
3 Copyright 2012-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 static void
test_special(void)26 test_special (void)
27 {
28 mpfr_t x, y;
29 int inex;
30
31 mpfr_init2 (x, MPFR_PREC_MIN);
32 mpfr_init2 (y, MPFR_PREC_MIN);
33
34 mpfr_set_nan (x);
35 inex = mpfr_round_nearest_away (mpfr_sin, y, x);
36 if (inex != 0)
37 {
38 printf ("Wrong ternary value for sin(NaN)\n");
39 exit (1);
40 }
41 if (mpfr_nan_p (y) == 0)
42 {
43 printf ("Wrong output for sin(NaN)\n");
44 exit (1);
45 }
46
47 mpfr_set_inf (x, 1);
48 inex = mpfr_round_nearest_away (mpfr_exp, y, x);
49 if (inex != 0)
50 {
51 printf ("Wrong ternary value for exp(+Inf)\n");
52 printf ("expected 0, got %d\n", inex);
53 exit (1);
54 }
55 if (mpfr_inf_p (y) == 0 || mpfr_sgn (y) <= 0)
56 {
57 printf ("Wrong output for exp(+Inf)\n");
58 exit (1);
59 }
60
61 mpfr_set_inf (x, -1);
62 inex = mpfr_round_nearest_away (mpfr_cbrt, y, x);
63 if (inex != 0)
64 {
65 printf ("Wrong ternary value for cbrt(-Inf)\n");
66 exit (1);
67 }
68 if (mpfr_inf_p (y) == 0 || mpfr_sgn (y) >= 0)
69 {
70 printf ("Wrong output for cbrt(-Inf)\n");
71 exit (1);
72 }
73
74 mpfr_clear (x);
75 mpfr_clear (y);
76 }
77
78 static void
test_nonspecial(void)79 test_nonspecial (void)
80 {
81 mpfr_t x, y;
82 int inex;
83
84 mpfr_init2 (x, 10);
85 mpfr_init2 (y, 10);
86
87 /* case where the computation on n+1 bits ends with a '0' */
88 mpfr_set_ui (x, 2, MPFR_RNDN);
89 inex = mpfr_round_nearest_away (mpfr_sin, y, x);
90 if (inex >= 0)
91 {
92 printf ("Wrong ternary value for sin(2)\n");
93 exit (1);
94 }
95 if (mpfr_cmp_ui_2exp (y, 931, -10) != 0)
96 {
97 printf ("Wrong output for sin(2)\n");
98 exit (1);
99 }
100
101 /* case where the computation on n+1 bits ends with a '1' and is exact */
102 mpfr_set_ui (x, 37, MPFR_RNDN);
103 inex = mpfr_round_nearest_away (mpfr_sqr, y, x);
104 if (inex <= 0)
105 {
106 printf ("Wrong ternary value for sqr(37)\n");
107 exit (1);
108 }
109 if (mpfr_cmp_ui (y, 1370) != 0)
110 {
111 printf ("Wrong output for sqr(37)\n");
112 exit (1);
113 }
114
115 /* case where the computation on n+1 bits ends with a '1' but is inexact */
116 mpfr_set_ui (x, 91, MPFR_RNDN);
117 inex = mpfr_round_nearest_away (mpfr_sqr, y, x);
118 if (inex <= 0)
119 {
120 printf ("Wrong ternary value for sqr(91)\n");
121 exit (1);
122 }
123 if (mpfr_cmp_ui (y, 8288) != 0)
124 {
125 printf ("Wrong output for sqr(91)\n");
126 exit (1);
127 }
128
129 mpfr_set_ui (x, 131, MPFR_RNDN);
130 inex = mpfr_round_nearest_away (mpfr_sqr, y, x);
131 if (inex >= 0)
132 {
133 printf ("Wrong ternary value for sqr(131)\n");
134 exit (1);
135 }
136 if (mpfr_cmp_ui (y, 17152) != 0)
137 {
138 printf ("Wrong output for sqr(131)\n");
139 exit (1);
140 }
141
142 mpfr_clear (x);
143 mpfr_clear (y);
144 }
145
146 int
main(int argc,char * argv[])147 main (int argc, char *argv[])
148 {
149 mpfr_exp_t emin;
150
151 tests_start_mpfr ();
152
153 /* mpfr_round_nearest_away requires emin is not the smallest possible */
154 if ((emin = mpfr_get_emin ()) == mpfr_get_emin_min ())
155 set_emin (mpfr_get_emin_min () + 1);
156
157 test_special ();
158
159 test_nonspecial ();
160
161 set_emin (emin);
162
163 tests_end_mpfr ();
164 return 0;
165 }
166
167