NativeMath.java revision 953:221a84ef44c0
1/*
2 * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.  Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26package jdk.nashorn.internal.objects;
27
28import jdk.nashorn.internal.objects.annotations.Attribute;
29import jdk.nashorn.internal.objects.annotations.Function;
30import jdk.nashorn.internal.objects.annotations.Property;
31import jdk.nashorn.internal.objects.annotations.ScriptClass;
32import jdk.nashorn.internal.objects.annotations.SpecializedFunction;
33import jdk.nashorn.internal.objects.annotations.Where;
34import jdk.nashorn.internal.runtime.JSType;
35import jdk.nashorn.internal.runtime.PropertyMap;
36import jdk.nashorn.internal.runtime.ScriptObject;
37
38/**
39 * ECMA 15.8 The Math Object
40 *
41 */
42@ScriptClass("Math")
43public final class NativeMath extends ScriptObject {
44
45    // initialized by nasgen
46    @SuppressWarnings("unused")
47    private static PropertyMap $nasgenmap$;
48
49    private NativeMath() {
50        // don't create me!
51        throw new UnsupportedOperationException();
52    }
53
54    /** ECMA 15.8.1.1 - E, always a double constant. Not writable or configurable */
55    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
56    public static final double E = Math.E;
57
58    /** ECMA 15.8.1.2 - LN10, always a double constant. Not writable or configurable */
59    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
60    public static final double LN10 = 2.302585092994046;
61
62    /** ECMA 15.8.1.3 - LN2, always a double constant. Not writable or configurable */
63    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
64    public static final double LN2 = 0.6931471805599453;
65
66    /** ECMA 15.8.1.4 - LOG2E, always a double constant. Not writable or configurable */
67    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
68    public static final double LOG2E = 1.4426950408889634;
69
70    /** ECMA 15.8.1.5 - LOG10E, always a double constant. Not writable or configurable */
71    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
72    public static final double LOG10E = 0.4342944819032518;
73
74    /** ECMA 15.8.1.6 - PI, always a double constant. Not writable or configurable */
75    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
76    public static final double PI = Math.PI;
77
78    /** ECMA 15.8.1.7 - SQRT1_2, always a double constant. Not writable or configurable */
79    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
80    public static final double SQRT1_2 = 0.7071067811865476;
81
82    /** ECMA 15.8.1.8 - SQRT2, always a double constant. Not writable or configurable */
83    @Property(attributes = Attribute.NON_ENUMERABLE_CONSTANT, where = Where.CONSTRUCTOR)
84    public static final double SQRT2 = 1.4142135623730951;
85
86    /**
87     * ECMA 15.8.2.1 abs(x)
88     *
89     * @param self  self reference
90     * @param x     argument
91     *
92     * @return abs of value
93     */
94    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
95    public static double abs(final Object self, final Object x) {
96        return Math.abs(JSType.toNumber(x));
97    }
98
99    /**
100     * ECMA 15.8.2.1 abs(x) - specialization for int values
101     *
102     * @param self  self reference
103     * @param x     argument
104     *
105     * @return abs of argument
106     */
107    @SpecializedFunction
108    public static int abs(final Object self, final int x) {
109        return Math.abs(x);
110    }
111
112    /**
113     * ECMA 15.8.2.1 abs(x) - specialization for long values
114     *
115     * @param self  self reference
116     * @param x     argument
117     *
118     * @return abs of argument
119     */
120    @SpecializedFunction
121    public static long abs(final Object self, final long x) {
122        return Math.abs(x);
123    }
124
125    /**
126     * ECMA 15.8.2.1 abs(x) - specialization for double values
127     *
128     * @param self  self reference
129     * @param x     argument
130     *
131     * @return abs of argument
132     */
133    @SpecializedFunction
134    public static double abs(final Object self, final double x) {
135        return Math.abs(x);
136    }
137
138    /**
139     * ECMA 15.8.2.2 acos(x)
140     *
141     * @param self  self reference
142     * @param x     argument
143     *
144     * @return acos of argument
145     */
146    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
147    public static double acos(final Object self, final Object x) {
148        return Math.acos(JSType.toNumber(x));
149    }
150
151    /**
152     * ECMA 15.8.2.2 acos(x) - specialization for double values
153     *
154     * @param self  self reference
155     * @param x     argument
156     *
157     * @return acos of argument
158     */
159    @SpecializedFunction
160    public static double acos(final Object self, final double x) {
161        return Math.acos(x);
162    }
163
164    /**
165     * ECMA 15.8.2.3 asin(x)
166     *
167     * @param self  self reference
168     * @param x     argument
169     *
170     * @return asin of argument
171     */
172    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
173    public static double asin(final Object self, final Object x) {
174        return Math.asin(JSType.toNumber(x));
175    }
176
177    /**
178     * ECMA 15.8.2.3 asin(x) - specialization for double values
179     *
180     * @param self  self reference
181     * @param x     argument
182     *
183     * @return asin of argument
184     */
185    @SpecializedFunction
186    public static double asin(final Object self, final double x) {
187        return Math.asin(x);
188    }
189
190    /**
191     * ECMA 15.8.2.4 atan(x)
192     *
193     * @param self  self reference
194     * @param x     argument
195     *
196     * @return atan of argument
197     */
198    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
199    public static double atan(final Object self, final Object x) {
200        return Math.atan(JSType.toNumber(x));
201    }
202
203    /**
204     * ECMA 15.8.2.4 atan(x) - specialization for double values
205     *
206     * @param self  self reference
207     * @param x     argument
208     *
209     * @return atan of argument
210     */
211    @SpecializedFunction
212    public static double atan(final Object self, final double x) {
213        return Math.atan(x);
214    }
215
216    /**
217     * ECMA 15.8.2.5 atan2(x,y)
218     *
219     * @param self  self reference
220     * @param x     first argument
221     * @param y     second argument
222     *
223     * @return atan2 of x and y
224     */
225    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
226    public static double atan2(final Object self, final Object y, final Object x) {
227        return Math.atan2(JSType.toNumber(y), JSType.toNumber(x));
228    }
229
230    /**
231     * ECMA 15.8.2.5 atan2(x,y) - specialization for double values
232     *
233     * @param self  self reference
234     * @param x     first argument
235     * @param y     second argument
236     *
237     * @return atan2 of x and y
238     */
239    @SpecializedFunction
240    public static double atan2(final Object self, final double y, final double x) {
241        return Math.atan2(y,x);
242    }
243
244    /**
245     * ECMA 15.8.2.6 ceil(x)
246     *
247     * @param self  self reference
248     * @param x     argument
249     *
250     * @return ceil of argument
251     */
252    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
253    public static double ceil(final Object self, final Object x) {
254        return Math.ceil(JSType.toNumber(x));
255    }
256
257    /**
258     * ECMA 15.8.2.6 ceil(x) - specialized version for ints
259     *
260     * @param self  self reference
261     * @param x     argument
262     *
263     * @return ceil of argument
264     */
265    @SpecializedFunction
266    public static int ceil(final Object self, final int x) {
267        return x;
268    }
269
270    /**
271     * ECMA 15.8.2.6 ceil(x) - specialized version for longs
272     *
273     * @param self  self reference
274     * @param x     argument
275     *
276     * @return ceil of argument
277     */
278    @SpecializedFunction
279    public static long ceil(final Object self, final long x) {
280        return x;
281    }
282
283    /**
284     * ECMA 15.8.2.6 ceil(x) - specialized version for doubles
285     *
286     * @param self  self reference
287     * @param x     argument
288     *
289     * @return ceil of argument
290     */
291    @SpecializedFunction
292    public static double ceil(final Object self, final double x) {
293        return Math.ceil(x);
294    }
295
296    /**
297     * ECMA 15.8.2.7 cos(x)
298     *
299     * @param self  self reference
300     * @param x     argument
301     *
302     * @return cos of argument
303     */
304    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
305    public static double cos(final Object self, final Object x) {
306        return Math.cos(JSType.toNumber(x));
307    }
308
309    /**
310     * ECMA 15.8.2.7 cos(x) - specialized version for doubles
311     *
312     * @param self  self reference
313     * @param x     argument
314     *
315     * @return cos of argument
316     */
317    @SpecializedFunction
318    public static double cos(final Object self, final double x) {
319        return Math.cos(x);
320    }
321
322    /**
323     * ECMA 15.8.2.8 exp(x)
324     *
325     * @param self  self reference
326     * @param x     argument
327     *
328     * @return exp of argument
329     */
330    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
331    public static double exp(final Object self, final Object x) {
332        return Math.exp(JSType.toNumber(x));
333    }
334
335    /**
336     * ECMA 15.8.2.9 floor(x)
337     *
338     * @param self  self reference
339     * @param x     argument
340     *
341     * @return floor of argument
342     */
343    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
344    public static double floor(final Object self, final Object x) {
345        return Math.floor(JSType.toNumber(x));
346    }
347
348    /**
349     * ECMA 15.8.2.9 floor(x) - specialized version for ints
350     *
351     * @param self  self reference
352     * @param x     argument
353     *
354     * @return floor of argument
355     */
356    @SpecializedFunction
357    public static int floor(final Object self, final int x) {
358        return x;
359    }
360
361    /**
362     * ECMA 15.8.2.9 floor(x) - specialized version for longs
363     *
364     * @param self  self reference
365     * @param x     argument
366     *
367     * @return floor of argument
368     */
369    @SpecializedFunction
370    public static long floor(final Object self, final long x) {
371        return x;
372    }
373
374    /**
375     * ECMA 15.8.2.9 floor(x) - specialized version for doubles
376     *
377     * @param self  self reference
378     * @param x     argument
379     *
380     * @return floor of argument
381     */
382    @SpecializedFunction
383    public static double floor(final Object self, final double x) {
384        return Math.floor(x);
385    }
386
387    /**
388     * ECMA 15.8.2.10 log(x)
389     *
390     * @param self  self reference
391     * @param x     argument
392     *
393     * @return log of argument
394     */
395    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
396    public static double log(final Object self, final Object x) {
397        return Math.log(JSType.toNumber(x));
398    }
399
400    /**
401     * ECMA 15.8.2.10 log(x) - specialized version for doubles
402     *
403     * @param self  self reference
404     * @param x     argument
405     *
406     * @return log of argument
407     */
408    @SpecializedFunction
409    public static double log(final Object self, final double x) {
410        return Math.log(x);
411    }
412
413    /**
414     * ECMA 15.8.2.11 max(x)
415     *
416     * @param self  self reference
417     * @param args  arguments
418     *
419     * @return the largest of the arguments, {@link Double#NEGATIVE_INFINITY} if no args given, or identity if one arg is given
420     */
421    @Function(arity = 2, attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
422    public static double max(final Object self, final Object... args) {
423        switch (args.length) {
424        case 0:
425            return Double.NEGATIVE_INFINITY;
426        case 1:
427            return JSType.toNumber(args[0]);
428        default:
429            double res = JSType.toNumber(args[0]);
430            for (int i = 1; i < args.length; i++) {
431                res = Math.max(res, JSType.toNumber(args[i]));
432            }
433            return res;
434        }
435    }
436
437    /**
438     * ECMA 15.8.2.11 max(x) - specialized no args version
439     *
440     * @param self  self reference
441     *
442     * @return {@link Double#NEGATIVE_INFINITY}
443     */
444    @SpecializedFunction
445    public static double max(final Object self) {
446        return Double.NEGATIVE_INFINITY;
447    }
448
449    /**
450     * ECMA 15.8.2.11 max(x) - specialized version for ints
451     *
452     * @param self  self reference
453     * @param x     first argument
454     * @param y     second argument
455     *
456     * @return largest value of x and y
457     */
458    @SpecializedFunction
459    public static int max(final Object self, final int x, final int y) {
460        return Math.max(x, y);
461    }
462
463    /**
464     * ECMA 15.8.2.11 max(x) - specialized version for longs
465     *
466     * @param self  self reference
467     * @param x     first argument
468     * @param y     second argument
469     *
470     * @return largest value of x and y
471     */
472    @SpecializedFunction
473    public static long max(final Object self, final long x, final long y) {
474        return Math.max(x, y);
475    }
476
477    /**
478     * ECMA 15.8.2.11 max(x) - specialized version for doubles
479     *
480     * @param self  self reference
481     * @param x     first argument
482     * @param y     second argument
483     *
484     * @return largest value of x and y
485     */
486    @SpecializedFunction
487    public static double max(final Object self, final double x, final double y) {
488        return Math.max(x, y);
489    }
490
491    /**
492     * ECMA 15.8.2.11 max(x) - specialized version for two Object args
493     *
494     * @param self  self reference
495     * @param x     first argument
496     * @param y     second argument
497     *
498     * @return largest value of x and y
499     */
500    @SpecializedFunction
501    public static double max(final Object self, final Object x, final Object y) {
502        return Math.max(JSType.toNumber(x), JSType.toNumber(y));
503    }
504
505    /**
506     * ECMA 15.8.2.12 min(x)
507     *
508     * @param self  self reference
509     * @param args  arguments
510     *
511     * @return the smallest of the arguments, {@link Double#NEGATIVE_INFINITY} if no args given, or identity if one arg is given
512     */
513    @Function(arity = 2, attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
514    public static double min(final Object self, final Object... args) {
515        switch (args.length) {
516        case 0:
517            return Double.POSITIVE_INFINITY;
518        case 1:
519            return JSType.toNumber(args[0]);
520        default:
521            double res = JSType.toNumber(args[0]);
522            for (int i = 1; i < args.length; i++) {
523                res = Math.min(res, JSType.toNumber(args[i]));
524            }
525            return res;
526        }
527    }
528
529    /**
530     * ECMA 15.8.2.11 min(x) - specialized no args version
531     *
532     * @param self  self reference
533     *
534     * @return {@link Double#POSITIVE_INFINITY}
535     */
536    @SpecializedFunction
537    public static double min(final Object self) {
538        return Double.POSITIVE_INFINITY;
539    }
540
541    /**
542     * ECMA 15.8.2.12 min(x) - specialized version for ints
543     *
544     * @param self  self reference
545     * @param x     first argument
546     * @param y     second argument
547     *
548     * @return smallest value of x and y
549     */
550    @SpecializedFunction
551    public static int min(final Object self, final int x, final int y) {
552        return Math.min(x, y);
553    }
554
555    /**
556     * ECMA 15.8.2.12 min(x) - specialized version for longs
557     *
558     * @param self  self reference
559     * @param x     first argument
560     * @param y     second argument
561     *
562     * @return smallest value of x and y
563     */
564    @SpecializedFunction
565    public static long min(final Object self, final long x, final long y) {
566        return Math.min(x, y);
567    }
568
569    /**
570     * ECMA 15.8.2.12 min(x) - specialized version for doubles
571     *
572     * @param self  self reference
573     * @param x     first argument
574     * @param y     second argument
575     *
576     * @return smallest value of x and y
577     */
578    @SpecializedFunction
579    public static double min(final Object self, final double x, final double y) {
580        return Math.min(x, y);
581    }
582
583    /**
584     * ECMA 15.8.2.12 min(x) - specialized version for two Object args
585     *
586     * @param self  self reference
587     * @param x     first argument
588     * @param y     second argument
589     *
590     * @return smallest value of x and y
591     */
592    @SpecializedFunction
593    public static double min(final Object self, final Object x, final Object y) {
594        return Math.min(JSType.toNumber(x), JSType.toNumber(y));
595    }
596
597    /**
598     * ECMA 15.8.2.13 pow(x,y)
599     *
600     * @param self  self reference
601     * @param x     first argument
602     * @param y     second argument
603     *
604     * @return x raised to the power of y
605     */
606    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
607    public static double pow(final Object self, final Object x, final Object y) {
608        return Math.pow(JSType.toNumber(x), JSType.toNumber(y));
609    }
610
611    /**
612     * ECMA 15.8.2.13 pow(x,y) - specialized version for doubles
613     *
614     * @param self  self reference
615     * @param x     first argument
616     * @param y     second argument
617     *
618     * @return x raised to the power of y
619     */
620    @SpecializedFunction
621    public static double pow(final Object self, final double x, final double y) {
622        return Math.pow(x, y);
623    }
624
625    /**
626     * ECMA 15.8.2.14 random()
627     *
628     * @param self  self reference
629     *
630     * @return random number in the range [0..1)
631     */
632    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
633    public static double random(final Object self) {
634        return Math.random();
635    }
636
637    /**
638     * ECMA 15.8.2.15 round(x)
639     *
640     * @param self  self reference
641     * @param x     argument
642     *
643     * @return x rounded
644     */
645    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
646    public static double round(final Object self, final Object x) {
647        final double d = JSType.toNumber(x);
648        if (Math.getExponent(d) >= 52) {
649            return d;
650        }
651        return Math.copySign(Math.floor(d + 0.5), d);
652    }
653
654    /**
655     * ECMA 15.8.2.16 sin(x)
656     *
657     * @param self  self reference
658     * @param x     argument
659     *
660     * @return sin of x
661     */
662    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
663    public static double sin(final Object self, final Object x) {
664        return Math.sin(JSType.toNumber(x));
665    }
666
667    /**
668     * ECMA 15.8.2.16 sin(x) - specialized version for doubles
669     *
670     * @param self  self reference
671     * @param x     argument
672     *
673     * @return sin of x
674     */
675    @SpecializedFunction
676    public static double sin(final Object self, final double x) {
677        return Math.sin(x);
678    }
679
680    /**
681     * ECMA 15.8.2.17 sqrt(x)
682     *
683     * @param self  self reference
684     * @param x     argument
685     *
686     * @return sqrt of x
687     */
688    @Function(attributes = Attribute.NOT_ENUMERABLE, where = Where.CONSTRUCTOR)
689    public static double sqrt(final Object self, final Object x) {
690        return Math.sqrt(JSType.toNumber(x));
691    }
692
693    /**
694     * ECMA 15.8.2.17 sqrt(x) - specialized version for doubles
695     *
696     * @param self  self reference
697     * @param x     argument
698     *
699     * @return sqrt of x
700     */
701    @SpecializedFunction
702    public static double sqrt(final Object self, final double x) {
703        return Math.sqrt(x);
704    }
705
706    /**
707     * ECMA 15.8.2.18 tan(x)
708     *
709     * @param self  self reference
710     * @param x     argument
711     *
712     * @return tan of x
713     */
714    @Function(attributes = Attribute.NOT_ENUMERABLE, where=Where.CONSTRUCTOR)
715    public static double tan(final Object self, final Object x) {
716        return Math.tan(JSType.toNumber(x));
717    }
718
719    /**
720     * ECMA 15.8.2.18 tan(x) - specialized version for doubles
721     *
722     * @param self  self reference
723     * @param x     argument
724     *
725     * @return tan of x
726     */
727    @SpecializedFunction
728    public static double tan(final Object self, final double x) {
729        return Math.tan(x);
730    }
731}
732