]>
git.saurik.com Git - apple/javascriptcore.git/blob - wtf/MathExtras.h
2 * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
13 * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 #ifndef WTF_MathExtras_h
27 #define WTF_MathExtras_h
37 #include <sys/types.h>
38 #include <machine/ieee.h>
56 const double piDouble
= 3.14159265358979323846;
57 const float piFloat
= 3.14159265358979323846f
;
59 const double piDouble
= M_PI
;
60 const float piFloat
= static_cast<float>(M_PI
);
64 const double piOverFourDouble
= 0.785398163397448309616;
65 const float piOverFourFloat
= 0.785398163397448309616f
;
67 const double piOverFourDouble
= M_PI_4
;
68 const float piOverFourFloat
= static_cast<float>(M_PI_4
);
73 // Work around a bug in the Mac OS X libc where ceil(-0.1) return +0.
74 inline double wtf_ceil(double x
) { return copysign(ceil(x
), x
); }
76 #define ceil(x) wtf_ceil(x)
83 inline bool isfinite(double x
) { return finite(x
) && !isnand(x
); }
86 inline bool isinf(double x
) { return !finite(x
) && !isnand(x
); }
89 inline bool signbit(double x
) { return x
< 0.0; } // FIXME: Wrong for negative 0.
97 inline bool isfinite(double x
) { return finite(x
); }
100 inline bool signbit(double x
) { struct ieee_double
*p
= (struct ieee_double
*)&x
; return p
->dbl_sign
; }
105 #if COMPILER(MSVC) || COMPILER(RVCT)
107 inline long lround(double num
) { return static_cast<long>(num
> 0 ? num
+ 0.5 : ceil(num
- 0.5)); }
108 inline long lroundf(float num
) { return static_cast<long>(num
> 0 ? num
+ 0.5f
: ceilf(num
- 0.5f
)); }
109 inline double round(double num
) { return num
> 0 ? floor(num
+ 0.5) : ceil(num
- 0.5); }
110 inline float roundf(float num
) { return num
> 0 ? floorf(num
+ 0.5f
) : ceilf(num
- 0.5f
); }
111 inline double trunc(double num
) { return num
> 0 ? floor(num
) : ceil(num
); }
117 inline bool isinf(double num
) { return !_finite(num
) && !_isnan(num
); }
118 inline bool isnan(double num
) { return !!_isnan(num
); }
119 inline bool signbit(double num
) { return _copysign(1.0, num
) < 0; }
121 inline double nextafter(double x
, double y
) { return _nextafter(x
, y
); }
122 inline float nextafterf(float x
, float y
) { return x
> y
? x
- FLT_EPSILON
: x
+ FLT_EPSILON
; }
124 inline double copysign(double x
, double y
) { return _copysign(x
, y
); }
125 inline int isfinite(double x
) { return _finite(x
); }
127 // Work around a bug in Win, where atan2(+-infinity, +-infinity) yields NaN instead of specific values.
128 inline double wtf_atan2(double x
, double y
)
130 double posInf
= std::numeric_limits
<double>::infinity();
131 double negInf
= -std::numeric_limits
<double>::infinity();
132 double nan
= std::numeric_limits
<double>::quiet_NaN();
136 if (x
== posInf
&& y
== posInf
)
137 result
= piOverFourDouble
;
138 else if (x
== posInf
&& y
== negInf
)
139 result
= 3 * piOverFourDouble
;
140 else if (x
== negInf
&& y
== posInf
)
141 result
= -piOverFourDouble
;
142 else if (x
== negInf
&& y
== negInf
)
143 result
= -3 * piOverFourDouble
;
145 result
= ::atan2(x
, y
);
150 // Work around a bug in the Microsoft CRT, where fmod(x, +-infinity) yields NaN instead of x.
151 inline double wtf_fmod(double x
, double y
) { return (!isinf(x
) && isinf(y
)) ? x
: fmod(x
, y
); }
153 // Work around a bug in the Microsoft CRT, where pow(NaN, 0) yields NaN instead of 1.
154 inline double wtf_pow(double x
, double y
) { return y
== 0 ? 1 : pow(x
, y
); }
156 #define atan2(x, y) wtf_atan2(x, y)
157 #define fmod(x, y) wtf_fmod(x, y)
158 #define pow(x, y) wtf_pow(x, y)
160 #endif // COMPILER(MSVC)
162 inline double deg2rad(double d
) { return d
* piDouble
/ 180.0; }
163 inline double rad2deg(double r
) { return r
* 180.0 / piDouble
; }
164 inline double deg2grad(double d
) { return d
* 400.0 / 360.0; }
165 inline double grad2deg(double g
) { return g
* 360.0 / 400.0; }
166 inline double turn2deg(double t
) { return t
* 360.0; }
167 inline double deg2turn(double d
) { return d
/ 360.0; }
168 inline double rad2grad(double r
) { return r
* 200.0 / piDouble
; }
169 inline double grad2rad(double g
) { return g
* piDouble
/ 200.0; }
171 inline float deg2rad(float d
) { return d
* piFloat
/ 180.0f
; }
172 inline float rad2deg(float r
) { return r
* 180.0f
/ piFloat
; }
173 inline float deg2grad(float d
) { return d
* 400.0f
/ 360.0f
; }
174 inline float grad2deg(float g
) { return g
* 360.0f
/ 400.0f
; }
175 inline float turn2deg(float t
) { return t
* 360.0f
; }
176 inline float deg2turn(float d
) { return d
/ 360.0f
; }
177 inline float rad2grad(float r
) { return r
* 200.0f
/ piFloat
; }
178 inline float grad2rad(float g
) { return g
* piFloat
/ 200.0f
; }
180 #endif // #ifndef WTF_MathExtras_h