| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 72 return %Math_atan2(TO_NUMBER_INLINE(y), TO_NUMBER_INLINE(x)); | 72 return %Math_atan2(TO_NUMBER_INLINE(y), TO_NUMBER_INLINE(x)); |
| 73 } | 73 } |
| 74 | 74 |
| 75 // ECMA 262 - 15.8.2.6 | 75 // ECMA 262 - 15.8.2.6 |
| 76 function MathCeil(x) { | 76 function MathCeil(x) { |
| 77 return %Math_ceil(TO_NUMBER_INLINE(x)); | 77 return %Math_ceil(TO_NUMBER_INLINE(x)); |
| 78 } | 78 } |
| 79 | 79 |
| 80 // ECMA 262 - 15.8.2.7 | 80 // ECMA 262 - 15.8.2.7 |
| 81 function MathCos(x) { | 81 function MathCos(x) { |
| 82 return %_MathCos(TO_NUMBER_INLINE(x)); | 82 return MathCosImpl(x); |
| 83 } | 83 } |
| 84 | 84 |
| 85 // ECMA 262 - 15.8.2.8 | 85 // ECMA 262 - 15.8.2.8 |
| 86 function MathExp(x) { | 86 function MathExp(x) { |
| 87 return %Math_exp(TO_NUMBER_INLINE(x)); | 87 return %Math_exp(TO_NUMBER_INLINE(x)); |
| 88 } | 88 } |
| 89 | 89 |
| 90 // ECMA 262 - 15.8.2.9 | 90 // ECMA 262 - 15.8.2.9 |
| 91 function MathFloor(x) { | 91 function MathFloor(x) { |
| 92 x = TO_NUMBER_INLINE(x); | 92 x = TO_NUMBER_INLINE(x); |
| (...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 178 return %_RandomHeapNumber(); | 178 return %_RandomHeapNumber(); |
| 179 } | 179 } |
| 180 | 180 |
| 181 // ECMA 262 - 15.8.2.15 | 181 // ECMA 262 - 15.8.2.15 |
| 182 function MathRound(x) { | 182 function MathRound(x) { |
| 183 return %RoundNumber(TO_NUMBER_INLINE(x)); | 183 return %RoundNumber(TO_NUMBER_INLINE(x)); |
| 184 } | 184 } |
| 185 | 185 |
| 186 // ECMA 262 - 15.8.2.16 | 186 // ECMA 262 - 15.8.2.16 |
| 187 function MathSin(x) { | 187 function MathSin(x) { |
| 188 return %_MathSin(TO_NUMBER_INLINE(x)); | 188 return MathSinImpl(x); |
| 189 } | 189 } |
| 190 | 190 |
| 191 // ECMA 262 - 15.8.2.17 | 191 // ECMA 262 - 15.8.2.17 |
| 192 function MathSqrt(x) { | 192 function MathSqrt(x) { |
| 193 return %_MathSqrt(TO_NUMBER_INLINE(x)); | 193 return %_MathSqrt(TO_NUMBER_INLINE(x)); |
| 194 } | 194 } |
| 195 | 195 |
| 196 // ECMA 262 - 15.8.2.18 | 196 // ECMA 262 - 15.8.2.18 |
| 197 function MathTan(x) { | 197 function MathTan(x) { |
| 198 return %_MathTan(TO_NUMBER_INLINE(x)); | 198 return MathSinImpl(x) / MathCosImpl(x); |
| 199 } | 199 } |
| 200 | 200 |
| 201 // Non-standard extension. | 201 // Non-standard extension. |
| 202 function MathImul(x, y) { | 202 function MathImul(x, y) { |
| 203 return %NumberImul(TO_NUMBER_INLINE(x), TO_NUMBER_INLINE(y)); | 203 return %NumberImul(TO_NUMBER_INLINE(x), TO_NUMBER_INLINE(y)); |
| 204 } | 204 } |
| 205 | 205 |
| 206 | 206 |
| 207 var MathSinImpl = function(x) { |
| 208 InitTrigonometricFunctions(); |
| 209 return MathSinImpl(x); |
| 210 } |
| 211 |
| 212 |
| 213 var MathCosImpl = function(x) { |
| 214 InitTrigonometricFunctions(); |
| 215 return MathCosImpl(x); |
| 216 } |
| 217 |
| 218 |
| 219 function InitTrigonometricFunctions() { |
| 220 var samples = 2048; // Table size. |
| 221 var pi = 3.1415926535897932; |
| 222 var pi_half = pi / 2; |
| 223 var inverse_pi_half = 1 / pi_half; |
| 224 var two_pi = pi * 2; |
| 225 var interval = pi_half / samples; |
| 226 var inverse_interval = samples / pi_half; |
| 227 var table_sin = new global.Float64Array(samples + 2); |
| 228 var table_cos_interval = new global.Float64Array(samples + 2); |
| 229 |
| 230 %PopulateTrigonometricTable(table_sin, table_cos_interval, samples); |
| 231 |
| 232 // This implements the following algorithm. |
| 233 // 1) Multiplication takes care of to-number conversion. |
| 234 // 2) Reduce x to the first quadrant [0, pi/2]. |
| 235 // Conveniently enough, in case of +/-Infinity, we get NaN. |
| 236 // 3) Replace x by (pi/2-x) if x was in the 2nd or 4th quadrant. |
| 237 // 4) Do a table lookup for the closest samples to the left and right of x. |
| 238 // 5) Find the derivatives at those sampling points by table lookup: |
| 239 // dsin(x)/dx = cos(x) = sin(pi/2-x) for x in [0, pi/2]. |
| 240 // 6) Use cubic spline interpolation to approximate sin(x). |
| 241 // 7) Negate the result if x was in the 3rd or 4th quadrant. |
| 242 // 8) Get rid of -0 by adding 0. |
| 243 MathSinImpl = function(x) { |
| 244 var multiple = %_MathFloor(x * inverse_pi_half); |
| 245 x = (multiple & 1) * pi_half + |
| 246 (1 - ((multiple & 1) << 1)) * (x - multiple * pi_half); |
| 247 var double_index = x * inverse_interval; |
| 248 var index = double_index | 0; |
| 249 var t1 = double_index - index; |
| 250 var t2 = 1 - t1; |
| 251 var y1 = table_sin[index]; |
| 252 var y2 = table_sin[index + 1]; |
| 253 var dy = y2 - y1; |
| 254 return (t2 * y1 + t1 * y2 + |
| 255 t1 * t2 * ((table_cos_interval[index] - dy) * t2 + |
| 256 (dy - table_cos_interval[index + 1]) * t1)) * |
| 257 (1 - (multiple & 2)) + 0; |
| 258 }; |
| 259 |
| 260 MathCosImpl = function(x) { |
| 261 return MathSinImpl(x + pi_half); |
| 262 }; |
| 263 |
| 264 %SetInlineBuiltinFlag(MathSinImpl); |
| 265 %SetInlineBuiltinFlag(MathCosImpl); |
| 266 } |
| 267 |
| 268 |
| 207 // ------------------------------------------------------------------- | 269 // ------------------------------------------------------------------- |
| 208 | 270 |
| 209 function SetUpMath() { | 271 function SetUpMath() { |
| 210 %CheckIsBootstrapping(); | 272 %CheckIsBootstrapping(); |
| 211 | 273 |
| 212 %SetPrototype($Math, $Object.prototype); | 274 %SetPrototype($Math, $Object.prototype); |
| 213 %SetProperty(global, "Math", $Math, DONT_ENUM); | 275 %SetProperty(global, "Math", $Math, DONT_ENUM); |
| 214 %FunctionSetInstanceClassName(MathConstructor, 'Math'); | 276 %FunctionSetInstanceClassName(MathConstructor, 'Math'); |
| 215 | 277 |
| 216 // Set up math constants. | 278 // Set up math constants. |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 269 "round", MathRound, | 331 "round", MathRound, |
| 270 "sin", MathSin, | 332 "sin", MathSin, |
| 271 "sqrt", MathSqrt, | 333 "sqrt", MathSqrt, |
| 272 "tan", MathTan, | 334 "tan", MathTan, |
| 273 "atan2", MathAtan2, | 335 "atan2", MathAtan2, |
| 274 "pow", MathPow, | 336 "pow", MathPow, |
| 275 "max", MathMax, | 337 "max", MathMax, |
| 276 "min", MathMin, | 338 "min", MathMin, |
| 277 "imul", MathImul | 339 "imul", MathImul |
| 278 )); | 340 )); |
| 341 |
| 342 %SetInlineBuiltinFlag(MathSin); |
| 343 %SetInlineBuiltinFlag(MathCos); |
| 344 %SetInlineBuiltinFlag(MathTan); |
| 279 } | 345 } |
| 280 | 346 |
| 281 SetUpMath(); | 347 SetUpMath(); |
| OLD | NEW |