1/*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16#ifndef ECMASCRIPT_BUILTIN_ENTRIES_H
17#define ECMASCRIPT_BUILTIN_ENTRIES_H
18
19#include <cstddef>
20#include <cstdint>
21#include <string>
22
23#include "ecmascript/ecma_string.h"
24#include "ecmascript/js_tagged_value.h"
25
26namespace panda::ecmascript {
27enum class BuiltinType : int32_t {
28    BT_FUNCTION,
29    BT_RANGEERROR,
30    BT_ERROR,
31    BT_OBJECT,
32    BT_SYNTAXERROR,
33    BT_TYPEERROR,
34    BT_REFERENCEERROR,
35    BT_URIERROR,
36    BT_SYMBOL,
37    BT_EVALERROR,
38    BT_NUMBER,
39    BT_PARSEFLOAT,
40    BT_DATE,
41    BT_BOOLEAN,
42    BT_BIGINT,
43    BT_PARSEINT,
44    BT_WEAKMAP,
45    BT_REGEXP,
46    BT_SET,
47    BT_MAP,
48    BT_WEAKREF,
49    BT_WEAKSET,
50    BT_FINALIZATIONREGISTRY,
51    BT_ARRAY,
52    BT_UINT8CLAMPEDARRAY,
53    BT_UINT8ARRAY,
54    BT_TYPEDARRAY,
55    BT_INT8ARRAY,
56    BT_UINT16ARRAY,
57    BT_UINT32ARRAY,
58    BT_INT16ARRAY,
59    BT_INT32ARRAY,
60    BT_FLOAT32ARRAY,
61    BT_FLOAT64ARRAY,
62    BT_BIGINT64ARRAY,
63    BT_BIGUINT64ARRAY,
64    BT_SHAREDARRAYBUFFER,
65    BT_DATAVIEW,
66    BT_STRING,
67    BT_ARRAYBUFFER,
68    BT_EVAL,
69    BT_ISFINITE,
70    BT_ARKPRIVATE,
71    BT_PRINT,
72    BT_DECODEURI,
73    BT_DECODEURICOMPONENT,
74    BT_ISNAN,
75    BT_ENCODEURI,
76    BT_ENCODEURICOMPONENT,
77    BT_MATH,
78    BT_JSON,
79    BT_ATOMICS,
80    BT_REFLECT,
81    BT_PROMISE,
82    BT_PROXY,
83    BT_GENERATORFUNCTION,
84    BT_INTL,
85    NUMBER_OF_BUILTINS
86};
87
88struct BuiltinEntries {
89    static constexpr size_t COUNT = static_cast<size_t>(BuiltinType::NUMBER_OF_BUILTINS);
90    struct BuiltinEntry {
91        JSTaggedValue box_ {JSTaggedValue::Hole()};
92        JSTaggedValue hClass_ {JSTaggedValue::Hole()};
93    } builtin_[COUNT];
94
95    uintptr_t Begin()
96    {
97        return reinterpret_cast<uintptr_t>(builtin_);
98    }
99
100    uintptr_t End()
101    {
102        return reinterpret_cast<uintptr_t>(builtin_ + COUNT);
103    }
104
105    void ClearByIndex(size_t index, JSTaggedValue value)
106    {
107        builtin_[index].box_ = value;
108        builtin_[index].hClass_ = JSTaggedValue::Hole();
109    }
110
111    static constexpr size_t SizeArch32 = sizeof(uint64_t) * 2 * COUNT;
112    static constexpr size_t SizeArch64 = sizeof(uint64_t) * 2 * COUNT;
113};
114STATIC_ASSERT_EQ_ARCH(sizeof(BuiltinEntries), BuiltinEntries::SizeArch32, BuiltinEntries::SizeArch64);
115
116class BuiltinIndex {
117public:
118    BuiltinIndex(const BuiltinIndex&) = delete;
119    BuiltinIndex& operator=(const BuiltinIndex&) = delete;
120
121    static const size_t NOT_FOUND = -1;
122
123    static BuiltinIndex& GetInstance()
124    {
125        static BuiltinIndex instance;
126        return instance;
127    }
128
129    size_t GetBuiltinBoxOffset(JSTaggedValue key) const
130    {
131        auto index = GetBuiltinIndex(key);
132        ASSERT(index != NOT_FOUND);
133        return sizeof(JSTaggedValue) * (index * 2); // 2 is size of BuiltinEntries
134    }
135
136    size_t GetBuiltinBoxOffset(size_t index)
137    {
138        return sizeof(JSTaggedValue) * (index * 2); // 2 is size of BuiltinEntries
139    }
140
141    size_t GetBuiltinIndex(JSTaggedValue key) const
142    {
143        auto ecmaString = EcmaString::Cast(key.GetTaggedObject());
144        auto str = std::string(ConvertToString(ecmaString));
145        return GetBuiltinIndex(str);
146    }
147
148    size_t GetBuiltinIndex(const std::string& key) const
149    {
150        auto it = builtinIndex_.find(key);
151        if (it == builtinIndex_.end()) {
152            return NOT_FOUND;
153        } else {
154            return static_cast<size_t>(it->second);
155        }
156    }
157
158    auto GetBuiltinKeys() -> std::vector<std::string> const
159    {
160        std::vector<std::string> keys;
161        for (const auto& it: builtinIndex_) {
162            keys.emplace_back(it.first);
163        }
164        return keys;
165    }
166
167private:
168    std::unordered_map<std::string, BuiltinType> builtinIndex_ = {
169        {"Function", BuiltinType::BT_FUNCTION},
170        {"RangeError", BuiltinType::BT_RANGEERROR},
171        {"Error", BuiltinType::BT_ERROR},
172        {"Object", BuiltinType::BT_OBJECT},
173        {"SyntaxError", BuiltinType::BT_SYNTAXERROR},
174        {"TypeError", BuiltinType::BT_TYPEERROR},
175        {"ReferenceError", BuiltinType::BT_REFERENCEERROR},
176        {"URIError", BuiltinType::BT_URIERROR},
177        {"Symbol", BuiltinType::BT_SYMBOL},
178        {"EvalError", BuiltinType::BT_EVALERROR},
179        {"Number", BuiltinType::BT_NUMBER},
180        {"parseFloat", BuiltinType::BT_PARSEFLOAT},
181        {"Date", BuiltinType::BT_DATE},
182        {"Boolean", BuiltinType::BT_BOOLEAN},
183        {"BigInt", BuiltinType::BT_BIGINT},
184        {"parseInt", BuiltinType::BT_PARSEINT},
185        {"WeakMap", BuiltinType::BT_WEAKMAP},
186        {"RegExp", BuiltinType::BT_REGEXP},
187        {"Set", BuiltinType::BT_SET},
188        {"Map", BuiltinType::BT_MAP},
189        {"WeakRef", BuiltinType::BT_WEAKREF},
190        {"WeakSet", BuiltinType::BT_WEAKSET},
191        {"FinalizationRegistry", BuiltinType::BT_FINALIZATIONREGISTRY},
192        {"Array", BuiltinType::BT_ARRAY},
193        {"Uint8ClampedArray", BuiltinType::BT_UINT8CLAMPEDARRAY},
194        {"Uint8Array", BuiltinType::BT_UINT8ARRAY},
195        {"TypedArray", BuiltinType::BT_TYPEDARRAY},
196        {"Int8Array", BuiltinType::BT_INT8ARRAY},
197        {"Uint16Array", BuiltinType::BT_UINT16ARRAY},
198        {"Uint32Array", BuiltinType::BT_UINT32ARRAY},
199        {"Int16Array", BuiltinType::BT_INT16ARRAY},
200        {"Int32Array", BuiltinType::BT_INT32ARRAY},
201        {"Float32Array", BuiltinType::BT_FLOAT32ARRAY},
202        {"Float64Array", BuiltinType::BT_FLOAT64ARRAY},
203        {"BigInt64Array", BuiltinType::BT_BIGINT64ARRAY},
204        {"BigUint64Array", BuiltinType::BT_BIGUINT64ARRAY},
205        {"SharedArrayBuffer", BuiltinType::BT_SHAREDARRAYBUFFER},
206        {"DataView", BuiltinType::BT_DATAVIEW},
207        {"String", BuiltinType::BT_STRING},
208        {"ArrayBuffer", BuiltinType::BT_ARRAYBUFFER},
209        {"eval", BuiltinType::BT_EVAL},
210        {"isFinite", BuiltinType::BT_ISFINITE},
211        {"ArkPrivate", BuiltinType::BT_ARKPRIVATE},
212        {"print", BuiltinType::BT_PRINT},
213        {"decodeURI", BuiltinType::BT_DECODEURI},
214        {"decodeURIComponent", BuiltinType::BT_DECODEURICOMPONENT},
215        {"isNaN", BuiltinType::BT_ISNAN},
216        {"encodeURI", BuiltinType::BT_ENCODEURI},
217        {"encodeURIComponent", BuiltinType::BT_ENCODEURICOMPONENT},
218        {"Math", BuiltinType::BT_MATH},
219        {"JSON", BuiltinType::BT_JSON},
220        {"Atomics", BuiltinType::BT_ATOMICS},
221        {"Reflect", BuiltinType::BT_REFLECT},
222        {"Promise", BuiltinType::BT_PROMISE},
223        {"Proxy", BuiltinType::BT_PROXY},
224        {"GeneratorFunction", BuiltinType::BT_GENERATORFUNCTION},
225        {"Intl", BuiltinType::BT_INTL},
226    };
227
228    BuiltinIndex() {}
229}; // class BuiltinIndex
230} // namespace panda::ecmascript
231#endif // ECMASCRIPT_BUILTIN_ENTRIES_H
232