1 /* Test file for mpfr_set_str. 2 3 Copyright 2004-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 /* The implicit \0 is useless, but we do not write num_to_text[62] otherwise 26 g++ complains. */ 27 static const char num_to_text36[] = "0123456789abcdefghijklmnopqrstuvwxyz"; 28 static const char num_to_text62[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ" 29 "abcdefghijklmnopqrstuvwxyz"; 30 31 static void 32 check_special (void) 33 { 34 mpfr_t x, y; 35 int i, res; 36 char *s; 37 38 mpfr_init (x); 39 mpfr_init (y); 40 41 /* Check dummy case */ 42 res = mpfr_strtofr (x, "1234567.89E1", NULL, 10, MPFR_RNDN); 43 mpfr_set_str (y, "1234567.89E1", 10, MPFR_RNDN); 44 if (mpfr_cmp (x, y)) 45 { 46 printf ("Results differ between strtofr and set_str.\n" 47 " set_str gives: "); 48 mpfr_dump (y); 49 printf (" strtofr gives: "); 50 mpfr_dump (x); 51 exit (1); 52 } 53 54 /* Check NAN */ 55 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 56 res = mpfr_strtofr (x, "NaN", &s, 10, MPFR_RNDN); 57 if (res != 0 || !mpfr_nan_p (x) || *s != 0) 58 { 59 printf ("Error for setting NAN (1)\n"); 60 exit (1); 61 } 62 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 63 res = mpfr_strtofr (x, "+NaN", &s, 10, MPFR_RNDN); 64 if (res != 0 || !mpfr_nan_p (x) || *s != 0) 65 { 66 printf ("Error for setting +NAN (1)\n"); 67 exit (1); 68 } 69 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 70 res = mpfr_strtofr (x, " -NaN", &s, 10, MPFR_RNDN); 71 if (res != 0 || !mpfr_nan_p (x) || *s != 0) 72 { 73 printf ("Error for setting -NAN (1)\n"); 74 exit (1); 75 } 76 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 77 res = mpfr_strtofr (x, "@nAn@xx", &s, 16, MPFR_RNDN); 78 if (res != 0 || !mpfr_nan_p (x) || strcmp(s, "xx") ) 79 { 80 printf ("Error for setting NAN (2)\n"); 81 exit (1); 82 } 83 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 84 res = mpfr_strtofr (x, "NAN(abcdEDF__1256)Hello", &s, 10, MPFR_RNDN); 85 if (res != 0 || !mpfr_nan_p (x) || strcmp(s, "Hello") ) 86 { 87 printf ("Error for setting NAN (3)\n"); 88 exit (1); 89 } 90 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 91 res = mpfr_strtofr (x, "NAN(abcdEDF)__1256)Hello", &s, 10, MPFR_RNDN); 92 if (res != 0 || !mpfr_nan_p (x) || strcmp(s, "__1256)Hello") ) 93 { 94 printf ("Error for setting NAN (4)\n"); 95 exit (1); 96 } 97 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 98 res = mpfr_strtofr (x, "NAN(abc%dEDF)__1256)Hello", &s, 10, MPFR_RNDN); 99 if (res != 0 || !mpfr_nan_p (x) || strcmp(s, "(abc%dEDF)__1256)Hello") ) 100 { 101 printf ("Error for setting NAN (5)\n"); 102 exit (1); 103 } 104 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 105 res = mpfr_strtofr (x, "NAN((abc))", &s, 10, MPFR_RNDN); 106 if (res != 0 || !mpfr_nan_p (x) || strcmp(s, "((abc))") ) 107 { 108 printf ("Error for setting NAN (6)\n"); 109 exit (1); 110 } 111 mpfr_set_ui (x, 0, MPFR_RNDN); /* make sure that x is modified */ 112 res = mpfr_strtofr (x, "NAN()foo", &s, 10, MPFR_RNDN); 113 if (res != 0 || !mpfr_nan_p (x) || strcmp(s, "foo") ) 114 { 115 printf ("Error for setting NAN (7)\n"); 116 exit (1); 117 } 118 119 /* Check infinity */ 120 for (i = 0; i <= 0xff; i++) 121 { 122 char t[11] = "+@INFINITY"; /* not char *: this will be modified. */ 123 char *p; 124 int base, j; 125 126 /* Test all the case variants, assuming ASCII or similar. 127 The first letters are changed first, so that at i = 8, 128 the 2^3 = 8 "INF" case variants have been tested, and 129 they don't need to be tested again for i > 8. */ 130 for (j = 0; j < 8; j++) 131 if ((i >> j) % 2 != 0) 132 t[j+2] += 'a' - 'A'; 133 134 /* Test "INFINITY", "+INFINITY", "-INFINITY", 135 "INF", "+INF", "-INF", 136 "@INF@", "+@INF@", "-@INF@", 137 up to case changes. */ 138 for (j = 0; j < 9; j++) 139 { 140 if (j == 3) 141 { 142 /* At i = 8, we have tested all the "INF" case variants. */ 143 if (i >= 8) 144 break; 145 t[5] = '\0'; 146 } 147 if (j == 6) 148 { 149 t[1] = '@'; 150 t[5] = '@'; 151 t[6] = '\0'; 152 } 153 if (j % 3 == 1) 154 t[j != 7] = '+'; 155 if (j % 3 == 2) 156 t[j != 8] = '-'; 157 p = t + (j % 3 == 0) + (j < 6); 158 base = randlimb () % (j < 6 ? 17 : 63); 159 if (base == 1) 160 base = 0; 161 res = mpfr_strtofr (x, p, &s, base, MPFR_RNDN); 162 if (res != 0 || !mpfr_inf_p (x) || *s != 0 || 163 (j % 3 != 2 ? MPFR_IS_NEG (x) : MPFR_IS_POS (x))) 164 { 165 printf ("Error for setting \"%s\" in base %d\n s=\"%s\"\n x=", 166 p, base, s); 167 mpfr_dump (x); 168 exit (1); 169 } 170 } 171 } 172 res = mpfr_strtofr (x, "INFANITY", &s, 8, MPFR_RNDN); 173 if (res != 0 || !mpfr_inf_p (x) || strcmp(s, "ANITY")) 174 { 175 printf ("Error for setting INFINITY (2)\n s=%s\n x=", s); 176 mpfr_dump (x); 177 exit (1); 178 } 179 res = mpfr_strtofr (x, "@INF@*2", &s, 11, MPFR_RNDN); 180 if (res != 0 || !mpfr_inf_p (x) || strcmp(s, "*2")) 181 { 182 printf ("Error for setting INFINITY (3)\n s=%s\n x=", s); 183 mpfr_dump (x); 184 exit (1); 185 } 186 187 /* Check Zero */ 188 res = mpfr_strtofr (x, " 00000", &s, 11, MPFR_RNDN); 189 if (res != 0 || !mpfr_zero_p (x) || s[0] != 0) 190 { 191 printf ("Error for setting ZERO (1)\n s=%s\n x=", s); 192 mpfr_dump (x); 193 exit (1); 194 } 195 196 /* Check base 62 */ 197 res = mpfr_strtofr (x, "A", NULL, 62, MPFR_RNDN); 198 if (res != 0 || mpfr_cmp_ui (x, 10)) 199 { 200 printf ("Error for setting 'A' in base 62\n x="); 201 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 202 putchar ('\n'); 203 exit (1); 204 } 205 res = mpfr_strtofr (x, "a", NULL, 62, MPFR_RNDN); 206 if (res != 0 || mpfr_cmp_ui (x, 36)) 207 { 208 printf ("Error for setting 'a' in base 62\n x="); 209 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 210 putchar ('\n'); 211 exit (1); 212 } 213 res = mpfr_strtofr (x, "Z", NULL, 62, MPFR_RNDN); 214 if (res != 0 || mpfr_cmp_ui (x, 35)) 215 { 216 printf ("Error for setting 'Z' in base 62\n x="); 217 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 218 putchar ('\n'); 219 exit (1); 220 } 221 res = mpfr_strtofr (x, "z", NULL, 62, MPFR_RNDN); 222 if (res != 0 || mpfr_cmp_ui (x, 61)) 223 { 224 printf ("Error for setting 'z' in base 62\n x="); 225 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 226 putchar ('\n'); 227 exit (1); 228 } 229 res = mpfr_strtofr (x, "ZA", NULL, 62, MPFR_RNDN); 230 if (res != 0 || mpfr_cmp_ui (x, 2180)) 231 { 232 printf ("Error for setting 'ZA' in base 62\n x="); 233 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 234 putchar ('\n'); 235 exit (1); 236 } 237 res = mpfr_strtofr (x, "za", NULL, 62, MPFR_RNDN); 238 if (res != 0 || mpfr_cmp_ui (x, 3818)) 239 { 240 printf ("Error for setting 'za' in base 62\n x="); 241 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 242 putchar ('\n'); 243 exit (1); 244 } 245 res = mpfr_strtofr (x, "aZ", NULL, 62, MPFR_RNDN); 246 if (res != 0 || mpfr_cmp_ui (x, 2267)) 247 { 248 printf ("Error for setting 'aZ' in base 62\n x="); 249 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 250 putchar ('\n'); 251 exit (1); 252 } 253 res = mpfr_strtofr (x, "Az", NULL, 62, MPFR_RNDN); 254 if (res != 0 || mpfr_cmp_ui (x, 681)) 255 { 256 printf ("Error for setting 'Az' in base 62\n x="); 257 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 258 putchar ('\n'); 259 exit (1); 260 } 261 262 /* Check base 60 */ 263 res = mpfr_strtofr (x, "Aa", NULL, 60, MPFR_RNDN); 264 if (res != 0 || mpfr_cmp_ui (x, 636)) 265 { 266 printf ("Error for setting 'Aa' in base 60\n x="); 267 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 268 putchar ('\n'); 269 exit (1); 270 } 271 res = mpfr_strtofr (x, "Zz", &s, 60, MPFR_RNDN); 272 if (res != 0 || mpfr_cmp_ui (x, 35) || strcmp(s, "z") ) 273 { 274 printf ("Error for setting 'Zz' in base 60\n x="); 275 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 276 putchar ('\n'); 277 exit (1); 278 } 279 280 /* Check base 61 */ 281 res = mpfr_strtofr (x, "z", &s, 61, MPFR_RNDN); 282 if (res != 0 || mpfr_cmp_ui (x, 0) || strcmp(s, "z") ) 283 { 284 printf ("Error for setting 'z' in base 61\n x="); 285 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); 286 putchar ('\n'); 287 exit (1); 288 } 289 290 mpfr_clear (x); 291 mpfr_clear (y); 292 } 293 294 /* The following RefTable has been generated by this following code */ 295 #if 0 296 #define MAX_NUM 100 297 298 int randomab (int a, int b) 299 { 300 return a + rand () % (b-a); 301 } 302 303 int 304 main (void) 305 { 306 int i, base; 307 mpfr_t x; 308 mpfr_prec_t p; 309 mpfr_exp_t e; 310 311 mpfr_init (x); 312 printf ("struct dymmy_test { \n" 313 " mpfr_prec_t prec; \n" 314 " int base; \n" 315 " const char *str; \n" 316 " const char *binstr; \n" 317 " } RefTable[] = { \n"); 318 for (i = 0 ; i < MAX_NUM ; i++) 319 { 320 p = randomab(2, 180); 321 base = randomab (2, 30); 322 e = randomab (-1<<15, 1<<15); 323 mpfr_set_prec (x, p); 324 mpfr_urandomb (x, RANDS); 325 mpfr_mul_2si (x, x, e, MPFR_RNDN); 326 printf("{%lu, %d,\n\"", p, base); 327 mpfr_out_str (stdout, base, p, x, MPFR_RNDN); 328 printf ("\",\n\""); 329 mpfr_out_str (stdout, 2, 0, x, MPFR_RNDN); 330 printf ("\"}%c\n", i == MAX_NUM-1 ? ' ' : ',' ); 331 } 332 printf("};\n"); 333 mpfr_clear (x); 334 } 335 #endif 336 337 static struct dymmy_test { 338 mpfr_prec_t prec; 339 int base; 340 const char *str; 341 const char *binstr; 342 } RefTable[] = { 343 {39, 20, 344 "1.1c9jeh9jg12d8iiggf26b8ce2cig24agai51d9@1445", 345 "1.00111010111010001110110001101011101011e6245"}, 346 {119, 3, 347 "1.2210112120221020220021000020101121120011021202212101222000011110211211122222001001221110102220122021121021101010120101e-5655", 348 "1.1111101110011110001101011100011000011100001011011100010011010010001000000111001010000001110111010100011000110010000000e-8963"}, 349 {166, 18, 350 "3.ecg67g31434b74d8hhbe2dbbb46g9546cae72cae0cfghfh00ed7gebe9ca63b47h08bgbdeb880a76dea12he31e1ccd67e9dh22a911b46h517b745169b2g43egg2e4eah820cdb2132d6a4f9c63505dd4a0dafbc@-5946", 351 "1.011110010000110011111011111100110110010110000010100001101111111000010000011111110101100000010110011001100000010001100101000001101000010010001011001011000110100011001e-24793"}, 352 {139, 4, 353 "1.020302230021023320300300101212330121100031233000032101123133120221012000000000000000000000000000000000000000000000000000000000000000000000e11221", 354 "1.001000110010101100001001001011111000110000110000010001100110111100011001010000001101101111000000001110010001011011011111011000101001000110e22442"}, 355 {126, 13, 356 "4.a3cb351c6c548a0475218519514c6c54366681447019ac70a387862c39c86546ab27608c9c2863328860aa2464288070a76c0773882728c5213a335289259@2897", 357 "1.01011010000001110001100001101111100111011010010111000011000101111011000100001010010100110111101001001001000000011100010000000e10722"}, 358 {6, 26, 359 "1.j79f6@-1593", 360 "1.00000e-7487"}, 361 {26, 18, 362 "3.5e99682hh310aa89hb2fb4h88@-5704", 363 "1.0110010100010101000101100e-23784"}, 364 {12, 21, 365 "4.j7f3e2ccdfa@-3524", 366 "1.10110101011e-15477"}, 367 {38, 28, 368 "o.agr0m367b9bmm76rplg7b53qlj7f02g717cab@6452", 369 "1.1001010011101100110100111000111010001e31021"}, 370 {75, 17, 371 "4.00abd9gc99902e1cae2caa7647gcc029g01370e96d3f8e9g02f814d3ge5faa29d40b9db470@5487", 372 "1.11100000110101010111101001110001001010111111010100000100001010100111011101e22429"}, 373 {91, 16, 374 "1.0a812a627160014a3bda1f00000000000000000000000000000000000000000000000000000000000000000000@7897", 375 "1.000010101000000100101010011000100111000101100000000000010100101000111011110110100001111100e31588"}, 376 {154, 19, 377 "1.989279dda02a8ic15e936ahig3c695f6059a3i01b7d1ge6a418bf84gd87e36061hb2bi62ciagcgb9226fafea41d2ig1e2f0a10ea3i40d6dahf598bdbh372bdf5901gh276866804ah53b6338bi@5285", 378 "1.110101101101101111110010001011110001100000010100011101101001000100110100000011110111000011011101011110010100110101011011111100101101001100000101101000010e22450"}, 379 {53, 2, 380 "1.0100010111100111001010000100011011111011011100110111e-20319", 381 "1.0100010111100111001010000100011011111011011100110111e-20319"}, 382 {76, 3, 383 "2.101212121100222100012112101120011222102000021110201110000202111122221100001e1511", 384 "1.000110101010111000011001011111110000001001101001011011111110111111010000111e2396"}, 385 {31, 9, 386 "1.171774371505084376877631528681e3258", 387 "1.110101101011111011111000110011e10327"}, 388 {175, 8, 389 "4.506242760242070533035566017365410474451421355546570157251400000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000e3483", 390 "1.001010001100101000101111100000101000100001110001010110110000111011011101100000011110111101011000010001001111001001010011000100010111011011011001101011110000011011110101010011e10451"}, 391 {103, 24, 392 "8.0hmlm3g183cj358fn4bimn5bie1l89k95m647474mm8jg5kh1c011gi0m7de9j7b48c595g1bki4n32kll7b882eg7klgga0h0gf11@4510", 393 "1.001000110101001101011010101001111010110100010100110101010101110000001011001101110110010111000101010111e20681"}, 394 {12, 9, 395 "3.00221080453e2479", 396 "1.11000111010e7859"}, 397 {86, 11, 398 "6.873680186953174a274754118026423965415553a088387303452447389287133a0956111602a5a085446@5035", 399 "1.0000000000110100010110000111010001010100101011000100101010010011101010000110011110001e17421"}, 400 {68, 10, 401 "6.1617378719016284192718392572980535262609909598793237475124371481233e481", 402 "1.0110001011000101110010111101100101111110001100001011110011001101111e1600"}, 403 {11, 15, 404 "5.ab10c18d45@907", 405 "1.0000101111e3546"}, 406 {77, 26, 407 "6.e6kl84g6h30o3nfnj7fjjff4n1ee6e5iop76gabj23e7hgan9o6724domc7bp4hdll95g817519f@5114", 408 "1.1011000101111111111110011011101100000100101000001001100000001011010001001000e24040"}, 409 {28, 27, 410 "d.odiqp9kgh84o8d2aoqg4c21hemi@3566", 411 "1.101001111001111111110011110e16959"}, 412 {45, 14, 413 "7.cddc6295a576980adbc8c16111d6301bad3146a1143c@-6227", 414 "1.10000000110011000000101100110001011100010111e-23706"}, 415 {54, 19, 416 "1.b6e67i2124hfga2g819g1d6527g2b603eg3cd8hhca9gecig8geg1@4248", 417 "1.11010100100010101101110110010100000010111010010101110e18045"}, 418 {49, 20, 419 "1.jj68bj6idadg44figi10d2ji99g6ddi6c6ich96a5h86i529@-3149", 420 "1.001011111101100100001010001000011100000000101110e-13609"}, 421 {171, 16, 422 "6.22cf0e566d8ff11359d70bd9200065cfd72600b12e00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000@5602", 423 "1.10001000101100111100001110010101100110110110001111111100010001001101011001110101110000101111011001001000000000000001100101110011111101011100100110000000001011000100101110e22410"}, 424 {144, 14, 425 "1.425d9709b4c125651ab88bb1a0370c14270d067a9a74a612dad48d5c025531c175c1b905201d0d9773aa686c8249db9c0b841b10821791c02baa2525a4aa7571850439c2cc965cd@-3351", 426 "1.11100111110001001101010111010000101010011000111001101011000001011110101110011011100100111001101101111011001001101011001101001011011101101111011e-12759"}, 427 {166, 6, 428 "3.324252232403440543134003140400220120040245215204322153511143504542403430152410543444455151104314552352030352125540101550151410414122051500201022252511512332523431554e8340", 429 "1.010101111101111101001001110010111110010000001111010101100110011011010110011001001100001111010101100000010111011111101110110111101110010001110001111000001010001111000e21560"}, 430 {141, 24, 431 "2.i3c88lkm2958l9ncb9f85kk35namjli84clek5j6jjkli82kb9m4e4i2g39me63db2094cif80gcba8ie6l15ia0d667kn9i1f77bdak599e1ach0j05cdn8kf6c6kfd82j2k6hj2c4d@4281", 432 "1.10011100001010110111001000000000101011100010101011001010001101110100110111011000111101000001111101100000110100100010101011001100100011001011e19629"}, 433 {84, 6, 434 "2.41022133512503223022555143021524424430350133500020112434301542311050052304150111243e982", 435 "1.11010001111111001010011100011000011100100111111010001111010010101001001000011100001e2539"}, 436 {56, 9, 437 "1.5305472255016741401411184703518332515066156086511016413e2936", 438 "1.0111110010001101000000110101110000110101001011001100111e9307"}, 439 {18, 8, 440 "3.63542400000000000e-599", 441 "1.11100111011000101e-1796"}, 442 {111, 13, 443 "8.b693ac7a24679b98708a0057a6202c867bc146740ab1971b380756a24c99804b63436419239ba0510030b819933771a636c57c5747b883@-6160", 444 "1.01011011111110100101110010100100000110000011011101001110010110000011101110111111010111000011011101101001100100e-22792"}, 445 {162, 16, 446 "4.f2abe958a313566adbf3169e55cdcff3785dbd5c0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000@382", 447 "1.00111100101010101111101001010110001010001100010011010101100110101011011011111100110001011010011110010101011100110111001111111100110111100001011101101111010101110e1530"}, 448 {117, 23, 449 "2.4b6kk3ag3if217ih1hggkk69bmcecfil1cd38dijh35j8e6ckhd335a4gj7l05bedk19473i8449b1ajc3jd3ka95eceheh72lh2jh17jamlm1142gll@-3628", 450 "1.10010010001010001110011000010000011111011101111100110101100100101111101110010011101001111010100010001111110100101111e-16411"}, 451 {179, 2, 452 "1.1101101011111010101000110101010101101110001011011010101001110111011010011110001000000110101100010010001110010110011000000110001011111001011110100011101000110001001000110100100110e14203", 453 "1.1101101011111010101000110101010101101110001011011010101001110111011010011110001000000110101100010010001110010110011000000110001011111001011110100011101000110001001000110100100110e14203"}, 454 {18, 27, 455 "4.ll743n2f654gh3154@-6039", 456 "1.01101001111010011e-28713"}, 457 {178, 15, 458 "1.e5443105cad2d014b700c42aa3de854c4b95322420695d07db3564ec07473da83bde123b74c794139265a838ebeca745ad3dc97d7c356271ca935ea8e83306562c2a8edc6e886c1b6b2d3e17038379c33826526770985c068@821", 459 "1.011100001000101100111111111111000100110111110011101010001111011001111101111001010011100100100101100011101001000000101001010100011111001011001010011101101001000111111010101101011e3208"}, 460 {161, 22, 461 "2.46ikji624bg042877h8g2jdki4ece6ede62841j7li843a4becdkkii86c54192jkefehikkb3kcb26ij1b3k9agfbb07dih88d6ej0ee0d63i8hedc7f0g0i9g7jf9gf6423j70h421bg5hf2bja9j0a432lb10@-5125", 462 "1.0111011000111110000010011100001100100110001011101001011110111010100000011100000010011101011100101100111100110000001101010101011110100011101111001011001111100000e-22854"}, 463 {62, 19, 464 "7.bgd1g0886a6c3a9ee67cc7g3bgf718i98d90788idi5587358e660iffc0ic6@3257", 465 "1.0101100100001110000100010110100100000111110001111001011110100e13838"}, 466 {127, 19, 467 "1.413bgf99eidba75ged25f7187080bce3h7ebdeghea4ig6c79g94di7b42a3e4cdi4ic6a53i71d2e4hdbe50ih0a0egf2fi469732131ig6g496bf7h8g3c86ie7h@-4465", 468 "1.001101111000011011100010010010010110111001001001110011110101111111000001110101111110001110010000110011111101000011000101111101e-18967"}, 469 {17, 21, 470 "4.7d5b70gh4k0gj4fj@-116", 471 "1.1000100010000110e-508"}, 472 {141, 13, 473 "2.2b4988c5cb57072a6a1a9c42224794a1cbc175a9bc673bb28aa045c3182b9396ca8bb8590969672b0239608a845a2c35c08908a58c2a83748c89241a6561422c7cc4866c8454@4358", 474 "1.10010110101000001000001001111001000100111110100010100110111011111011010010101000110101110000111100010000101101000110000000000001111110110011e16127"}, 475 {39, 7, 476 "3.00350342452505221136410100232265245244e202", 477 "1.10011000111110011010100110101101010010e568"}, 478 {119, 24, 479 "5.2aene587kc2d9a55mm8clhn4dn0a551de58b1fcli8e8hf1jlm7i0376dl5fhb2k8acka03077mnbn9d4dmi0641dce871c81g2b3ge76m3kngm4a9g5gh@-892", 480 "1.0111101010010100001001111110000000100101110010010111111100100101100001010010100110111000101100101010111000101111000010e-4088"}, 481 {41, 14, 482 "5.c3dc5c49373d0c0075624931133022185bd08b16@-5294", 483 "1.0101011000010111111111000010100110011111e-20154"}, 484 {41, 6, 485 "3.2411143454422033245255450304104450302500e2250", 486 "1.1110111101010101001001100000100011110111e5817"}, 487 {17, 13, 488 "3.65789aa26aa273b1@-4490", 489 "1.1100011101010111e-16614"}, 490 {10, 26, 491 "1.5p4hag1fl@6017", 492 "1.110010111e28282"}, 493 {130, 11, 494 "2.606a72601843700427667823172635a47055021a0a68a99326875195a179483948407aa13726244552332114a1784aaa7239956521604460876871a65708458aa@-6285", 495 "1.110001001110111110110111000010101000110010011110010101100100001000101011010010000001000101000110111111110101000100000111100010100e-21742"}, 496 {29, 20, 497 "j.4356d9b7i38i955jjj1j442501bj@163", 498 "1.1010101011110011100000100100e708"}, 499 {140, 21, 500 "9.2f5k7aid6bj2b2g5bff29i73hk3a8d8g0i7ifa07hkb79g4hd3c7j6g4hjj2jbhai01gkje3h9g3gj3i34f0194kaed32iea9dcgcj8h7i1khdkf965c1ak97gf3h03fcab3ggi03fa@4864", 501 "1.0101011100011101000110101001010011111111010011000111111111100000011011100111010001100101100110001110001001100101001100110000011110100101101e21367"}, 502 {133, 13, 503 "2.3721a9107307a71c75c07c83b70a25a9853619030b5bcb55101ca5c2060bca46c331b92b33aa957c3ac7c817335287c6917999c38c3806b6b5919623023ac52063bb@6602", 504 "1.011001101111100001100100110100010100010011100010111110110100100000000010011101001011000100000110011011101001010010011110111100010010e24431"}, 505 {118, 2, 506 "1.001010111011011000100010001110111000001100101000101101010001110110000111101110111011011101111100110010000101001001001e18960", 507 "1.001010111011011000100010001110111000001100101000101101010001110110000111101110111011011101111100110010000101001001001e18960"}, 508 {102, 23, 509 "l.26lhk42clcm9g940eihakhi32gb3331lld488cf1j4f73ge051bfl8gcmcg78gkjc2iibjf752eag0dee6dafa97k79jlh11j3270@-2160", 510 "1.01101011011000100101110111110001011000101101011001011111001101000110111010000010011111101110101100010e-9767"}, 511 {156, 18, 512 "b.eb927dd4g48abee3cc2begehb9c3b8h83cae152db850ac2f3g816d6787825122c8h3aa3g8023h23000a8hg61065b3e367ac59ca373067730f96dd0d3b73b3c43fef91750b333gd497b8ce9228e7@5504", 513 "1.11000110111100011101100011001001110011101100011111010100101110010010010011111001100000011010011111111011001011111010001001011001110001100001101000000110000e22954"}, 514 {158, 5, 515 "3.0112043214104344433122444210142004032004444213123303302023242414000243311324332203224340334422234000104132020124210141322013240010134130441413233111204013422e-10468", 516 "1.1001011000111111110100100101110011100001110100101001101110011001101001101011010010111010111111101010100011100010101100110111011101000110110100000111001100011e-24305"}, 517 {7, 9, 518 "2.141540e-146", 519 "1.001111e-462"}, 520 {111, 5, 521 "3.21233234110011204313222402442032333320324004133424222041314021020411320312421014434003440431230413141402230403e7641", 522 "1.10010000000101010000101010101011011010000100010010010000010110001111000111111111000110111001100101101110101101e17743"}, 523 {76, 13, 524 "7.1c0861453a4ac156b6119ba7548251b5cb00b7c409c2bb8138214676468c9949676226013c1@4639", 525 "1.001000011000000011101101101010100010010001010111100110010101111110110010111e17169"}, 526 {6, 25, 527 "c.aj660@-6978", 528 "1.11000e-32402"}, 529 {156, 3, 530 "2.22101000022222000012110122210202211110020121210120112102122121111210000211020001020201202200011021211102012110220222110022001121011022011202000110120021012e-14744", 531 "1.11010001111000101111110000010011001101000100010010110011100100110001100111011101011111111100011111001100001111100101100000001000001100000000010010001011101e-23368"}, 532 {7, 23, 533 "1.4hclk2@2148", 534 "1.110110e9716"}, 535 {69, 11, 536 "2.77684920493191632416690544493465617a187218365952a6740034288687745a26@3263", 537 "1.01111000111000001111001110000110000110001111110011101100101111011100e11289"}, 538 {146, 21, 539 "3.agg4d0dj636d526d4i8643ch5jee4ge2c3i46k121857dbedagd98cjifaf0fgc09ca739g2fkfbfh06i687kic2kb8c7i48gda57bb6d9bh81eh49h0d8e3i7ad2kgb1ek86b86g3589k27d@3562", 540 "1.0010111111111100101010101010001100110101010011011100001110111000101101001110001110010100000001010001000111010000010011110100010010101100101000001e15647"}, 541 {20, 3, 542 "1.2000000021102111102e-16642", 543 "1.1011101011111110000e-26377"}, 544 {68, 13, 545 "1.a43205b2164676727806614acc0398925569c3962a3ba419881a5c63b651aa3ab46@-618", 546 "1.1111011000001110010100111000110010110110011001110001100101011111000e-2287"}, 547 {129, 4, 548 "2.22033002012102010122130132103000303000120122313322000222121000300000000000000000000000000000000000000000000000000000000000000000e13222", 549 "1.01010001111000010000110010010000100011010011100011110010011000000110011000000011000011010110111111010000000101010011001000000110e26445"}, 550 {22, 6, 551 "1.420033001013011530142e11704", 552 "1.001000110010110110001e30255"}, 553 {108, 6, 554 "1.03345424443433104422104400512453214240453335230205104304115343030341144544051005432030344054100542125304500e7375", 555 "1.00101101110001011101101111000010101011101000001111001110001101100000111100010101010101101100011110111010000e19064"}, 556 {91, 27, 557 "2.ao077kf8oqoihn5pm6f5eqdcgnd2132d7p6n7di8ep82a1a9be99pm36g1emacbenaeiqphpgpdjhmm9ke3pn4pdea@-5482", 558 "1.111101100001000011101010001000000111000100100111110010101101110001101101101101101010111110e-26066"}, 559 {96, 9, 560 "8.25805186310703506315505842015248775712246416686874260383701323213202658278523870037877823670166e-8134", 561 "1.11010111111000011100111001011010001110010001011101011101110101000101100100100010110011001010000e-25782"}, 562 {161, 16, 563 "7.3a7627c1e42ef738698e292f0b81728c4b14fe8c000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000@-3342", 564 "1.1100111010011101100010011111000001111001000010111011110111001110000110100110001110001010010010111100001011100000010111001010001100010010110001010011111110100011e-13366"}, 565 {90, 3, 566 "2.10212200011211012002002221112120210222002020100202111000211012122020011102022112222021001e-3447", 567 "1.11100010111011011000101111110001000101000111110001100001010111101101011011110001000010001e-5463"}, 568 {100, 27, 569 "a.f81hjjakdnc021op6ffh530ec8ige6n2fqc8f8j7ia7qelebgqkm4ic5ohh652hq1kgpag6pp0ldin6ce1fg6mj34077f5qc5oe@6576", 570 "1.011101001010010011110001100011111111010001110110100100101001010000101011101011110010010011111100000e31271"}, 571 {152, 16, 572 "e.37ac48a0303f903c9d20883eddea4300d1190000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000@-1388", 573 "1.1100011011110101100010010001010000000110000001111111001000000111100100111010010000010001000001111101101110111101010010000110000000011010001000110010000e-5549"}, 574 {106, 20, 575 "1.3g2h7i2776d50gjibi937f8cdci3idecdeh3j2gba0j8d1ghgg3eg609ji55h5g7jeai1bii3a4f9jhjfij6jd1g3cg0f6024e252gc3e@6422", 576 "1.100110000101011010100111100110000000100101000110110011010010000101000100110010001110011110111100010000111e27755"}, 577 {23, 17, 578 "9.f72e724454d1g0f60g93g6@-6563", 579 "1.0011100011110110010001e-26823"}, 580 {98, 6, 581 "1.2444223304453415235424343034030405514010421403514410005234221430055051205523402412055242134042045e-8535", 582 "1.1101110011010001101001001111100101111010100111001011110001000010100101101110011011101100000111011e-22063"}, 583 {4, 18, 584 "1.gec@-6711", 585 "1.100e-27984"}, 586 {69, 24, 587 "8.d45gdfnhkhb7a20nj96dnggic83imhjne0cceldechn1m4e9fbd9db0ablngjf9n7810@6975", 588 "1.00100111111100101100110011110110110000110110110010100101011111000100e31983"}, 589 {122, 8, 590 "4.0227760456667717717077553523466457265600000000000000000000000000000000000000000000000000000000000000000000000000000000000e-1767", 591 "1.0000001001011111111000010010111011011011111100111111100111100011111110110101110101001110011011010010111101011010111000000e-5299"}, 592 {144, 23, 593 "8.b01c48dg20bek9a5k376clc501aecg92bdjaeji2dm9230i7j3k36jm50b0c5a0753i2b18534cji34bcl2li033cc534m52k2gbegc25a5g30lf4calag58026i5d7li61jg9digj5ceb1@-4456", 594 "1.00010000110011010111011011110111001101111001010110001101011100100101101110110000010011011111100000100110001001001111111011010110000000001111110e-20154"}, 595 {111, 4, 596 "2.23100111310122202021232133233012212012232222323230133100000000000000000000000000000000000000000000000000000000e-10458", 597 "1.01011010000010101110100011010100010001001101110011111101111000110100110000110101110101010111011101100011111010e-20915"}, 598 {117, 10, 599 "1.61207328685870427963864999744776917701013812304254540861834226053316419217753608451422967376154318603744156166920074e-6440", 600 "1.01100011000100111001100010000000110010100001001011111010100001101111100100101100111010100011101110001010011010010010e-21393"}, 601 {106, 16, 602 "1.dd30a1d24091263243ca1c144f0000000000000000000000000000000000000000000000000000000000000000000000000000000@354", 603 "1.110111010011000010100001110100100100000010010001001001100011001001000011110010100001110000010100010011110e1416"}, 604 {77, 14, 605 "4.90d6913ba57b149d8d85a58c311b4d537c10bd7d3c10d69c62bc08d32269760126a58115a105@-7311", 606 "1.1001000000111100000111001001011000110101001111100001100111010100010000011111e-27834"}, 607 {8, 4, 608 "3.2230000e15197", 609 "1.1101011e30395"}, 610 {81, 24, 611 "1.84ni25h558abmhg2dk7bl2jbbmkf4i8i2bemc5cgmk9jf301c00k24271m9h7mgm4301be1lnldn4364@2573", 612 "1.01110010011000110110100101011001011111101111101100010110101101011101100001000010e11797"}, 613 {94, 2, 614 "1.010010010101111001001011111111100100011110110100010001101111111100100101101100110101001011111e32427", 615 "1.010010010101111001001011111111100100011110110100010001101111111100100101101100110101001011111e32427"}, 616 {77, 21, 617 "1.87e4k9df85g50ead6fcj4h86820ikdjdjg93d90ca406g470hhkh7ciaba1aggg753g36553ebh5@2538", 618 "1.0010001100011000111010000010011001010011000000100101010001100000111101000111e11148"}, 619 {80, 17, 620 "1.923gga999230g94fce02efg753ce001045a35e0264c9c2cb17850e32484fc3526dcg38ed874g5f2@3392", 621 "1.0011100111101001001101111001110100001100111110011110110001100110101010111001110e13865"}, 622 {99, 7, 623 "4.53646362336126606650465342500160461331562113222506144210636341332436342025203333264316511653025011e-5540", 624 "1.01101101111001001100001101101101010011001001100110111000010000101000011001001001101000011101011001e-15551"}, 625 {119, 20, 626 "1.c8966iabcf4de94ad15f9e83j407i3he7fch54h5jh0g5d74e06c057gg72a107didj8d1j8geibbfec5j36c3fgd5e12edjb9g10j7c9i03f33hi80ce0@7153", 627 "1.0101110101100011110001001110100110011000100000001001000110111110011111100011111010011101011111101101010011110111110100e30915"}, 628 {93, 13, 629 "2.c749cb562c3a758b1a21a650666a4c6c53c76ca58a1a75a0358c9ac3866887972b3551a03aa6c150856531258508@193", 630 "1.10101111101001011010111101100100111110011111010110111101100100010011001001100011110100111110e715"}, 631 {145, 14, 632 "1.c61614b64261d22c62cb9d16163ca4d144ac23351b708506b3b610b1b67b764ca974448d7a2c6515a6bc97503d4b2a530c75b2b677a464c6629c69b6c3d7860d7749b4b653c434d5@2050", 633 "1.111111100001101111100011001111100010010000101000011110000001110100111001011010100001001010111111010001111101000110011000011101110110001001100101e7805"}, 634 {159, 23, 635 "4.bj9l07l0215e7l6lf1dkf62i056l37jaa0gdih717656f1kk1a77883jf99jg31le43em76bmcg4lddl782ihkla0m392886d8lm67d6c3a1l4j12kg0l1k52ee77lmk0gech11g8jeei680k85bi460c7el17@-1539", 636 "1.01010100110100100101100001011100000001100011110001001101000010000001000010000110000110010001110100001101011101101001001101101111001101101111101001010010010100e-6960"}, 637 {24, 25, 638 "g.m749al09kflg5b42jnn4a7b@-2820", 639 "1.01010010101011010111011e-13092"}, 640 {88, 18, 641 "3.5ed0gad0bhhb7aa9ge2ad1dhcg6833f3e068936hghf23gd2aa69f13539f15hfce50aa64achfee49bfg7249g@-4058", 642 "1.001000010110011011000101100000101111101001100011101101001111110111000010010110010001100e-16920"} 643 }; 644 645 static void 646 check_reftable (void) 647 { 648 int i, base; 649 mpfr_t x, y; 650 mpfr_prec_t p; 651 char *s; 652 653 mpfr_init2 (x, 200); 654 mpfr_init2 (y, 200); 655 for (i = 0 ; i < numberof (RefTable) ; i++) 656 { 657 base = RefTable[i].base; 658 p = RefTable[i].prec; 659 mpfr_set_prec (x, p); 660 mpfr_set_prec (y, p); 661 mpfr_set_str_binary (x, RefTable[i].binstr); 662 mpfr_strtofr (y, RefTable[i].str, &s, base, MPFR_RNDN); 663 if (s == NULL || *s != 0) 664 { 665 printf ("strtofr didn't parse entire input for i=%d:\n" 666 " Str=%s", i, RefTable[i].str); 667 exit (1); 668 } 669 if (mpfr_cmp (x, y)) 670 { 671 printf ("Results differ between strtofr and set_binary for i=%d:\n" 672 " Set binary gives: ", i); 673 mpfr_dump (x); 674 printf (" strtofr gives: "); 675 mpfr_dump (y); 676 printf (" setstr gives: "); 677 mpfr_set_str (x, RefTable[i].str, base, MPFR_RNDN); 678 mpfr_dump (x); 679 mpfr_set_prec (x, 2*p); 680 mpfr_set_str (x, RefTable[i].str, base, MPFR_RNDN); 681 printf (" setstr ++ gives: "); 682 mpfr_dump (x); 683 exit (1); 684 } 685 } 686 mpfr_clear (y); 687 mpfr_clear (x); 688 } 689 690 static void 691 check_parse (void) 692 { 693 mpfr_t x; 694 char *s; 695 int res; 696 697 mpfr_init (x); 698 699 /* Invalid data */ 700 mpfr_set_si (x, -1, MPFR_RNDN); 701 res = mpfr_strtofr (x, " invalid", NULL, 10, MPFR_RNDN); 702 if (MPFR_NOTZERO (x) || MPFR_IS_NEG (x)) 703 { 704 printf ("Failed parsing ' invalid' (1)\n X="); 705 mpfr_dump (x); 706 exit (1); 707 } 708 MPFR_ASSERTN (res == 0); 709 mpfr_set_si (x, -1, MPFR_RNDN); 710 res = mpfr_strtofr (x, " invalid", &s, 0, MPFR_RNDN); 711 if (MPFR_NOTZERO (x) || MPFR_IS_NEG (x) || strcmp (s, " invalid")) 712 { 713 printf ("Failed parsing ' invalid' (2)\n S=%s\n X=", s); 714 mpfr_dump (x); 715 exit (1); 716 } 717 MPFR_ASSERTN (res == 0); 718 /* Check if it stops correctly */ 719 mpfr_strtofr (x, "15*x", &s, 10, MPFR_RNDN); 720 if (mpfr_cmp_ui (x, 15) || strcmp (s, "*x")) 721 { 722 printf ("Failed parsing '15*x'\n S=%s\n X=", s); 723 mpfr_dump (x); 724 exit (1); 725 } 726 /* Check for leading spaces */ 727 mpfr_strtofr (x, " 1.5E-10 *x^2", &s, 10, MPFR_RNDN); 728 if (mpfr_cmp_str1 (x, "1.5E-10") || strcmp (s, " *x^2")) 729 { 730 printf ("Failed parsing '1.5E-10*x^2'\n S=%s\n X=", s); 731 mpfr_dump (x); 732 exit (1); 733 } 734 /* Check for leading sign */ 735 mpfr_strtofr (x, " +17.5E-42E ", &s, 10, MPFR_RNDN); 736 if (mpfr_cmp_str1 (x, "17.5E-42") || strcmp (s, "E ")) 737 { 738 printf ("Failed parsing '+17.5E-42E '\n S=%s\n X=", s); 739 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 740 exit (1); 741 } 742 mpfr_strtofr (x, "-17.5E+42E\n", &s, 10, MPFR_RNDN); 743 if (mpfr_cmp_str1 (x, "-17.5E42") || strcmp (s, "E\n")) 744 { 745 printf ("Failed parsing '-17.5E+42\\n'\n S=%s\n X=", s); 746 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 747 exit (1); 748 } 749 /* P form */ 750 mpfr_strtofr (x, "0x42P17", &s, 16, MPFR_RNDN); 751 if (mpfr_cmp_str (x, "8650752", 10, MPFR_RNDN) || *s != 0) 752 { 753 printf ("Failed parsing '0x42P17' (base = 16)\n S='%s'\n X=", s); 754 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 755 exit (1); 756 } 757 mpfr_strtofr (x, "-0X42p17", &s, 16, MPFR_RNDN); 758 if (mpfr_cmp_str (x, "-8650752", 10, MPFR_RNDN) || *s != 0) 759 { 760 printf ("Failed parsing '-0x42p17' (base = 16)\n S='%s'\n X=", s); 761 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 762 exit (1); 763 } 764 mpfr_strtofr (x, "42p17", &s, 16, MPFR_RNDN); 765 if (mpfr_cmp_str (x, "8650752", 10, MPFR_RNDN) || *s != 0) 766 { 767 printf ("Failed parsing '42p17' (base = 16)\n S='%s'\n X=", s); 768 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 769 exit (1); 770 } 771 mpfr_strtofr (x, "-42P17", &s, 16, MPFR_RNDN); 772 if (mpfr_cmp_str (x, "-8650752", 10, MPFR_RNDN) || *s != 0) 773 { 774 printf ("Failed parsing '-42P17' (base = 16)\n S='%s'\n X=", s); 775 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 776 exit (1); 777 } 778 mpfr_strtofr (x, "0b1001P17", &s, 2, MPFR_RNDN); 779 if (mpfr_cmp_str (x, "1179648", 10, MPFR_RNDN) || *s != 0) 780 { 781 printf ("Failed parsing '0b1001P17' (base = 2)\n S='%s'\n X=", s); 782 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 783 exit (1); 784 } 785 mpfr_strtofr (x, "-0B1001p17", &s, 2, MPFR_RNDN); 786 if (mpfr_cmp_str (x, "-1179648", 10, MPFR_RNDN) || *s != 0) 787 { 788 printf ("Failed parsing '-0B1001p17' (base = 2)\n S='%s'\n X=", s); 789 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 790 exit (1); 791 } 792 mpfr_strtofr (x, "1001p17", &s, 2, MPFR_RNDN); 793 if (mpfr_cmp_str (x, "1179648", 10, MPFR_RNDN) || *s != 0) 794 { 795 printf ("Failed parsing '1001p17' (base = 2)\n S='%s'\n X=", s); 796 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 797 exit (1); 798 } 799 mpfr_strtofr (x, "-1001P17", &s, 2, MPFR_RNDN); 800 if (mpfr_cmp_str (x, "-1179648", 10, MPFR_RNDN) || *s != 0) 801 { 802 printf ("Failed parsing '-1001P17' (base = 2)\n S='%s'\n X=", s); 803 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 804 exit (1); 805 } 806 /* Check for auto-detection of the base */ 807 mpfr_strtofr (x, "+0x42P17", &s, 0, MPFR_RNDN); 808 if (mpfr_cmp_str (x, "42P17", 16, MPFR_RNDN) || *s != 0) 809 { 810 printf ("Failed parsing '+0x42P17'\n S=%s\n X=", s); 811 mpfr_out_str (stdout, 16, 0, x, MPFR_RNDN); putchar ('\n'); 812 exit (1); 813 } 814 mpfr_strtofr (x, "-42E17", &s, 0, MPFR_RNDN); 815 if (mpfr_cmp_str (x, "-42E17", 10, MPFR_RNDN) || *s != 0) 816 { 817 printf ("Failed parsing '-42E17'\n S=%s\n X=", s); 818 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 819 exit (1); 820 } 821 mpfr_strtofr (x, "-42P17", &s, 0, MPFR_RNDN); 822 if (mpfr_cmp_str (x, "-42", 10, MPFR_RNDN) || strcmp (s, "P17")) 823 { 824 printf ("Failed parsing '-42P17' (base = 0)\n S='%s'\n X=", s); 825 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 826 exit (1); 827 } 828 mpfr_strtofr (x, " 0b0101.011@42", &s, 0, MPFR_RNDN); 829 if (mpfr_cmp_str (x, "0101.011@42", 2, MPFR_RNDN) || *s != 0) 830 { 831 printf ("Failed parsing '0101.011@42'\n S=%s\n X=", s); 832 mpfr_out_str (stdout, 2, 0, x, MPFR_RNDN); putchar ('\n'); 833 exit (1); 834 } 835 mpfr_strtofr (x, " 0b0101.011P42", &s, 0, MPFR_RNDN); 836 if (mpfr_cmp_str (x, "0101.011@42", 2, MPFR_RNDN) || *s != 0) 837 { 838 printf ("Failed parsing '0101.011@42'\n S=%s\n X=", s); 839 mpfr_out_str (stdout, 2, 0, x, MPFR_RNDN); putchar ('\n'); 840 exit (1); 841 } 842 mpfr_strtofr (x, "+0x42@17", &s, 0, MPFR_RNDN); 843 if (mpfr_cmp_str (x, "4.2@18", 16, MPFR_RNDN) || *s != 0) 844 { 845 printf ("Failed parsing '+0x42P17'\n S=%s\n X=", s); 846 mpfr_out_str (stdout, 16, 0, x, MPFR_RNDN); putchar ('\n'); 847 exit (1); 848 } 849 850 851 /* Check for space inside the mantissa */ 852 mpfr_strtofr (x, "+0x4 2@17", &s, 0, MPFR_RNDN); 853 if (mpfr_cmp_ui (x, 4) || strcmp(s," 2@17")) 854 { 855 printf ("Failed parsing '+0x4 2@17'\n S=%s\n X=", s); 856 mpfr_out_str (stdout, 16, 0, x, MPFR_RNDN); putchar ('\n'); 857 exit (1); 858 } 859 mpfr_strtofr (x, "+0x42 P17", &s, 0, MPFR_RNDN); 860 if (mpfr_cmp_ui (x, 0x42) || strcmp(s," P17")) 861 { 862 printf ("Failed parsing '+0x42 P17'\n S=%s\n X=", s); 863 mpfr_out_str (stdout, 16, 0, x, MPFR_RNDN); putchar ('\n'); 864 exit (1); 865 } 866 /* Space between mantissa and exponent */ 867 mpfr_strtofr (x, " -0b0101P 17", &s, 0, MPFR_RNDN); 868 if (mpfr_cmp_si (x, -5) || strcmp(s,"P 17")) 869 { 870 printf ("Failed parsing '-0b0101P 17'\n S=%s\n X=", s); 871 mpfr_out_str (stdout, 2, 0, x, MPFR_RNDN); putchar ('\n'); 872 exit (1); 873 } 874 /* Check for Invalid exponent. */ 875 mpfr_strtofr (x, " -0b0101PF17", &s, 0, MPFR_RNDN); 876 if (mpfr_cmp_si (x, -5) || strcmp(s,"PF17")) 877 { 878 printf ("Failed parsing '-0b0101PF17'\n S=%s\n X=", s); 879 mpfr_out_str (stdout, 2, 0, x, MPFR_RNDN); putchar ('\n'); 880 exit (1); 881 } 882 /* At least one digit in the mantissa. */ 883 mpfr_strtofr (x, " .E10", &s, 0, MPFR_RNDN); 884 if (strcmp(s," .E10")) 885 { 886 printf ("Failed parsing ' .E10'\n S=%s\n X=", s); 887 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 888 exit (1); 889 } 890 /* Check 2 '.': 2.3.4 */ 891 mpfr_strtofr (x, "-1.2.3E4", &s, 0, MPFR_RNDN); 892 if (mpfr_cmp_str1 (x, "-1.2") || strcmp(s,".3E4")) 893 { 894 printf ("Failed parsing '-1.2.3E4'\n S=%s\n X=", s); 895 mpfr_out_str (stdout, 10, 0, x, MPFR_RNDN); putchar ('\n'); 896 exit (1); 897 } 898 /* Check for 0x and 0b */ 899 mpfr_strtofr (x, " 0xG", &s, 0, MPFR_RNDN); 900 if (mpfr_cmp_ui (x, 0) || strcmp(s,"xG")) 901 { 902 printf ("Failed parsing ' 0xG'\n S=%s\n X=", s); 903 mpfr_out_str (stdout, 16, 0, x, MPFR_RNDN); putchar ('\n'); 904 exit (1); 905 } 906 mpfr_strtofr (x, " 0b2", &s, 0, MPFR_RNDN); 907 if (mpfr_cmp_ui (x, 0) || strcmp(s,"b2")) 908 { 909 printf ("Failed parsing ' 0b2'\n S=%s\n X=", s); 910 mpfr_out_str (stdout, 2, 0, x, MPFR_RNDN); putchar ('\n'); 911 exit (1); 912 } 913 mpfr_strtofr (x, "-0x.23@2Z33", &s, 0, MPFR_RNDN); 914 if (mpfr_cmp_si (x, -0x23) || strcmp(s,"Z33")) 915 { 916 printf ("Failed parsing '-0x.23@2Z33'\n S=%s\n X=", s); 917 mpfr_out_str (stdout, 16, 0, x, MPFR_RNDN); putchar ('\n'); 918 exit (1); 919 } 920 mpfr_strtofr (x, " 0x", &s, 0, MPFR_RNDN); 921 if (mpfr_cmp_ui (x, 0) || strcmp(s,"x")) 922 { 923 printf ("Failed parsing ' 0x'\n S=%s\n X=", s); 924 mpfr_out_str (stdout, 16, 0, x, MPFR_RNDN); putchar ('\n'); 925 exit (1); 926 } 927 928 mpfr_clear (x); 929 } 930 931 static void 932 check_overflow (void) 933 { 934 mpfr_t x; 935 char *s; 936 937 mpfr_init (x); 938 939 /* Huge overflow */ 940 mpfr_strtofr (x, "123456789E2147483646", &s, 0, MPFR_RNDN); 941 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x) ) 942 { 943 printf ("Check overflow failed (1) with:\n s=%s\n x=", s); 944 mpfr_dump (x); 945 exit (1); 946 } 947 mpfr_strtofr (x, "123456789E9223372036854775807", &s, 0, MPFR_RNDN); 948 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x) ) 949 { 950 printf ("Check overflow failed (2) with:\n s='%s'\n x=", s); 951 mpfr_dump (x); 952 #if defined(__GNUC__) 953 printf ("This failure is triggered by GCC bug 86554:\n" 954 " https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86554\n" 955 " https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87276 " 956 "(about this test)\nWorkaround: disable code hoisting " 957 "with -fno-code-hoisting in CFLAGS.\n"); 958 /* Note: In Debian, this error is obtained with gcc-snapshot from 959 20180908-1 to 20181127-1. With gcc-snapshot from 20181209-1 to 960 20190102-1 (at least), the MPFR build no longer seems affected 961 in general, but using --with-gmp-build=... together with 962 --enable-assert still triggers this failure. This bug has been 963 fixed in the GCC trunk rev 267725, thus the future gcc-snapshot 964 versions should no longer have this bug. */ 965 #endif 966 exit (1); 967 } 968 mpfr_strtofr (x, "123456789E170141183460469231731687303715884105728", 969 &s, 0, MPFR_RNDN); 970 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x) ) 971 { 972 printf ("Check overflow failed (3) with:\n s=%s\n x=", s); 973 mpfr_dump (x); 974 exit (1); 975 } 976 977 /* Limit overflow */ 978 mpfr_strtofr (x, "12E2147483646", &s, 0, MPFR_RNDN); 979 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x) ) 980 { 981 printf ("Check overflow failed (4) with:\n s=%s\n x=", s); 982 mpfr_dump (x); 983 exit (1); 984 } 985 mpfr_strtofr (x, "12E2147483645", &s, 0, MPFR_RNDN); 986 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x)) 987 { 988 printf ("Check overflow failed (5) with:\n s=%s\n x=", s); 989 mpfr_dump (x); 990 exit (1); 991 } 992 mpfr_strtofr (x, "0123456789ABCDEF@2147483640", &s, 16, MPFR_RNDN); 993 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x)) 994 { 995 printf ("Check overflow failed (6) with:\n s=%s\n x=", s); 996 mpfr_dump (x); 997 exit (1); 998 } 999 mpfr_strtofr (x, "0123456789ABCDEF@540000000", &s, 16, MPFR_RNDN); 1000 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x)) 1001 { 1002 printf ("Check overflow failed (7) with:\n s=%s\n x=", s); 1003 mpfr_dump (x); 1004 exit (1); 1005 } 1006 mpfr_strtofr (x, "1@2305843009213693951", &s, 16, MPFR_RNDN); 1007 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x)) 1008 { 1009 printf ("Check overflow failed (8) with:\n s=%s\n x=", s); 1010 mpfr_dump (x); 1011 exit (1); 1012 } 1013 mpfr_strtofr (x, "1@2305843009213693951", &s, 17, MPFR_RNDN); 1014 if (s[0] != 0 || !MPFR_IS_INF (x) || !MPFR_IS_POS (x)) 1015 { 1016 printf ("Check overflow failed (9) with:\n s=%s\n x=", s); 1017 mpfr_dump (x); 1018 exit (1); 1019 } 1020 1021 /* Check underflow */ 1022 mpfr_strtofr (x, "123456789E-2147483646", &s, 0, MPFR_RNDN); 1023 if (s[0] != 0 || !MPFR_IS_ZERO (x) || !MPFR_IS_POS (x) ) 1024 { 1025 printf ("Check underflow failed (1) with:\n s=%s\n x=", s); 1026 mpfr_dump (x); 1027 exit (1); 1028 } 1029 mpfr_strtofr (x, "123456789E-9223372036854775807", &s, 0, MPFR_RNDN); 1030 if (s[0] != 0 || !MPFR_IS_ZERO (x) || !MPFR_IS_POS (x) ) 1031 { 1032 printf ("Check underflow failed (2) with:\n s='%s'\n x=", s); 1033 mpfr_dump (x); 1034 exit (1); 1035 } 1036 mpfr_strtofr (x, "-123456789E-170141183460469231731687303715884105728", 1037 &s, 0, MPFR_RNDN); 1038 if (s[0] != 0 || !MPFR_IS_ZERO (x) || !MPFR_IS_NEG (x) ) 1039 { 1040 printf ("Check underflow failed (3) with:\n s=%s\n x=", s); 1041 mpfr_dump (x); 1042 exit (1); 1043 } 1044 mpfr_strtofr (x, "0123456789ABCDEF@-540000000", &s, 16, MPFR_RNDN); 1045 if (s[0] != 0 || !MPFR_IS_ZERO (x) || !MPFR_IS_POS (x)) 1046 { 1047 printf ("Check overflow failed (7) with:\n s=%s\n x=", s); 1048 mpfr_dump (x); 1049 exit (1); 1050 } 1051 mpfr_strtofr (x, "1@-2305843009213693952", &s, 16, MPFR_RNDN); 1052 if (s[0] != 0 || !MPFR_IS_ZERO (x) || !MPFR_IS_POS (x) ) 1053 { 1054 printf ("Check underflow failed (8) with:\n s='%s'\n x=", s); 1055 mpfr_dump (x); 1056 exit (1); 1057 } 1058 1059 mpfr_clear (x); 1060 } 1061 1062 static void 1063 check_retval (void) 1064 { 1065 mpfr_t x; 1066 int res; 1067 1068 mpfr_init2 (x, 10); 1069 1070 res = mpfr_strtofr (x, "01011000111", NULL, 2, MPFR_RNDN); 1071 MPFR_ASSERTN (res == 0); 1072 res = mpfr_strtofr (x, "11011000111", NULL, 2, MPFR_RNDN); 1073 MPFR_ASSERTN (res > 0); 1074 res = mpfr_strtofr (x, "110110001101", NULL, 2, MPFR_RNDN); 1075 MPFR_ASSERTN (res < 0); 1076 1077 mpfr_clear (x); 1078 } 1079 1080 /* Bug found by Christoph Lauter (in mpfr_set_str). */ 1081 static struct bug20081025_test { 1082 mpfr_rnd_t rnd; 1083 int inexact; 1084 const char *str; 1085 const char *binstr; 1086 } Bug20081028Table[] = { 1087 {MPFR_RNDN, -1, "1.00000000000000000006", "1"}, 1088 {MPFR_RNDZ, -1, "1.00000000000000000006", "1"}, 1089 {MPFR_RNDU, +1, "1.00000000000000000006", 1090 "10000000000000000000000000000001e-31"}, 1091 {MPFR_RNDD, -1, "1.00000000000000000006", "1"}, 1092 1093 1094 {MPFR_RNDN, +1, "-1.00000000000000000006", "-1"}, 1095 {MPFR_RNDZ, +1, "-1.00000000000000000006", "-1"}, 1096 {MPFR_RNDU, +1, "-1.00000000000000000006", "-1"}, 1097 {MPFR_RNDD, -1, "-1.00000000000000000006", 1098 "-10000000000000000000000000000001e-31"}, 1099 1100 {MPFR_RNDN, +1, "0.999999999999999999999999999999999999999999999", "1"}, 1101 {MPFR_RNDZ, -1, "0.999999999999999999999999999999999999999999999", 1102 "11111111111111111111111111111111e-32"}, 1103 {MPFR_RNDU, +1, "0.999999999999999999999999999999999999999999999", "1"}, 1104 {MPFR_RNDD, -1, "0.999999999999999999999999999999999999999999999", 1105 "11111111111111111111111111111111e-32"}, 1106 1107 {MPFR_RNDN, -1, "-0.999999999999999999999999999999999999999999999", "-1"}, 1108 {MPFR_RNDZ, +1, "-0.999999999999999999999999999999999999999999999", 1109 "-11111111111111111111111111111111e-32"}, 1110 {MPFR_RNDU, +1, "-0.999999999999999999999999999999999999999999999", 1111 "-11111111111111111111111111111111e-32"}, 1112 {MPFR_RNDD, -1, "-0.999999999999999999999999999999999999999999999", "-1"} 1113 }; 1114 1115 static void 1116 bug20081028 (void) 1117 { 1118 int i; 1119 int inexact, res; 1120 mpfr_rnd_t rnd; 1121 mpfr_t x, y; 1122 char *s; 1123 1124 mpfr_init2 (x, 32); 1125 mpfr_init2 (y, 32); 1126 for (i = 0 ; i < numberof (Bug20081028Table) ; i++) 1127 { 1128 rnd = Bug20081028Table[i].rnd; 1129 inexact = Bug20081028Table[i].inexact; 1130 mpfr_set_str_binary (x, Bug20081028Table[i].binstr); 1131 res = mpfr_strtofr (y, Bug20081028Table[i].str, &s, 10, rnd); 1132 if (s == NULL || *s != 0) 1133 { 1134 printf ("Error in Bug20081028: strtofr didn't parse entire input\n" 1135 "for (i=%d) Str=\"%s\"", i, Bug20081028Table[i].str); 1136 exit (1); 1137 } 1138 if (! SAME_SIGN (res, inexact)) 1139 { 1140 printf ("Error in Bug20081028: expected %s ternary value, " 1141 "got %d\nfor (i=%d) Rnd=%s Str=\"%s\"\n Set binary gives: ", 1142 inexact > 0 ? "positive" : "negative", 1143 res, i, mpfr_print_rnd_mode(rnd), Bug20081028Table[i].str); 1144 mpfr_dump (x); 1145 printf (" strtofr gives: "); 1146 mpfr_dump (y); 1147 exit (1); 1148 } 1149 if (mpfr_cmp (x, y)) 1150 { 1151 printf ("Error in Bug20081028: Results differ between strtofr and " 1152 "set_binary\nfor (i=%d) Rnd=%s Str=\"%s\"\n" 1153 " Set binary gives: ", 1154 i, mpfr_print_rnd_mode(rnd), Bug20081028Table[i].str); 1155 mpfr_dump (x); 1156 printf (" strtofr gives: "); 1157 mpfr_dump (y); 1158 exit (1); 1159 } 1160 } 1161 mpfr_clear (y); 1162 mpfr_clear (x); 1163 } 1164 1165 /* check that 1.23e is correctly parsed, cf 1166 https://gmplib.org/list-archives/gmp-bugs/2010-March/001898.html */ 1167 static void 1168 test20100310 (void) 1169 { 1170 mpfr_t x, y; 1171 char str[] = "1.23e", *endptr; 1172 1173 mpfr_init2 (x, 53); 1174 mpfr_init2 (y, 53); 1175 mpfr_strtofr (x, str, &endptr, 10, MPFR_RNDN); 1176 mpfr_strtofr (y, "1.23", NULL, 10, MPFR_RNDN); 1177 if (mpfr_cmp (x, y) != 0) 1178 { 1179 printf ("x <> y in test20100310\n"); 1180 exit (1); 1181 } 1182 if (endptr != str + 4) /* strtofr should take into account '1.23', 1183 not '1.23e' */ 1184 { 1185 printf ("endptr <> str + 4 in test20100310\n"); 1186 exit (1); 1187 } 1188 mpfr_clear (x); 1189 mpfr_clear (y); 1190 } 1191 1192 /* From a bug reported by Joseph S. Myers 1193 https://sympa.inria.fr/sympa/arc/mpfr/2012-08/msg00005.html */ 1194 static void 1195 bug20120814 (void) 1196 { 1197 mpfr_exp_t emin = -30, e; 1198 mpfr_t x, y; 1199 int r; 1200 char s[64], *p; 1201 1202 mpfr_init2 (x, 2); 1203 mpfr_set_ui_2exp (x, 3, emin - 2, MPFR_RNDN); 1204 mpfr_get_str (s + 1, &e, 10, 19, x, MPFR_RNDD); 1205 s[0] = s[1]; 1206 s[1] = '.'; 1207 for (p = s; *p != 0; p++) ; 1208 *p = 'e'; 1209 sprintf (p + 1, "%d", (int) e - 1); 1210 1211 mpfr_init2 (y, 4); 1212 r = mpfr_strtofr (y, s, NULL, 0, MPFR_RNDN); 1213 if (r <= 0 || ! mpfr_equal_p (x, y)) 1214 { 1215 printf ("Error in bug20120814\n"); 1216 printf ("mpfr_strtofr failed on string \"%s\"\n", s); 1217 printf ("Expected inex > 0 and y = 0.1100E%d\n", (int) emin); 1218 printf ("Got inex = %-6d and y = ", r); 1219 mpfr_dump (y); 1220 exit (1); 1221 } 1222 1223 mpfr_clear (x); 1224 mpfr_clear (y); 1225 } 1226 1227 static void 1228 bug20120829 (void) 1229 { 1230 mpfr_t x1, x2, e; 1231 int inex1, inex2, i, r; 1232 char s[48] = "1e-1"; 1233 1234 mpfr_init2 (e, 128); 1235 mpfr_inits2 (4, x1, x2, (mpfr_ptr) 0); 1236 1237 inex1 = mpfr_set_si (e, -1, MPFR_RNDN); 1238 MPFR_ASSERTN (inex1 == 0); 1239 1240 for (i = 1; i <= sizeof(s) - 5; i++) 1241 { 1242 s[3+i] = '0'; 1243 s[4+i] = 0; 1244 inex1 = mpfr_mul_ui (e, e, 10, MPFR_RNDN); 1245 MPFR_ASSERTN (inex1 == 0); 1246 RND_LOOP_NO_RNDF (r) 1247 { 1248 mpfr_rnd_t rnd = (mpfr_rnd_t) r; 1249 1250 inex1 = mpfr_exp10 (x1, e, rnd); 1251 inex1 = VSIGN (inex1); 1252 inex2 = mpfr_strtofr (x2, s, NULL, 0, rnd); 1253 inex2 = VSIGN (inex2); 1254 /* On 32-bit machines, for i = 7, r8389, r8391 and r8394 do: 1255 strtofr.c:...: MPFR assertion failed: cy == 0 1256 r8396 is OK. 1257 On 64-bit machines, for i = 15, 1258 r8389 does: strtofr.c:678: MPFR assertion failed: err < (64 - 0) 1259 r8391 does: strtofr.c:680: MPFR assertion failed: h < ysize 1260 r8394 and r8396 are OK. 1261 */ 1262 if (! mpfr_equal_p (x1, x2) || inex1 != inex2) 1263 { 1264 printf ("Error in bug20120829 for i = %d, rnd = %s\n", 1265 i, mpfr_print_rnd_mode (rnd)); 1266 printf ("Expected inex = %d, x = ", inex1); 1267 mpfr_dump (x1); 1268 printf ("Got inex = %d, x = ", inex2); 1269 mpfr_dump (x2); 1270 exit (1); 1271 } 1272 } 1273 } 1274 1275 mpfr_clears (e, x1, x2, (mpfr_ptr) 0); 1276 } 1277 1278 /* https://sympa.inria.fr/sympa/arc/mpfr/2016-12/msg00043.html 1279 mpfr_strtofr can return an incorrect ternary value. 1280 Note: As a consequence, the value can also be incorrect if the current 1281 exponent range is not the maximum one (since the ternary value is used 1282 to resolve double rounding in mpfr_check_range); this can happen only 1283 if the value is a midpoint between 0 and the minimum positive number 1284 or the opposite. */ 1285 static void 1286 bug20161217 (void) 1287 { 1288 mpfr_t fp, z; 1289 static const char * num = "0.1387778780781445675529539585113525390625e31"; 1290 /* The above number is 5^47/2^9. */ 1291 int inex; 1292 1293 mpfr_init2 (fp, 110); 1294 mpfr_init2 (z, 110); 1295 1296 inex = mpfr_strtofr (fp, num, NULL, 10, MPFR_RNDN); 1297 MPFR_ASSERTN(inex == 0); 1298 mpfr_set_str_binary (z, "10001100001000010011110110011101101001010000001011011110010001010100010100100110111101000010001011001100001101E-9"); 1299 MPFR_ASSERTN(mpfr_equal_p (fp, z)); 1300 1301 /* try with 109 bits */ 1302 mpfr_set_prec (fp, 109); 1303 inex = mpfr_strtofr (fp, num, NULL, 10, MPFR_RNDN); 1304 MPFR_ASSERTN(inex < 0); 1305 mpfr_set_str_binary (z, "10001100001000010011110110011101101001010000001011011110010001010100010100100110111101000010001011001100001100E-9"); 1306 MPFR_ASSERTN(mpfr_equal_p (fp, z)); 1307 1308 mpfr_clear (fp); 1309 mpfr_clear (z); 1310 } 1311 1312 /* check bug in MPFR 3.1.5 is fixed: cf 1313 https://sympa.inria.fr/sympa/arc/mpfr/2017-03/msg00009.html 1314 Note: same bug as bug20161217. See also the comments of bug20161217; 1315 here, this is a case where the value is incorrect. */ 1316 static void 1317 bug20170308 (void) 1318 { 1319 mpfr_exp_t emin; 1320 /* the following is slightly larger than 2^-1075, thus should be rounded 1321 to 0.5*2^-1074, with ternary value < 0 */ 1322 char str[] = "2.47032822920623272089E-324"; 1323 mpfr_t z; 1324 int inex; 1325 1326 emin = mpfr_get_emin (); 1327 mpfr_init2 (z, 53); 1328 set_emin (-1073); 1329 /* with emin = -1073, the smallest positive number is 0.5*2^emin = 2^(-1074), 1330 thus str should be rounded to 2^(-1074) with inex > 0 */ 1331 inex = mpfr_strtofr (z, str, NULL, 10, MPFR_RNDN); 1332 MPFR_ASSERTN(inex > 0 && mpfr_cmp_ui_2exp (z, 1, -1074) == 0); 1333 set_emin (-1074); 1334 /* with emin = -1074, str should be rounded to 2^(-1075) with inex < 0 */ 1335 inex = mpfr_strtofr (z, str, NULL, 10, MPFR_RNDN); 1336 MPFR_ASSERTN(inex < 0 && mpfr_cmp_ui_2exp (z, 1, -1075) == 0); 1337 mpfr_clear (z); 1338 set_emin (emin); 1339 } 1340 1341 /* r13299 fails with 8-bit limbs (micro-gmp/8). */ 1342 static void 1343 bug20181127 (void) 1344 { 1345 char s[] = "9.Z6nrLVSMG1bDcCF2ONJdX@-183295525"; /* base 58 */ 1346 mpfr_t x, y; 1347 1348 mpfr_inits2 (6, x, y, (mpfr_ptr) 0); 1349 mpfr_set_ui_2exp (x, 5, -1073741701, MPFR_RNDN); 1350 mpfr_strtofr (y, s, NULL, 58, MPFR_RNDZ); 1351 if (! mpfr_equal_p (x, y)) 1352 { 1353 printf ("Error in bug20181127 on %s (base 58)\n", s); 1354 printf ("Expected x = "); 1355 mpfr_dump (x); 1356 printf ("Got y = "); 1357 mpfr_dump (y); 1358 printf ("*Note* In base 58, x ~= "); 1359 mpfr_out_str (stdout, 58, 8, x, MPFR_RNDN); 1360 printf ("\n"); 1361 exit (1); 1362 } 1363 mpfr_clears (x, y, (mpfr_ptr) 0); 1364 } 1365 1366 static void 1367 coverage (void) 1368 { 1369 #if _MPFR_EXP_FORMAT >= 3 && _MPFR_PREC_FORMAT == 3 && MPFR_PREC_BITS == 64 1370 char str3[] = "1@-2112009130072406892"; 1371 char str31[] = "1@-511170973314085831"; 1372 mpfr_t x; 1373 int inex; 1374 mpfr_exp_t emin; 1375 1376 /* exercise assertion cy == 0 around line 698 of strtofr.c */ 1377 emin = mpfr_get_emin (); 1378 set_emin (mpfr_get_emin_min ()); 1379 /* emin = -4611686018427387903 on a 64-bit machine */ 1380 mpfr_init2 (x, 1); 1381 inex = mpfr_strtofr (x, str3, NULL, 3, MPFR_RNDN); 1382 /* 3^-2112009130072406892 is slightly larger than (2^64)^-52303988630398057 1383 thus we should get inex < 0 */ 1384 MPFR_ASSERTN(inex < 0); 1385 MPFR_ASSERTN(mpfr_cmp_ui_2exp (x, 1, -52303988630398057 * 64) == 0); 1386 inex = mpfr_strtofr (x, str31, NULL, 31, MPFR_RNDN); 1387 /* 31^-511170973314085831 is slightly smaller than (2^64)^-39569396093273623 1388 thus we should get inex > 0 */ 1389 MPFR_ASSERTN(inex > 0); 1390 MPFR_ASSERTN(mpfr_cmp_ui_2exp (x, 1, -39569396093273623 * 64) == 0); 1391 mpfr_clear (x); 1392 set_emin (emin); 1393 #endif 1394 } 1395 1396 #define BSIZE 512 1397 1398 static void 1399 random_tests (void) 1400 { 1401 char s0[BSIZE], s1[BSIZE], s2[BSIZE+64]; 1402 mpfr_t x0, x1, x2; 1403 int prec, i; 1404 1405 for (prec = MPFR_PREC_MIN; prec < 300; prec++) 1406 { 1407 mpfr_inits2 (prec, x0, x1, x2, (mpfr_ptr) 0); 1408 1409 for (i = 0; i < 20; i++) 1410 { 1411 const char *num_to_text; 1412 mpfr_exp_t e0, e1; 1413 int base, j, k, neg; 1414 int noteq = 0; 1415 char d; 1416 1417 /* We want the same exponent for x0 and its successor x1. 1418 This is not possible for precision 1 in base 2. */ 1419 do 1420 base = 2 + (randlimb () % 61); 1421 while (prec == 1 && base == 2); 1422 1423 num_to_text = base <= 36 ? num_to_text36 : num_to_text62; 1424 1425 do 1426 { 1427 /* Let's consider only positive numbers. We should test 1428 negative numbers, but they should be built later, just 1429 for the test itself. */ 1430 tests_default_random (x0, 0, 1431 mpfr_get_emin (), mpfr_get_emax (), 1); 1432 mpfr_set (x1, x0, MPFR_RNDN); 1433 mpfr_nextabove (x1); 1434 mpfr_get_str (s0, &e0, base, BSIZE - 1, x0, MPFR_RNDU); 1435 mpfr_get_str (s1, &e1, base, BSIZE - 1, x1, MPFR_RNDD); 1436 } 1437 while (! (mpfr_regular_p (x0) && mpfr_regular_p (x1) && e0 == e1)); 1438 1439 /* 0 < x0 <= (s0,e) <= (s1,e) <= x1 with e = e0 = e1. 1440 Let's build a string s2 randomly formed by: 1441 - the common prefix of s0 and s1; 1442 - some of the following digits of s0 (possibly none); 1443 - the next digit of s0 + 1; 1444 - some of the following digits of s1 (possibly none). 1445 Then 0 < x0 <= (s0,e) < (s2,e) <= (s1,e) <= x1, and with 1446 a very high probability that (s2,e) < (s1,e); noteq is 1447 set to true in this case. 1448 For instance, if: 1449 s0 = 123456789 1450 s1 = 124012345 1451 one can have, e.g.: 1452 s2 = 12345734 1453 s2 = 123556789 1454 s2 = 124 1455 s2 = 124012 1456 s2 is not taken completely randomly between s0 and s1, but it 1457 will be built rather easily, and with the randomness of x0, 1458 we should cover all cases, with s2 very close to s0, s2 very 1459 close to s1, or not too close to either. */ 1460 1461 neg = RAND_BOOL (); 1462 s2[0] = neg ? '-' : '+'; 1463 s2[1] = '.'; 1464 1465 for (j = 0; 1466 MPFR_ASSERTN (s0[j] != 0 && s1[j] != 0), s0[j] == s1[j]; 1467 j++) 1468 s2[j+2] = s0[j]; 1469 1470 /* k is the position of the first differing digit. */ 1471 k = j; 1472 1473 while (j < BSIZE - 2 && randlimb () % 8 != 0) 1474 { 1475 MPFR_ASSERTN (s0[j] != 0); 1476 s2[j+2] = s0[j]; 1477 j++; 1478 } 1479 1480 MPFR_ASSERTN (s0[j] != 0); 1481 /* We will increment the next digit. Thus while s0[j] is the 1482 maximum digit, go back until this is no longer the case 1483 (the first digit after the common prefix cannot be the 1484 maximum digit, so that we will stop early enough). */ 1485 while ((d = s0[j]) == num_to_text[base - 1]) 1486 j--; 1487 noteq = j != k; 1488 s2[j+2] = d = *(strchr (num_to_text, d) + 1); 1489 if (d != s1[j]) 1490 noteq = 1; 1491 j++; 1492 1493 while (j < BSIZE - 1 && randlimb () % 8 != 0) 1494 { 1495 MPFR_ASSERTN (s1[j] != 0); 1496 s2[j+2] = s1[j]; 1497 j++; 1498 } 1499 1500 sprintf (s2 + (j+2), "@%" MPFR_EXP_FSPEC "d", (mpfr_eexp_t) e0); 1501 1502 while (noteq == 0 && j < BSIZE - 1) 1503 { 1504 if (s1[j] != '0') 1505 noteq = 1; 1506 j++; 1507 } 1508 1509 if (neg) 1510 { 1511 mpfr_neg (x0, x0, MPFR_RNDN); 1512 mpfr_neg (x1, x1, MPFR_RNDN); 1513 } 1514 1515 if (noteq) 1516 { 1517 mpfr_strtofr (x2, s2, NULL, base, MPFR_RNDZ); 1518 if (! mpfr_equal_p (x2, x0)) 1519 { 1520 printf ("Error in random_tests for prec=%d i=%d base=%d\n", 1521 prec, i, base); 1522 printf ("s0 = %s\ns1 = %s\ns2 = %s\n", s0, s1, s2); 1523 printf ("x0 = "); 1524 mpfr_dump (x0); 1525 printf ("x2 = "); 1526 mpfr_dump (x2); 1527 exit (1); 1528 } 1529 } 1530 1531 mpfr_strtofr (x2, s2, NULL, base, MPFR_RNDA); 1532 if (! mpfr_equal_p (x2, x1)) 1533 { 1534 printf ("Error in random_tests for prec=%d i=%d base=%d\n", 1535 prec, i, base); 1536 printf ("s0 = %s\ns1 = %s\ns2 = %s\n", s0, s1, s2); 1537 printf ("x1 = "); 1538 mpfr_dump (x1); 1539 printf ("x2 = "); 1540 mpfr_dump (x2); 1541 exit (1); 1542 } 1543 } 1544 mpfr_clears (x0, x1, x2, (mpfr_ptr) 0); 1545 } 1546 } 1547 1548 int 1549 main (int argc, char *argv[]) 1550 { 1551 tests_start_mpfr (); 1552 1553 coverage (); 1554 check_special(); 1555 check_reftable (); 1556 check_parse (); 1557 check_overflow (); 1558 check_retval (); 1559 bug20081028 (); 1560 test20100310 (); 1561 bug20120814 (); 1562 bug20120829 (); 1563 bug20161217 (); 1564 bug20170308 (); 1565 bug20181127 (); 1566 random_tests (); 1567 1568 tests_end_mpfr (); 1569 return 0; 1570 } 1571