[JSC] Pass VM& parameter as much as possible
[WebKit.git] / Source / JavaScriptCore / runtime / NumberConstructor.cpp
1 /*
2  *  Copyright (C) 1999-2000,2003 Harri Porten (porten@kde.org)
3  *  Copyright (C) 2007, 2008, 2011, 2015-2016 Apple Inc. All rights reserved.
4  *
5  *  This library is free software; you can redistribute it and/or
6  *  modify it under the terms of the GNU Lesser General Public
7  *  License as published by the Free Software Foundation; either
8  *  version 2 of the License, or (at your option) any later version.
9  *
10  *  This library is distributed in the hope that it will be useful,
11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  *  Lesser General Public License for more details.
14  *
15  *  You should have received a copy of the GNU Lesser General Public
16  *  License along with this library; if not, write to the Free Software
17  *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301
18  *  USA
19  *
20  */
21
22 #include "config.h"
23 #include "NumberConstructor.h"
24
25 #include "Lookup.h"
26 #include "NumberObject.h"
27 #include "NumberPrototype.h"
28 #include "JSCInlines.h"
29 #include "JSGlobalObjectFunctions.h"
30 #include "StructureInlines.h"
31
32 namespace JSC {
33
34 static EncodedJSValue JSC_HOST_CALL numberConstructorFuncIsInteger(ExecState*);
35 static EncodedJSValue JSC_HOST_CALL numberConstructorFuncIsSafeInteger(ExecState*);
36
37 } // namespace JSC
38
39 #include "NumberConstructor.lut.h"
40
41 namespace JSC {
42
43 STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(NumberConstructor);
44
45 const ClassInfo NumberConstructor::s_info = { "Function", &InternalFunction::s_info, &numberConstructorTable, nullptr, CREATE_METHOD_TABLE(NumberConstructor) };
46
47 /* Source for NumberConstructor.lut.h
48 @begin numberConstructorTable
49   isFinite       JSBuiltin                           DontEnum|Function 1
50   isNaN          JSBuiltin                           DontEnum|Function 1
51   isSafeInteger  numberConstructorFuncIsSafeInteger  DontEnum|Function 1
52 @end
53 */
54
55 static EncodedJSValue JSC_HOST_CALL callNumberConstructor(ExecState*);
56 static EncodedJSValue JSC_HOST_CALL constructNumberConstructor(ExecState*);
57
58 NumberConstructor::NumberConstructor(VM& vm, Structure* structure)
59     : InternalFunction(vm, structure, callNumberConstructor, constructNumberConstructor)
60 {
61 }
62
63 void NumberConstructor::finishCreation(VM& vm, NumberPrototype* numberPrototype)
64 {
65     Base::finishCreation(vm, NumberPrototype::info()->className);
66     ASSERT(inherits(vm, info()));
67
68     JSGlobalObject* globalObject = numberPrototype->globalObject(vm);
69
70     putDirectWithoutTransition(vm, vm.propertyNames->prototype, numberPrototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
71     putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
72
73     putDirectWithoutTransition(vm, Identifier::fromString(&vm, "EPSILON"), jsDoubleNumber(std::numeric_limits<double>::epsilon()), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
74     putDirectWithoutTransition(vm, Identifier::fromString(&vm, "MAX_VALUE"), jsDoubleNumber(1.7976931348623157E+308), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
75     putDirectWithoutTransition(vm, Identifier::fromString(&vm, "MIN_VALUE"), jsDoubleNumber(5E-324), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
76     putDirectWithoutTransition(vm, Identifier::fromString(&vm, "MAX_SAFE_INTEGER"), jsDoubleNumber(maxSafeInteger()), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
77     putDirectWithoutTransition(vm, Identifier::fromString(&vm, "MIN_SAFE_INTEGER"), jsDoubleNumber(minSafeInteger()), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
78     putDirectWithoutTransition(vm, Identifier::fromString(&vm, "NEGATIVE_INFINITY"), jsDoubleNumber(-std::numeric_limits<double>::infinity()), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
79     putDirectWithoutTransition(vm, Identifier::fromString(&vm, "POSITIVE_INFINITY"), jsDoubleNumber(std::numeric_limits<double>::infinity()), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
80     putDirectWithoutTransition(vm, vm.propertyNames->NaN, jsNaN(), PropertyAttribute::DontDelete | PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
81
82     putDirectWithoutTransition(vm, vm.propertyNames->parseInt, numberPrototype->globalObject(vm)->parseIntFunction(), static_cast<unsigned>(PropertyAttribute::DontEnum));
83     putDirectWithoutTransition(vm, vm.propertyNames->parseFloat, numberPrototype->globalObject(vm)->parseFloatFunction(), static_cast<unsigned>(PropertyAttribute::DontEnum));
84
85     JSC_NATIVE_INTRINSIC_FUNCTION_WITHOUT_TRANSITION(Identifier::fromString(&vm, "isInteger"), numberConstructorFuncIsInteger, static_cast<unsigned>(PropertyAttribute::DontEnum), 1, NumberIsIntegerIntrinsic);
86 }
87
88 // ECMA 15.7.1
89 static EncodedJSValue JSC_HOST_CALL constructNumberConstructor(ExecState* exec)
90 {
91     VM& vm = exec->vm();
92     auto scope = DECLARE_THROW_SCOPE(vm);
93     double n = exec->argumentCount() ? exec->uncheckedArgument(0).toNumber(exec) : 0;
94     RETURN_IF_EXCEPTION(scope, encodedJSValue());
95     Structure* structure = InternalFunction::createSubclassStructure(exec, exec->newTarget(), exec->lexicalGlobalObject()->numberObjectStructure());
96     RETURN_IF_EXCEPTION(scope, encodedJSValue());
97
98     NumberObject* object = NumberObject::create(vm, structure);
99     object->setInternalValue(vm, jsNumber(n));
100     return JSValue::encode(object);
101 }
102
103 // ECMA 15.7.2
104 static EncodedJSValue JSC_HOST_CALL callNumberConstructor(ExecState* exec)
105 {
106     return JSValue::encode(jsNumber(!exec->argumentCount() ? 0 : exec->uncheckedArgument(0).toNumber(exec)));
107 }
108
109 // ECMA-262 20.1.2.3
110 static EncodedJSValue JSC_HOST_CALL numberConstructorFuncIsInteger(ExecState* exec)
111 {
112     return JSValue::encode(jsBoolean(NumberConstructor::isIntegerImpl(exec->argument(0))));
113 }
114
115 // ECMA-262 20.1.2.5
116 static EncodedJSValue JSC_HOST_CALL numberConstructorFuncIsSafeInteger(ExecState* exec)
117 {
118     JSValue argument = exec->argument(0);
119     bool isInteger;
120     if (argument.isInt32())
121         isInteger = true;
122     else if (!argument.isDouble())
123         isInteger = false;
124     else {
125         double number = argument.asDouble();
126         isInteger = trunc(number) == number && std::abs(number) <= maxSafeInteger();
127     }
128     return JSValue::encode(jsBoolean(isInteger));
129 }
130
131 } // namespace JSC