ViewVC Help
View File | Revision Log | Show Annotations | Download File | View Changeset | Root Listing
root/src/trunk/lib/msun/src/e_log10.c
Revision: 10591
Committed: Sat Jun 9 15:08:31 2018 UTC (5 years, 10 months ago) by laffer1
Content type: text/plain
File size: 2652 byte(s)
Log Message:
sync src

File Contents

# Content
1 /* $MidnightBSD$ */
2
3 /* @(#)e_log10.c 1.3 95/01/18 */
4 /*
5 * ====================================================
6 * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved.
7 *
8 * Developed at SunSoft, a Sun Microsystems, Inc. business.
9 * Permission to use, copy, modify, and distribute this
10 * software is freely granted, provided that this notice
11 * is preserved.
12 * ====================================================
13 */
14
15 #include <sys/cdefs.h>
16 __FBSDID("$FreeBSD: stable/10/lib/msun/src/e_log10.c 251292 2013-06-03 09:14:31Z das $");
17
18 /*
19 * Return the base 10 logarithm of x. See e_log.c and k_log.h for most
20 * comments.
21 *
22 * log10(x) = (f - 0.5*f*f + k_log1p(f)) / ln10 + k * log10(2)
23 * in not-quite-routine extra precision.
24 */
25
26 #include <float.h>
27
28 #include "math.h"
29 #include "math_private.h"
30 #include "k_log.h"
31
32 static const double
33 two54 = 1.80143985094819840000e+16, /* 0x43500000, 0x00000000 */
34 ivln10hi = 4.34294481878168880939e-01, /* 0x3fdbcb7b, 0x15200000 */
35 ivln10lo = 2.50829467116452752298e-11, /* 0x3dbb9438, 0xca9aadd5 */
36 log10_2hi = 3.01029995663611771306e-01, /* 0x3FD34413, 0x509F6000 */
37 log10_2lo = 3.69423907715893078616e-13; /* 0x3D59FEF3, 0x11F12B36 */
38
39 static const double zero = 0.0;
40 static volatile double vzero = 0.0;
41
42 double
43 __ieee754_log10(double x)
44 {
45 double f,hfsq,hi,lo,r,val_hi,val_lo,w,y,y2;
46 int32_t i,k,hx;
47 u_int32_t lx;
48
49 EXTRACT_WORDS(hx,lx,x);
50
51 k=0;
52 if (hx < 0x00100000) { /* x < 2**-1022 */
53 if (((hx&0x7fffffff)|lx)==0)
54 return -two54/vzero; /* log(+-0)=-inf */
55 if (hx<0) return (x-x)/zero; /* log(-#) = NaN */
56 k -= 54; x *= two54; /* subnormal number, scale up x */
57 GET_HIGH_WORD(hx,x);
58 }
59 if (hx >= 0x7ff00000) return x+x;
60 if (hx == 0x3ff00000 && lx == 0)
61 return zero; /* log(1) = +0 */
62 k += (hx>>20)-1023;
63 hx &= 0x000fffff;
64 i = (hx+0x95f64)&0x100000;
65 SET_HIGH_WORD(x,hx|(i^0x3ff00000)); /* normalize x or x/2 */
66 k += (i>>20);
67 y = (double)k;
68 f = x - 1.0;
69 hfsq = 0.5*f*f;
70 r = k_log1p(f);
71
72 /* See e_log2.c for most details. */
73 hi = f - hfsq;
74 SET_LOW_WORD(hi,0);
75 lo = (f - hi) - hfsq + r;
76 val_hi = hi*ivln10hi;
77 y2 = y*log10_2hi;
78 val_lo = y*log10_2lo + (lo+hi)*ivln10lo + lo*ivln10hi;
79
80 /*
81 * Extra precision in for adding y*log10_2hi is not strictly needed
82 * since there is no very large cancellation near x = sqrt(2) or
83 * x = 1/sqrt(2), but we do it anyway since it costs little on CPUs
84 * with some parallelism and it reduces the error for many args.
85 */
86 w = y2 + val_hi;
87 val_lo += (y2 - w) + val_hi;
88 val_hi = w;
89
90 return val_lo + val_hi;
91 }
92
93 #if (LDBL_MANT_DIG == 53)
94 __weak_reference(log10, log10l);
95 #endif

Properties

Name Value
svn:keywords MidnightBSD=%H