Skip to content

Commit d1fb7b4

Browse files
author
fdedinec
committed
better correction of the bug found by Morten Welinder
1 parent d4ce63b commit d1fb7b4

File tree

1 file changed

+47
-52
lines changed

1 file changed

+47
-52
lines changed

expm1.c

+47-52
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
* Correctly rounded expm1 = e^x - 1
33
*
44
* Author : Christoph Lauter (ENS Lyon)
5+
* One bug fix by Florent de Dinechin
56
*
67
* This file is part of the crlibm library developed by the Arenaire
78
* project at Ecole Normale Superieure de Lyon
@@ -230,7 +231,7 @@ void expm1_common_td(double *expm1h, double *expm1m, double *expm1l,
230231
expm = polyWithTablesmdb.d;
231232
expl = polyWithTablesldb.d;
232233

233-
/* Substraction of -1
234+
/* Subtraction of -1
234235
235236
We use a conditional Add133
236237
*/
@@ -245,7 +246,7 @@ void expm1_common_td(double *expm1h, double *expm1m, double *expm1l,
245246

246247

247248
double expm1_rn(double x) {
248-
db_number xdb, shiftedXMultdb, twoToM;
249+
db_number xdb, shiftedXMultdb, polyTblhdb, polyTblmdb;
249250
int xIntHi, expoX, k, M, index1, index2;
250251
double highPoly, tt1h, t1h, t1l, xSqh, xSql, xSqHalfh, xSqHalfl, xCubeh, xCubel, t2h, t2l, templ, tt3h, tt3l;
251252
double polyh, polyl, expm1h, expm1m, expm1l;
@@ -499,36 +500,23 @@ double expm1_rn(double x) {
499500

500501
Add12(t11,t12,tablesh,t10);
501502
t13 = t12 + tablesl;
502-
Add12(exph,expm, t11,t13);
503+
Add12(polyTblhdb.d,polyTblmdb.d,t11,t13);
503504

504505
/* Reconstruction: multiplication by 2^M */
505506

507+
/* Implement the multiplication by addition to overcome the
508+
problem of the non-representability of 2^1024 (M = 1024)
509+
This case is possible if polyTblhdb.d < 1
510+
*/
506511

507-
/* Bug found by Morten Welinder, tanks to him:
508-
The multiplication was implemented as
509-
510-
polyTblhdb.i[HI] += M << 20;
512+
polyTblhdb.i[HI] += M << 20;
513+
if(polyTblmdb.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
511514
polyTblmdb.i[HI] += M << 20;
512515

513-
(where polyTblh/l were dbnumber versions of exph and expm)
514-
515-
polyTblh is under control, but he found one case where polyTblm is zero
516-
(for x=-4.1588039009762204 and a few neighbouring values)
517-
In this case M=-6, and adding -6 to the 0 exponent gives a very large value.
518-
519-
Anyway the version fixed here is barely slower.
520-
521-
*/
522-
523-
/* build 2^M -- let's hope the compiler schedules it early enough */
524-
525-
twoToM.i[HI] = 0x3FF00000 + (M << 20);
526-
twoToM.i[LO] = 0;
527-
528-
exph *= twoToM.d;
529-
expm *= twoToM.d;
516+
exph = polyTblhdb.d;
517+
expm = polyTblmdb.d;
530518

531-
/* Substraction of 1
519+
/* Subtraction of 1
532520
533521
Testing if the operation is necessary is more expensive than
534522
performing it in any case.
@@ -537,7 +525,7 @@ double expm1_rn(double x) {
537525
arguments 1/4 <= x <= ln(2) (0.25 <= x <= 0.69)
538526
We must therefore use conditional Add12s
539527
540-
Since we perform a substraction, we may not have addition overflow towards +inf
528+
Since we perform a subtraction, we may not have addition overflow towards +inf
541529
542530
*/
543531

@@ -836,18 +824,19 @@ double expm1_rd(double x) {
836824

837825
/* Reconstruction: multiplication by 2^M */
838826

839-
/* Implement the multiplication by multiplication to overcome the
827+
/* Implement the multiplication by addition to overcome the
840828
problem of the non-representability of 2^1024 (M = 1024)
841829
This case is possible if polyTblhdb.d < 1
842830
*/
843831

844832
polyTblhdb.i[HI] += M << 20;
845-
polyTblmdb.i[HI] += M << 20;
833+
if(polyTblmdb.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
834+
polyTblmdb.i[HI] += M << 20;
846835

847836
exph = polyTblhdb.d;
848837
expm = polyTblmdb.d;
849838

850-
/* Substraction of 1
839+
/* Subtraction of 1
851840
852841
Testing if the operation is necessary is more expensive than
853842
performing it in any case.
@@ -856,7 +845,7 @@ double expm1_rd(double x) {
856845
arguments 1/4 <= x <= ln(2) (0.25 <= x <= 0.69)
857846
We must therefore use conditional Add12s
858847
859-
Since we perform a substraction, we may not have addition overflow towards +inf
848+
Since we perform a subtraction, we may not have addition overflow towards +inf
860849
861850
*/
862851

@@ -1160,18 +1149,19 @@ double expm1_ru(double x) {
11601149

11611150
/* Reconstruction: multiplication by 2^M */
11621151

1163-
/* Implement the multiplication by multiplication to overcome the
1152+
/* Implement the multiplication by addition to overcome the
11641153
problem of the non-representability of 2^1024 (M = 1024)
11651154
This case is possible if polyTblhdb.d < 1
11661155
*/
11671156

11681157
polyTblhdb.i[HI] += M << 20;
1169-
polyTblmdb.i[HI] += M << 20;
1158+
if(polyTblmdb.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
1159+
polyTblmdb.i[HI] += M << 20;
11701160

11711161
exph = polyTblhdb.d;
11721162
expm = polyTblmdb.d;
11731163

1174-
/* Substraction of 1
1164+
/* Subtraction of 1
11751165
11761166
Testing if the operation is necessary is more expensive than
11771167
performing it in any case.
@@ -1180,7 +1170,7 @@ double expm1_ru(double x) {
11801170
arguments 1/4 <= x <= ln(2) (0.25 <= x <= 0.69)
11811171
We must therefore use conditional Add12s
11821172
1183-
Since we perform a substraction, we may not have addition overflow towards +inf
1173+
Since we perform a subtraction, we may not have addition overflow towards +inf
11841174
11851175
*/
11861176

@@ -1492,18 +1482,19 @@ double expm1_rz(double x) {
14921482

14931483
/* Reconstruction: multiplication by 2^M */
14941484

1495-
/* Implement the multiplication by multiplication to overcome the
1485+
/* Implement the multiplication by addition to overcome the
14961486
problem of the non-representability of 2^1024 (M = 1024)
14971487
This case is possible if polyTblhdb.d < 1
14981488
*/
14991489

1500-
polyTblhdb.i[HI] += M << 20;
1501-
polyTblmdb.i[HI] += M << 20;
1490+
polyTblhdb.i[HI] += M << 20;
1491+
if(polyTblmdb.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
1492+
polyTblmdb.i[HI] += M << 20;
15021493

15031494
exph = polyTblhdb.d;
15041495
expm = polyTblmdb.d;
15051496

1506-
/* Substraction of 1
1497+
/* Subtraction of 1
15071498
15081499
Testing if the operation is necessary is more expensive than
15091500
performing it in any case.
@@ -1512,7 +1503,7 @@ double expm1_rz(double x) {
15121503
arguments 1/4 <= x <= ln(2) (0.25 <= x <= 0.69)
15131504
We must therefore use conditional Add12s
15141505
1515-
Since we perform a substraction, we may not have addition overflow towards +inf
1506+
Since we perform a subtraction, we may not have addition overflow towards +inf
15161507
15171508
*/
15181509

@@ -2207,22 +2198,24 @@ interval j_expm1(interval x)
22072198

22082199
/* Reconstruction: multiplication by 2^M */
22092200

2210-
/* Implement the multiplication by multiplication to overcome the
2201+
/* Implement the multiplication by addition to overcome the
22112202
problem of the non-representability of 2^1024 (M = 1024)
22122203
This case is possible if polyTblhdb.d < 1
22132204
*/
22142205

22152206
polyTblhdb_inf.i[HI] += M_inf << 20;
22162207
polyTblhdb_sup.i[HI] += M_sup << 20;
2217-
polyTblmdb_inf.i[HI] += M_inf << 20;
2218-
polyTblmdb_sup.i[HI] += M_sup << 20;
2208+
if(polyTblmdb_inf.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
2209+
polyTblmdb_inf.i[HI] += M_inf << 20;
2210+
if(polyTblmdb_sup.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
2211+
polyTblmdb_sup.i[HI] += M_sup << 20;
22192212

22202213
exph_inf = polyTblhdb_inf.d;
22212214
exph_sup = polyTblhdb_sup.d;
22222215
expm_inf = polyTblmdb_inf.d;
22232216
expm_sup = polyTblmdb_sup.d;
22242217

2225-
/* Substraction of 1
2218+
/* Subtraction of 1
22262219
22272220
Testing if the operation is necessary is more expensive than
22282221
performing it in any case.
@@ -2231,7 +2224,7 @@ interval j_expm1(interval x)
22312224
arguments 1/4 <= x <= ln(2) (0.25 <= x <= 0.69)
22322225
We must therefore use conditional Add12s
22332226
2234-
Since we perform a substraction, we may not have addition overflow towards +inf
2227+
Since we perform a subtraction, we may not have addition overflow towards +inf
22352228
22362229
*/
22372230

@@ -2348,18 +2341,19 @@ interval j_expm1(interval x)
23482341

23492342
/* Reconstruction: multiplication by 2^M */
23502343

2351-
/* Implement the multiplication by multiplication to overcome the
2344+
/* Implement the multiplication by addition to overcome the
23522345
problem of the non-representability of 2^1024 (M = 1024)
23532346
This case is possible if polyTblhdb.d < 1
23542347
*/
23552348

23562349
polyTblhdb_inf.i[HI] += M_inf << 20;
2357-
polyTblmdb_inf.i[HI] += M_inf << 20;
2350+
if(polyTblmdb_inf.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
2351+
polyTblmdb_inf.i[HI] += M_inf << 20;
23582352

23592353
exph_inf = polyTblhdb_inf.d;
23602354
expm_inf = polyTblmdb_inf.d;
23612355

2362-
/* Substraction of 1
2356+
/* Subtraction of 1
23632357
23642358
Testing if the operation is necessary is more expensive than
23652359
performing it in any case.
@@ -2368,7 +2362,7 @@ interval j_expm1(interval x)
23682362
arguments 1/4 <= x <= ln(2) (0.25 <= x <= 0.69)
23692363
We must therefore use conditional Add12s
23702364
2371-
Since we perform a substraction, we may not have addition overflow towards +inf
2365+
Since we perform a subtraction, we may not have addition overflow towards +inf
23722366
23732367
*/
23742368

@@ -2460,18 +2454,19 @@ interval j_expm1(interval x)
24602454

24612455
/* Reconstruction: multiplication by 2^M */
24622456

2463-
/* Implement the multiplication by multiplication to overcome the
2457+
/* Implement the multiplication by addition to overcome the
24642458
problem of the non-representability of 2^1024 (M = 1024)
24652459
This case is possible if polyTblhdb.d < 1
24662460
*/
24672461

24682462
polyTblhdb_sup.i[HI] += M_sup << 20;
2469-
polyTblmdb_sup.i[HI] += M_sup << 20;
2463+
if(polyTblmdb_sup.d!=0.0) /* predicted true, but it happens for x=-4.1588039009762204, thanks Morten */
2464+
polyTblmdb_sup.i[HI] += M_sup << 20;
24702465

24712466
exph_sup = polyTblhdb_sup.d;
24722467
expm_sup = polyTblmdb_sup.d;
24732468

2474-
/* Substraction of 1
2469+
/* Subtraction of 1
24752470
24762471
Testing if the operation is necessary is more expensive than
24772472
performing it in any case.
@@ -2480,7 +2475,7 @@ interval j_expm1(interval x)
24802475
arguments 1/4 <= x <= ln(2) (0.25 <= x <= 0.69)
24812476
We must therefore use conditional Add12s
24822477
2483-
Since we perform a substraction, we may not have addition overflow towards +inf
2478+
Since we perform a subtraction, we may not have addition overflow towards +inf
24842479
24852480
*/
24862481

0 commit comments

Comments
 (0)