1*c9945492SAndroid Build Coastguard Worker #include <math.h> 2*c9945492SAndroid Build Coastguard Worker #include <stdint.h> 3*c9945492SAndroid Build Coastguard Worker scalbn(double x,int n)4*c9945492SAndroid Build Coastguard Workerdouble scalbn(double x, int n) 5*c9945492SAndroid Build Coastguard Worker { 6*c9945492SAndroid Build Coastguard Worker union {double f; uint64_t i;} u; 7*c9945492SAndroid Build Coastguard Worker double_t y = x; 8*c9945492SAndroid Build Coastguard Worker 9*c9945492SAndroid Build Coastguard Worker if (n > 1023) { 10*c9945492SAndroid Build Coastguard Worker y *= 0x1p1023; 11*c9945492SAndroid Build Coastguard Worker n -= 1023; 12*c9945492SAndroid Build Coastguard Worker if (n > 1023) { 13*c9945492SAndroid Build Coastguard Worker y *= 0x1p1023; 14*c9945492SAndroid Build Coastguard Worker n -= 1023; 15*c9945492SAndroid Build Coastguard Worker if (n > 1023) 16*c9945492SAndroid Build Coastguard Worker n = 1023; 17*c9945492SAndroid Build Coastguard Worker } 18*c9945492SAndroid Build Coastguard Worker } else if (n < -1022) { 19*c9945492SAndroid Build Coastguard Worker /* make sure final n < -53 to avoid double 20*c9945492SAndroid Build Coastguard Worker rounding in the subnormal range */ 21*c9945492SAndroid Build Coastguard Worker y *= 0x1p-1022 * 0x1p53; 22*c9945492SAndroid Build Coastguard Worker n += 1022 - 53; 23*c9945492SAndroid Build Coastguard Worker if (n < -1022) { 24*c9945492SAndroid Build Coastguard Worker y *= 0x1p-1022 * 0x1p53; 25*c9945492SAndroid Build Coastguard Worker n += 1022 - 53; 26*c9945492SAndroid Build Coastguard Worker if (n < -1022) 27*c9945492SAndroid Build Coastguard Worker n = -1022; 28*c9945492SAndroid Build Coastguard Worker } 29*c9945492SAndroid Build Coastguard Worker } 30*c9945492SAndroid Build Coastguard Worker u.i = (uint64_t)(0x3ff+n)<<52; 31*c9945492SAndroid Build Coastguard Worker x = y * u.f; 32*c9945492SAndroid Build Coastguard Worker return x; 33*c9945492SAndroid Build Coastguard Worker } 34