------- Comment #16 from rob1weld at aol dot com 2007-06-13 07:53 ------- I did some testing on the CVS of crlibm, (it needs a few files from crlibm-1.0beta1.tar.gz).
The new docs list these interesting features: portable to any system implementing the ISO-C99 and IEEE-754 standards, correctly rounded in the four rounding modes, proven, both theoretically and in the implementation, and reasonably efficient in terms of performance (both average and worst-case) and resource usage, exploit fused multiply-and-add operators for the Itanium and PowerPC platforms. optimized for double precision arithmetic and float the subtleties of subnormal numbers are handled properly Compared with the best libraries crlibm offers a precision improvement of a fraction of a unit in the last place (ulp) in round to nearest mode but in the three other rounding modes (used in interval arithmetic) gains up to one ulp of precision in each computation. Results: GNU C Library 2.6 crlibm version 1.0beta1 GMP version 4.2.1 MPFR version 2.2.1-p5 min time avg time max time -------------- log -------------- default libm 65 204 1006 MPFR 155 17637 67921 CRLibm 35 127 896 -------------- exp -------------- default libm 151 154 164 MPFR 8951 11970 24460 CRLibm 215 222 1252 -------------- sin -------------- default libm 118 137 174 MPFR 9189 31276 85022 CRLibm 77 198 10513 -------------- cos -------------- default libm 116 136 177 MPFR 4065 21546 66963 CRLibm 69 203 9929 -------------- tan -------------- default libm 126 150 188 MPFR 12525 36528 93573 CRLibm 97 335 24587 -------------- asin -------------- default libm 257 270 278 MPFR 31985 104582 533268 CRLibm 69 319 2442 -------------- acos -------------- default libm 266 281 293 MPFR 32585 102440 533559 CRLibm 99 335 2435 -------------- atan -------------- default libm 178 192 197 MPFR 18172 35185 261762 CRLibm 101 265 11572 -------------- log10 -------------- default libm 67 206 1004 MPFR 157 39135 159891 CRLibm 38 326 1691 -------------- log2 -------------- default libm 68 212 1021 MPFR 155 21607 84683 CRLibm 38 327 1695 -------------- sinpi -------------- default libm 127 136 153 MPFR 12884 20203 70476 CRLibm 324 349 1242 -------------- cospi -------------- default libm 127 136 157 MPFR 8461 13748 37559 CRLibm 914 935 961 -------------- tanpi -------------- default libm 135 148 169 MPFR 15784 23623 59309 CRLibm 2340 2441 2479 The libm library is the least accurate and on average the fastest; though not fastest for every function instance. The most accurate is always CRLibm, sometimes it is fastest. The MPFR library is second most accurate and from 50 to over 300 times slower than CRLibm. Here are a few tests of transcendental functions using normal rounding: # ./crlibm_soaktest acos RN 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 275 failures out of 1000000 (ratio 2.750000e-04) # ./crlibm_soaktest acospi RN 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 17393 failures out of 1000000 (ratio 1.739300e-02) # ./crlibm_soaktest asin RN 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 5837 failures out of 1000000 (ratio 5.837000e-03) # ./crlibm_soaktest asinpi RN 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 252488 failures out of 1000000 (ratio 2.524880e-01) # ./crlibm_soaktest atan RN 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 220 failures out of 1000000 (ratio 2.200000e-04) # ./crlibm_soaktest atanpi RN 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 318734 failures out of 1000000 (ratio 3.187340e-01) # ./crlibm_soaktest cos RN 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 413003 failures out of 1000000 (ratio 4.130030e-01) Here is one example of testing the "cos" function with other roundings: # ./crlibm_soaktest cos RU 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 695290 failures out of 1000000 (ratio 6.952900e-01) # ./crlibm_soaktest cos RD 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 694636 failures out of 1000000 (ratio 6.946360e-01) # ./crlibm_soaktest cos RZ 1 | grep 1000000 CRLIBM : 0 failures out of 1000000 (ratio 0.000000e+00) LIBM : 695241 failures out of 1000000 (ratio 6.952410e-01) The libm library does better with normal rounding, in the other modes it is worse. Here is another compilation of paranoia. I replaced the "log" and "pow" functions with crlibm. The "sqrt" and "floor" are not implemented in crlibm so I used libm. # gcc -o paranoia_crlibm paranoia.c -Dlog=log_rn -Dpow=pow_rn -lcrlibm -lm # ./paranoia_crlibm ... No failures, defects nor flaws have been discovered. Rounding appears to conform to the proposed IEEE standard P754, except for possibly Double Rounding during Gradual Underflow. The arithmetic diagnosed appears to be Excellent! Considering the nasty command line used to compile the test it worked well. I'm going to see if I can make a patch that takes parts of glibc, fdlibm and _all_ of crlibm and uses it to replace all instances of "-lm" and "-lfdlibm" in gcc 4.3.0 after some more testing. Then we can have gcc provide the same (exactly correct to a part of a ulp) answer on any platform. The support for PowerPC and Itanium processors will appeal to some. The compilation time is a couple of minutes, the check tests perform many thousands of tests in seconds. I'm still reading the "proof". Note: "Proof" does NOT mean it passes "check tests" - "proof" means that there is a mechanical proof (computer program) that proves with advanced math that the algorithms are correct. This will improve our documentation where we make claims of IEEE 754 compatability (but don't offer it on all platforms). -- http://gcc.gnu.org/bugzilla/show_bug.cgi?id=32180