• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2022 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 #include "ecmascript/base/config.h"
17 #include "ecmascript/dependent_infos.h"
18 #include "ecmascript/dfx/native_module_failure_info.h"
19 #include "ecmascript/base/typed_array_helper-inl.h"
20 #include "ecmascript/mem/barriers.h"
21 #include "ecmascript/builtins/builtins.h"
22 #include "ecmascript/builtins/builtins_errors.h"
23 #include "ecmascript/ecma_string-inl.h"
24 #include "ecmascript/enum_cache.h"
25 #include "ecmascript/ic/ic_handler.h"
26 #include "ecmascript/ic/profile_type_info.h"
27 #include "ecmascript/ic/proto_change_details.h"
28 #include "ecmascript/jobs/pending_job.h"
29 #include "ecmascript/js_api/js_api_arraylist.h"
30 #include "ecmascript/js_api/js_api_arraylist_iterator.h"
31 #include "ecmascript/js_api/js_api_bitvector.h"
32 #include "ecmascript/js_api/js_api_bitvector_iterator.h"
33 #include "ecmascript/js_api/js_api_buffer.h"
34 #include "ecmascript/js_api/js_api_deque.h"
35 #include "ecmascript/js_api/js_api_deque_iterator.h"
36 #include "ecmascript/js_api/js_api_hashmap_iterator.h"
37 #include "ecmascript/js_api/js_api_hashset.h"
38 #include "ecmascript/js_api/js_api_hashset_iterator.h"
39 #include "ecmascript/js_api/js_api_lightweightmap.h"
40 #include "ecmascript/js_api/js_api_lightweightmap_iterator.h"
41 #include "ecmascript/js_api/js_api_lightweightset.h"
42 #include "ecmascript/js_api/js_api_lightweightset_iterator.h"
43 #include "ecmascript/js_api/js_api_linked_list.h"
44 #include "ecmascript/js_api/js_api_linked_list_iterator.h"
45 #include "ecmascript/js_api/js_api_list.h"
46 #include "ecmascript/js_api/js_api_list_iterator.h"
47 #include "ecmascript/js_api/js_api_plain_array.h"
48 #include "ecmascript/js_api/js_api_plain_array_iterator.h"
49 #include "ecmascript/js_api/js_api_queue.h"
50 #include "ecmascript/js_api/js_api_queue_iterator.h"
51 #include "ecmascript/js_api/js_api_stack_iterator.h"
52 #include "ecmascript/js_api/js_api_tree_map.h"
53 #include "ecmascript/js_api/js_api_tree_map_iterator.h"
54 #include "ecmascript/js_api/js_api_tree_set.h"
55 #include "ecmascript/js_api/js_api_tree_set_iterator.h"
56 #include "ecmascript/js_api/js_api_vector.h"
57 #include "ecmascript/js_api/js_api_vector_iterator.h"
58 #include "ecmascript/js_arguments.h"
59 #include "ecmascript/js_array_iterator.h"
60 #include "ecmascript/js_arraybuffer.h"
61 #include "ecmascript/js_async_from_sync_iterator.h"
62 #include "ecmascript/js_async_function.h"
63 #include "ecmascript/js_async_generator_object.h"
64 #include "ecmascript/js_finalization_registry.h"
65 #include "ecmascript/js_for_in_iterator.h"
66 #include "ecmascript/js_map.h"
67 #include "ecmascript/js_map_iterator.h"
68 #include "ecmascript/js_object.h"
69 #include "ecmascript/js_primitive_ref.h"
70 #include "ecmascript/js_promise.h"
71 #include "ecmascript/js_realm.h"
72 #include "ecmascript/js_regexp.h"
73 #include "ecmascript/js_regexp_iterator.h"
74 #include "ecmascript/js_set.h"
75 #include "ecmascript/js_set_iterator.h"
76 #include "ecmascript/js_string_iterator.h"
77 #include "ecmascript/js_typed_array.h"
78 #include "ecmascript/js_weak_container.h"
79 #include "ecmascript/js_weak_ref.h"
80 #include "ecmascript/jspandafile/program_object.h"
81 #include "ecmascript/marker_cell.h"
82 #include "ecmascript/object_factory.h"
83 #include "ecmascript/require/js_cjs_exports.h"
84 #include "ecmascript/require/js_cjs_require.h"
85 #include "ecmascript/shared_mm/shared_mm.h"
86 #include "ecmascript/shared_objects/js_shared_array.h"
87 #include "ecmascript/shared_objects/js_sendable_arraybuffer.h"
88 #include "ecmascript/shared_objects/js_shared_array_iterator.h"
89 #include "ecmascript/shared_objects/js_shared_map.h"
90 #include "ecmascript/shared_objects/js_shared_map_iterator.h"
91 #include "ecmascript/shared_objects/js_shared_set.h"
92 #include "ecmascript/shared_objects/js_shared_set_iterator.h"
93 #include "ecmascript/shared_objects/js_shared_typed_array.h"
94 #include "ecmascript/symbol_table.h"
95 #include "ecmascript/template_map.h"
96 #include "ecmascript/vtable.h"
97 #ifdef ARK_SUPPORT_INTL
98 #include "ecmascript/js_collator.h"
99 #include "ecmascript/js_date_time_format.h"
100 #include "ecmascript/js_displaynames.h"
101 #include "ecmascript/js_list_format.h"
102 #include "ecmascript/js_number_format.h"
103 #include "ecmascript/js_plural_rules.h"
104 #include "ecmascript/js_relative_time_format.h"
105 #include "ecmascript/js_segmenter.h"
106 #include "ecmascript/js_segments.h"
107 #include "ecmascript/js_segment_iterator.h"
108 #endif
109 namespace panda::ecmascript {
110 using Error = builtins::BuiltinsError;
111 using RangeError = builtins::BuiltinsRangeError;
112 using ReferenceError = builtins::BuiltinsReferenceError;
113 using TypeError = builtins::BuiltinsTypeError;
114 using AggregateError = builtins::BuiltinsAggregateError;
115 using URIError = builtins::BuiltinsURIError;
116 using SyntaxError = builtins::BuiltinsSyntaxError;
117 using EvalError = builtins::BuiltinsEvalError;
118 using OOMError = builtins::BuiltinsOOMError;
119 using ErrorType = base::ErrorType;
120 using ErrorHelper = base::ErrorHelper;
121 
ObjectFactory(JSThread * thread,Heap * heap,SharedHeap * sHeap)122 ObjectFactory::ObjectFactory(JSThread *thread, Heap *heap, SharedHeap *sHeap)
123     : thread_(thread), vm_(thread->GetEcmaVM()), heap_(heap), sHeap_(sHeap) {}
124 
NewMethodForNativeFunction(const void * func,FunctionKind kind,kungfu::BuiltinsStubCSigns::ID builtinId,MemSpaceType methodSpaceType)125 JSHandle<Method> ObjectFactory::NewMethodForNativeFunction(const void *func, FunctionKind kind,
126                                                            kungfu::BuiltinsStubCSigns::ID builtinId,
127                                                            MemSpaceType methodSpaceType)
128 {
129     uint32_t numArgs = 2;  // function object and this
130     auto method = NewSMethod(nullptr, methodSpaceType);
131     method->SetNativePointer(const_cast<void *>(func));
132     method->SetNativeBit(true);
133     if (builtinId != BUILTINS_STUB_ID(INVALID)) {
134         bool isFast = kungfu::BuiltinsStubCSigns::IsFastBuiltin(builtinId);
135         method->SetFastBuiltinBit(isFast);
136         method->SetBuiltinId(static_cast<uint8_t>(builtinId));
137     }
138     method->SetNumArgsWithCallField(numArgs);
139     method->SetFunctionKind(kind);
140     return method;
141 }
142 
NewEcmaHClassClass(JSHClass * hclass,uint32_t size,JSType type)143 JSHandle<JSHClass> ObjectFactory::NewEcmaHClassClass(JSHClass *hclass, uint32_t size, JSType type)
144 {
145     NewObjectHook();
146     uint32_t classSize = JSHClass::SIZE;
147     auto *newClass = static_cast<JSHClass *>(heap_->AllocateClassClass(hclass, classSize));
148     newClass->Initialize(thread_, size, type, 0);
149 
150     return JSHandle<JSHClass>(thread_, newClass);
151 }
152 
InitClassClass()153 JSHandle<JSHClass> ObjectFactory::InitClassClass()
154 {
155     JSHandle<JSHClass> hClassHandle = NewEcmaHClassClass(nullptr, JSHClass::SIZE, JSType::HCLASS);
156     JSHClass *hclass = reinterpret_cast<JSHClass *>(hClassHandle.GetTaggedValue().GetTaggedObject());
157     hclass->SetClass(thread_, hclass);
158     return hClassHandle;
159 }
160 
NewEcmaHClass(JSHClass * hclass,uint32_t size,JSType type,uint32_t inlinedProps)161 JSHandle<JSHClass> ObjectFactory::NewEcmaHClass(JSHClass *hclass, uint32_t size, JSType type, uint32_t inlinedProps)
162 {
163     NewObjectHook();
164     uint32_t classSize = JSHClass::SIZE;
165     auto *newClass = static_cast<JSHClass *>(heap_->AllocateNonMovableOrHugeObject(hclass, classSize));
166     newClass->Initialize(thread_, size, type, inlinedProps);
167 
168     return JSHandle<JSHClass>(thread_, newClass);
169 }
170 
171 // This function don't UpdateProtoClass
NewEcmaHClass(uint32_t size,uint32_t inlinedProps,JSType type,const JSHandle<JSTaggedValue> & prototype,const JSHandle<JSTaggedValue> & layout)172 JSHandle<JSHClass> ObjectFactory::NewEcmaHClass(uint32_t size, uint32_t inlinedProps, JSType type,
173     const JSHandle<JSTaggedValue> &prototype, const JSHandle<JSTaggedValue> &layout)
174 {
175     NewSObjectHook();
176     uint32_t classSize = JSHClass::SIZE;
177     auto *newClass = static_cast<JSHClass *>(heap_->AllocateNonMovableOrHugeObject(
178         JSHClass::Cast(thread_->GlobalConstants()->GetHClassClass().GetTaggedObject()), classSize));
179     newClass->Initialize(thread_, size, type, inlinedProps, layout);
180     JSHandle<JSHClass> hclass(thread_, newClass);
181     if (prototype->IsJSObject()) {
182         prototype->GetTaggedObject()->GetClass()->SetIsPrototype(true);
183     }
184     hclass->SetProto(thread_, prototype.GetTaggedValue());
185     hclass->SetNumberOfProps(inlinedProps);
186     hclass->SetExtensible(false);
187     return hclass;
188 }
189 
NewEcmaReadOnlyHClass(JSHClass * hclass,uint32_t size,JSType type,uint32_t inlinedProps)190 JSHandle<JSHClass> ObjectFactory::NewEcmaReadOnlyHClass(JSHClass *hclass, uint32_t size, JSType type,
191                                                         uint32_t inlinedProps)
192 {
193     NewObjectHook();
194     uint32_t classSize = JSHClass::SIZE;
195     auto *newClass = static_cast<JSHClass *>(heap_->AllocateReadOnlyOrHugeObject(hclass, classSize));
196     ASSERT(newClass != nullptr);
197     newClass->Initialize(thread_, size, type, inlinedProps);
198 
199     return JSHandle<JSHClass>(thread_, newClass);
200 }
201 
NewEcmaHClass(uint32_t size,JSType type,uint32_t inlinedProps)202 JSHandle<JSHClass> ObjectFactory::NewEcmaHClass(uint32_t size, JSType type, uint32_t inlinedProps)
203 {
204     return NewEcmaHClass(JSHClass::Cast(thread_->GlobalConstants()->GetHClassClass().GetTaggedObject()),
205                          size, type, inlinedProps);
206 }
207 
InitObjectFields(const TaggedObject * object,JSTaggedValue initValue)208 void ObjectFactory::InitObjectFields(const TaggedObject *object, JSTaggedValue initValue)
209 {
210     auto *klass = object->GetClass();
211     auto objBodySize = klass->GetObjectSize() - TaggedObject::TaggedObjectSize();
212     ASSERT(objBodySize % JSTaggedValue::TaggedTypeSize() == 0);
213     uint32_t numOfFields = objBodySize / JSTaggedValue::TaggedTypeSize();
214     size_t addr = reinterpret_cast<uintptr_t>(object) + TaggedObject::TaggedObjectSize();
215     for (uint32_t i = 0; i < numOfFields; i++) {
216         auto *fieldAddr = reinterpret_cast<JSTaggedType *>(addr + i * JSTaggedValue::TaggedTypeSize());
217         *fieldAddr = JSTaggedValue::Undefined().GetRawData();
218     }
219 }
220 
NewJSArrayBufferData(const JSHandle<JSArrayBuffer> & array,int32_t length)221 void ObjectFactory::NewJSArrayBufferData(const JSHandle<JSArrayBuffer> &array, int32_t length)
222 {
223     if (length == 0) {
224         return;
225     }
226 
227     JSTaggedValue data = array->GetArrayBufferData(thread_);
228     size_t size = static_cast<size_t>(length) * sizeof(uint8_t);
229     if (!data.IsUndefined()) {
230         auto *pointer = JSNativePointer::Cast(data.GetTaggedObject());
231         auto newData = vm_->GetNativeAreaAllocator()->AllocateBuffer(size);
232         heap_->IncNativeSizeAfterLastGC(size);
233         if (memset_s(newData, length, 0, length) != EOK) {
234             LOG_FULL(FATAL) << "memset_s failed";
235             UNREACHABLE();
236         }
237         pointer->ResetExternalPointer(thread_, newData);
238         if (g_isEnableCMCGC) {
239             common::BaseRuntime::NotifyNativeReset(pointer->GetBindingSize(), size);
240         }
241         vm_->GetNativeAreaAllocator()->ModifyNativeSizeStats(pointer->GetBindingSize(), size,
242                                                              NativeFlag::ARRAY_BUFFER);
243         return;
244     }
245 
246     auto newData = vm_->GetNativeAreaAllocator()->AllocateBuffer(size);
247     heap_->IncNativeSizeAfterLastGC(size);
248     if (memset_s(newData, length, 0, length) != EOK) {
249         LOG_FULL(FATAL) << "memset_s failed";
250         UNREACHABLE();
251     }
252     JSHandle<JSNativePointer> pointer = NewJSNativePointer(newData, NativeAreaAllocator::FreeBufferFunc,
253                                                            vm_->GetNativeAreaAllocator(), false, size, Concurrent::NO,
254                                                            NativeFlag::ARRAY_BUFFER);
255     array->SetArrayBufferData(thread_, pointer);
256     array->SetWithNativeAreaAllocator(true);
257     vm_->GetNativeAreaAllocator()->IncreaseNativeSizeStats(length, NativeFlag::ARRAY_BUFFER);
258 }
259 
NewJSSendableArrayBufferData(const JSHandle<JSSendableArrayBuffer> & array,int32_t length)260 void ObjectFactory::NewJSSendableArrayBufferData(const JSHandle<JSSendableArrayBuffer> &array, int32_t length)
261 {
262     if (length == 0) {
263         return;
264     }
265 
266     JSTaggedValue data = array->GetArrayBufferData(thread_);
267     size_t size = static_cast<size_t>(length) * sizeof(uint8_t);
268     NativeAreaAllocator *nativeAreaAllocator = sHeap_->GetNativeAreaAllocator();
269     if (!data.IsUndefined()) {
270         auto *pointer = JSNativePointer::Cast(data.GetTaggedObject());
271         auto newData = nativeAreaAllocator->AllocateBuffer(size);
272         if (newData == nullptr) {
273             LOG_ECMA(FATAL) << "ObjectFactory::NewJSSendableArrayBufferData:newData is nullptr";
274         }
275         if (memset_s(newData, length, 0, length) != EOK) {
276             LOG_FULL(FATAL) << "memset_s failed";
277             UNREACHABLE();
278         }
279         pointer->ResetExternalPointer(thread_, newData);
280         if (g_isEnableCMCGC) {
281             common::BaseRuntime::NotifyNativeReset(pointer->GetBindingSize(), size);
282         }
283         nativeAreaAllocator->ModifyNativeSizeStats(pointer->GetBindingSize(), size,
284                                                    NativeFlag::ARRAY_BUFFER);
285         return;
286     }
287 
288     auto newData = nativeAreaAllocator->AllocateBuffer(size);
289     if (newData == nullptr) {
290         LOG_ECMA(FATAL) << "ObjectFactory::NewJSSendableArrayBufferData:newData is nullptr";
291     }
292     if (memset_s(newData, length, 0, length) != EOK) {
293         LOG_FULL(FATAL) << "memset_s failed";
294         UNREACHABLE();
295     }
296     JSHandle<JSNativePointer> pointer = NewSJSNativePointer(newData, NativeAreaAllocator::FreeBufferFunc,
297                                                             nativeAreaAllocator, false, size,
298                                                             NativeFlag::ARRAY_BUFFER);
299     array->SetArrayBufferData(thread_, pointer);
300     array->SetWithNativeAreaAllocator(true);
301     nativeAreaAllocator->IncreaseNativeSizeStats(length, NativeFlag::ARRAY_BUFFER);
302 }
303 
NewJSSendableArrayBuffer(int32_t length)304 JSHandle<JSSendableArrayBuffer> ObjectFactory::NewJSSendableArrayBuffer(int32_t length)
305 {
306     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
307 
308     JSHandle<JSFunction> constructor(env->GetSBuiltininArrayBufferFunction());
309     JSHandle<JSSendableArrayBuffer> sendableArrayBuffer(NewJSObjectByConstructor(constructor));
310     sendableArrayBuffer->SetArrayBufferByteLength(length);
311     if (length > 0) {
312         NewJSSendableArrayBufferData(sendableArrayBuffer, length);
313         sendableArrayBuffer->SetShared(false);
314     }
315     return sendableArrayBuffer;
316 }
317 
NewJSSendableArrayBuffer(void * buffer,int32_t length,const NativePointerCallback & deleter,void * data)318 JSHandle<JSSendableArrayBuffer> ObjectFactory::NewJSSendableArrayBuffer(void *buffer, int32_t length,
319                                                                         const NativePointerCallback &deleter,
320                                                                         void *data)
321 {
322     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
323 
324     JSHandle<JSFunction> constructor(env->GetSBuiltininArrayBufferFunction());
325     JSHandle<JSSendableArrayBuffer> sendableArrayBuffer(NewJSObjectByConstructor(constructor));
326     length = buffer == nullptr ? 0 : length;
327     sendableArrayBuffer->SetArrayBufferByteLength(length);
328     if (length > 0) {
329         JSHandle<JSNativePointer> pointer = NewSJSNativePointer(buffer, deleter, data, false, length);
330         sendableArrayBuffer->SetArrayBufferData(thread_, pointer.GetTaggedValue());
331         sendableArrayBuffer->SetShared(false);
332         sendableArrayBuffer->SetWithNativeAreaAllocator(deleter == NativeAreaAllocator::FreeBufferFunc &&
333                                                 data == vm_->GetNativeAreaAllocator());
334     }
335     return sendableArrayBuffer;
336 }
337 
NewJSSharedArrayBufferData(const JSHandle<JSArrayBuffer> & array,int32_t length)338 void ObjectFactory::NewJSSharedArrayBufferData(const JSHandle<JSArrayBuffer> &array, int32_t length)
339 {
340     if (length == 0) {
341         return;
342     }
343     void *newData = nullptr;
344     size_t size =
345         JSSharedMemoryManager::GetInstance()->CreateOrLoad(&newData, length) ? static_cast<size_t>(length) : 0U;
346     if (memset_s(newData, length, 0, length) != EOK) {
347         LOG_FULL(FATAL) << "memset_s failed";
348         UNREACHABLE();
349     }
350     JSHandle<JSNativePointer> pointer = NewJSNativePointer(newData, JSSharedMemoryManager::RemoveSharedMemory,
351                                                            JSSharedMemoryManager::GetInstance(), false, size);
352     array->SetArrayBufferData(thread_, pointer);
353     array->SetWithNativeAreaAllocator(false);
354 }
355 
NewJSArrayBuffer(int32_t length)356 JSHandle<JSArrayBuffer> ObjectFactory::NewJSArrayBuffer(int32_t length)
357 {
358     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
359 
360     JSHandle<JSFunction> constructor(env->GetArrayBufferFunction());
361     JSHandle<JSArrayBuffer> arrayBuffer(NewJSObjectByConstructor(constructor));
362     arrayBuffer->SetArrayBufferByteLength(length);
363     if (length > 0) {
364         auto newData = vm_->GetNativeAreaAllocator()->AllocateBuffer(length);
365         heap_->IncNativeSizeAfterLastGC(length);
366         if (memset_s(newData, length, 0, length) != EOK) {
367             LOG_FULL(FATAL) << "memset_s failed";
368             UNREACHABLE();
369         }
370         JSHandle<JSNativePointer> pointer = NewJSNativePointer(newData, NativeAreaAllocator::FreeBufferFunc,
371                                                                vm_->GetNativeAreaAllocator(), false, length,
372                                                                Concurrent::NO, NativeFlag::ARRAY_BUFFER);
373         arrayBuffer->SetArrayBufferData(thread_, pointer.GetTaggedValue());
374         arrayBuffer->SetWithNativeAreaAllocator(true);
375         vm_->GetNativeAreaAllocator()->IncreaseNativeSizeStats(length, NativeFlag::ARRAY_BUFFER);
376     }
377     return arrayBuffer;
378 }
379 
NewJSArrayBuffer(void * buffer,int32_t length,const NativePointerCallback & deleter,void * data,bool share)380 JSHandle<JSArrayBuffer> ObjectFactory::NewJSArrayBuffer(void *buffer, int32_t length,
381                                                         const NativePointerCallback &deleter, void *data, bool share)
382 {
383     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
384 
385     JSHandle<JSFunction> constructor(env->GetArrayBufferFunction());
386     JSHandle<JSArrayBuffer> arrayBuffer(NewJSObjectByConstructor(constructor));
387     length = buffer == nullptr ? 0 : length;
388     arrayBuffer->SetArrayBufferByteLength(length);
389     if (length > 0) {
390         JSHandle<JSNativePointer> pointer = NewJSNativePointer(buffer, deleter, data, false, length);
391         arrayBuffer->SetArrayBufferData(thread_, pointer.GetTaggedValue());
392         arrayBuffer->SetShared(share);
393         arrayBuffer->SetWithNativeAreaAllocator(deleter == NativeAreaAllocator::FreeBufferFunc &&
394                                                 data == vm_->GetNativeAreaAllocator());
395     }
396     return arrayBuffer;
397 }
398 
NewJSDataView(JSHandle<JSArrayBuffer> buffer,uint32_t offset,uint32_t length)399 JSHandle<JSDataView> ObjectFactory::NewJSDataView(JSHandle<JSArrayBuffer> buffer, uint32_t offset, uint32_t length)
400 {
401     uint32_t arrayLength = buffer->GetArrayBufferByteLength();
402     if (arrayLength < static_cast<uint64_t>(offset) + length) {
403         THROW_TYPE_ERROR_AND_RETURN(thread_, "offset or length error",
404                                     JSHandle<JSDataView>(thread_, JSTaggedValue::Undefined()));
405     }
406     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
407 
408     JSHandle<JSFunction> constructor(env->GetDataViewFunction());
409     JSHandle<JSDataView> arrayBuffer(NewJSObjectByConstructor(constructor));
410     arrayBuffer->SetDataView(thread_, JSTaggedValue::True());
411     arrayBuffer->SetViewedArrayBuffer(thread_, buffer.GetTaggedValue());
412     arrayBuffer->SetByteLength(length);
413     arrayBuffer->SetByteOffset(offset);
414     return arrayBuffer;
415 }
416 
NewJSSharedArrayBuffer(int32_t length)417 JSHandle<JSArrayBuffer> ObjectFactory::NewJSSharedArrayBuffer(int32_t length)
418 {
419     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
420 
421     JSHandle<JSFunction> constructor(env->GetSharedArrayBufferFunction());
422     JSHandle<JSArrayBuffer> sharedArrayBuffer(NewJSObjectByConstructor(constructor));
423     sharedArrayBuffer->SetArrayBufferByteLength(length);
424     if (length > 0) {
425         NewJSSharedArrayBufferData(sharedArrayBuffer, length);
426         sharedArrayBuffer->SetShared(true);
427     }
428     return sharedArrayBuffer;
429 }
430 
NewJSSharedArrayBuffer(void * buffer,int32_t length)431 JSHandle<JSArrayBuffer> ObjectFactory::NewJSSharedArrayBuffer(void *buffer, int32_t length)
432 {
433     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
434 
435     JSHandle<JSFunction> constructor(env->GetSharedArrayBufferFunction());
436     JSHandle<JSArrayBuffer> sharedArrayBuffer(NewJSObjectByConstructor(constructor));
437     length = buffer == nullptr ? 0 : length;
438     sharedArrayBuffer->SetArrayBufferByteLength(length);
439     if (length > 0) {
440         JSHandle<JSNativePointer> pointer = NewJSNativePointer(buffer, JSSharedMemoryManager::RemoveSharedMemory,
441                                                                JSSharedMemoryManager::GetInstance(), false, length);
442         sharedArrayBuffer->SetArrayBufferData(thread_, pointer);
443         sharedArrayBuffer->SetShared(true);
444         sharedArrayBuffer->SetWithNativeAreaAllocator(false);
445     }
446     return sharedArrayBuffer;
447 }
448 
NewJSRegExpByteCodeData(const JSHandle<JSRegExp> & regexp,void * buffer,size_t size)449 void ObjectFactory::NewJSRegExpByteCodeData(const JSHandle<JSRegExp> &regexp, void *buffer, size_t size)
450 {
451     if (buffer == nullptr) {
452         return;
453     }
454 
455     auto newBuffer = vm_->GetNativeAreaAllocator()->AllocateBuffer(size);
456     heap_->IncNativeSizeAfterLastGC(size);
457     if (memcpy_s(newBuffer, size, buffer, size) != EOK) {
458         LOG_FULL(FATAL) << "memcpy_s failed";
459         UNREACHABLE();
460     }
461     JSTaggedValue data = regexp->GetByteCodeBuffer(thread_);
462     if (!data.IsUndefined()) {
463         JSNativePointer *native = JSNativePointer::Cast(data.GetTaggedObject());
464         native->ResetExternalPointer(thread_, newBuffer);
465         if (g_isEnableCMCGC) {
466             common::BaseRuntime::NotifyNativeReset(native->GetBindingSize(), size);
467         }
468         return;
469     }
470     JSHandle<JSNativePointer> pointer = NewJSNativePointer(newBuffer, NativeAreaAllocator::FreeBufferFunc,
471                                                            vm_->GetNativeAreaAllocator(), false, size, Concurrent::NO,
472                                                            NativeFlag::REGEXP_BTYECODE);
473     regexp->SetByteCodeBuffer(thread_, pointer.GetTaggedValue());
474     regexp->SetLength(static_cast<uint32_t>(size));
475     vm_->GetNativeAreaAllocator()->IncreaseNativeSizeStats(size, NativeFlag::REGEXP_BTYECODE);
476 }
477 
NewEcmaHClass(uint32_t size,JSType type,const JSHandle<JSTaggedValue> & prototype)478 JSHandle<JSHClass> ObjectFactory::NewEcmaHClass(uint32_t size, JSType type, const JSHandle<JSTaggedValue> &prototype)
479 {
480     const int inlinedProps = JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS;
481     return NewEcmaHClass(size, inlinedProps, type, prototype);
482 }
483 
NewEcmaHClass(uint32_t size,uint32_t inlinedProps,JSType type,const JSHandle<JSTaggedValue> & prototype)484 JSHandle<JSHClass> ObjectFactory::NewEcmaHClass(uint32_t size, uint32_t inlinedProps, JSType type,
485                                                 const JSHandle<JSTaggedValue> &prototype)
486 {
487     return NewEcmaHClass(thread_->GetGlobalEnv(), size, inlinedProps, type, prototype);
488 }
489 
NewEcmaHClass(const JSHandle<GlobalEnv> & env,uint32_t size,uint32_t inlinedProps,JSType type,const JSHandle<JSTaggedValue> & prototype)490 JSHandle<JSHClass> ObjectFactory::NewEcmaHClass(const JSHandle<GlobalEnv> &env,
491     uint32_t size, uint32_t inlinedProps, JSType type, const JSHandle<JSTaggedValue> &prototype)
492 {
493     NewObjectHook();
494     uint32_t classSize = JSHClass::SIZE;
495     auto *newClass = static_cast<JSHClass *>(heap_->AllocateNonMovableOrHugeObject(
496         JSHClass::Cast(thread_->GlobalConstants()->GetHClassClass().GetTaggedObject()), classSize));
497     newClass->Initialize(thread_, size, type, inlinedProps);
498     JSHandle<JSHClass> hclass(thread_, newClass);
499     hclass->SetPrototype(thread_, env, prototype.GetTaggedValue());
500     return hclass;
501 }
502 
NewJSObject(const JSHandle<JSHClass> & jshclass)503 JSHandle<JSObject> ObjectFactory::NewJSObject(const JSHandle<JSHClass> &jshclass)
504 {
505     JSHandle<JSObject> obj(thread_, JSObject::Cast(NewObject(jshclass)));
506     JSHandle<TaggedArray> emptyArray = EmptyArray();
507     obj->InitializeHash();
508     obj->SetElements<SKIP_BARRIER>(thread_, emptyArray);
509     obj->SetProperties<SKIP_BARRIER>(thread_, emptyArray);
510     return obj;
511 }
512 
CloneProperties(const JSHandle<TaggedArray> & old)513 JSHandle<TaggedArray> ObjectFactory::CloneProperties(const JSHandle<TaggedArray> &old)
514 {
515     uint32_t newLength = old->GetLength();
516     if (newLength == 0) {
517         return EmptyArray();
518     }
519     NewObjectHook();
520     auto klass = old->GetClass();
521     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), newLength);
522     auto header = heap_->AllocateYoungOrHugeObject(klass, size);
523     JSHandle<TaggedArray> newArray(thread_, header);
524     newArray->InitializeWithSpecialValue(JSTaggedValue::Hole(), newLength, old->GetExtraLength());
525     for (uint32_t i = 0; i < newLength; i++) {
526         JSTaggedValue value = old->Get(thread_, i);
527         newArray->Set(thread_, i, value);
528     }
529     return newArray;
530 }
531 
CloneObjectLiteral(JSHandle<JSObject> object)532 JSHandle<JSObject> ObjectFactory::CloneObjectLiteral(JSHandle<JSObject> object)
533 {
534     NewObjectHook();
535     auto klass = JSHandle<JSHClass>(thread_, object->GetClass());
536 
537     JSHandle<JSObject> cloneObject = NewJSObject(klass);
538 
539     JSHandle<TaggedArray> elements(thread_, object->GetElements(thread_));
540     auto newElements = CloneProperties(elements);
541     cloneObject->SetElements(thread_, newElements.GetTaggedValue());
542 
543     JSHandle<TaggedArray> properties(thread_, object->GetProperties(thread_));
544     auto newProperties = CloneProperties(properties);
545     cloneObject->SetProperties(thread_, newProperties.GetTaggedValue());
546     uint32_t length = std::min(klass->GetInlinedProperties(), klass->NumberOfProps());
547 
548     for (uint32_t i = 0; i < length; i++) {
549         cloneObject->SetPropertyInlinedPropsWithRep(thread_, i, object->GetPropertyInlinedProps(thread_, i));
550     }
551     return cloneObject;
552 }
553 
CloneArrayLiteral(JSHandle<JSArray> object)554 JSHandle<JSArray> ObjectFactory::CloneArrayLiteral(JSHandle<JSArray> object)
555 {
556     NewObjectHook();
557     auto klass = JSHandle<JSHClass>(thread_, object->GetClass());
558 
559     JSHandle<JSArray> cloneObject(NewJSObject(klass));
560     cloneObject->SetArrayLength(thread_, object->GetArrayLength());
561     cloneObject->SetTrackInfo(thread_, JSTaggedValue::Undefined());
562 
563     JSHandle<TaggedArray> elements(thread_, object->GetElements(thread_));
564     static constexpr uint8_t MAX_READ_ONLY_ARRAY_LENGTH = 10;
565     uint32_t elementsLength = elements->GetLength();
566     MemSpaceType type = elementsLength > MAX_READ_ONLY_ARRAY_LENGTH ?
567         MemSpaceType::SEMI_SPACE : MemSpaceType::NON_MOVABLE;
568 
569 #if !defined ENABLE_COW_ARRAY
570     type = MemSpaceType::SEMI_SPACE;
571 #endif
572 
573     if (type == MemSpaceType::NON_MOVABLE && elements.GetTaggedValue().IsCOWArray()) {
574         // share the same elements array in nonmovable space.
575         cloneObject->SetElements(thread_, elements.GetTaggedValue());
576     } else {
577         auto newElements = CopyArray(elements, elementsLength, elementsLength, JSTaggedValue::Hole(), type);
578         cloneObject->SetElements(thread_, newElements.GetTaggedValue());
579     }
580 
581     if (type == MemSpaceType::NON_MOVABLE && !object->GetElements(thread_).IsCOWArray()) {
582         ASSERT(g_isEnableCMCGC ||
583             !Region::ObjectAddressToRange(object->GetElements(thread_).GetTaggedObject())->InNonMovableSpace());
584         // Set the first shared elements into the old object.
585         object->SetElements(thread_, cloneObject->GetElements(thread_));
586     }
587 
588     JSHandle<TaggedArray> properties(thread_, object->GetProperties(thread_));
589     uint32_t propertiesLength = properties->GetLength();
590     type = propertiesLength > MAX_READ_ONLY_ARRAY_LENGTH ?
591         MemSpaceType::SEMI_SPACE : MemSpaceType::NON_MOVABLE;
592 
593 #if !defined ENABLE_COW_ARRAY
594     type = MemSpaceType::SEMI_SPACE;
595 #endif
596 
597     if (type == MemSpaceType::NON_MOVABLE && properties.GetTaggedValue().IsCOWArray()) {
598         // share the same properties array in nonmovable space.
599         cloneObject->SetProperties(thread_, properties.GetTaggedValue());
600     } else {
601         auto newProperties = CopyArray(properties, propertiesLength, propertiesLength, JSTaggedValue::Hole(), type);
602         cloneObject->SetProperties(thread_, newProperties.GetTaggedValue());
603     }
604 
605     if (type == MemSpaceType::NON_MOVABLE && !object->GetProperties(thread_).IsCOWArray()) {
606         ASSERT(g_isEnableCMCGC ||
607             !Region::ObjectAddressToRange(object->GetProperties(thread_).GetTaggedObject())->InNonMovableSpace());
608         // Set the first shared properties into the old object.
609         object->SetProperties(thread_, cloneObject->GetProperties(thread_));
610     }
611 
612     for (uint32_t i = 0; i < klass->GetInlinedProperties(); i++) {
613         cloneObject->SetPropertyInlinedPropsWithRep(thread_, i, object->GetPropertyInlinedProps(thread_, i));
614     }
615     return cloneObject;
616 }
617 
CloneProperties(const JSHandle<TaggedArray> & old,const JSHandle<JSTaggedValue> & env,const JSHandle<JSObject> & obj)618 JSHandle<TaggedArray> ObjectFactory::CloneProperties(const JSHandle<TaggedArray> &old,
619                                                      const JSHandle<JSTaggedValue> &env, const JSHandle<JSObject> &obj)
620 {
621     uint32_t newLength = old->GetLength();
622     if (newLength == 0) {
623         return EmptyArray();
624     }
625     NewObjectHook();
626     auto klass = old->GetClass();
627     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), newLength);
628     auto header = heap_->AllocateYoungOrHugeObject(klass, size);
629     JSHandle<TaggedArray> newArray(thread_, header);
630     newArray->InitializeWithSpecialValue(JSTaggedValue::Hole(), newLength, old->GetExtraLength());
631 
632     for (uint32_t i = 0; i < newLength; i++) {
633         JSTaggedValue value = old->Get(thread_, i);
634         if (!value.IsJSFunction()) {
635             newArray->Set(thread_, i, value);
636         } else {
637             JSHandle<JSFunction> valueHandle(thread_, value);
638             JSHandle<JSFunction> newFunc = CloneJSFunction(valueHandle);
639             newFunc->SetLexicalEnv(thread_, env);
640             newFunc->SetHomeObject(thread_, obj);
641             newArray->Set(thread_, i, newFunc);
642         }
643     }
644     return newArray;
645 }
646 
CloneObjectLiteral(JSHandle<JSObject> object,const JSHandle<JSTaggedValue> & env,bool canShareHClass)647 JSHandle<JSObject> ObjectFactory::CloneObjectLiteral(JSHandle<JSObject> object,
648                                                      const JSHandle<JSTaggedValue> &env,
649                                                      bool canShareHClass)
650 {
651     NewObjectHook();
652     auto klass = JSHandle<JSHClass>(thread_, object->GetClass());
653 
654     if (!canShareHClass) {
655         klass = JSHClass::Clone(thread_, klass);
656     }
657 
658     JSHandle<JSObject> cloneObject = NewJSObject(klass);
659 
660     JSHandle<TaggedArray> elements(thread_, object->GetElements(thread_));
661     auto newElements = CloneProperties(elements, env, cloneObject);
662     cloneObject->SetElements(thread_, newElements.GetTaggedValue());
663 
664     JSHandle<TaggedArray> properties(thread_, object->GetProperties(thread_));
665     auto newProperties = CloneProperties(properties, env, cloneObject);
666     cloneObject->SetProperties(thread_, newProperties.GetTaggedValue());
667     uint32_t length = std::min(klass->GetInlinedProperties(), klass->NumberOfProps());
668 
669     for (uint32_t i = 0; i < length; i++) {
670         auto layout = LayoutInfo::Cast(klass->GetLayout(thread_).GetTaggedObject());
671         JSTaggedValue value = object->GetPropertyInlinedProps(thread_, i);
672         if (!layout->GetAttr(thread_, i).IsTaggedRep() || (!value.IsJSFunction() && !value.IsAccessorData())) {
673             cloneObject->SetPropertyInlinedPropsWithRep(thread_, i, value);
674         } else if (value.IsJSFunction()) {
675             JSHandle<JSFunction> valueHandle(thread_, value);
676             JSHandle<JSFunction> newFunc = CloneJSFunction(valueHandle);
677             newFunc->SetLexicalEnv(thread_, env);
678             newFunc->SetHomeObject(thread_, cloneObject);
679             cloneObject->SetPropertyInlinedProps(thread_, i, newFunc.GetTaggedValue());
680         } else {
681             if (value.IsAccessorData()) {
682                 JSHandle<AccessorData> accessor = NewAccessorData();
683                 value = accessor.GetTaggedValue();
684             }
685             cloneObject->SetPropertyInlinedPropsWithRep(thread_, i, value);
686         }
687     }
688     return cloneObject;
689 }
690 
CloneJSFunction(JSHandle<JSFunction> func)691 JSHandle<JSFunction> ObjectFactory::CloneJSFunction(JSHandle<JSFunction> func)
692 {
693     JSHandle<JSHClass> jshclass(thread_, func->GetJSHClass());
694     JSHandle<Method> method(thread_, func->GetMethod(thread_));
695     JSHandle<JSFunction> cloneFunc = NewJSFunctionByHClass(method, jshclass);
696 
697     JSTaggedValue length = func->GetPropertyInlinedProps(thread_, JSFunction::LENGTH_INLINE_PROPERTY_INDEX);
698     cloneFunc->SetPropertyInlinedProps(thread_, JSFunction::LENGTH_INLINE_PROPERTY_INDEX, length);
699     cloneFunc->SetLength(func->GetLength());
700     cloneFunc->SetModule(thread_, func->GetModule(thread_));
701     return cloneFunc;
702 }
703 
CloneSFunction(JSHandle<JSFunction> func)704 JSHandle<JSFunction> ObjectFactory::CloneSFunction(JSHandle<JSFunction> func)
705 {
706     ASSERT(func.GetTaggedValue().IsJSSharedFunction());
707     JSHandle<JSHClass> jshclass(thread_, func->GetJSHClass());
708     JSHandle<Method> method(thread_, func->GetMethod(thread_));
709     JSHandle<JSFunction> cloneFunc = NewSFunctionByHClass(method, jshclass);
710 
711     JSTaggedValue length = func->GetPropertyInlinedProps(thread_, JSFunction::LENGTH_INLINE_PROPERTY_INDEX);
712     cloneFunc->SetPropertyInlinedProps(thread_, JSFunction::LENGTH_INLINE_PROPERTY_INDEX, length);
713     cloneFunc->SetLength(func->GetLength());
714     cloneFunc->SetModule(thread_, func->GetModule(thread_));
715     return cloneFunc;
716 }
717 
CreateJSFunctionFromTemplate(JSHandle<FunctionTemplate> funcTemp)718 JSHandle<JSFunction> ObjectFactory::CreateJSFunctionFromTemplate(JSHandle<FunctionTemplate> funcTemp)
719 {
720     NewObjectHook();
721     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
722     auto kind = funcTemp->GetFunctionKind(thread_);
723     JSHandle<JSHClass> jshclass;
724     if (kind == FunctionKind::NORMAL_FUNCTION ||
725         kind == FunctionKind::GETTER_FUNCTION ||
726         kind == FunctionKind::SETTER_FUNCTION) {
727         jshclass = JSHandle<JSHClass>::Cast(env->GetFunctionClassWithoutProto());
728     } else if (kind == FunctionKind::ASYNC_FUNCTION) {
729         jshclass = JSHandle<JSHClass>::Cast(env->GetAsyncFunctionClass());
730     } else {
731         jshclass = JSHandle<JSHClass>::Cast(env->GetGeneratorFunctionClass());
732     }
733     JSHandle<Method> method = JSHandle<Method>(thread_, funcTemp->GetMethod(thread_));
734     JSHandle<JSFunction> newFunc = NewJSFunctionByHClass(method, jshclass);
735 
736     newFunc->SetLength(funcTemp->GetLength());
737     newFunc->SetModule(thread_, funcTemp->GetModule(thread_));
738     return newFunc;
739 }
740 
CreateSFunctionFromTemplate(JSHandle<FunctionTemplate> funcTemp)741 JSHandle<JSFunction> ObjectFactory::CreateSFunctionFromTemplate(JSHandle<FunctionTemplate> funcTemp)
742 {
743     NewObjectHook();
744     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
745     auto kind = funcTemp->GetFunctionKind(thread_);
746     JSHandle<JSHClass> jshclass;
747     if (kind == FunctionKind::NORMAL_FUNCTION ||
748         kind == FunctionKind::GETTER_FUNCTION ||
749         kind == FunctionKind::SETTER_FUNCTION) {
750         jshclass = JSHandle<JSHClass>::Cast(env->GetSFunctionClassWithoutProto());
751     } else if (kind == FunctionKind::ASYNC_FUNCTION) {
752         jshclass = JSHandle<JSHClass>::Cast(env->GetAsyncFunctionClass());
753     } else {
754         jshclass = JSHandle<JSHClass>::Cast(env->GetGeneratorFunctionClass());
755     }
756     JSHandle<Method> method(thread_, funcTemp->GetMethod(thread_));
757     JSHandle<JSFunction> newFunc = NewSFunctionByHClass(method, jshclass);
758 
759     newFunc->SetLength(funcTemp->GetLength());
760     newFunc->SetModule(thread_, funcTemp->GetModule(thread_));
761     return newFunc;
762 }
763 
CloneClassCtor(JSHandle<JSFunction> ctor,const JSHandle<JSTaggedValue> & lexenv,bool canShareHClass)764 JSHandle<JSFunction> ObjectFactory::CloneClassCtor(JSHandle<JSFunction> ctor, const JSHandle<JSTaggedValue> &lexenv,
765                                                    bool canShareHClass)
766 {
767     NewObjectHook();
768     JSHandle<JSHClass> hclass(thread_, ctor->GetClass());
769 
770     if (!canShareHClass) {
771         hclass = JSHClass::Clone(thread_, hclass);
772     }
773 
774     JSHandle<Method> method(thread_, ctor->GetMethod(thread_));
775     ASSERT_PRINT(method->GetFunctionKind() == FunctionKind::CLASS_CONSTRUCTOR ||
776                  method->GetFunctionKind() == FunctionKind::DERIVED_CONSTRUCTOR,
777                  "cloned function is not class");
778     JSHandle<JSFunction> cloneCtor = NewJSFunctionByHClass(method, hclass);
779     uint32_t length = std::min(hclass->GetInlinedProperties(), hclass->NumberOfProps());
780 
781     for (uint32_t i = 0; i < length; i++) {
782         auto layout = LayoutInfo::Cast(hclass->GetLayout(thread_).GetTaggedObject());
783         JSTaggedValue value = ctor->GetPropertyInlinedProps(thread_, i);
784         if (!layout->GetAttr(thread_, i).IsTaggedRep() || !value.IsJSFunction()) {
785             cloneCtor->SetPropertyInlinedPropsWithRep(thread_, i, value);
786         } else {
787             JSHandle<JSFunction> valueHandle(thread_, value);
788             JSHandle<JSFunction> newFunc = CloneJSFunction(valueHandle);
789             newFunc->SetLexicalEnv(thread_, lexenv);
790             newFunc->SetHomeObject(thread_, cloneCtor);
791             cloneCtor->SetPropertyInlinedProps(thread_, i, newFunc.GetTaggedValue());
792         }
793     }
794 
795     JSHandle<TaggedArray> elements(thread_, ctor->GetElements(thread_));
796     auto newElements = CloneProperties(elements, lexenv, JSHandle<JSObject>(cloneCtor));
797     cloneCtor->SetElements(thread_, newElements.GetTaggedValue());
798 
799     JSHandle<TaggedArray> properties(thread_, ctor->GetProperties(thread_));
800     auto newProperties = CloneProperties(properties, lexenv, JSHandle<JSObject>(cloneCtor));
801     cloneCtor->SetProperties(thread_, newProperties.GetTaggedValue());
802 
803     return cloneCtor;
804 }
805 
NewNonMovableJSObject(const JSHandle<JSHClass> & jshclass)806 JSHandle<JSObject> ObjectFactory::NewNonMovableJSObject(const JSHandle<JSHClass> &jshclass)
807 {
808     JSHandle<JSObject> obj(thread_,
809                            JSObject::Cast(NewNonMovableObject(jshclass, jshclass->GetInlinedProperties())));
810     obj->InitializeHash();
811     obj->SetElements<SKIP_BARRIER>(thread_, EmptyArray());
812     obj->SetProperties<SKIP_BARRIER>(thread_, EmptyArray());
813     return obj;
814 }
815 
NewJSPrimitiveRef(const JSHandle<JSHClass> & hclass,const JSHandle<JSTaggedValue> & object)816 JSHandle<JSPrimitiveRef> ObjectFactory::NewJSPrimitiveRef(const JSHandle<JSHClass> &hclass,
817                                                           const JSHandle<JSTaggedValue> &object)
818 {
819     JSHandle<JSPrimitiveRef> obj = JSHandle<JSPrimitiveRef>::Cast(NewJSObject(hclass));
820     obj->SetValue(thread_, object);
821     return obj;
822 }
823 
NewJSArray()824 JSHandle<JSArray> ObjectFactory::NewJSArray()
825 {
826     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
827     JSHandle<JSFunction> function(env->GetArrayFunction());
828     return JSHandle<JSArray>(NewJSObjectByConstructor(function));
829 }
830 
NewJSArray(size_t length,JSHandle<JSHClass> & hclass)831 JSHandle<JSArray> ObjectFactory::NewJSArray(size_t length, JSHandle<JSHClass> &hclass)
832 {
833     JSHandle<JSObject> obj = NewJSObject(hclass);
834     JSArray::Cast(*obj)->SetLength(length);
835     JSArray::Cast(*obj)->SetTrackInfo(thread_, JSTaggedValue::Undefined());
836     auto accessor = thread_->GlobalConstants()->GetArrayLengthAccessor();
837     JSArray::Cast(*obj)->SetPropertyInlinedProps(thread_, JSArray::LENGTH_INLINE_PROPERTY_INDEX, accessor);
838     return JSHandle<JSArray>(obj);
839 }
840 
NewJsonFixedArray(size_t start,size_t length,const std::vector<JSHandle<JSTaggedValue>> & vec)841 JSHandle<TaggedArray> ObjectFactory::NewJsonFixedArray(size_t start, size_t length,
842                                                        const std::vector<JSHandle<JSTaggedValue>> &vec)
843 {
844     if (length == 0) {
845         return EmptyArray();
846     }
847 
848     MemSpaceType spaceType = length < LENGTH_THRESHOLD ? MemSpaceType::SEMI_SPACE : MemSpaceType::OLD_SPACE;
849     JSHandle<TaggedArray> array = NewTaggedArrayWithoutInit(length, spaceType);
850     array->SetExtraLength(0);
851     for (size_t i = 0; i < length; i++) {
852         array->Set(thread_, i, vec[start + i]);
853     }
854     return array;
855 }
856 
857 // For slow keys, cacheHclass != receiver's hclass.
NewJSForinIterator(const JSHandle<JSTaggedValue> & obj,const JSHandle<JSTaggedValue> keys,const JSHandle<JSTaggedValue> cachedHClass,const uint32_t enumCacheKind)858 JSHandle<JSForInIterator> ObjectFactory::NewJSForinIterator(const JSHandle<JSTaggedValue> &obj,
859                                                             const JSHandle<JSTaggedValue> keys,
860                                                             const JSHandle<JSTaggedValue> cachedHClass,
861                                                             const uint32_t enumCacheKind)
862 {
863     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
864     JSHandle<JSHClass> hclass(env->GetForinIteratorClass());
865     uint32_t enumLength = JSHandle<TaggedArray>::Cast(keys)->GetLength();
866     JSHandle<JSForInIterator> it = JSHandle<JSForInIterator>::Cast(NewJSObject(hclass));
867 
868     it->SetCachedHClass(thread_, cachedHClass);
869     it->SetCacheKind(enumCacheKind);
870     it->SetIndex(0);
871     it->SetKeys(thread_, keys);
872     it->SetObject(thread_, obj);
873     it->SetLength(enumLength);
874 
875     return it;
876 }
877 
CreateJSRegExpInstanceClass(JSHandle<JSTaggedValue> proto)878 JSHandle<JSHClass> ObjectFactory::CreateJSRegExpInstanceClass(JSHandle<JSTaggedValue> proto)
879 {
880     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
881     JSHandle<JSHClass> regexpClass = NewEcmaHClass(JSRegExp::SIZE, JSType::JS_REG_EXP, proto);
882 
883     uint32_t fieldOrder = 0;
884     JSHandle<LayoutInfo> layoutInfoHandle = CreateLayoutInfo(1);
885     {
886         PropertyAttributes attributes = PropertyAttributes::Default(true, false, false);
887         attributes.SetIsInlinedProps(true);
888         attributes.SetRepresentation(Representation::TAGGED);
889         attributes.SetOffset(fieldOrder++);
890         layoutInfoHandle->AddKey(thread_, 0, globalConst->GetLastIndexString(), attributes);
891     }
892 
893     {
894         regexpClass->SetLayout(thread_, layoutInfoHandle);
895         regexpClass->SetNumberOfProps(fieldOrder);
896     }
897 
898     return regexpClass;
899 }
900 
CreateJSArrayInstanceClass(const JSHandle<GlobalEnv> & env,JSHandle<JSTaggedValue> proto,uint32_t inlinedProps)901 JSHandle<JSHClass> ObjectFactory::CreateJSArrayInstanceClass(const JSHandle<GlobalEnv> &env,
902     JSHandle<JSTaggedValue> proto, uint32_t inlinedProps)
903 {
904     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
905     JSHandle<JSHClass> arrayClass = NewEcmaHClass(env, JSArray::SIZE, inlinedProps, JSType::JS_ARRAY, proto);
906 
907     uint32_t fieldOrder = 0;
908     ASSERT(JSArray::LENGTH_INLINE_PROPERTY_INDEX == fieldOrder);
909     JSHandle<LayoutInfo> layoutInfoHandle = CreateLayoutInfo(1);
910     {
911         PropertyAttributes attributes = PropertyAttributes::DefaultAccessor(true, false, false);
912         attributes.SetIsInlinedProps(true);
913         attributes.SetRepresentation(Representation::TAGGED);
914         attributes.SetOffset(fieldOrder++);
915         layoutInfoHandle->AddKey(thread_, 0, globalConst->GetLengthString(), attributes);
916     }
917 
918     {
919         arrayClass->SetLayout(thread_, layoutInfoHandle);
920         arrayClass->SetNumberOfProps(fieldOrder);
921     }
922     arrayClass->SetIsStableElements(true);
923     arrayClass->SetHasConstructor(false);
924 
925     return arrayClass;
926 }
927 
CreateJSArguments(const JSHandle<GlobalEnv> & env)928 JSHandle<JSHClass> ObjectFactory::CreateJSArguments(const JSHandle<GlobalEnv> &env)
929 {
930     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
931     JSHandle<JSTaggedValue> proto = env->GetObjectFunctionPrototype();
932 
933     JSHandle<JSHClass> argumentsClass = NewEcmaHClass(JSArguments::SIZE, JSType::JS_ARGUMENTS, proto);
934 
935     uint32_t fieldOrder = 0;
936     ASSERT(JSArguments::LENGTH_INLINE_PROPERTY_INDEX == fieldOrder);
937     JSHandle<LayoutInfo> layoutInfoHandle = CreateLayoutInfo(JSArguments::LENGTH_OF_INLINE_PROPERTIES);
938     {
939         PropertyAttributes attributes = PropertyAttributes::Default(true, false, true);
940         attributes.SetIsInlinedProps(true);
941         attributes.SetRepresentation(Representation::TAGGED);
942         attributes.SetOffset(fieldOrder++);
943         layoutInfoHandle->AddKey(thread_, JSArguments::LENGTH_INLINE_PROPERTY_INDEX, globalConst->GetLengthString(),
944                                  attributes);
945     }
946 
947     ASSERT(JSArguments::ITERATOR_INLINE_PROPERTY_INDEX == fieldOrder);
948     {
949         PropertyAttributes attributes = PropertyAttributes::Default(true, false, true);
950         attributes.SetIsInlinedProps(true);
951         attributes.SetRepresentation(Representation::TAGGED);
952         attributes.SetOffset(fieldOrder++);
953         layoutInfoHandle->AddKey(thread_, JSArguments::ITERATOR_INLINE_PROPERTY_INDEX,
954                                  env->GetIteratorSymbol().GetTaggedValue(), attributes);
955     }
956 
957     {
958         ASSERT(JSArguments::CALLER_INLINE_PROPERTY_INDEX == fieldOrder);
959         PropertyAttributes attributes = PropertyAttributes::Default(false, false, false);
960         attributes.SetIsInlinedProps(true);
961         attributes.SetIsAccessor(true);
962         attributes.SetRepresentation(Representation::TAGGED);
963         attributes.SetOffset(fieldOrder++);
964         layoutInfoHandle->AddKey(thread_, JSArguments::CALLER_INLINE_PROPERTY_INDEX,
965                                  thread_->GlobalConstants()->GetHandledCallerString().GetTaggedValue(), attributes);
966     }
967 
968     {
969         ASSERT(JSArguments::CALLEE_INLINE_PROPERTY_INDEX == fieldOrder);
970         PropertyAttributes attributes = PropertyAttributes::Default(false, false, false);
971         attributes.SetIsInlinedProps(true);
972         attributes.SetIsAccessor(true);
973         attributes.SetRepresentation(Representation::TAGGED);
974         attributes.SetOffset(fieldOrder++);
975         layoutInfoHandle->AddKey(thread_, JSArguments::CALLEE_INLINE_PROPERTY_INDEX,
976                                  thread_->GlobalConstants()->GetHandledCalleeString().GetTaggedValue(), attributes);
977     }
978 
979     {
980         argumentsClass->SetLayout(thread_, layoutInfoHandle);
981         argumentsClass->SetNumberOfProps(fieldOrder);
982     }
983     argumentsClass->SetIsStableElements(true);
984     return argumentsClass;
985 }
986 
NewJSArguments()987 JSHandle<JSArguments> ObjectFactory::NewJSArguments()
988 {
989     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
990     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetArgumentsClass());
991     JSHandle<JSArguments> obj = JSHandle<JSArguments>::Cast(NewJSObject(hclass));
992     return obj;
993 }
994 
GetJSError(const ErrorType & errorType,const char * data,StackCheck needCheckStack)995 JSHandle<JSObject> ObjectFactory::GetJSError(const ErrorType &errorType, const char *data, StackCheck needCheckStack)
996 {
997     ASSERT_PRINT(errorType == ErrorType::ERROR || errorType == ErrorType::EVAL_ERROR ||
998                      errorType == ErrorType::RANGE_ERROR || errorType == ErrorType::REFERENCE_ERROR ||
999                      errorType == ErrorType::SYNTAX_ERROR || errorType == ErrorType::TYPE_ERROR ||
1000                      errorType == ErrorType::URI_ERROR || errorType == ErrorType::OOM_ERROR ||
1001                      errorType == ErrorType::TERMINATION_ERROR,
1002                  "The error type is not in the valid range.");
1003     if (data != nullptr) {
1004         JSHandle<EcmaString> handleMsg = NewFromUtf8(data);
1005         return NewJSError(errorType, handleMsg, needCheckStack);
1006     }
1007     JSHandle<EcmaString> emptyString(thread_->GlobalConstants()->GetHandledEmptyString());
1008     return NewJSError(errorType, emptyString, needCheckStack);
1009 }
1010 
NewJSError(const JSHandle<GlobalEnv> & env,const ErrorType & errorType,const JSHandle<EcmaString> & message,StackCheck needCheckStack)1011 JSHandle<JSObject> ObjectFactory::NewJSError(const JSHandle<GlobalEnv> &env, const ErrorType &errorType,
1012                                              const JSHandle<EcmaString> &message, StackCheck needCheckStack)
1013 {
1014     // if there have exception in thread, then return current exception, no need to new js error.
1015     if (thread_->HasPendingException()) {
1016         JSHandle<JSObject> obj(thread_, thread_->GetException());
1017         return obj;
1018     }
1019 
1020     // current frame may be entry frame, exception happened in JSFunction::Call and JSFunction::Construct,
1021     // in this case sp = the prev frame (interpreter frame).
1022     if (!thread_->IsAsmInterpreter()) {
1023         FrameHandler frameHandler(thread_);
1024         if (frameHandler.IsInterpretedEntryFrame()) {
1025             thread_->SetCurrentSPFrame(frameHandler.GetPrevJSFrame());
1026         }
1027     }
1028 
1029     JSHandle<JSTaggedValue> nativeConstructor;
1030     switch (errorType) {
1031         case ErrorType::RANGE_ERROR:
1032             nativeConstructor = env->GetRangeErrorFunction();
1033             break;
1034         case ErrorType::EVAL_ERROR:
1035             nativeConstructor = env->GetEvalErrorFunction();
1036             break;
1037         case ErrorType::REFERENCE_ERROR:
1038             nativeConstructor = env->GetReferenceErrorFunction();
1039             break;
1040         case ErrorType::TYPE_ERROR:
1041             nativeConstructor = env->GetTypeErrorFunction();
1042             break;
1043         case ErrorType::URI_ERROR:
1044             nativeConstructor = env->GetURIErrorFunction();
1045             break;
1046         case ErrorType::SYNTAX_ERROR:
1047             nativeConstructor = env->GetSyntaxErrorFunction();
1048             break;
1049         case ErrorType::OOM_ERROR:
1050             nativeConstructor = env->GetOOMErrorFunction();
1051             break;
1052         case ErrorType::TERMINATION_ERROR:
1053             nativeConstructor = env->GetTerminationErrorFunction();
1054             break;
1055         default:
1056             nativeConstructor = env->GetErrorFunction();
1057             break;
1058     }
1059     JSHandle<JSFunction> nativeFunc = JSHandle<JSFunction>::Cast(nativeConstructor);
1060     JSHandle<JSTaggedValue> nativePrototype(thread_, nativeFunc->GetFunctionPrototype(thread_));
1061     JSHandle<JSTaggedValue> undefined = thread_->GlobalConstants()->GetHandledUndefined();
1062     EcmaRuntimeCallInfo *info =
1063         EcmaInterpreter::NewRuntimeCallInfo(thread_, nativeConstructor, nativePrototype, undefined, 1, needCheckStack);
1064     RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSObject, thread_);
1065     info->SetCallArg(message.GetTaggedValue());
1066     JSTaggedValue obj = reinterpret_cast<EcmaEntrypoint>(nativeFunc->GetNativePointer())(info);
1067     RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSObject, thread_);
1068     JSHandle<JSObject> handleNativeInstanceObj(thread_, obj);
1069     auto sp = const_cast<JSTaggedType *>(thread_->GetCurrentSPFrame());
1070     ASSERT(FrameHandler::GetFrameType(sp) == FrameType::INTERPRETER_ENTRY_FRAME);
1071     auto prevEntry = InterpretedEntryFrame::GetFrameFromSp(sp)->GetPrevFrameFp();
1072     thread_->SetCurrentSPFrame(prevEntry);
1073     return handleNativeInstanceObj;
1074 }
1075 
NewJSError(const ErrorType & errorType,const JSHandle<EcmaString> & message,StackCheck needCheckStack)1076 JSHandle<JSObject> ObjectFactory::NewJSError(const ErrorType &errorType, const JSHandle<EcmaString> &message,
1077     StackCheck needCheckStack)
1078 {
1079     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
1080     return NewJSError(env, errorType, message, needCheckStack);
1081 }
1082 
NewJSAggregateError()1083 JSHandle<JSObject> ObjectFactory::NewJSAggregateError()
1084 {
1085     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
1086     JSHandle<JSFunction> constructor(env->GetAggregateErrorFunction());
1087     return NewJSObjectByConstructor(constructor);
1088 }
1089 
CreateNapiObject()1090 JSHandle<JSObject> ObjectFactory::CreateNapiObject()
1091 {
1092     JSHandle<GlobalEnv> globalEnv = vm_->GetGlobalEnv();
1093     JSHandle<JSFunction> constructor(globalEnv->GetObjectFunction());
1094     JSHandle<JSHClass> ihc(globalEnv->GetObjectFunctionNapiClass());
1095     JSHandle<JSHClass> tsIhc(globalEnv->GetObjectFunctionTsNapiClass());
1096     JSHandle<JSObject> jsObject;
1097     if (ihc != tsIhc) {
1098         jsObject = NewJSObjectWithInit(tsIhc);
1099     } else {
1100         jsObject = NewJSObjectWithInit(ihc);
1101     }
1102     return jsObject;
1103 }
1104 
NewJSObjectByConstructor(const JSHandle<GlobalEnv> & env,const JSHandle<JSFunction> & constructor,uint32_t inlinedProps)1105 JSHandle<JSObject> ObjectFactory::NewJSObjectByConstructor(const JSHandle<GlobalEnv> &env,
1106     const JSHandle<JSFunction> &constructor, uint32_t inlinedProps)
1107 {
1108     if (!constructor->HasFunctionPrototype(thread_) ||
1109         (constructor->GetProtoOrHClass(thread_).IsHeapObject() &&
1110          constructor->GetFunctionPrototype(thread_).IsECMAObject())) {
1111         JSHandle<JSHClass> jshclass;
1112         if (LIKELY(inlinedProps == JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS)) {
1113             jshclass = JSHandle<JSHClass>(thread_, JSFunction::GetOrCreateInitialJSHClass(thread_, constructor));
1114         } else {
1115             jshclass = NewEcmaHClass(JSObject::SIZE, inlinedProps, JSType::JS_OBJECT,
1116                                      env->GetObjectFunctionPrototype());
1117         }
1118         JSHandle<JSObject> obj;
1119         if (jshclass->IsJSShared()) {
1120             obj = NewSharedOldSpaceJSObject(jshclass);
1121             if (jshclass->IsDictionaryMode()) {
1122                 auto fieldLayout = jshclass->GetLayout(thread_);
1123                 ASSERT(fieldLayout.IsDictionary());
1124                 auto dict = JSHandle<TaggedArray>(thread_, fieldLayout);
1125                 auto properties = NewAndCopySNameDictionary(dict, dict->GetLength());
1126                 obj->SetProperties(thread_, properties);
1127             }
1128             if (constructor->IsClassConstructor()) {
1129                 JSTaggedValue elementsDic =
1130                     constructor->GetPropertyInlinedProps(thread_, ClassInfoExtractor::SENDABLE_ELEMENTS_INDEX);
1131                 if (elementsDic.IsDictionary()) {
1132                     JSHandle<TaggedArray> elementsDicHld(thread_, elementsDic);
1133                     JSHandle<TaggedArray> elements =
1134                         NewAndCopySNameDictionary(elementsDicHld, elementsDicHld->GetLength());
1135                     obj->SetElements(thread_, elements);
1136                     jshclass->SetIsDictionaryElement(true);
1137                 }
1138             }
1139             InitializeJSObject(obj, jshclass);
1140         } else {
1141             obj = NewJSObjectWithInit(jshclass);
1142         }
1143         return obj;
1144     }
1145     JSHandle<JSObject> result =
1146         NewJSObjectByConstructor(JSHandle<JSFunction>(env->GetObjectFunction()), JSHandle<JSTaggedValue>(constructor));
1147     if (thread_->HasPendingException()) {
1148         LOG_FULL(FATAL) << "NewJSObjectByConstructor should not throw Exception! ";
1149     }
1150     return result;
1151 }
1152 
NewJSObjectByConstructor(const JSHandle<JSFunction> & constructor,uint32_t inlinedProps)1153 JSHandle<JSObject> ObjectFactory::NewJSObjectByConstructor(const JSHandle<JSFunction> &constructor,
1154                                                            uint32_t inlinedProps)
1155 {
1156     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
1157     return NewJSObjectByConstructor(env, constructor, inlinedProps);
1158 }
1159 
NewJSObjectByConstructor(const JSHandle<JSFunction> & constructor,const JSHandle<JSTaggedValue> & newTarget)1160 JSHandle<JSObject> ObjectFactory::NewJSObjectByConstructor(const JSHandle<JSFunction> &constructor,
1161                                                            const JSHandle<JSTaggedValue> &newTarget)
1162 {
1163     if (constructor->IsJSShared() && !newTarget->IsJSShared()) {
1164         THROW_TYPE_ERROR_AND_RETURN(thread_, "shared ctor cannot assign unshared newTarget",
1165                                     JSHandle<JSObject>(thread_, JSTaggedValue::Undefined()));
1166     }
1167     JSHandle<JSHClass> jshclass;
1168     if (!constructor->HasFunctionPrototype(thread_) ||
1169         (constructor->GetProtoOrHClass(thread_).IsHeapObject() &&
1170          constructor->GetFunctionPrototype(thread_).IsECMAObject())) {
1171         jshclass = JSFunction::GetInstanceJSHClass(thread_, constructor, newTarget);
1172     } else {
1173         JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
1174         jshclass = JSFunction::GetInstanceJSHClass(thread_, JSHandle<JSFunction>(env->GetObjectFunction()), newTarget);
1175     }
1176     // Check this exception elsewhere
1177     RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSObject, thread_);
1178     JSHandle<JSObject> obj;
1179     if (jshclass->IsJSShared()) {
1180         obj = NewSharedOldSpaceJSObject(jshclass);
1181         if (jshclass->IsDictionaryMode()) {
1182             auto fieldLayout = jshclass->GetLayout(thread_);
1183             ASSERT(fieldLayout.IsDictionary());
1184             auto dict = JSHandle<TaggedArray>(thread_, fieldLayout);
1185             auto properties = NewAndCopySNameDictionary(dict, dict->GetLength());
1186             obj->SetProperties(thread_, properties);
1187         }
1188         if (constructor->IsClassConstructor() && newTarget->IsClassConstructor()) {
1189             JSTaggedValue elementsDicOfCtor =
1190                 constructor->GetPropertyInlinedProps(thread_, ClassInfoExtractor::SENDABLE_ELEMENTS_INDEX);
1191             JSTaggedValue elementsDicOfTrg =
1192                 JSHandle<JSFunction>(newTarget)->GetPropertyInlinedProps(thread_,
1193                     ClassInfoExtractor::SENDABLE_ELEMENTS_INDEX);
1194             if (elementsDicOfCtor.IsDictionary() && elementsDicOfTrg.IsDictionary()) {
1195                 JSHandle<TaggedArray> elements;
1196                 MergeSendableClassElementsDic(elements, JSHandle<JSTaggedValue>(thread_, elementsDicOfCtor),
1197                                               JSHandle<JSTaggedValue>(thread_, elementsDicOfTrg));
1198                 obj->SetElements(thread_, elements);
1199                 jshclass->SetIsDictionaryElement(true);
1200             }
1201         }
1202         InitializeJSObject(obj, jshclass);
1203     } else {
1204         obj = NewJSObjectWithInit(jshclass);
1205     }
1206     return obj;
1207 }
1208 
MergeSendableClassElementsDic(JSHandle<TaggedArray> & elements,const JSHandle<JSTaggedValue> & elementsDicOfCtorVal,const JSHandle<JSTaggedValue> & elementsDicOfTrgVal)1209 void ObjectFactory::MergeSendableClassElementsDic(JSHandle<TaggedArray> &elements,
1210                                                   const JSHandle<JSTaggedValue> &elementsDicOfCtorVal,
1211                                                   const JSHandle<JSTaggedValue> &elementsDicOfTrgVal)
1212 {
1213     JSHandle<JSTaggedValue> undefinedVal = thread_->GlobalConstants()->GetHandledUndefined();
1214 
1215     JSHandle<TaggedArray> elementsDicOfCtorHdl(elementsDicOfCtorVal);
1216     if (elementsDicOfCtorVal.GetTaggedValue() == elementsDicOfTrgVal.GetTaggedValue()) {
1217         elements = NewAndCopySNameDictionary(elementsDicOfCtorHdl, elementsDicOfCtorHdl->GetLength());
1218     } else {
1219         JSHandle<TaggedArray> elementsDicDicOfTrgHdl(elementsDicOfTrgVal);
1220         JSHandle<NumberDictionary> elementsDicOfCtor(elementsDicOfCtorVal);
1221         JSMutableHandle<JSTaggedValue> key(thread_, JSTaggedValue::Undefined());
1222 
1223         JSMutableHandle<NumberDictionary> newElementsDicUpdate(thread_, elementsDicOfCtor);
1224         uint32_t headerSize = 4;
1225         for (uint32_t i = headerSize; i < elementsDicDicOfTrgHdl->GetLength(); i++) {
1226             key.Update(elementsDicDicOfTrgHdl->Get(thread_, i));
1227             if (key->IsInt()) {
1228                 JSHandle<NumberDictionary> elementsDicOfTrg(elementsDicOfTrgVal);
1229 
1230                 int entry = elementsDicOfTrg->FindEntry(thread_, key.GetTaggedValue());
1231                 PropertyAttributes attributes = elementsDicOfTrg->GetAttributes(thread_, entry);
1232                 JSHandle<NumberDictionary> newElementsDic =
1233                     NumberDictionary::Put(thread_, elementsDicOfCtor, key, undefinedVal, attributes);
1234                 newElementsDicUpdate.Update(newElementsDic);
1235             }
1236         }
1237         JSHandle<TaggedArray> newElementsDicHld(newElementsDicUpdate);
1238         elements = NewAndCopySNameDictionary(newElementsDicHld, newElementsDicHld->GetLength());
1239     }
1240 }
1241 
NewJSObjectWithInit(const JSHandle<JSHClass> & jshclass)1242 JSHandle<JSObject> ObjectFactory::NewJSObjectWithInit(const JSHandle<JSHClass> &jshclass)
1243 {
1244     JSHandle<JSObject> obj = NewJSObject(jshclass);
1245     InitializeJSObject(obj, jshclass);
1246     return obj;
1247 }
1248 
InitializeJSObject(const JSHandle<JSObject> & obj,const JSHandle<JSHClass> & jshclass)1249 void ObjectFactory::InitializeJSObject(const JSHandle<JSObject> &obj, const JSHandle<JSHClass> &jshclass)
1250 {
1251     JSType type = jshclass->GetObjectType();
1252     switch (type) {
1253         case JSType::JS_OBJECT:
1254         case JSType::JS_XREF_OBJECT:
1255         case JSType::JS_ERROR:
1256         case JSType::JS_EVAL_ERROR:
1257         case JSType::JS_RANGE_ERROR:
1258         case JSType::JS_REFERENCE_ERROR:
1259         case JSType::JS_TYPE_ERROR:
1260         case JSType::JS_AGGREGATE_ERROR:
1261         case JSType::JS_URI_ERROR:
1262         case JSType::JS_SYNTAX_ERROR:
1263         case JSType::JS_OOM_ERROR:
1264         case JSType::JS_TERMINATION_ERROR:
1265         case JSType::JS_ASYNCITERATOR:
1266         case JSType::JS_SHARED_OBJECT:
1267         case JSType::JS_SHARED_FUNCTION:
1268         case JSType::JS_ITERATOR: {
1269             break;
1270         }
1271 #ifdef ARK_SUPPORT_INTL
1272         case JSType::JS_INTL: {
1273             JSIntl::Cast(*obj)->SetFallbackSymbol<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1274             JSHandle<JSSymbol> jsSymbol = NewPublicSymbolWithChar("IntlLegacyConstructedSymbol");
1275             JSIntl::Cast(*obj)->SetFallbackSymbol(thread_, jsSymbol);
1276             break;
1277         }
1278         case JSType::JS_LOCALE: {
1279             JSLocale::Cast(*obj)->SetIcuField<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1280             break;
1281         }
1282         case JSType::JS_DATE_TIME_FORMAT: {
1283             JSDateTimeFormat::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1284             JSDateTimeFormat::Cast(*obj)->SetCalendar<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1285             JSDateTimeFormat::Cast(*obj)->SetNumberingSystem<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1286             JSDateTimeFormat::Cast(*obj)->SetTimeZone<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1287             JSDateTimeFormat::Cast(*obj)->SetLocaleIcu<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1288             JSDateTimeFormat::Cast(*obj)->SetSimpleDateTimeFormatIcu<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1289             JSDateTimeFormat::Cast(*obj)->SetIso8601<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1290             JSDateTimeFormat::Cast(*obj)->SetBoundFormat<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1291             JSDateTimeFormat::Cast(*obj)->SetHourCycle(HourCycleOption::EXCEPTION);
1292             JSDateTimeFormat::Cast(*obj)->SetDateStyle(DateTimeStyleOption::EXCEPTION);
1293             JSDateTimeFormat::Cast(*obj)->SetTimeStyle(DateTimeStyleOption::EXCEPTION);
1294             break;
1295         }
1296         case JSType::JS_NUMBER_FORMAT: {
1297             JSNumberFormat::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1298             JSNumberFormat::Cast(*obj)->SetNumberingSystem<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1299             JSNumberFormat::Cast(*obj)->SetCurrency<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1300             JSNumberFormat::Cast(*obj)->SetUnit<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1301             JSNumberFormat::Cast(*obj)->SetMinimumIntegerDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1302             JSNumberFormat::Cast(*obj)->SetMinimumFractionDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1303             JSNumberFormat::Cast(*obj)->SetMaximumFractionDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1304             JSNumberFormat::Cast(*obj)->SetMinimumSignificantDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1305             JSNumberFormat::Cast(*obj)->SetMaximumSignificantDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1306             JSNumberFormat::Cast(*obj)->SetUseGrouping<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1307             JSNumberFormat::Cast(*obj)->SetBoundFormat<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1308             JSNumberFormat::Cast(*obj)->SetIcuField<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1309             JSNumberFormat::Cast(*obj)->SetStyle(StyleOption::EXCEPTION);
1310             JSNumberFormat::Cast(*obj)->SetCurrencySign(CurrencySignOption::EXCEPTION);
1311             JSNumberFormat::Cast(*obj)->SetCurrencyDisplay(CurrencyDisplayOption::EXCEPTION);
1312             JSNumberFormat::Cast(*obj)->SetUnitDisplay(UnitDisplayOption::EXCEPTION);
1313             JSNumberFormat::Cast(*obj)->SetSignDisplay(SignDisplayOption::EXCEPTION);
1314             JSNumberFormat::Cast(*obj)->SetCompactDisplay(CompactDisplayOption::EXCEPTION);
1315             JSNumberFormat::Cast(*obj)->SetNotation(NotationOption::EXCEPTION);
1316             JSNumberFormat::Cast(*obj)->SetRoundingType(RoundingType::EXCEPTION);
1317             break;
1318         }
1319         case JSType::JS_RELATIVE_TIME_FORMAT: {
1320             JSRelativeTimeFormat::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1321             JSRelativeTimeFormat::Cast(*obj)->SetNumberingSystem<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1322             JSRelativeTimeFormat::Cast(*obj)->SetIcuField<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1323             JSRelativeTimeFormat::Cast(*obj)->SetStyle(RelativeStyleOption::EXCEPTION);
1324             JSRelativeTimeFormat::Cast(*obj)->SetNumeric(NumericOption::EXCEPTION);
1325             break;
1326         }
1327         case JSType::JS_COLLATOR: {
1328             JSCollator::Cast(*obj)->SetIcuField<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1329             JSCollator::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1330             JSCollator::Cast(*obj)->SetCollation<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1331             JSCollator::Cast(*obj)->SetBoundCompare<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1332             JSCollator::Cast(*obj)->SetUsage(UsageOption::EXCEPTION);
1333             JSCollator::Cast(*obj)->SetCaseFirst(CaseFirstOption::EXCEPTION);
1334             JSCollator::Cast(*obj)->SetSensitivity(SensitivityOption::EXCEPTION);
1335             JSCollator::Cast(*obj)->SetIgnorePunctuation(false);
1336             JSCollator::Cast(*obj)->SetNumeric(false);
1337             break;
1338         }
1339         case JSType::JS_PLURAL_RULES: {
1340             JSPluralRules::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1341             JSPluralRules::Cast(*obj)->SetMinimumIntegerDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1342             JSPluralRules::Cast(*obj)->SetMinimumFractionDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1343             JSPluralRules::Cast(*obj)->SetMaximumFractionDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1344             JSPluralRules::Cast(*obj)->SetMinimumSignificantDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1345             JSPluralRules::Cast(*obj)->SetMaximumSignificantDigits<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1346             JSPluralRules::Cast(*obj)->SetIcuPR<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1347             JSPluralRules::Cast(*obj)->SetIcuNF<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1348             JSPluralRules::Cast(*obj)->SetRoundingType(RoundingType::EXCEPTION);
1349             JSPluralRules::Cast(*obj)->SetType(TypeOption::EXCEPTION);
1350             break;
1351         }
1352         case JSType::JS_DISPLAYNAMES: {
1353             JSDisplayNames::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1354             JSDisplayNames::Cast(*obj)->SetType(TypednsOption::EXCEPTION);
1355             JSDisplayNames::Cast(*obj)->SetStyle(StyOption::EXCEPTION);
1356             JSDisplayNames::Cast(*obj)->SetFallback(FallbackOption::EXCEPTION);
1357             JSDisplayNames::Cast(*obj)->SetIcuLDN<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1358             break;
1359         }
1360         case JSType::JS_SEGMENTER: {
1361             JSSegmenter::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1362             JSSegmenter::Cast(*obj)->SetGranularity(GranularityOption::EXCEPTION);
1363             JSSegmenter::Cast(*obj)->SetIcuField<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1364             break;
1365         }
1366         case JSType::JS_SEGMENTS: {
1367             JSSegments::Cast(*obj)->SetIcuField<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1368             JSSegments::Cast(*obj)->SetSegmentsString<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1369             JSSegments::Cast(*obj)->SetUnicodeString<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1370             JSSegments::Cast(*obj)->SetGranularity(GranularityOption::EXCEPTION);
1371             break;
1372         }
1373         case JSType::JS_SEGMENT_ITERATOR: {
1374             JSSegmentIterator::Cast(*obj)->SetIcuField<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1375             JSSegmentIterator::Cast(*obj)->SetIteratedString<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1376             JSSegmentIterator::Cast(*obj)->SetUnicodeString<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1377             JSSegmentIterator::Cast(*obj)->SetGranularity(GranularityOption::EXCEPTION);
1378             break;
1379         }
1380         case JSType::JS_LIST_FORMAT: {
1381             JSListFormat::Cast(*obj)->SetLocale<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1382             JSListFormat::Cast(*obj)->SetType(ListTypeOption::EXCEPTION);
1383             JSListFormat::Cast(*obj)->SetStyle(ListStyleOption::EXCEPTION);
1384             JSListFormat::Cast(*obj)->SetIcuLF<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1385             break;
1386         }
1387 #else
1388         case JSType::JS_INTL:
1389         case JSType::JS_LOCALE:
1390         case JSType::JS_DATE_TIME_FORMAT:
1391         case JSType::JS_NUMBER_FORMAT:
1392         case JSType::JS_RELATIVE_TIME_FORMAT:
1393         case JSType::JS_COLLATOR:
1394         case JSType::JS_PLURAL_RULES:
1395         case JSType::JS_DISPLAYNAMES:
1396         case JSType::JS_SEGMENTER:
1397         case JSType::JS_SEGMENTS:
1398         case JSType::JS_SEGMENT_ITERATOR:
1399         case JSType::JS_LIST_FORMAT: {
1400             break;
1401         }
1402 #endif
1403         case JSType::JS_ARRAY: {
1404             JSArray::Cast(*obj)->SetLength(0);
1405             JSArray::Cast(*obj)->SetTrackInfo(thread_, JSTaggedValue::Undefined());
1406             ASSERT(!obj->GetJSHClass()->IsDictionaryMode());
1407             auto accessor = thread_->GlobalConstants()->GetArrayLengthAccessor();
1408             JSArray::Cast(*obj)->SetPropertyInlinedProps(thread_, JSArray::LENGTH_INLINE_PROPERTY_INDEX, accessor);
1409             break;
1410         }
1411         case JSType::JS_SHARED_ARRAY: {
1412             JSSharedArray::Cast(*obj)->SetLength(0);
1413             JSSharedArray::Cast(*obj)->SetTrackInfo(thread_, JSTaggedValue::Undefined());
1414             ASSERT(!obj->GetJSHClass()->IsDictionaryMode());
1415             JSSharedArray::Cast(*obj)->SetModRecord(0);
1416             auto accessor = thread_->GlobalConstants()->GetSharedArrayLengthAccessor();
1417             JSSharedArray::Cast(*obj)->SetPropertyInlinedProps(thread_, JSArray::LENGTH_INLINE_PROPERTY_INDEX,
1418                                                                accessor);
1419             break;
1420         }
1421         case JSType::JS_DATE:
1422             JSDate::Cast(*obj)->SetTimeValue(thread_, JSTaggedValue(0.0));
1423             JSDate::Cast(*obj)->SetLocalOffset(thread_, JSTaggedValue(JSDate::MAX_DOUBLE));
1424             break;
1425         case JSType::JS_TYPED_ARRAY:
1426         case JSType::JS_INT8_ARRAY:
1427         case JSType::JS_UINT8_ARRAY:
1428         case JSType::JS_UINT8_CLAMPED_ARRAY:
1429         case JSType::JS_INT16_ARRAY:
1430         case JSType::JS_UINT16_ARRAY:
1431         case JSType::JS_INT32_ARRAY:
1432         case JSType::JS_UINT32_ARRAY:
1433         case JSType::JS_FLOAT32_ARRAY:
1434         case JSType::JS_FLOAT64_ARRAY:
1435         case JSType::JS_BIGINT64_ARRAY:
1436         case JSType::JS_BIGUINT64_ARRAY:
1437             JSTypedArray::Cast(*obj)->SetViewedArrayBufferOrByteArray<SKIP_BARRIER>(thread_,
1438                                                                                     JSTaggedValue::Undefined());
1439             JSTypedArray::Cast(*obj)->SetTypedArrayName<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1440             JSTypedArray::Cast(*obj)->SetByteLength(0);
1441             JSTypedArray::Cast(*obj)->SetByteOffset(0);
1442             JSTypedArray::Cast(*obj)->SetArrayLength(0);
1443             JSTypedArray::Cast(*obj)->SetContentType(ContentType::None);
1444             break;
1445         case JSType::JS_SHARED_TYPED_ARRAY:
1446         case JSType::JS_SHARED_INT8_ARRAY:
1447         case JSType::JS_SHARED_UINT8_ARRAY:
1448         case JSType::JS_SHARED_UINT8_CLAMPED_ARRAY:
1449         case JSType::JS_SHARED_INT16_ARRAY:
1450         case JSType::JS_SHARED_UINT16_ARRAY:
1451         case JSType::JS_SHARED_INT32_ARRAY:
1452         case JSType::JS_SHARED_UINT32_ARRAY:
1453         case JSType::JS_SHARED_FLOAT32_ARRAY:
1454         case JSType::JS_SHARED_FLOAT64_ARRAY:
1455         case JSType::JS_SHARED_BIGINT64_ARRAY:
1456         case JSType::JS_SHARED_BIGUINT64_ARRAY:
1457             JSSharedTypedArray::Cast(*obj)->SetViewedArrayBufferOrByteArray<SKIP_BARRIER>(thread_,
1458                                                                                           JSTaggedValue::Undefined());
1459             JSSharedTypedArray::Cast(*obj)->SetTypedArrayName<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1460             JSSharedTypedArray::Cast(*obj)->SetByteLength(0);
1461             JSSharedTypedArray::Cast(*obj)->SetByteOffset(0);
1462             JSSharedTypedArray::Cast(*obj)->SetArrayLength(0);
1463             JSSharedTypedArray::Cast(*obj)->SetContentType(ContentType::None);
1464             JSSharedTypedArray::Cast(*obj)->SetModRecord(0);
1465             break;
1466         case JSType::JS_REG_EXP:
1467             JSRegExp::Cast(*obj)->SetByteCodeBuffer<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1468             JSRegExp::Cast(*obj)->SetOriginalSource<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1469             JSRegExp::Cast(*obj)->SetOriginalFlags(thread_, JSTaggedValue(0));
1470             JSRegExp::Cast(*obj)->SetGroupName<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1471             JSRegExp::Cast(*obj)->SetLength(0);
1472             break;
1473         case JSType::JS_PRIMITIVE_REF:
1474             JSPrimitiveRef::Cast(*obj)->SetValue<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1475             break;
1476         case JSType::JS_SET:
1477             JSSet::Cast(*obj)->SetLinkedSet(thread_, JSTaggedValue::Undefined());
1478             break;
1479         case JSType::JS_SHARED_SET:
1480             JSSharedSet::Cast(*obj)->SetLinkedSet(thread_, JSTaggedValue::Undefined());
1481             JSSharedSet::Cast(*obj)->SetModRecord(0);
1482             break;
1483         case JSType::JS_MAP:
1484             JSMap::Cast(*obj)->SetLinkedMap<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1485             break;
1486         case JSType::JS_SHARED_MAP:
1487             JSSharedMap::Cast(*obj)->SetLinkedMap<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1488             JSSharedMap::Cast(*obj)->SetModRecord(0);
1489             break;
1490         case JSType::JS_WEAK_MAP:
1491             JSWeakMap::Cast(*obj)->SetLinkedMap<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1492             break;
1493         case JSType::JS_WEAK_SET:
1494             JSWeakSet::Cast(*obj)->SetLinkedSet<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1495             break;
1496         case JSType::JS_WEAK_REF:
1497             JSWeakRef::Cast(*obj)->SetWeakObject<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1498             break;
1499         case JSType::JS_FINALIZATION_REGISTRY:
1500             JSFinalizationRegistry::Cast(*obj)->SetCleanupCallback<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1501             JSFinalizationRegistry::Cast(*obj)->SetNoUnregister<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1502             JSFinalizationRegistry::Cast(*obj)->SetMaybeUnregister<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1503             JSFinalizationRegistry::Cast(*obj)->SetNext(thread_, JSTaggedValue::Null());
1504             JSFinalizationRegistry::Cast(*obj)->SetPrev(thread_, JSTaggedValue::Null());
1505             break;
1506         case JSType::JS_GENERATOR_OBJECT:
1507             JSGeneratorObject::Cast(*obj)->SetGeneratorContext<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1508             JSGeneratorObject::Cast(*obj)->SetResumeResult<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1509             JSGeneratorObject::Cast(*obj)->SetGeneratorState(JSGeneratorState::UNDEFINED);
1510             JSGeneratorObject::Cast(*obj)->SetResumeMode(GeneratorResumeMode::UNDEFINED);
1511             break;
1512         case JSType::JS_ASYNC_GENERATOR_OBJECT:
1513             JSAsyncGeneratorObject::Cast(*obj)->SetGeneratorContext<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1514             JSAsyncGeneratorObject::Cast(*obj)->SetAsyncGeneratorQueue(thread_, GetEmptyTaggedQueue().GetTaggedValue());
1515             JSAsyncGeneratorObject::Cast(*obj)->SetGeneratorBrand<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1516             JSAsyncGeneratorObject::Cast(*obj)->SetResumeResult<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1517             JSAsyncGeneratorObject::Cast(*obj)->SetAsyncGeneratorState(JSAsyncGeneratorState::UNDEFINED);
1518             JSAsyncGeneratorObject::Cast(*obj)->SetResumeMode(AsyncGeneratorResumeMode::UNDEFINED);
1519             break;
1520         case JSType::JS_STRING_ITERATOR:
1521             JSStringIterator::Cast(*obj)->SetStringIteratorNextIndex(0);
1522             JSStringIterator::Cast(*obj)->SetIteratedString<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1523             break;
1524         case JSType::JS_ASYNC_FROM_SYNC_ITERATOR:
1525             JSAsyncFromSyncIterator::Cast(*obj)->SetSyncIteratorRecord<SKIP_BARRIER>(thread_,
1526                                                                                      JSTaggedValue::Undefined());
1527             break;
1528         case JSType::JS_ASYNC_FROM_SYNC_ITER_UNWARP_FUNCTION:
1529             JSAsyncFromSyncIterUnwarpFunction::Cast(*obj)->SetDone<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1530             break;
1531         case JSType::JS_ARRAY_BUFFER:
1532             JSArrayBuffer::Cast(*obj)->SetArrayBufferData<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1533             JSArrayBuffer::Cast(*obj)->SetArrayBufferByteLength(0);
1534             JSArrayBuffer::Cast(*obj)->ClearBitField();
1535             break;
1536         case JSType::JS_SHARED_ARRAY_BUFFER:
1537             JSArrayBuffer::Cast(*obj)->SetArrayBufferData<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1538             JSArrayBuffer::Cast(*obj)->SetArrayBufferByteLength(0);
1539             JSArrayBuffer::Cast(*obj)->SetShared(true);
1540             break;
1541         case JSType::JS_SENDABLE_ARRAY_BUFFER:
1542             JSSendableArrayBuffer::Cast(*obj)->SetArrayBufferData<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1543             JSSendableArrayBuffer::Cast(*obj)->SetArrayBufferByteLength(0);
1544             break;
1545         case JSType::JS_PROMISE:
1546             JSPromise::Cast(*obj)->SetPromiseState(PromiseState::PENDING);
1547             JSPromise::Cast(*obj)->SetPromiseResult<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1548             JSPromise::Cast(*obj)->SetPromiseRejectReactions(thread_, GetEmptyTaggedQueue().GetTaggedValue());
1549             JSPromise::Cast(*obj)->SetPromiseFulfillReactions(thread_, GetEmptyTaggedQueue().GetTaggedValue());
1550             JSPromise::Cast(*obj)->SetAsyncTaskId(vm_->GetAsyncTaskId());
1551 
1552             JSPromise::Cast(*obj)->SetPromiseIsHandled(false);
1553             break;
1554         case JSType::JS_DATA_VIEW:
1555             JSDataView::Cast(*obj)->SetDataView(thread_, JSTaggedValue(false));
1556             JSDataView::Cast(*obj)->SetViewedArrayBuffer<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1557             JSDataView::Cast(*obj)->SetByteLength(0);
1558             JSDataView::Cast(*obj)->SetByteOffset(0);
1559             break;
1560         // non ECMA standard jsapi container
1561         case JSType::JS_API_ARRAY_LIST: {
1562             JSAPIArrayList::Cast(*obj)->SetLength(thread_, JSTaggedValue(0));
1563             break;
1564         }
1565         case JSType::JS_API_HASH_MAP: {
1566             JSAPIHashMap::Cast(*obj)->SetSize(0);
1567             JSAPIHashMap::Cast(*obj)->SetTable<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1568             break;
1569         }
1570         case JSType::JS_API_HASH_SET: {
1571             JSAPIHashSet::Cast(*obj)->SetSize(0);
1572             JSAPIHashSet::Cast(*obj)->SetTable<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1573             break;
1574         }
1575         case JSType::JS_API_TREE_MAP: {
1576             JSAPITreeMap::Cast(*obj)->SetTreeMap<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1577             break;
1578         }
1579         case JSType::JS_API_TREE_SET: {
1580             JSAPITreeSet::Cast(*obj)->SetTreeSet<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1581             break;
1582         }
1583         case JSType::JS_API_QUEUE: {
1584             JSAPIQueue::Cast(*obj)->SetLength(thread_, JSTaggedValue(0));
1585             JSAPIQueue::Cast(*obj)->SetFront(0);
1586             JSAPIQueue::Cast(*obj)->SetTail(0);
1587             break;
1588         }
1589         case JSType::JS_API_PLAIN_ARRAY: {
1590             JSAPIPlainArray::Cast(*obj)->SetLength(0);
1591             JSAPIPlainArray::Cast(*obj)->SetValues(thread_, JSTaggedValue(0));
1592             JSAPIPlainArray::Cast(*obj)->SetKeys(thread_, JSTaggedValue(0));
1593             break;
1594         }
1595         case JSType::JS_API_STACK: {
1596             JSAPIStack::Cast(*obj)->SetTop(0);
1597             break;
1598         }
1599         case JSType::JS_API_DEQUE: {
1600             JSAPIDeque::Cast(*obj)->SetFirst(0);
1601             JSAPIDeque::Cast(*obj)->SetLast(0);
1602             break;
1603         }
1604         case JSType::JS_API_LIGHT_WEIGHT_MAP: {
1605             JSAPILightWeightMap::Cast(*obj)->SetLength(0);
1606             JSAPILightWeightMap::Cast(*obj)->SetHashes<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1607             JSAPILightWeightMap::Cast(*obj)->SetKeys<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1608             JSAPILightWeightMap::Cast(*obj)->SetValues<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1609             break;
1610         }
1611         case JSType::JS_API_LIGHT_WEIGHT_SET: {
1612             JSAPILightWeightSet::Cast(*obj)->SetLength(0);
1613             JSAPILightWeightSet::Cast(*obj)->SetHashes<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1614             JSAPILightWeightSet::Cast(*obj)->SetValues<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1615             break;
1616         }
1617         case JSType::JS_API_VECTOR: {
1618             JSAPIVector::Cast(*obj)->SetLength(0);
1619             break;
1620         }
1621         case JSType::JS_API_BITVECTOR: {
1622             JSAPIBitVector::Cast(*obj)->SetNativePointer<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1623             JSAPIBitVector::Cast(*obj)->SetLength(0);
1624             JSAPIBitVector::Cast(*obj)->SetModRecord(0);
1625             break;
1626         }
1627         case JSType::JS_API_FAST_BUFFER: {
1628             JSAPIFastBuffer::Cast(*obj)->SetFastBufferData<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1629             JSAPIFastBuffer::Cast(*obj)->SetLength(0);
1630             JSAPIFastBuffer::Cast(*obj)->SetOffset(0);
1631             break;
1632         }
1633         case JSType::JS_API_LIST: {
1634             JSAPIList::Cast(*obj)->SetSingleList<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1635             JSAPIList::Cast(*obj)->SetBitField(0UL);
1636             break;
1637         }
1638         case JSType::JS_API_LINKED_LIST: {
1639             JSAPILinkedList::Cast(*obj)->SetDoubleList<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1640             break;
1641         }
1642         case JSType::JS_ASYNC_FUNC_OBJECT:
1643             JSAsyncFuncObject::Cast(*obj)->SetGeneratorContext<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1644             JSAsyncFuncObject::Cast(*obj)->SetResumeResult<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1645             JSAsyncFuncObject::Cast(*obj)->SetPromise<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1646             break;
1647         case JSType::JS_FUNCTION:
1648         case JSType::JS_GENERATOR_FUNCTION:
1649             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1650             break;
1651         case JSType::JS_ASYNC_GENERATOR_FUNCTION:
1652             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1653             break;
1654         case JSType::JS_PROXY_REVOC_FUNCTION:
1655             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1656             JSProxyRevocFunction::Cast(*obj)->SetRevocableProxy<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1657             break;
1658         case JSType::JS_PROMISE_REACTIONS_FUNCTION:
1659             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1660             JSPromiseReactionsFunction::Cast(*obj)->SetPromise(thread_, JSTaggedValue::Undefined());
1661             JSPromiseReactionsFunction::Cast(*obj)->SetAlreadyResolved<SKIP_BARRIER>(thread_,
1662                                                                                      JSTaggedValue::Undefined());
1663             break;
1664         case JSType::JS_PROMISE_EXECUTOR_FUNCTION:
1665             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1666             JSPromiseExecutorFunction::Cast(*obj)->SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1667             break;
1668         case JSType::JS_ASYNC_MODULE_FULFILLED_FUNCTION:
1669             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1670             JSAsyncModuleFulfilledFunction::Cast(*obj)->SetModule<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1671             break;
1672         case JSType::JS_ASYNC_MODULE_REJECTED_FUNCTION:
1673             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1674             JSAsyncModuleRejectedFunction::Cast(*obj)->SetModule<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1675             break;
1676         case JSType::JS_ASYNC_GENERATOR_RESUME_NEXT_RETURN_PROCESSOR_RST_FTN:
1677             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1678             JSAsyncGeneratorResNextRetProRstFtn::Cast(*obj)->SetAsyncGeneratorObject<SKIP_BARRIER>(thread_,
1679                 JSTaggedValue::Undefined());
1680             break;
1681         case JSType::JS_PROMISE_ALL_RESOLVE_ELEMENT_FUNCTION:
1682             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1683             JSPromiseAllResolveElementFunction::Cast(*obj)->
1684                 SetIndex<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1685             JSPromiseAllResolveElementFunction::Cast(*obj)->
1686                 SetValues<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1687             JSPromiseAllResolveElementFunction::Cast(*obj)->
1688                 SetCapabilities<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1689             JSPromiseAllResolveElementFunction::Cast(*obj)->
1690                 SetRemainingElements<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1691             JSPromiseAllResolveElementFunction::Cast(*obj)->
1692                 SetAlreadyCalled<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1693             break;
1694         case JSType::JS_PROMISE_ANY_REJECT_ELEMENT_FUNCTION:
1695             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1696             JSPromiseAnyRejectElementFunction::Cast(*obj)->SetIndex(0);
1697             JSPromiseAnyRejectElementFunction::Cast(*obj)->
1698                 SetErrors<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1699             JSPromiseAnyRejectElementFunction::Cast(*obj)->
1700                 SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1701             JSPromiseAnyRejectElementFunction::Cast(*obj)->
1702                 SetRemainingElements<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1703             JSPromiseAnyRejectElementFunction::Cast(*obj)->
1704                 SetAlreadyCalled<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1705             break;
1706         case JSType::JS_PROMISE_ALL_SETTLED_ELEMENT_FUNCTION:
1707             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1708             JSPromiseAllSettledElementFunction::Cast(*obj)->SetIndex(0);
1709             JSPromiseAllSettledElementFunction::Cast(*obj)->
1710                 SetValues<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1711             JSPromiseAllSettledElementFunction::Cast(*obj)->
1712                 SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1713             JSPromiseAllSettledElementFunction::Cast(*obj)->
1714                 SetRemainingElements<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1715             JSPromiseAllSettledElementFunction::Cast(*obj)->
1716                 SetAlreadyCalled<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1717             break;
1718         case JSType::JS_PROMISE_FINALLY_FUNCTION:
1719             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1720             JSPromiseFinallyFunction::Cast(*obj)->SetOnFinally<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1721             JSPromiseFinallyFunction::Cast(*obj)->SetConstructor<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1722             break;
1723         case JSType::JS_PROMISE_VALUE_THUNK_OR_THROWER_FUNCTION:
1724             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1725             JSPromiseValueThunkOrThrowerFunction::Cast(*obj)->SetResult<SKIP_BARRIER>(thread_,
1726                                                                                       JSTaggedValue::Undefined());
1727             break;
1728         case JSType::JS_INTL_BOUND_FUNCTION:
1729             JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>(obj));
1730             JSIntlBoundFunction::Cast(*obj)->SetNumberFormat<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1731             JSIntlBoundFunction::Cast(*obj)->SetDateTimeFormat<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1732             JSIntlBoundFunction::Cast(*obj)->SetCollator<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1733             break;
1734         case JSType::JS_BOUND_FUNCTION:
1735             JSBoundFunction::Cast(*obj)->SetMethod<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1736             JSBoundFunction::Cast(*obj)->SetBoundTarget<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1737             JSBoundFunction::Cast(*obj)->SetBoundThis<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1738             JSBoundFunction::Cast(*obj)->SetBoundArguments<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1739             break;
1740         case JSType::JS_ARGUMENTS:
1741             break;
1742         case JSType::JS_FORIN_ITERATOR:
1743         case JSType::JS_MAP_ITERATOR:
1744         case JSType::JS_SET_ITERATOR:
1745         case JSType::JS_REG_EXP_ITERATOR:
1746         case JSType::JS_API_ARRAYLIST_ITERATOR:
1747         case JSType::JS_API_TREEMAP_ITERATOR:
1748         case JSType::JS_API_TREESET_ITERATOR:
1749         case JSType::JS_API_QUEUE_ITERATOR:
1750         case JSType::JS_API_DEQUE_ITERATOR:
1751         case JSType::JS_API_LIGHT_WEIGHT_MAP_ITERATOR:
1752         case JSType::JS_API_LIGHT_WEIGHT_SET_ITERATOR:
1753         case JSType::JS_API_STACK_ITERATOR:
1754         case JSType::JS_API_VECTOR_ITERATOR:
1755         case JSType::JS_API_BITVECTOR_ITERATOR:
1756         case JSType::JS_API_HASHMAP_ITERATOR:
1757         case JSType::JS_API_HASHSET_ITERATOR:
1758         case JSType::JS_ARRAY_ITERATOR:
1759         case JSType::JS_API_PLAIN_ARRAY_ITERATOR:
1760             break;
1761         case JSType::JS_CJS_MODULE:
1762             CjsModule::Cast(*obj)->SetId<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1763             CjsModule::Cast(*obj)->SetExports<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1764             CjsModule::Cast(*obj)->SetPath<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1765             CjsModule::Cast(*obj)->SetFilename<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1766             CjsModule::Cast(*obj)->SetStatus(CjsModuleStatus::UNLOAD);
1767             break;
1768         case JSType::JS_CJS_EXPORTS:
1769             CjsExports::Cast(*obj)->SetExports<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1770             break;
1771         case JSType::JS_CJS_REQUIRE:
1772             CjsRequire::Cast(*obj)->SetCache<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1773             CjsRequire::Cast(*obj)->SetParent<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
1774             break;
1775         default:
1776             LOG_ECMA(FATAL) << "this branch is unreachable, type: " << static_cast<size_t>(type);
1777             UNREACHABLE();
1778     }
1779 }
1780 template FreeObject* ObjectFactory::FillFreeObject<true>(uintptr_t, size_t, RemoveSlots, uintptr_t);
1781 template FreeObject* ObjectFactory::FillFreeObject<false>(uintptr_t, size_t, RemoveSlots, uintptr_t);
1782 
1783 template <bool needBarrier>
FillFreeObject(uintptr_t address,size_t size,RemoveSlots removeSlots,uintptr_t hugeObjectHead)1784 FreeObject *ObjectFactory::FillFreeObject(uintptr_t address, size_t size, RemoveSlots removeSlots,
1785                                           uintptr_t hugeObjectHead)
1786 {
1787     FreeObject *object = nullptr;
1788     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
1789     if (size >= FreeObject::SIZE_OFFSET && size < FreeObject::SIZE) {
1790         object = reinterpret_cast<FreeObject *>(address);
1791             object->SetFreeObjectClass(JSHClass::Cast(globalConst->GetFreeObjectWithOneFieldClass().GetTaggedObject()));
1792         object->SetNext(INVALID_OBJECT);
1793     } else if (size >= FreeObject::SIZE) {
1794         object = reinterpret_cast<FreeObject *>(address);
1795             object->SetFreeObjectClass(
1796                 JSHClass::Cast(globalConst->GetFreeObjectWithTwoFieldClass().GetTaggedObject()));
1797         object->SetAvailable(size);
1798         object->SetNext(INVALID_OBJECT);
1799         if (UNLIKELY(heap_->ShouldVerifyHeap())) {
1800             FillFreeMemoryRange(address + FreeObject::SIZE, address + size);
1801         }
1802     } else if (size == FreeObject::NEXT_OFFSET) {
1803         object = reinterpret_cast<FreeObject *>(address);
1804             object->SetFreeObjectClass(
1805                 JSHClass::Cast(globalConst->GetFreeObjectWithNoneFieldClass().GetTaggedObject()));
1806     } else {
1807         LOG_ECMA(DEBUG) << "Fill free object size is smaller";
1808     }
1809 
1810 #ifdef ARK_USE_SATB_BARRIER
1811     // SATB relies on the overwriting of old values to ensure the accuracy of marking
1812     if constexpr (needBarrier) {
1813         // SATB must rely on WriteBarrier to record the old value.
1814         int step = 8;
1815         ASSERT(size % step == 0);
1816         for (uintptr_t i = 0; i < size; i += step) {
1817             Barriers::CMCWriteBarrier(thread_, reinterpret_cast<void*>(address), i, JSTaggedValue::Hole().GetRawData());
1818         }
1819     }
1820 #endif
1821     if (removeSlots == RemoveSlots::YES) {
1822         // For huge object, the region of `object` might not be its 1st region. Use `hugeObjectHead` instead.
1823         Region *region = Region::ObjectAddressToRange(hugeObjectHead == 0 ? object :
1824                                                       reinterpret_cast<TaggedObject *>(hugeObjectHead));
1825         heap_->ClearSlotsRange(region, address, address + size);
1826     }
1827     return object;
1828 }
1829 
NewObject(const JSHandle<JSHClass> & hclass)1830 TaggedObject *ObjectFactory::NewObject(const JSHandle<JSHClass> &hclass)
1831 {
1832     NewObjectHook();
1833     TaggedObject *header = heap_->AllocateYoungOrHugeObject(*hclass);
1834     uint32_t inobjPropCount = hclass->GetInlinedProperties();
1835     if (inobjPropCount > 0) {
1836         InitializeExtraProperties(hclass, header, inobjPropCount);
1837     }
1838     return header;
1839 }
1840 
NewNonMovableObject(const JSHandle<JSHClass> & hclass,uint32_t inobjPropCount)1841 TaggedObject *ObjectFactory::NewNonMovableObject(const JSHandle<JSHClass> &hclass, uint32_t inobjPropCount)
1842 {
1843     NewObjectHook();
1844     TaggedObject *header = heap_->AllocateNonMovableOrHugeObject(*hclass);
1845     if (inobjPropCount > 0) {
1846         InitializeExtraProperties(hclass, header, inobjPropCount);
1847     }
1848     return header;
1849 }
1850 
InitializeExtraProperties(const JSHandle<JSHClass> & hclass,TaggedObject * obj,uint32_t inobjPropCount)1851 void ObjectFactory::InitializeExtraProperties(const JSHandle<JSHClass> &hclass,
1852                                               TaggedObject *obj, uint32_t inobjPropCount)
1853 {
1854     ASSERT(inobjPropCount * JSTaggedValue::TaggedTypeSize() < hclass->GetObjectSize());
1855     auto paddr = reinterpret_cast<uintptr_t>(obj) + hclass->GetObjectSize();
1856     // The object which created by AOT speculative hclass, should be initialized as hole, means does not exist,
1857     // to follow ECMA spec.
1858     JSTaggedType initVal;
1859     bool inProgress = hclass->IsObjSizeTrackingInProgress();
1860     if (inProgress) {
1861         const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
1862         initVal = globalConst->GetFreeObjectWithNoneFieldClass().GetRawData();
1863     } else {
1864         initVal = hclass->IsAOT() ? JSTaggedValue::VALUE_HOLE : JSTaggedValue::VALUE_UNDEFINED;
1865     }
1866     for (uint32_t i = 0; i < inobjPropCount; ++i) {
1867         paddr -= JSTaggedValue::TaggedTypeSize();
1868         *reinterpret_cast<JSTaggedType *>(paddr) = initVal;
1869     }
1870     if (inProgress) {
1871         hclass->ObjSizeTrackingStep(thread_);
1872     }
1873 }
1874 
OrdinaryNewJSObjectCreate(const JSHandle<JSTaggedValue> & proto)1875 JSHandle<JSObject> ObjectFactory::OrdinaryNewJSObjectCreate(const JSHandle<JSTaggedValue> &proto)
1876 {
1877     JSHandle<JSTaggedValue> protoValue(proto);
1878     JSHandle<JSHClass> hclass(thread_, thread_->GlobalConstants()->GetObjectClass().GetTaggedObject());
1879     JSHandle<JSHClass> newClass = JSHClass::TransProtoWithoutLayout(thread_, hclass, protoValue);
1880     JSHandle<JSObject> newObj = NewJSObject(newClass);
1881     newObj->GetJSHClass()->SetExtensible(true);
1882     return newObj;
1883 }
1884 
GetHClassByFunctionKind(const JSHandle<GlobalEnv> & env,FunctionKind kind)1885 JSHandle<JSHClass> ObjectFactory::GetHClassByFunctionKind(const JSHandle<GlobalEnv> &env, FunctionKind kind)
1886 {
1887     JSHandle<JSHClass> hclass;
1888     if (kind == FunctionKind::BASE_CONSTRUCTOR) {
1889         hclass = JSHandle<JSHClass>::Cast(env->GetFunctionClassWithProto());
1890     } else if (JSFunction::IsConstructorKind(kind)) {
1891         hclass = JSHandle<JSHClass>::Cast(env->GetConstructorFunctionClass());
1892     } else if (kind == FunctionKind::CONCURRENT_FUNCTION) {
1893         hclass = JSHandle<JSHClass>::Cast(env->GetAsyncFunctionClass());
1894     } else {
1895         hclass = JSHandle<JSHClass>::Cast(env->GetNormalFunctionClass());
1896     }
1897     return hclass;
1898 }
1899 
NewJSFunction(const JSHandle<GlobalEnv> & env,const void * nativeFunc,FunctionKind kind,kungfu::BuiltinsStubCSigns::ID builtinId,MemSpaceType methodSpaceType)1900 JSHandle<JSFunction> ObjectFactory::NewJSFunction(const JSHandle<GlobalEnv> &env, const void *nativeFunc,
1901                                                   FunctionKind kind, kungfu::BuiltinsStubCSigns::ID builtinId,
1902                                                   MemSpaceType methodSpaceType)
1903 {
1904     JSHandle<JSHClass> hclass = GetHClassByFunctionKind(env, kind);
1905     if (builtinId != BUILTINS_STUB_ID(INVALID)) {
1906         JSHandle<Method> method = NewMethodForNativeFunction(nativeFunc, kind, builtinId, methodSpaceType);
1907         return NewJSFunctionByHClass(method, hclass);
1908     }
1909     return NewNativeFunctionByHClass(hclass, nativeFunc, kind);
1910 }
1911 
NewJSFunction(const JSHandle<GlobalEnv> & env,const JSHandle<Method> & method)1912 JSHandle<JSFunction> ObjectFactory::NewJSFunction(const JSHandle<GlobalEnv> &env,
1913                                                   const JSHandle<Method> &method)
1914 {
1915     FunctionKind kind = method->GetFunctionKind();
1916     JSHandle<JSHClass> hclass = GetHClassByFunctionKind(env, kind);
1917     return NewJSFunctionByHClass(method, hclass);
1918 }
1919 
NewJSBuiltinFunction(const JSHandle<GlobalEnv> env,const void * nativeFunc,FunctionKind kind,kungfu::BuiltinsStubCSigns::ID builtinId,MemSpaceType methodSpaceType)1920 JSHandle<JSFunction> ObjectFactory::NewJSBuiltinFunction(const JSHandle<GlobalEnv> env, const void *nativeFunc,
1921                                                          FunctionKind kind, kungfu::BuiltinsStubCSigns::ID builtinId,
1922                                                          MemSpaceType methodSpaceType)
1923 {
1924     JSHandle<JSHClass> hclass = GetHClassByFunctionKind(env, kind);
1925     if (builtinId != BUILTINS_STUB_ID(INVALID)) {
1926         JSHandle<Method> method = NewMethodForNativeFunction(nativeFunc, kind, builtinId, methodSpaceType);
1927         return NewJSBuiltinFunctionByHClass(env, method, hclass);
1928     }
1929     return NewNativeBuiltinFunctionByHClass(env, hclass, nativeFunc, kind);
1930 }
1931 
NewJSBuiltinFunction(const JSHandle<GlobalEnv> & env,const JSHandle<Method> & method)1932 JSHandle<JSFunction> ObjectFactory::NewJSBuiltinFunction(const JSHandle<GlobalEnv> &env,
1933                                                          const JSHandle<Method> &method)
1934 {
1935     FunctionKind kind = method->GetFunctionKind();
1936     JSHandle<JSHClass> hclass = GetHClassByFunctionKind(env, kind);
1937     return NewJSBuiltinFunctionByHClass(env, method, hclass);
1938 }
1939 
NewSFunction(const JSHandle<GlobalEnv> & env,const void * nativeFunc,FunctionKind kind,kungfu::BuiltinsStubCSigns::ID builtinId,MemSpaceType spaceType)1940 JSHandle<JSFunction> ObjectFactory::NewSFunction(const JSHandle<GlobalEnv> &env,
1941                                                  const void *nativeFunc,
1942                                                  FunctionKind kind,
1943                                                  kungfu::BuiltinsStubCSigns::ID builtinId,
1944                                                  MemSpaceType spaceType)
1945 {
1946     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetSFunctionClassWithoutProto());
1947     if (builtinId != BUILTINS_STUB_ID(INVALID)) {
1948         JSHandle<Method> method = NewSMethodForNativeFunction(nativeFunc, kind, builtinId, spaceType);
1949         return NewSFunctionByHClass(method, hclass);
1950     }
1951     return NewNativeSFunctionByHClass(hclass, nativeFunc, kind);
1952 }
1953 
NewDependentInfos(uint32_t capacity)1954 JSHandle<DependentInfos> ObjectFactory::NewDependentInfos(uint32_t capacity)
1955 {
1956     JSHandle<WeakVector> weakVector = WeakVector::Create(thread_, capacity);
1957     return JSHandle<DependentInfos>::Cast(weakVector);
1958 }
1959 
CreateFunctionClass(FunctionKind kind,uint32_t size,JSType type,const JSHandle<JSTaggedValue> & prototype,uint32_t inlinedProps)1960 JSHandle<JSHClass> ObjectFactory::CreateFunctionClass(FunctionKind kind, uint32_t size, JSType type,
1961                                                       const JSHandle<JSTaggedValue> &prototype, uint32_t inlinedProps)
1962 {
1963     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
1964     JSHandle<JSHClass> functionClass = NewEcmaHClass(size, inlinedProps, type, prototype);
1965     functionClass->SetCallable(true);
1966     // FunctionKind = BASE_CONSTRUCTOR
1967     if (JSFunction::IsConstructorKind(kind)) {
1968         functionClass->SetConstructor(true);
1969     }
1970     functionClass->SetExtensible(true);
1971 
1972     uint32_t fieldOrder = 0;
1973     ASSERT(JSFunction::LENGTH_INLINE_PROPERTY_INDEX == fieldOrder);
1974     ASSERT(inlinedProps >= JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS);
1975     JSHandle<LayoutInfo> layoutInfoHandle;
1976     if (inlinedProps == JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS) {
1977         layoutInfoHandle = CreateLayoutInfo(JSFunction::LENGTH_OF_INLINE_PROPERTIES);
1978     } else {
1979         layoutInfoHandle = CreateLayoutInfo(static_cast<int>(inlinedProps));
1980     }
1981     {
1982         PropertyAttributes attributes = PropertyAttributes::DefaultAccessor(false, false, true);
1983         attributes.SetIsInlinedProps(true);
1984         attributes.SetRepresentation(Representation::TAGGED);
1985         attributes.SetOffset(fieldOrder);
1986         layoutInfoHandle->AddKey(thread_, fieldOrder, globalConst->GetLengthString(), attributes);
1987         fieldOrder++;
1988     }
1989 
1990     ASSERT(JSFunction::NAME_INLINE_PROPERTY_INDEX == fieldOrder);
1991     // not set name in-object property on class which may have a name() method
1992     if (!JSFunction::IsClassConstructor(kind)) {
1993         PropertyAttributes attributes = PropertyAttributes::DefaultAccessor(false, false, true);
1994         attributes.SetIsInlinedProps(true);
1995         attributes.SetRepresentation(Representation::TAGGED);
1996         attributes.SetOffset(fieldOrder);
1997         layoutInfoHandle->AddKey(thread_, fieldOrder,
1998                                  thread_->GlobalConstants()->GetHandledNameString().GetTaggedValue(), attributes);
1999         fieldOrder++;
2000     }
2001 
2002     if (JSFunction::HasPrototype(kind) && !JSFunction::IsClassConstructor(kind)) {
2003         ASSERT(JSFunction::PROTOTYPE_INLINE_PROPERTY_INDEX == fieldOrder);
2004         PropertyAttributes attributes = PropertyAttributes::DefaultAccessor(true, false, false);
2005         attributes.SetIsInlinedProps(true);
2006         attributes.SetRepresentation(Representation::TAGGED);
2007         attributes.SetOffset(fieldOrder);
2008         layoutInfoHandle->AddKey(thread_, fieldOrder, globalConst->GetPrototypeString(), attributes);
2009         fieldOrder++;
2010     } else if (JSFunction::IsClassConstructor(kind)) {
2011         ASSERT(JSFunction::CLASS_PROTOTYPE_INLINE_PROPERTY_INDEX == fieldOrder);
2012         PropertyAttributes attributes = PropertyAttributes::DefaultAccessor(false, false, false);
2013         attributes.SetIsInlinedProps(true);
2014         attributes.SetRepresentation(Representation::TAGGED);
2015         attributes.SetOffset(fieldOrder);
2016         layoutInfoHandle->AddKey(thread_, fieldOrder, globalConst->GetPrototypeString(), attributes);
2017         fieldOrder++;
2018     }
2019 
2020     functionClass->SetLayout(thread_, layoutInfoHandle);
2021     functionClass->SetNumberOfProps(fieldOrder);
2022     return functionClass;
2023 }
2024 
CreateDefaultClassPrototypeHClass(JSHClass * hclass)2025 JSHandle<JSHClass> ObjectFactory::CreateDefaultClassPrototypeHClass(JSHClass *hclass)
2026 {
2027     uint32_t size = ClassInfoExtractor::NON_STATIC_RESERVED_LENGTH;
2028     JSHandle<LayoutInfo> layout = CreateLayoutInfo(size, MemSpaceType::OLD_SPACE, GrowMode::KEEP);
2029     PropertyAttributes attributes = PropertyAttributes::Default(true, false, true);  // non-enumerable
2030 
2031     attributes.SetIsInlinedProps(true);
2032     attributes.SetRepresentation(Representation::TAGGED);
2033     attributes.SetOffset(ClassInfoExtractor::CONSTRUCTOR_INDEX);
2034     layout->AddKey(thread_, ClassInfoExtractor::CONSTRUCTOR_INDEX,
2035         thread_->GlobalConstants()->GetConstructorString(), attributes);
2036 
2037     JSHandle<JSHClass> defaultHClass = NewEcmaHClass(hclass, JSObject::SIZE, JSType::JS_OBJECT, size);
2038     defaultHClass->SetLayout(thread_, layout);
2039     defaultHClass->SetNumberOfProps(size);
2040     defaultHClass->SetClassPrototype(true);
2041     defaultHClass->SetIsPrototype(true);
2042     return defaultHClass;
2043 }
2044 
CreateDefaultClassConstructorHClass(JSHClass * hclass)2045 JSHandle<JSHClass> ObjectFactory::CreateDefaultClassConstructorHClass(JSHClass *hclass)
2046 {
2047     uint32_t size = ClassInfoExtractor::STATIC_RESERVED_LENGTH;
2048     JSHandle<LayoutInfo> layout = CreateLayoutInfo(size, MemSpaceType::OLD_SPACE, GrowMode::KEEP);
2049 
2050     JSHandle<TaggedArray> array = NewTaggedArray(size);
2051     array->Set(thread_, ClassInfoExtractor::LENGTH_INDEX, thread_->GlobalConstants()->GetLengthString());
2052     array->Set(thread_, ClassInfoExtractor::NAME_INDEX, thread_->GlobalConstants()->GetNameString());
2053     array->Set(thread_, ClassInfoExtractor::PROTOTYPE_INDEX, thread_->GlobalConstants()->GetPrototypeString());
2054     for (uint32_t index = ClassInfoExtractor::LENGTH_INDEX; index < size; index++) {
2055         PropertyAttributes attributes;
2056         if (index == ClassInfoExtractor::PROTOTYPE_INDEX) {
2057             attributes = PropertyAttributes::DefaultAccessor(false, false, false);
2058         } else {
2059             attributes = PropertyAttributes::Default(false, false, true);
2060         }
2061         attributes.SetIsInlinedProps(true);
2062         attributes.SetRepresentation(Representation::TAGGED);
2063         attributes.SetOffset(index);
2064         layout->AddKey(thread_, index, array->Get(thread_, index), attributes);
2065     }
2066 
2067     JSHandle<JSHClass> defaultHClass = NewEcmaHClass(hclass, JSFunction::SIZE, JSType::JS_FUNCTION, size);
2068     defaultHClass->SetLayout(thread_, layout);
2069     defaultHClass->SetNumberOfProps(size);
2070     defaultHClass->SetClassConstructor(true);
2071     defaultHClass->SetConstructor(true);
2072     return defaultHClass;
2073 }
2074 
SetCodeEntryToFunctionFromMethod(const JSHandle<JSFunction> & func,const JSHandle<Method> & method)2075 void ObjectFactory::SetCodeEntryToFunctionFromMethod(const JSHandle<JSFunction> &func, const JSHandle<Method> &method)
2076 {
2077     uintptr_t entry = method->GetCodeEntryOrLiteral();
2078     func->SetCodeEntry(entry);
2079 }
2080 
CreateJSFunctionByType(const JSHandle<JSHClass> & clazz,MemSpaceType type)2081 JSHandle<JSFunction> ObjectFactory::CreateJSFunctionByType(const JSHandle<JSHClass> &clazz, MemSpaceType type)
2082 {
2083     JSHandle<JSFunction> function;
2084     switch (type) {
2085         case MemSpaceType::SEMI_SPACE:
2086             function = JSHandle<JSFunction>::Cast(NewJSObject(clazz));
2087             break;
2088         case MemSpaceType::OLD_SPACE:
2089             function = JSHandle<JSFunction>::Cast(NewOldSpaceJSObject(clazz));
2090             break;
2091         case MemSpaceType::NON_MOVABLE:
2092             function = JSHandle<JSFunction>::Cast(NewNonMovableJSObject(clazz));
2093             break;
2094         default:
2095             LOG_ECMA(FATAL) << "this branch is unreachable";
2096             UNREACHABLE();
2097     }
2098     clazz->SetCallable(true);
2099     clazz->SetExtensible(true);
2100     return function;
2101 }
2102 
SetupJSFunctionByHClass(const JSHandle<JSFunction> & function,const JSHandle<Method> & method)2103 void ObjectFactory::SetupJSFunctionByHClass(const JSHandle<JSFunction> &function, const JSHandle<Method> &method)
2104 {
2105     function->SetMethod(thread_, method);
2106     function->SetTaskConcurrentFuncFlag(0); // 0 : default value
2107     if (method->IsNativeWithCallField()) {
2108         SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
2109     } else if (method->IsAotWithCallField()) {
2110         thread_->GetEcmaVM()->GetAOTFileManager()->
2111             SetAOTFuncEntry(method->GetJSPandaFile(thread_), *function, *method);
2112     } else {
2113         SetCodeEntryToFunctionFromMethod(function, method);
2114     }
2115 }
2116 
NewJSFunctionByHClass(const JSHandle<Method> & method,const JSHandle<JSHClass> & clazz,MemSpaceType type)2117 JSHandle<JSFunction> ObjectFactory::NewJSFunctionByHClass(const JSHandle<Method> &method,
2118                                                           const JSHandle<JSHClass> &clazz,
2119                                                           MemSpaceType type)
2120 {
2121     JSHandle<JSFunction> function = CreateJSFunctionByType(clazz, type);
2122     JSFunction::InitializeJSFunction(thread_, function, method->GetFunctionKind());
2123     SetupJSFunctionByHClass(function, method);
2124     return function;
2125 }
2126 
NewJSBuiltinFunctionByHClass(const JSHandle<GlobalEnv> env,const JSHandle<Method> & method,const JSHandle<JSHClass> & clazz,MemSpaceType type)2127 JSHandle<JSFunction> ObjectFactory::NewJSBuiltinFunctionByHClass(const JSHandle<GlobalEnv> env,
2128                                                                  const JSHandle<Method> &method,
2129                                                                  const JSHandle<JSHClass> &clazz, MemSpaceType type)
2130 {
2131     JSHandle<JSFunction> function = CreateJSFunctionByType(clazz, type);
2132     JSFunction::InitializeJSBuiltinFunction(thread_, env, function, method->GetFunctionKind());
2133     SetupJSFunctionByHClass(function, method);
2134     return function;
2135 }
2136 
GetReadOnlyMethodForNativeFunction(FunctionKind kind)2137 JSTaggedValue ObjectFactory::GetReadOnlyMethodForNativeFunction(FunctionKind kind)
2138 {
2139     size_t constantIndex;
2140     switch (kind) {
2141         case FunctionKind::NORMAL_FUNCTION:
2142             constantIndex = static_cast<size_t>(ConstantIndex::NORMAL_FUNCTION_METHOD_INDEX);
2143             break;
2144         case FunctionKind::GETTER_FUNCTION:
2145             constantIndex = static_cast<size_t>(ConstantIndex::GETTER_FUNCTION_METHOD_INDEX);
2146             break;
2147         case FunctionKind::SETTER_FUNCTION:
2148             constantIndex = static_cast<size_t>(ConstantIndex::SETTER_FUNCTION_METHOD_INDEX);
2149             break;
2150         case FunctionKind::ARROW_FUNCTION:
2151             constantIndex = static_cast<size_t>(ConstantIndex::ARROW_FUNCTION_METHOD_INDEX);
2152             break;
2153         case FunctionKind::ASYNC_ARROW_FUNCTION:
2154             constantIndex = static_cast<size_t>(ConstantIndex::ASYNC_ARROW_FUNCTION_METHOD_INDEX);
2155             break;
2156         case FunctionKind::CONCURRENT_FUNCTION:
2157             constantIndex = static_cast<size_t>(ConstantIndex::CONCURRENT_FUNCTION_METHOD_INDEX);
2158             break;
2159         case FunctionKind::ASYNC_FUNCTION:
2160             constantIndex = static_cast<size_t>(ConstantIndex::ASYNC_FUNCTION_METHOD_INDEX);
2161             break;
2162         case FunctionKind::BASE_CONSTRUCTOR:
2163             constantIndex = static_cast<size_t>(ConstantIndex::BASE_CONSTRUCTOR_METHOD_INDEX);
2164             break;
2165         case FunctionKind::CLASS_CONSTRUCTOR:
2166             constantIndex = static_cast<size_t>(ConstantIndex::CLASS_CONSTRUCTOR_METHOD_INDEX);
2167             break;
2168         case FunctionKind::BUILTIN_PROXY_CONSTRUCTOR:
2169             constantIndex = static_cast<size_t>(ConstantIndex::BUILTIN_PROXY_CONSTRUCTOR_METHOD_INDEX);
2170             break;
2171         case FunctionKind::BUILTIN_CONSTRUCTOR:
2172             constantIndex = static_cast<size_t>(ConstantIndex::BUILTIN_CONSTRUCTOR_METHOD_INDEX);
2173             break;
2174         case FunctionKind::DERIVED_CONSTRUCTOR:
2175             constantIndex = static_cast<size_t>(ConstantIndex::DERIVED_CONSTRUCTOR_METHOD_INDEX);
2176             break;
2177         case FunctionKind::GENERATOR_FUNCTION:
2178             constantIndex = static_cast<size_t>(ConstantIndex::GENERATOR_FUNCTION_METHOD_INDEX);
2179             break;
2180         case FunctionKind::NONE_FUNCTION:
2181             constantIndex = static_cast<size_t>(ConstantIndex::NONE_FUNCTION_METHOD_INDEX);
2182             break;
2183         case FunctionKind::ASYNC_GENERATOR_FUNCTION:
2184             constantIndex = static_cast<size_t>(ConstantIndex::ASYNC_GENERATOR_FUNCTION_METHOD_INDEX);
2185             break;
2186         default:
2187             LOG_ECMA(FATAL) << "cannot get method for native function of kind "
2188                 << std::to_string(static_cast<int>(kind));
2189             UNREACHABLE();
2190     }
2191     JSTaggedValue methodValue = thread_->GlobalConstants()->GetGlobalConstantObject(constantIndex);
2192     return methodValue;
2193 }
2194 
NewNativeFunctionByHClass(const JSHandle<JSHClass> & clazz,const void * nativeFunc,FunctionKind kind,MemSpaceType type)2195 JSHandle<JSFunction> ObjectFactory::NewNativeFunctionByHClass(const JSHandle<JSHClass> &clazz,
2196                                                               const void *nativeFunc,
2197                                                               FunctionKind kind,
2198                                                               MemSpaceType type)
2199 {
2200     JSHandle<JSFunction> function = CreateJSFunctionByType(clazz, type);
2201     JSFunction::InitializeJSFunction(thread_, function, kind);
2202     function->SetMethod(thread_, GetReadOnlyMethodForNativeFunction(kind));
2203     function->SetNativePointer(const_cast<void *>(nativeFunc));
2204     function->SetTaskConcurrentFuncFlag(0); // 0 : default value
2205     return function;
2206 }
2207 
NewNativeBuiltinFunctionByHClass(const JSHandle<GlobalEnv> env,const JSHandle<JSHClass> & clazz,const void * nativeFunc,FunctionKind kind,MemSpaceType type)2208 JSHandle<JSFunction> ObjectFactory::NewNativeBuiltinFunctionByHClass(const JSHandle<GlobalEnv> env,
2209                                                                      const JSHandle<JSHClass> &clazz,
2210                                                                      const void *nativeFunc,
2211                                                                      FunctionKind kind,
2212                                                                      MemSpaceType type)
2213 {
2214     JSHandle<JSFunction> function = CreateJSFunctionByType(clazz, type);
2215     JSFunction::InitializeJSBuiltinFunction(thread_, env, function, kind);
2216     function->SetMethod(thread_, GetReadOnlyMethodForNativeFunction(kind));
2217     function->SetNativePointer(const_cast<void *>(nativeFunc));
2218     function->SetTaskConcurrentFuncFlag(0); // 0 : default value
2219     return function;
2220 }
2221 
NewJSFunctionByHClass(const void * func,const JSHandle<JSHClass> & clazz,FunctionKind kind)2222 JSHandle<JSFunction> ObjectFactory::NewJSFunctionByHClass(const void *func, const JSHandle<JSHClass> &clazz,
2223                                                           FunctionKind kind)
2224 {
2225     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(NewJSObject(clazz));
2226     clazz->SetCallable(true);
2227     clazz->SetExtensible(true);
2228     JSFunction::InitializeJSFunction(thread_, function, kind);
2229     function->SetMethod(thread_, GetReadOnlyMethodForNativeFunction(kind));
2230     function->SetNativePointer(const_cast<void *>(func));
2231     return function;
2232 }
2233 
2234 // new function with name/length accessor
NewJSFunctionByHClassWithoutAccessor(const JSHandle<GlobalEnv> & env,const void * func,const JSHandle<JSHClass> & clazz,FunctionKind kind)2235 JSHandle<JSFunction> ObjectFactory::NewJSFunctionByHClassWithoutAccessor(const JSHandle<GlobalEnv> &env,
2236     const void *func, const JSHandle<JSHClass> &clazz, FunctionKind kind)
2237 {
2238     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(NewJSObject(clazz));
2239     clazz->SetCallable(true);
2240     clazz->SetExtensible(true);
2241     JSFunction::InitializeBuiltinWithDefaultValue(thread_, env, function);
2242     function->SetMethod(thread_, GetReadOnlyMethodForNativeFunction(kind));
2243     function->SetNativePointer(const_cast<void *>(func));
2244     return function;
2245 }
2246 
InitializeMethod(const MethodLiteral * methodLiteral,JSHandle<Method> & method)2247 void ObjectFactory::InitializeMethod(const MethodLiteral *methodLiteral, JSHandle<Method> &method)
2248 {
2249     if (methodLiteral != nullptr) {
2250         method->SetCallField(methodLiteral->GetCallField());
2251         method->SetLiteralInfo(methodLiteral->GetLiteralInfo());
2252         method->SetNativePointerOrBytecodeArray(const_cast<void *>(methodLiteral->GetNativePointer()));
2253         method->SetExtraLiteralInfo(methodLiteral->GetExtraLiteralInfo());
2254         method->SetExpectedPropertyCount(methodLiteral->GetExpectedPropertyCount());
2255     } else {
2256         method->SetCallField(0ULL);
2257         method->SetLiteralInfo(0ULL);
2258         method->SetNativePointerOrBytecodeArray(nullptr);
2259         method->SetExtraLiteralInfo(0ULL);
2260         method->SetExpectedPropertyCount(MethodLiteral::MAX_EXPECTED_PROPERTY_COUNT);
2261     }
2262     method->SetCodeEntryOrLiteral(reinterpret_cast<uintptr_t>(methodLiteral));
2263     method->SetConstantPool<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2264     method->SetFpDelta(0);
2265 }
2266 
NewMethod(const MethodLiteral * methodLiteral,MemSpaceType spaceType)2267 JSHandle<Method> ObjectFactory::NewMethod(const MethodLiteral *methodLiteral, MemSpaceType spaceType)
2268 {
2269     NewObjectHook();
2270     TaggedObject *header = nullptr;
2271     if (spaceType == NON_MOVABLE) {
2272         header = heap_->AllocateNonMovableOrHugeObject(
2273             JSHClass::Cast(thread_->GlobalConstants()->GetMethodClass().GetTaggedObject()));
2274     } else {
2275         header = heap_->AllocateOldOrHugeObject(
2276             JSHClass::Cast(thread_->GlobalConstants()->GetMethodClass().GetTaggedObject()));
2277     }
2278     JSHandle<Method> method(thread_, header);
2279     InitializeMethod(methodLiteral, method);
2280     return method;
2281 }
2282 
NewMethod(const JSPandaFile * jsPandaFile,MethodLiteral * methodLiteral,JSHandle<ConstantPool> constpool,uint32_t entryIndex,bool needSetAotFlag,bool * canFastCall)2283 JSHandle<Method> ObjectFactory::NewMethod(const JSPandaFile *jsPandaFile, MethodLiteral *methodLiteral,
2284                                           JSHandle<ConstantPool> constpool, uint32_t entryIndex,
2285                                           bool needSetAotFlag, bool *canFastCall)
2286 {
2287     JSHandle<Method> method;
2288     if (jsPandaFile->IsNewVersion()) {
2289         method = Method::Create(thread_, jsPandaFile, methodLiteral);
2290     } else {
2291         method = NewMethod(methodLiteral);
2292         method->SetConstantPool(thread_, constpool);
2293     }
2294     if (needSetAotFlag) {
2295         thread_->GetEcmaVM()->GetAOTFileManager()->
2296             SetAOTFuncEntry(jsPandaFile, nullptr, *method, entryIndex, canFastCall);
2297     } else {
2298         method->InitInterpreterStatusForCompiledMethod(thread_);
2299     }
2300     return method;
2301 }
2302 
NewJSNativeErrorFunction(const JSHandle<GlobalEnv> & env,const void * nativeFunc)2303 JSHandle<JSFunction> ObjectFactory::NewJSNativeErrorFunction(const JSHandle<GlobalEnv> &env, const void *nativeFunc)
2304 {
2305     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetNativeErrorFunctionClass());
2306     return NewNativeBuiltinFunctionByHClass(env, hclass, nativeFunc, FunctionKind::BUILTIN_CONSTRUCTOR);
2307 }
2308 
NewSpecificTypedArrayFunction(const JSHandle<GlobalEnv> & env,const void * nativeFunc,kungfu::BuiltinsStubCSigns::ID builtinId)2309 JSHandle<JSFunction> ObjectFactory::NewSpecificTypedArrayFunction(const JSHandle<GlobalEnv> &env,
2310                                                                   const void *nativeFunc,
2311                                                                   kungfu::BuiltinsStubCSigns::ID builtinId)
2312 {
2313     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetSpecificTypedArrayFunctionClass());
2314     if (builtinId != BUILTINS_STUB_ID(INVALID)) {
2315         JSHandle<Method> method = NewMethodForNativeFunction(nativeFunc, FunctionKind::BUILTIN_CONSTRUCTOR, builtinId);
2316         return NewJSBuiltinFunctionByHClass(env, method, hclass);
2317     }
2318     return NewNativeBuiltinFunctionByHClass(env, hclass, nativeFunc, FunctionKind::BUILTIN_CONSTRUCTOR);
2319 }
2320 
NewAotFunction(uint32_t numArgs,uintptr_t codeEntry)2321 JSHandle<JSFunction> ObjectFactory::NewAotFunction(uint32_t numArgs, uintptr_t codeEntry)
2322 {
2323     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2324     JSHandle<Method> method = NewMethodForNativeFunction(reinterpret_cast<void *>(codeEntry));
2325     method->SetAotCodeBit(true);
2326     method->SetNativeBit(false);
2327     method->SetNumArgsWithCallField(numArgs);
2328     method->SetCodeEntryOrLiteral(codeEntry);
2329     JSHandle<JSFunction> jsfunc = NewJSFunction(env, method);
2330     return jsfunc;
2331 }
2332 
SetNativePointerToFunctionFromMethod(const JSHandle<JSFunctionBase> & func,const JSHandle<Method> & method)2333 void ObjectFactory::SetNativePointerToFunctionFromMethod(const JSHandle<JSFunctionBase> &func,
2334                                                          const JSHandle<Method> &method)
2335 {
2336     void *nativePointer = const_cast<void *>(method->GetNativePointer());
2337     func->SetNativePointer(nativePointer);
2338 }
2339 
NewJSBoundFunction(const JSHandle<JSTaggedValue> & target,const JSHandle<JSTaggedValue> & boundThis,const JSHandle<TaggedArray> & args)2340 JSHandle<JSBoundFunction> ObjectFactory::NewJSBoundFunction(const JSHandle<JSTaggedValue> &target,
2341                                                             const JSHandle<JSTaggedValue> &boundThis,
2342                                                             const JSHandle<TaggedArray> &args)
2343 {
2344     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2345     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
2346 
2347     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetBoundFunctionClass());
2348     JSHandle<JSBoundFunction> bundleFunction = JSHandle<JSBoundFunction>::Cast(NewJSObject(hclass));
2349     // set properties
2350     JSHandle<JSTaggedValue> accessor = globalConst->GetHandledFunctionNameAccessor();
2351     bundleFunction->SetPropertyInlinedProps(thread_, JSFunction::NAME_INLINE_PROPERTY_INDEX,
2352                                             accessor.GetTaggedValue());
2353     accessor = globalConst->GetHandledFunctionLengthAccessor();
2354     bundleFunction->SetPropertyInlinedProps(thread_, JSFunction::LENGTH_INLINE_PROPERTY_INDEX,
2355                                             accessor.GetTaggedValue());
2356 
2357     bundleFunction->SetBoundTarget(thread_, target);
2358     bundleFunction->SetBoundThis(thread_, boundThis);
2359     bundleFunction->SetBoundArguments(thread_, args);
2360 
2361     if (target.GetTaggedValue().IsConstructor()) {
2362         bundleFunction->SetConstructor(true);
2363     }
2364     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_GLOBAL_CALL_JS_BOUND_FUNCTION));
2365     bundleFunction->SetMethod(thread_, method);
2366     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(bundleFunction), method);
2367     return bundleFunction;
2368 }
2369 
NewJSIntlBoundFunction(MethodIndex idx,int functionLength)2370 JSHandle<JSIntlBoundFunction> ObjectFactory::NewJSIntlBoundFunction(MethodIndex idx, int functionLength)
2371 {
2372     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2373     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetJSIntlBoundFunctionClass());
2374 
2375     JSHandle<JSIntlBoundFunction> intlBoundFunc = JSHandle<JSIntlBoundFunction>::Cast(NewJSObject(hclass));
2376     intlBoundFunc->SetNumberFormat<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2377     intlBoundFunc->SetDateTimeFormat<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2378     intlBoundFunc->SetCollator<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2379     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(intlBoundFunc);
2380     JSFunction::InitializeJSBuiltinFunction(thread_, env, function);
2381     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(idx));
2382     function->SetMethod(thread_, method);
2383     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
2384     JSFunction::SetFunctionLength(thread_, function, JSTaggedValue(functionLength));
2385     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
2386     JSHandle<JSTaggedValue> emptyString = globalConst->GetHandledEmptyString();
2387     JSHandle<JSTaggedValue> nameKey = globalConst->GetHandledNameString();
2388     PropertyDescriptor nameDesc(thread_, emptyString, false, false, true);
2389     JSTaggedValue::DefinePropertyOrThrow(thread_, JSHandle<JSTaggedValue>::Cast(function), nameKey, nameDesc);
2390     RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSIntlBoundFunction, thread_);
2391     return intlBoundFunc;
2392 }
2393 
NewJSProxyRevocFunction(const JSHandle<JSProxy> & proxy)2394 JSHandle<JSProxyRevocFunction> ObjectFactory::NewJSProxyRevocFunction(const JSHandle<JSProxy> &proxy)
2395 {
2396     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2397     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
2398     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetProxyRevocFunctionClass());
2399 
2400     JSHandle<JSProxyRevocFunction> revocFunction = JSHandle<JSProxyRevocFunction>::Cast(NewJSObject(hclass));
2401     revocFunction->SetRevocableProxy<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2402     revocFunction->SetRevocableProxy(thread_, proxy);
2403     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(revocFunction);
2404     JSFunction::InitializeJSBuiltinFunction(thread_, env, function);
2405     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROXY_INVALIDATE_PROXY_FUNCTION));
2406     function->SetMethod(thread_, method);
2407     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
2408     JSFunction::SetFunctionLength(thread_, function, JSTaggedValue(0));
2409     JSHandle<JSTaggedValue> emptyString = globalConst->GetHandledEmptyString();
2410     JSHandle<JSTaggedValue> nameKey = globalConst->GetHandledNameString();
2411     PropertyDescriptor nameDesc(thread_, emptyString, false, false, true);
2412     JSTaggedValue::DefinePropertyOrThrow(thread_, JSHandle<JSTaggedValue>::Cast(function), nameKey, nameDesc);
2413     RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSProxyRevocFunction, thread_);
2414     return revocFunction;
2415 }
2416 
NewJSAsyncAwaitStatusFunction(MethodIndex idx)2417 JSHandle<JSAsyncAwaitStatusFunction> ObjectFactory::NewJSAsyncAwaitStatusFunction(MethodIndex idx)
2418 {
2419     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2420     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetAsyncAwaitStatusFunctionClass());
2421 
2422     JSHandle<JSAsyncAwaitStatusFunction> awaitFunction =
2423         JSHandle<JSAsyncAwaitStatusFunction>::Cast(NewJSObject(hclass));
2424     awaitFunction->SetAsyncContext<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2425     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(awaitFunction));
2426     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(idx));
2427     awaitFunction->SetMethod(thread_, method);
2428     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(awaitFunction), method);
2429     return awaitFunction;
2430 }
2431 
NewJSGeneratorObject(JSHandle<JSTaggedValue> generatorFunction)2432 JSHandle<JSGeneratorObject> ObjectFactory::NewJSGeneratorObject(JSHandle<JSTaggedValue> generatorFunction)
2433 {
2434     JSHandle<JSTaggedValue> proto(thread_, JSHandle<JSFunction>::Cast(generatorFunction)->GetProtoOrHClass(thread_));
2435     if (!proto->IsECMAObject()) {
2436         JSHandle<GlobalEnv> realmHandle = JSObject::GetFunctionRealm(thread_, generatorFunction);
2437         RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSGeneratorObject, thread_);
2438         proto = realmHandle->GetGeneratorPrototype();
2439     }
2440     JSHandle<JSHClass> hclass = NewEcmaHClass(JSGeneratorObject::SIZE, JSType::JS_GENERATOR_OBJECT, proto);
2441     JSHandle<JSGeneratorObject> generatorObject = JSHandle<JSGeneratorObject>::Cast(NewJSObjectWithInit(hclass));
2442     generatorObject->SetGeneratorContext<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2443     generatorObject->SetResumeResult<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2444     return generatorObject;
2445 }
2446 
NewJSAsyncGeneratorObject(JSHandle<JSTaggedValue> generatorFunction)2447 JSHandle<JSAsyncGeneratorObject> ObjectFactory::NewJSAsyncGeneratorObject(JSHandle<JSTaggedValue> generatorFunction)
2448 {
2449     JSHandle<JSTaggedValue> proto(thread_, JSHandle<JSFunction>::Cast(generatorFunction)->GetProtoOrHClass(thread_));
2450     if (!proto->IsECMAObject()) {
2451         JSHandle<GlobalEnv> realmHandle = JSObject::GetFunctionRealm(thread_, generatorFunction);
2452         RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSAsyncGeneratorObject, thread_);
2453         proto = realmHandle->GetAsyncGeneratorPrototype();
2454     }
2455     JSHandle<JSHClass> hclass = NewEcmaHClass(JSAsyncGeneratorObject::SIZE,
2456                                               JSType::JS_ASYNC_GENERATOR_OBJECT, proto);
2457     JSHandle<JSAsyncGeneratorObject> generatorObject =
2458         JSHandle<JSAsyncGeneratorObject>::Cast(NewJSObjectWithInit(hclass));
2459     return generatorObject;
2460 }
2461 
NewJSAsyncFuncObject()2462 JSHandle<JSAsyncFuncObject> ObjectFactory::NewJSAsyncFuncObject()
2463 {
2464     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2465     JSHandle<JSTaggedValue> proto = env->GetInitialGenerator();
2466     JSHandle<JSHClass> hclass = NewEcmaHClass(JSAsyncFuncObject::SIZE, JSType::JS_ASYNC_FUNC_OBJECT, proto);
2467     JSHandle<JSAsyncFuncObject> asyncFuncObject = JSHandle<JSAsyncFuncObject>::Cast(NewJSObjectWithInit(hclass));
2468     return asyncFuncObject;
2469 }
2470 
NewCompletionRecord(CompletionRecordType type,JSHandle<JSTaggedValue> value)2471 JSHandle<CompletionRecord> ObjectFactory::NewCompletionRecord(CompletionRecordType type, JSHandle<JSTaggedValue> value)
2472 {
2473     NewObjectHook();
2474     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2475         JSHClass::Cast(thread_->GlobalConstants()->GetCompletionRecordClass().GetTaggedObject()));
2476     JSHandle<CompletionRecord> obj(thread_, header);
2477     obj->SetType(type);
2478     obj->SetValue(thread_, value);
2479     return obj;
2480 }
2481 
NewGeneratorContext()2482 JSHandle<GeneratorContext> ObjectFactory::NewGeneratorContext()
2483 {
2484     NewObjectHook();
2485     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2486         JSHClass::Cast(thread_->GlobalConstants()->GetGeneratorContextClass().GetTaggedObject()));
2487     JSHandle<GeneratorContext> obj(thread_, header);
2488     obj->SetRegsArray<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2489     obj->SetMethod<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2490     obj->SetThis<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2491     obj->SetAcc<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2492     obj->SetGeneratorObject<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2493     obj->SetLexicalEnv<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2494     obj->SetNRegs(0);
2495     obj->SetBCOffset(0);
2496     return obj;
2497 }
2498 
NewJSPrimitiveRef(const JSHandle<JSFunction> & function,const JSHandle<JSTaggedValue> & object)2499 JSHandle<JSPrimitiveRef> ObjectFactory::NewJSPrimitiveRef(const JSHandle<JSFunction> &function,
2500                                                           const JSHandle<JSTaggedValue> &object)
2501 {
2502     JSHandle<JSPrimitiveRef> obj(NewJSObjectByConstructor(function));
2503     obj->SetValue(thread_, object);
2504 
2505     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2506     if (function.GetTaggedValue() == env->GetStringFunction().GetTaggedValue()) {
2507         JSHandle<JSTaggedValue> lengthStr = thread_->GlobalConstants()->GetHandledLengthString();
2508         uint32_t length = EcmaStringAccessor(object.GetTaggedValue()).GetLength();
2509         PropertyDescriptor desc(thread_, JSHandle<JSTaggedValue>(thread_, JSTaggedValue(length)), false, false, false);
2510         JSTaggedValue::DefinePropertyOrThrow(thread_, JSHandle<JSTaggedValue>(obj), lengthStr, desc);
2511         RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSPrimitiveRef, thread_);
2512     }
2513 
2514     return obj;
2515 }
2516 
NewJSPrimitiveRef(PrimitiveType type,const JSHandle<JSTaggedValue> & object)2517 JSHandle<JSPrimitiveRef> ObjectFactory::NewJSPrimitiveRef(PrimitiveType type, const JSHandle<JSTaggedValue> &object)
2518 {
2519     ObjectFactory *factory = vm_->GetFactory();
2520     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2521     JSHandle<JSTaggedValue> function;
2522     switch (type) {
2523         case PrimitiveType::PRIMITIVE_NUMBER:
2524             function = env->GetNumberFunction();
2525             break;
2526         case PrimitiveType::PRIMITIVE_STRING:
2527             function = env->GetStringFunction();
2528             break;
2529         case PrimitiveType::PRIMITIVE_SYMBOL:
2530             function = env->GetSymbolFunction();
2531             break;
2532         case PrimitiveType::PRIMITIVE_BOOLEAN:
2533             function = env->GetBooleanFunction();
2534             break;
2535         case PrimitiveType::PRIMITIVE_BIGINT:
2536             function = env->GetBigIntFunction();
2537             break;
2538         default:
2539             LOG_ECMA(FATAL) << "this branch is unreachable, type: " << static_cast<size_t>(type);
2540             UNREACHABLE();
2541     }
2542     JSHandle<JSFunction> funcHandle(function);
2543     return factory->NewJSPrimitiveRef(funcHandle, object);
2544 }
2545 
NewJSString(const JSHandle<JSTaggedValue> & str,const JSHandle<JSTaggedValue> & newTarget)2546 JSHandle<JSPrimitiveRef> ObjectFactory::NewJSString(const JSHandle<JSTaggedValue> &str,
2547                                                     const JSHandle<JSTaggedValue> &newTarget)
2548 {
2549     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2550     JSHandle<JSFunction> stringFunc(env->GetStringFunction());
2551     JSHandle<JSPrimitiveRef> obj;
2552     if (newTarget->IsUndefined()) {
2553         obj = JSHandle<JSPrimitiveRef>::Cast(NewJSObjectByConstructor(stringFunc));
2554     } else {
2555         JSHandle<JSObject> newObject = NewJSObjectByConstructor(stringFunc, newTarget);
2556         RETURN_HANDLE_IF_ABRUPT_COMPLETION(JSPrimitiveRef, thread_);
2557         obj = JSHandle<JSPrimitiveRef>::Cast(newObject);
2558     }
2559     obj->SetValue(thread_, str);
2560     return obj;
2561 }
2562 
NewGlobalEnv(bool lazyInit,bool isRealm)2563 JSHandle<GlobalEnv> ObjectFactory::NewGlobalEnv(bool lazyInit, bool isRealm)
2564 {
2565     NewObjectHook();
2566     // Note: Global env must be allocated in non-movable heap, since its getters will directly return
2567     //       the offsets of the properties as the address of Handles.
2568     const GlobalEnvConstants* globalConst = thread_->GlobalConstants();
2569     JSHandle<JSHClass> hClassHandle = JSHandle<JSHClass>(thread_, globalConst->GetHClassClass());
2570     JSHandle<JSHClass> globalEnvClass = NewEcmaHClass(*hClassHandle, GlobalEnv::SIZE,
2571                                                       JSType::GLOBAL_ENV);
2572     TaggedObject *header = heap_->AllocateNonMovableOrHugeObject(*globalEnvClass);
2573     InitObjectFields(header);
2574     auto globalEnv = JSHandle<GlobalEnv>(thread_, GlobalEnv::Cast(header));
2575     thread_->GetEcmaVM()->RecordGlobalEnv(GlobalEnv::Cast(header));
2576     thread_->SetInGlobalEnvInitialize(true);
2577     globalEnv->Init(thread_);
2578     Builtins builtins;
2579     builtins.Initialize(globalEnv, thread_, lazyInit, isRealm);
2580     thread_->SetInGlobalEnvInitialize(false);
2581     return globalEnv;
2582 }
2583 
NewLexicalEnv(int numSlots)2584 JSHandle<LexicalEnv> ObjectFactory::NewLexicalEnv(int numSlots)
2585 {
2586     NewObjectHook();
2587     size_t size = LexicalEnv::ComputeSize(numSlots);
2588     auto header = heap_->AllocateYoungOrHugeObject(
2589         JSHClass::Cast(thread_->GlobalConstants()->GetLexicalEnvClass().GetTaggedObject()), size);
2590     JSHandle<LexicalEnv> array(thread_, header);
2591     array->InitializeWithSpecialValue(JSTaggedValue::Hole(), numSlots + LexicalEnv::RESERVED_ENV_LENGTH);
2592     return array;
2593 }
2594 
NewEmptySymbol()2595 JSHandle<JSSymbol> ObjectFactory::NewEmptySymbol()
2596 {
2597     NewObjectHook();
2598     TaggedObject *header = heap_->AllocateNonMovableOrHugeObject(
2599         JSHClass::Cast(thread_->GlobalConstants()->GetSymbolClass().GetTaggedObject()));
2600     JSHandle<JSSymbol> obj(thread_, JSSymbol::Cast(header));
2601     obj->SetDescription<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2602     obj->SetFlags(0);
2603     obj->SetHashField(0);
2604     return obj;
2605 }
2606 
NewJSSymbol()2607 JSHandle<JSSymbol> ObjectFactory::NewJSSymbol()
2608 {
2609     NewObjectHook();
2610     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2611         JSHClass::Cast(thread_->GlobalConstants()->GetSymbolClass().GetTaggedObject()));
2612     JSHandle<JSSymbol> obj(thread_, JSSymbol::Cast(header));
2613     obj->SetDescription<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2614     obj->SetFlags(0);
2615     obj->SetHashField(SymbolTable::Hash(thread_, obj.GetTaggedValue()));
2616     return obj;
2617 }
2618 
NewPrivateSymbol()2619 JSHandle<JSSymbol> ObjectFactory::NewPrivateSymbol()
2620 {
2621     JSHandle<JSSymbol> obj = NewJSSymbol();
2622     obj->SetPrivate();
2623     return obj;
2624 }
2625 
NewPrivateNameSymbol(const JSHandle<JSTaggedValue> & name)2626 JSHandle<JSSymbol> ObjectFactory::NewPrivateNameSymbol(const JSHandle<JSTaggedValue> &name)
2627 {
2628     NewObjectHook();
2629     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2630         JSHClass::Cast(thread_->GlobalConstants()->GetSymbolClass().GetTaggedObject()));
2631     JSHandle<JSSymbol> obj(thread_, JSSymbol::Cast(header));
2632     obj->SetFlags(0);
2633     obj->SetPrivateNameSymbol();
2634     obj->SetDescription(thread_, name);
2635     obj->SetHashField(SymbolTable::Hash(thread_, name.GetTaggedValue()));
2636     return obj;
2637 }
2638 
NewWellKnownSymbol(const JSHandle<JSTaggedValue> & name)2639 JSHandle<JSSymbol> ObjectFactory::NewWellKnownSymbol(const JSHandle<JSTaggedValue> &name)
2640 {
2641     NewObjectHook();
2642     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2643         JSHClass::Cast(thread_->GlobalConstants()->GetSymbolClass().GetTaggedObject()));
2644     JSHandle<JSSymbol> obj(thread_, JSSymbol::Cast(header));
2645     obj->SetFlags(0);
2646     obj->SetWellKnownSymbol();
2647     obj->SetDescription(thread_, name);
2648     obj->SetHashField(SymbolTable::Hash(thread_, name.GetTaggedValue()));
2649     return obj;
2650 }
2651 
NewPublicSymbol(const JSHandle<JSTaggedValue> & name)2652 JSHandle<JSSymbol> ObjectFactory::NewPublicSymbol(const JSHandle<JSTaggedValue> &name)
2653 {
2654     NewObjectHook();
2655     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2656         JSHClass::Cast(thread_->GlobalConstants()->GetSymbolClass().GetTaggedObject()));
2657     JSHandle<JSSymbol> obj(thread_, JSSymbol::Cast(header));
2658     obj->SetFlags(0);
2659     obj->SetDescription(thread_, name);
2660     obj->SetHashField(SymbolTable::Hash(thread_, name.GetTaggedValue()));
2661     return obj;
2662 }
2663 
NewSymbolWithTable(const JSHandle<JSTaggedValue> & name)2664 JSHandle<JSSymbol> ObjectFactory::NewSymbolWithTable(const JSHandle<JSTaggedValue> &name)
2665 {
2666     JSHandle<SymbolTable> tableHandle(thread_, vm_->GetRegisterSymbols());
2667     if (tableHandle->ContainsKey(thread_, name.GetTaggedValue())) {
2668         JSTaggedValue objValue = tableHandle->GetSymbol(thread_, name.GetTaggedValue());
2669         return JSHandle<JSSymbol>(thread_, objValue);
2670     }
2671 
2672     JSHandle<JSSymbol> obj = NewPublicSymbol(name);
2673     JSHandle<JSTaggedValue> valueHandle(obj);
2674     JSHandle<JSTaggedValue> keyHandle(name);
2675     JSHandle<SymbolTable> table = SymbolTable::Insert(thread_, tableHandle, keyHandle, valueHandle);
2676     vm_->SetRegisterSymbols(table.GetTaggedValue());
2677     return obj;
2678 }
2679 
NewPrivateNameSymbolWithChar(std::string_view description)2680 JSHandle<JSSymbol> ObjectFactory::NewPrivateNameSymbolWithChar(std::string_view description)
2681 {
2682     JSHandle<EcmaString> string = NewFromUtf8(description);
2683     return NewPrivateNameSymbol(JSHandle<JSTaggedValue>(string));
2684 }
2685 
NewWellKnownSymbolWithChar(std::string_view description)2686 JSHandle<JSSymbol> ObjectFactory::NewWellKnownSymbolWithChar(std::string_view description)
2687 {
2688     JSHandle<EcmaString> string = NewFromUtf8(description);
2689     return NewWellKnownSymbol(JSHandle<JSTaggedValue>(string));
2690 }
2691 
NewPublicSymbolWithChar(std::string_view description)2692 JSHandle<JSSymbol> ObjectFactory::NewPublicSymbolWithChar(std::string_view description)
2693 {
2694     JSHandle<EcmaString> string = NewFromUtf8(description);
2695     return NewPublicSymbol(JSHandle<JSTaggedValue>(string));
2696 }
2697 
NewSymbolWithTableWithChar(std::string_view description)2698 JSHandle<JSSymbol> ObjectFactory::NewSymbolWithTableWithChar(std::string_view description)
2699 {
2700     JSHandle<EcmaString> string = NewFromUtf8(description);
2701     return NewSymbolWithTable(JSHandle<JSTaggedValue>(string));
2702 }
2703 
NewAccessorData()2704 JSHandle<AccessorData> ObjectFactory::NewAccessorData()
2705 {
2706     NewObjectHook();
2707     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2708         JSHClass::Cast(thread_->GlobalConstants()->GetAccessorDataClass().GetTaggedObject()));
2709     JSHandle<AccessorData> acc(thread_, AccessorData::Cast(header));
2710     acc->SetGetter<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2711     acc->SetSetter<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2712     return acc;
2713 }
2714 
NewInternalAccessor(void * setter,void * getter)2715 JSHandle<AccessorData> ObjectFactory::NewInternalAccessor(void *setter, void *getter)
2716 {
2717     NewObjectHook();
2718     TaggedObject *header = heap_->AllocateNonMovableOrHugeObject(
2719         JSHClass::Cast(thread_->GlobalConstants()->GetInternalAccessorClass().GetTaggedObject()));
2720     JSHandle<InternalAccessor> obj(thread_, InternalAccessor::Cast(header));
2721 
2722     obj->SetSetter(reinterpret_cast<InternalAccessor::InternalSetFunc>(setter));
2723     obj->SetGetter(reinterpret_cast<InternalAccessor::InternalGetFunc>(getter));
2724     return JSHandle<AccessorData>::Cast(obj);
2725 }
2726 
NewPromiseCapability()2727 JSHandle<PromiseCapability> ObjectFactory::NewPromiseCapability()
2728 {
2729     NewObjectHook();
2730     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2731         JSHClass::Cast(thread_->GlobalConstants()->GetCapabilityRecordClass().GetTaggedObject()));
2732     JSHandle<PromiseCapability> obj(thread_, header);
2733     obj->SetPromise<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2734     obj->SetResolve<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2735     obj->SetReject<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2736     return obj;
2737 }
2738 
NewJSPromise()2739 JSHandle<JSPromise> ObjectFactory::NewJSPromise()
2740 {
2741     NewObjectHook();
2742     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
2743     JSHandle<JSFunction> promiseObj(env->GetPromiseFunction());
2744     JSHandle<JSPromise> jsPromise = JSHandle<JSPromise>(NewJSObjectByConstructor(promiseObj));
2745     return jsPromise;
2746 }
2747 
NewPromiseReaction()2748 JSHandle<PromiseReaction> ObjectFactory::NewPromiseReaction()
2749 {
2750     NewObjectHook();
2751     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2752         JSHClass::Cast(thread_->GlobalConstants()->GetReactionsRecordClass().GetTaggedObject()));
2753     JSHandle<PromiseReaction> obj(thread_, header);
2754     obj->SetPromiseCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2755     obj->SetHandler<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2756     obj->SetType(PromiseType::RESOLVE);
2757     return obj;
2758 }
2759 
NewPromiseIteratorRecord(const JSHandle<JSTaggedValue> & itor,bool done)2760 JSHandle<PromiseIteratorRecord> ObjectFactory::NewPromiseIteratorRecord(const JSHandle<JSTaggedValue> &itor, bool done)
2761 {
2762     NewObjectHook();
2763     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2764         JSHClass::Cast(thread_->GlobalConstants()->GetPromiseIteratorRecordClass().GetTaggedObject()));
2765     JSHandle<PromiseIteratorRecord> obj(thread_, header);
2766     obj->SetIterator(thread_, itor.GetTaggedValue());
2767     obj->SetDone(done);
2768     return obj;
2769 }
2770 
NewMicroJobQueue()2771 JSHandle<job::MicroJobQueue> ObjectFactory::NewMicroJobQueue()
2772 {
2773     NewObjectHook();
2774     TaggedObject *header = heap_->AllocateNonMovableOrHugeObject(
2775         JSHClass::Cast(thread_->GlobalConstants()->GetMicroJobQueueClass().GetTaggedObject()));
2776     JSHandle<job::MicroJobQueue> obj(thread_, header);
2777     obj->SetPromiseJobQueue(thread_, GetEmptyTaggedQueue().GetTaggedValue());
2778     obj->SetScriptJobQueue(thread_, GetEmptyTaggedQueue().GetTaggedValue());
2779     return obj;
2780 }
2781 
NewPendingJob(const JSHandle<JSFunction> & func,const JSHandle<TaggedArray> & argv)2782 JSHandle<job::PendingJob> ObjectFactory::NewPendingJob(const JSHandle<JSFunction> &func,
2783                                                        const JSHandle<TaggedArray> &argv)
2784 {
2785     NewObjectHook();
2786     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
2787         JSHClass::Cast(thread_->GlobalConstants()->GetPendingJobClass().GetTaggedObject()));
2788     JSHandle<job::PendingJob> obj(thread_, header);
2789     obj->SetJob(thread_, func.GetTaggedValue());
2790     obj->SetArguments(thread_, argv.GetTaggedValue());
2791 #if defined(ENABLE_HITRACE)
2792     obj->SetChainId(0);
2793     obj->SetSpanId(0);
2794     obj->SetParentSpanId(0);
2795     obj->SetFlags(0);
2796     obj->SetJobId(0);
2797 #endif
2798     return obj;
2799 }
2800 
NewJSProxy(const JSHandle<JSTaggedValue> & target,const JSHandle<JSTaggedValue> & handler)2801 JSHandle<JSProxy> ObjectFactory::NewJSProxy(const JSHandle<JSTaggedValue> &target,
2802                                             const JSHandle<JSTaggedValue> &handler)
2803 {
2804     NewObjectHook();
2805     TaggedObject *header = nullptr;
2806     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
2807     JSHandle<JSObject> emptyObject = OrdinaryNewJSObjectCreate(vm_->GetGlobalEnv()->GetObjectFunctionPrototype());
2808 
2809     if (target->IsCallable()) {
2810         auto jsProxyCallableClass = JSHClass::Cast(globalConst->GetJSProxyCallableClass().GetTaggedObject());
2811         auto jsProxyConstructClass = JSHClass::Cast(globalConst->GetJSProxyConstructClass().GetTaggedObject());
2812         header = target->IsConstructor() ? heap_->AllocateYoungOrHugeObject(jsProxyConstructClass)
2813                                          : heap_->AllocateYoungOrHugeObject(jsProxyCallableClass);
2814     } else {
2815         header = heap_->AllocateYoungOrHugeObject(
2816             JSHClass::Cast(thread_->GlobalConstants()->GetJSProxyOrdinaryClass().GetTaggedObject()));
2817     }
2818 
2819     JSHandle<JSProxy> proxy(thread_, header);
2820     proxy->InitializeHash();
2821     proxy->SetMethod(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_GLOBAL_CALL_JS_PROXY));
2822     proxy->SetTarget(thread_, target.GetTaggedValue());
2823     proxy->SetHandler(thread_, handler.GetTaggedValue());
2824     proxy->SetPrivateField(thread_, emptyObject.GetTaggedValue());
2825     proxy->SetIsRevoked(false);
2826     return proxy;
2827 }
2828 
NewJSRealm()2829 JSHandle<JSRealm> ObjectFactory::NewJSRealm()
2830 {
2831     JSHandle<GlobalEnv> globalEnv = NewGlobalEnv(false, true);
2832     JSHandle<JSTaggedValue> protoValue = thread_->GlobalConstants()->GetHandledJSRealmClass();
2833     JSHandle<JSHClass> hclassHandle = NewEcmaHClass(JSRealm::SIZE, JSType::JS_REALM, protoValue);
2834     JSHandle<JSRealm> realm(NewJSObject(hclassHandle));
2835     realm->SetGlobalEnv(thread_, globalEnv.GetTaggedValue());
2836     realm->SetValue<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
2837 
2838     JSHandle<JSTaggedValue> realmObj = globalEnv->GetJSGlobalObject();
2839     JSHandle<JSTaggedValue> realmkey(thread_->GlobalConstants()->GetHandledGlobalString());
2840     PropertyDescriptor realmDesc(thread_, JSHandle<JSTaggedValue>::Cast(realmObj), true, false, true);
2841     [[maybe_unused]] bool status =
2842         JSObject::DefineOwnProperty(thread_, JSHandle<JSObject>::Cast(realm), realmkey, realmDesc);
2843     ASSERT_PRINT(status == true, "Realm defineOwnProperty failed");
2844 
2845     return realm;
2846 }
2847 
NewTaggedArray(uint32_t length,JSTaggedValue initVal,bool nonMovable)2848 JSHandle<TaggedArray> ObjectFactory::NewTaggedArray(uint32_t length, JSTaggedValue initVal, bool nonMovable)
2849 {
2850     if (nonMovable) {
2851         return NewTaggedArray(length, initVal, MemSpaceType::NON_MOVABLE);
2852     }
2853     return NewTaggedArray(length, initVal, MemSpaceType::SEMI_SPACE);
2854 }
2855 
NewTaggedArray(uint32_t length,JSTaggedValue initVal,MemSpaceType spaceType)2856 JSHandle<TaggedArray> ObjectFactory::NewTaggedArray(uint32_t length, JSTaggedValue initVal, MemSpaceType spaceType)
2857 {
2858     NewObjectHook();
2859     if (length == 0) {
2860         return EmptyArray();
2861     }
2862 
2863     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
2864     TaggedObject *header = nullptr;
2865     JSHClass *arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject());
2866     switch (spaceType) {
2867         case MemSpaceType::SEMI_SPACE:
2868             header = heap_->AllocateYoungOrHugeObject(arrayClass, size);
2869             break;
2870         case MemSpaceType::OLD_SPACE:
2871             header = heap_->AllocateOldOrHugeObject(arrayClass, size);
2872             break;
2873         case MemSpaceType::NON_MOVABLE:
2874             header = heap_->AllocateNonMovableOrHugeObject(arrayClass, size);
2875             break;
2876         case MemSpaceType::SHARED_OLD_SPACE:
2877             header = sHeap_->AllocateOldOrHugeObject(thread_, arrayClass, size);
2878             break;
2879         case MemSpaceType::SHARED_NON_MOVABLE:
2880             header = sHeap_->AllocateNonMovableOrHugeObject(thread_, arrayClass, size);
2881             break;
2882         default:
2883             LOG_ECMA(FATAL) << "this branch is unreachable";
2884             UNREACHABLE();
2885     }
2886 
2887     JSHandle<TaggedArray> array(thread_, header);
2888     array->InitializeWithSpecialValue(initVal, length);
2889     return array;
2890 }
2891 
NewAndCopyTaggedArray(JSHandle<TaggedArray> & srcElements,uint32_t newLength,uint32_t oldLength,uint32_t k)2892 JSHandle<TaggedArray> ObjectFactory::NewAndCopyTaggedArray(JSHandle<TaggedArray> &srcElements, uint32_t newLength,
2893                                                            uint32_t oldLength, uint32_t k)
2894 {
2895     ASSERT(oldLength <= newLength);
2896     MemSpaceType spaceType = newLength < LENGTH_THRESHOLD ? MemSpaceType::SEMI_SPACE : MemSpaceType::OLD_SPACE;
2897     JSHandle<TaggedArray> dstElements = NewTaggedArrayWithoutInit(newLength, spaceType);
2898     dstElements->SetExtraLength(srcElements->GetExtraLength());
2899     if (newLength == 0) {
2900         return dstElements;
2901     }
2902     dstElements->Copy(thread_, 0, k, srcElements.GetObject<TaggedArray>(), oldLength);
2903     for (uint32_t i = oldLength; i < newLength; i++) {
2904         dstElements->Set(thread_, i, JSTaggedValue::Hole());
2905     }
2906     return dstElements;
2907 }
2908 
NewAndCopyTaggedArraySkipBarrier(JSHandle<TaggedArray> & srcElements,uint32_t newLength,uint32_t oldLength,uint32_t k)2909 JSHandle<TaggedArray> ObjectFactory::NewAndCopyTaggedArraySkipBarrier(JSHandle<TaggedArray> &srcElements,
2910     uint32_t newLength, uint32_t oldLength, uint32_t k)
2911 {
2912     ASSERT(oldLength <= newLength);
2913     MemSpaceType spaceType = newLength < LENGTH_THRESHOLD ? MemSpaceType::SEMI_SPACE : MemSpaceType::OLD_SPACE;
2914     JSHandle<TaggedArray> dstElements = NewTaggedArrayWithoutInit(newLength, spaceType);
2915     if (newLength == 0) {
2916         return dstElements;
2917     }
2918     dstElements->Copy<false>(thread_, 0, k, srcElements.GetObject<TaggedArray>(), oldLength);
2919     for (uint32_t i = oldLength; i < newLength; i++) {
2920         dstElements->Set(thread_, i, JSTaggedValue::Hole());
2921     }
2922     return dstElements;
2923 }
2924 
NewAndCopySNameDictionary(JSHandle<TaggedArray> & srcElements,uint32_t length)2925 JSHandle<TaggedArray> ObjectFactory::NewAndCopySNameDictionary(JSHandle<TaggedArray> &srcElements, uint32_t length)
2926 {
2927     JSHandle<TaggedArray> dstElements = NewSDictionaryArray(length);
2928     if (length == 0) {
2929         return dstElements;
2930     }
2931     for (uint32_t i = 0; i < length; i++) {
2932         dstElements->Set(thread_, i, srcElements->Get(thread_, i));
2933     }
2934     return dstElements;
2935 }
2936 
NewAndCopyJSArrayObject(JSHandle<JSObject> thisObjHandle,uint32_t newLength,uint32_t oldLength,uint32_t k)2937 JSHandle<JSObject> ObjectFactory::NewAndCopyJSArrayObject(JSHandle<JSObject> thisObjHandle, uint32_t newLength,
2938                                                           uint32_t oldLength, uint32_t k)
2939 {
2940     ASSERT(oldLength <= newLength);
2941     JSHandle<TaggedArray> dstElements(NewTaggedArray(newLength));
2942     JSHandle<JSTaggedValue> holeHandle(thread_, JSTaggedValue::Hole());
2943     JSHandle<JSObject> arrayObj = JSHandle<JSObject>(NewJSStableArrayWithElements(dstElements));
2944     if (newLength == 0) {
2945         return JSHandle<JSObject>(arrayObj);
2946     }
2947     for (uint32_t i = 0; i < oldLength; i++) {
2948         JSHandle<JSTaggedValue> value(thread_, ElementAccessor::Get(thread_, thisObjHandle, i + k));
2949         ElementAccessor::Set(thread_, arrayObj, i, value, true);
2950     }
2951     for (uint32_t i = oldLength; i < newLength; i++) {
2952         ElementAccessor::Set(thread_, arrayObj, i, holeHandle, true);
2953     }
2954     return arrayObj;
2955 }
2956 
NewAndCopyTaggedArrayByObject(JSHandle<JSObject> thisObjHandle,uint32_t newLength,uint32_t oldLength,uint32_t k)2957 JSHandle<TaggedArray> ObjectFactory::NewAndCopyTaggedArrayByObject(JSHandle<JSObject> thisObjHandle, uint32_t newLength,
2958                                                                    uint32_t oldLength, uint32_t k)
2959 {
2960     ASSERT(oldLength <= newLength);
2961     MemSpaceType spaceType = newLength < LENGTH_THRESHOLD ? MemSpaceType::SEMI_SPACE : MemSpaceType::OLD_SPACE;
2962     JSHandle<TaggedArray> dstElements(NewTaggedArrayWithoutInit(newLength, spaceType));
2963     TaggedArray *srcElements = TaggedArray::Cast(thisObjHandle->GetElements(thread_).GetTaggedObject());
2964     dstElements->SetExtraLength(srcElements->GetExtraLength());
2965     if (newLength == 0) {
2966         return dstElements;
2967     }
2968 
2969     for (uint32_t i = 0; i < oldLength; i++) {
2970         dstElements->Set(thread_, i, ElementAccessor::Get(thread_, thisObjHandle, i + k));
2971     }
2972     for (uint32_t i = oldLength; i < newLength; i++) {
2973         dstElements->Set(thread_, i, JSTaggedValue::Hole());
2974     }
2975     return dstElements;
2976 }
2977 
NewAndCopyMutantTaggedArrayByObject(JSHandle<JSObject> thisObjHandle,uint32_t newLength,uint32_t oldLength,uint32_t k)2978 JSHandle<MutantTaggedArray> ObjectFactory::NewAndCopyMutantTaggedArrayByObject(JSHandle<JSObject> thisObjHandle,
2979                                                                                uint32_t newLength, uint32_t oldLength,
2980                                                                                uint32_t k)
2981 {
2982     ASSERT(oldLength <= newLength);
2983     MemSpaceType spaceType = newLength < LENGTH_THRESHOLD ? MemSpaceType::SEMI_SPACE : MemSpaceType::OLD_SPACE;
2984     JSHandle<MutantTaggedArray> dstElements(NewMutantTaggedArrayWithoutInit(newLength, spaceType));
2985     MutantTaggedArray *srcElements = MutantTaggedArray::Cast(thisObjHandle->GetElements(thread_).GetTaggedObject());
2986     dstElements->SetExtraLength(srcElements->GetExtraLength());
2987     if (newLength == 0) {
2988         return dstElements;
2989     }
2990     for (uint32_t i = 0; i < oldLength; i++) {
2991         ElementsKind kind = thisObjHandle->GetClass()->GetElementsKind();
2992         JSTaggedValue value = JSTaggedValue(ElementAccessor::ConvertTaggedValueWithElementsKind(
2993             ElementAccessor::Get(thread_, thisObjHandle, i + k), kind));
2994         dstElements->Set<false>(thread_, i, value);
2995     }
2996     for (uint32_t i = oldLength; i < newLength; i++) {
2997         ElementsKind kind = thisObjHandle->GetClass()->GetElementsKind();
2998         JSTaggedValue value = JSTaggedValue(ElementAccessor::ConvertTaggedValueWithElementsKind(JSTaggedValue::Hole(),
2999                                                                                                 kind));
3000         dstElements->Set<false>(thread_, i, value);
3001     }
3002     return dstElements;
3003 }
3004 
3005 // private
NewTaggedArrayWithoutInit(uint32_t length,MemSpaceType spaceType)3006 JSHandle<TaggedArray> ObjectFactory::NewTaggedArrayWithoutInit(uint32_t length, MemSpaceType spaceType)
3007 {
3008     NewObjectHook();
3009     if (length == 0) {
3010         return EmptyArray();
3011     }
3012 
3013     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3014     TaggedObject *header = nullptr;
3015     auto arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject());
3016     switch (spaceType) {
3017         case MemSpaceType::SEMI_SPACE:
3018             header = heap_->AllocateYoungOrHugeObject(arrayClass, size);
3019             break;
3020         case MemSpaceType::OLD_SPACE:
3021             header = heap_->AllocateOldOrHugeObject(arrayClass, size);
3022             break;
3023         case MemSpaceType::SHARED_OLD_SPACE:
3024             header = sHeap_->AllocateOldOrHugeObject(thread_, arrayClass, size);
3025             break;
3026         default:
3027             LOG_ECMA(FATAL) << "this branch is unreachable";
3028             UNREACHABLE();
3029     }
3030     JSHandle<TaggedArray> array(thread_, header);
3031     array->SetLength(length);
3032     return array;
3033 }
3034 
3035 // private
NewMutantTaggedArrayWithoutInit(uint32_t length,MemSpaceType spaceType)3036 JSHandle<MutantTaggedArray> ObjectFactory::NewMutantTaggedArrayWithoutInit(uint32_t length, MemSpaceType spaceType)
3037 {
3038     NewObjectHook();
3039     if (length == 0) {
3040         return EmptyMutantArray();
3041     }
3042 
3043     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3044     TaggedObject *header = nullptr;
3045     auto arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetMutantTaggedArrayClass().GetTaggedObject());
3046     switch (spaceType) {
3047         case MemSpaceType::SEMI_SPACE:
3048             header = heap_->AllocateYoungOrHugeObject(arrayClass, size);
3049             break;
3050         case MemSpaceType::OLD_SPACE:
3051             header = heap_->AllocateOldOrHugeObject(arrayClass, size);
3052             break;
3053         default:
3054             LOG_ECMA(FATAL) << "this branch is unreachable";
3055             UNREACHABLE();
3056     }
3057     JSHandle<MutantTaggedArray> array(thread_, header);
3058     array->SetLength(length);
3059     return array;
3060 }
3061 
NewTaggedArray(uint32_t length,JSTaggedValue initVal)3062 JSHandle<TaggedArray> ObjectFactory::NewTaggedArray(uint32_t length, JSTaggedValue initVal)
3063 {
3064     NewObjectHook();
3065     if (length == 0) {
3066         return EmptyArray();
3067     }
3068     MemSpaceType spaceType = length < LENGTH_THRESHOLD ? MemSpaceType::SEMI_SPACE : MemSpaceType::OLD_SPACE;
3069     JSHandle<TaggedArray> array = NewTaggedArrayWithoutInit(length, spaceType);
3070     array->InitializeWithSpecialValue(initVal, length);
3071     return array;
3072 }
3073 
NewCOWTaggedArray(uint32_t length,JSTaggedValue initVal)3074 JSHandle<COWTaggedArray> ObjectFactory::NewCOWTaggedArray(uint32_t length, JSTaggedValue initVal)
3075 {
3076     NewObjectHook();
3077     ASSERT(length > 0);
3078 
3079     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3080     auto header = heap_->AllocateNonMovableOrHugeObject(
3081         JSHClass::Cast(thread_->GlobalConstants()->GetCOWArrayClass().GetTaggedObject()), size);
3082     JSHandle<COWTaggedArray> cowArray(thread_, header);
3083     cowArray->InitializeWithSpecialValue(initVal, length);
3084     return cowArray;
3085 }
3086 
NewCOWMutantTaggedArray(uint32_t length,JSTaggedType initVal)3087 JSHandle<COWMutantTaggedArray> ObjectFactory::NewCOWMutantTaggedArray(uint32_t length, JSTaggedType initVal)
3088 {
3089     NewObjectHook();
3090     ASSERT(length > 0);
3091 
3092     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3093     auto header = heap_->AllocateNonMovableOrHugeObject(
3094         JSHClass::Cast(thread_->GlobalConstants()->GetCOWMutantTaggedArrayClass().GetTaggedObject()), size);
3095     JSHandle<COWMutantTaggedArray> cowMutantTaggedArray(thread_, header);
3096     cowMutantTaggedArray->InitializeWithSpecialValue(initVal, length);
3097     return cowMutantTaggedArray;
3098 }
3099 
NewMutantTaggedArray(uint32_t length,JSTaggedType initVal)3100 JSHandle<MutantTaggedArray> ObjectFactory::NewMutantTaggedArray(uint32_t length, JSTaggedType initVal)
3101 {
3102     NewObjectHook();
3103     ASSERT(length > 0);
3104 
3105     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3106     auto header = heap_->AllocateYoungOrHugeObject(
3107         JSHClass::Cast(thread_->GlobalConstants()->GetMutantTaggedArrayClass().GetTaggedObject()), size);
3108     JSHandle<MutantTaggedArray> mutantTaggedArray(thread_, header);
3109     mutantTaggedArray->InitializeWithSpecialValue(initVal, length);
3110     return mutantTaggedArray;
3111 }
3112 
NewTaggedHashArray(uint32_t length)3113 JSHandle<TaggedHashArray> ObjectFactory::NewTaggedHashArray(uint32_t length)
3114 {
3115     if (length == 0) {
3116         return JSHandle<TaggedHashArray>::Cast(EmptyArray());
3117     }
3118 
3119     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3120     auto header = heap_->AllocateYoungOrHugeObject(
3121         JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject()), size);
3122     JSHandle<TaggedHashArray> array(thread_, header);
3123     array->InitializeWithSpecialValue(JSTaggedValue::Hole(), length);
3124     return array;
3125 }
3126 
NewByteArray(uint32_t length,uint32_t size,void * srcData,MemSpaceType spaceType)3127 JSHandle<ByteArray> ObjectFactory::NewByteArray(uint32_t length, uint32_t size, void *srcData,
3128                                                 MemSpaceType spaceType)
3129 {
3130     size_t byteSize = ByteArray::ComputeSize(size, length);
3131     JSHClass *arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetByteArrayClass().GetTaggedObject());
3132     TaggedObject *header = AllocObjectWithSpaceType(byteSize, arrayClass, spaceType);
3133     JSHandle<ByteArray> array(thread_, header);
3134 
3135     void *data = array->GetData();
3136 
3137     if (srcData != nullptr) {
3138         if (memcpy_s(data, length * size, srcData, length * size) != EOK) {
3139             LOG_FULL(FATAL) << "memcpy_s failed";
3140             UNREACHABLE();
3141         }
3142     } else {
3143         if (memset_s(data, length * size, 0, length * size) != EOK) {
3144             LOG_FULL(FATAL) << "memset_s failed";
3145             UNREACHABLE();
3146         }
3147     }
3148 
3149     array->SetArrayLength(length);
3150     array->SetByteLength(size);
3151     return array;
3152 }
3153 
NewLinkedNode(int hash,const JSHandle<JSTaggedValue> & key,const JSHandle<JSTaggedValue> & value,const JSHandle<LinkedNode> & next)3154 JSHandle<LinkedNode> ObjectFactory::NewLinkedNode(int hash, const JSHandle<JSTaggedValue> &key,
3155                                                   const JSHandle<JSTaggedValue> &value,
3156                                                   const JSHandle<LinkedNode> &next)
3157 {
3158     NewObjectHook();
3159     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3160     auto header = heap_->AllocateYoungOrHugeObject(
3161         JSHClass::Cast(globalConst->GetLinkedNode().GetTaggedObject()), LinkedNode::SIZE);
3162     JSHandle<LinkedNode> node(thread_, header);
3163     node->InitLinkedNode(thread_, hash, key, value, next);
3164 
3165     return node;
3166 }
3167 
NewTreeNode(int hash,const JSHandle<JSTaggedValue> & key,const JSHandle<JSTaggedValue> & value)3168 JSHandle<RBTreeNode> ObjectFactory::NewTreeNode(int hash, const JSHandle<JSTaggedValue> &key,
3169                                                 const JSHandle<JSTaggedValue> &value)
3170 {
3171     NewObjectHook();
3172     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3173     auto header = heap_->AllocateYoungOrHugeObject(
3174         JSHClass::Cast(globalConst->GetRBTreeNode().GetTaggedObject()), RBTreeNode::SIZE);
3175     JSHandle<RBTreeNode> treenode(thread_, header);
3176     treenode->InitRBTreeNode(thread_, hash, key, value, 1);
3177     return treenode;
3178 }
3179 
NewDictionaryArray(uint32_t length)3180 JSHandle<TaggedArray> ObjectFactory::NewDictionaryArray(uint32_t length)
3181 {
3182     NewObjectHook();
3183     ASSERT(length > 0);
3184 
3185     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3186     auto header = heap_->AllocateYoungOrHugeObject(
3187         JSHClass::Cast(thread_->GlobalConstants()->GetDictionaryClass().GetTaggedObject()), size);
3188     JSHandle<TaggedArray> array(thread_, header);
3189     array->InitializeWithSpecialValue(JSTaggedValue::Undefined(), length);
3190 
3191     return array;
3192 }
3193 
ExtendArray(const JSHandle<TaggedArray> & old,uint32_t length,JSTaggedValue initVal,MemSpaceType type,ElementsKind kind)3194 JSHandle<TaggedArray> ObjectFactory::ExtendArray(const JSHandle<TaggedArray> &old, uint32_t length,
3195                                                  JSTaggedValue initVal, MemSpaceType type,
3196                                                  [[maybe_unused]] ElementsKind kind)
3197 {
3198     ASSERT(length >= old->GetLength());
3199     NewObjectHook();
3200     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length);
3201     JSHClass *arrayClass = nullptr;
3202     // If old element is Mutantarray, need conversion according to kind.
3203     if (old->GetClass()->IsMutantTaggedArray()) {
3204         arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetMutantTaggedArrayClass().GetTaggedObject());
3205     } else {
3206         arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject());
3207     }
3208     TaggedObject *header = AllocObjectWithSpaceType(size, arrayClass, type);
3209     JSHandle<TaggedArray> newArray(thread_, header);
3210     newArray->SetLength(length);
3211     newArray->SetExtraLength(old->GetExtraLength());
3212 
3213     uint32_t oldLength = old->GetLength();
3214     uint32_t index = 0;
3215     auto isMutantTaggedArray = old->GetClass()->IsMutantTaggedArray();
3216     for (; index < oldLength; ++index) {
3217         if (isMutantTaggedArray) {
3218             newArray->Set<false>(thread_, index, old->Get(thread_, index));
3219         } else {
3220             newArray->Set(thread_, index, old->Get(thread_, index));
3221         }
3222     }
3223     auto isSpecialHole = initVal.IsHole() && isMutantTaggedArray;
3224     JSTaggedValue specialHole = JSTaggedValue(base::SPECIAL_HOLE);
3225     for (; index < length; ++index) {
3226         if (isSpecialHole) {
3227             newArray->Set<false>(thread_, index, specialHole);
3228         } else {
3229             newArray->Set(thread_, index, initVal);
3230         }
3231     }
3232 
3233     return newArray;
3234 }
3235 
CopyPartArray(const JSHandle<TaggedArray> & old,uint32_t start,uint32_t end)3236 JSHandle<TaggedArray> ObjectFactory::CopyPartArray(const JSHandle<TaggedArray> &old, uint32_t start,
3237                                                    uint32_t end)
3238 {
3239     ASSERT(start <= end);
3240     ASSERT(end <= old->GetLength());
3241 
3242     uint32_t newLength = end - start;
3243     if (newLength == 0) {
3244         return EmptyArray();
3245     }
3246 
3247     NewObjectHook();
3248     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), newLength);
3249     auto header = heap_->AllocateYoungOrHugeObject(
3250         JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject()), size);
3251     JSHandle<TaggedArray> newArray(thread_, header);
3252     newArray->InitializeWithSpecialValue(JSTaggedValue::Hole(), newLength, old->GetExtraLength());
3253 
3254     for (uint32_t i = 0; i < newLength; i++) {
3255         JSTaggedValue value = old->Get(thread_, i + start);
3256         if (value.IsHole()) {
3257             break;
3258         }
3259         newArray->Set(thread_, i, value);
3260     }
3261     return newArray;
3262 }
3263 
CopyArray(const JSHandle<TaggedArray> & old,uint32_t oldLength,uint32_t newLength,JSTaggedValue initVal,MemSpaceType type,ElementsKind kind)3264 JSHandle<TaggedArray> ObjectFactory::CopyArray(const JSHandle<TaggedArray> &old, uint32_t oldLength, uint32_t newLength,
3265                                                JSTaggedValue initVal, MemSpaceType type, ElementsKind kind)
3266 {
3267     if (newLength == 0) {
3268         return EmptyArray();
3269     }
3270     if (newLength > oldLength) {
3271         return ExtendArray(old, newLength, initVal, type, kind);
3272     }
3273     NewObjectHook();
3274     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), newLength);
3275     TaggedObject *header = nullptr;
3276     if (type == MemSpaceType::NON_MOVABLE) {
3277         // COW array is shared in nonmovable space.
3278         JSHClass *cowArrayClass = nullptr;
3279         if (old->GetClass()->IsMutantTaggedArray()) {
3280             cowArrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetCOWMutantTaggedArrayClass()
3281                                            .GetTaggedObject());
3282         } else {
3283             cowArrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetCOWArrayClass().GetTaggedObject());
3284         }
3285         header = AllocObjectWithSpaceType(size, cowArrayClass, type);
3286     } else {
3287         JSHClass *arrayClass = nullptr;
3288         if (old->GetClass()->IsMutantTaggedArray()) {
3289             arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetMutantTaggedArrayClass().GetTaggedObject());
3290         } else {
3291             arrayClass = JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject());
3292         }
3293         header = AllocObjectWithSpaceType(size, arrayClass, type);
3294     }
3295 
3296     JSHandle<TaggedArray> newArray(thread_, header);
3297     newArray->SetLength(newLength);
3298     newArray->SetExtraLength(old->GetExtraLength());
3299     if (old->GetClass()->IsMutantTaggedArray()) {
3300         newArray->Copy<false>(thread_, 0, 0, *old, newLength);
3301     } else {
3302         newArray->Copy(thread_, 0, 0, *old, newLength);
3303     }
3304 
3305     return newArray;
3306 }
3307 
CopyFromKeyArray(const JSHandle<TaggedArray> & old)3308 JSHandle<TaggedArray> ObjectFactory::CopyFromKeyArray(const JSHandle<TaggedArray> &old)
3309 {
3310     NewObjectHook();
3311     uint32_t newLength = old->GetLength();
3312     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), newLength);
3313     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
3314         JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject()), size);
3315     JSHandle<TaggedArray> newArray(thread_, header);
3316     newArray->SetLength(newLength);
3317     newArray->SetExtraLength(old->GetExtraLength());
3318 
3319     for (uint32_t i = 0; i < newLength; i++) {
3320         JSTaggedValue value = old->Get(thread_, i);
3321         newArray->Set(thread_, i, value);
3322     }
3323     return newArray;
3324 }
3325 
CreateLayoutInfo(int properties,MemSpaceType type,GrowMode mode)3326 JSHandle<LayoutInfo> ObjectFactory::CreateLayoutInfo(int properties, MemSpaceType type, GrowMode mode)
3327 {
3328     int growLength =
3329         mode == GrowMode::GROW ? static_cast<int>(LayoutInfo::ComputeGrowCapacity(properties)) : properties;
3330     uint32_t arrayLength = LayoutInfo::ComputeArrayLength(growLength);
3331     JSHandle<LayoutInfo> layoutInfoHandle = JSHandle<LayoutInfo>::Cast(NewTaggedArrayWithoutInit(arrayLength, type));
3332     layoutInfoHandle->Initialize(thread_);
3333     return layoutInfoHandle;
3334 }
3335 
ExtendLayoutInfo(const JSHandle<LayoutInfo> & old,int properties)3336 JSHandle<LayoutInfo> ObjectFactory::ExtendLayoutInfo(const JSHandle<LayoutInfo> &old, int properties)
3337 {
3338     ASSERT(properties >= old->NumberOfElements());
3339     uint32_t arrayLength = LayoutInfo::ComputeArrayLength(LayoutInfo::ComputeGrowCapacity(properties));
3340     ASSERT(arrayLength > old->GetLength());
3341 
3342     auto oldArray = JSHandle<TaggedArray>(old);
3343     auto newArray = NewTaggedArrayWithoutInit(arrayLength, MemSpaceType::SEMI_SPACE);
3344     JSHandle<LayoutInfo>::Cast(newArray)->Initialize(thread_, oldArray->GetExtraLength());
3345 
3346     uint32_t oldLength = old->GetLength();
3347     if (g_isEnableCMCGC) {
3348         for (uint32_t i = 0; i < oldLength; i++) {
3349             JSTaggedValue value = oldArray->Get<RBMode::FAST_CMC_RB>(thread_, i);
3350             newArray->Set(thread_, i, value);
3351         }
3352     } else {
3353         for (uint32_t i = 0; i < oldLength; i++) {
3354             JSTaggedValue value = oldArray->Get<RBMode::FAST_NO_RB>(thread_, i);
3355             newArray->Set(thread_, i, value);
3356         }
3357     }
3358     return JSHandle<LayoutInfo>::Cast(newArray);
3359 }
3360 
CopyLayoutInfo(const JSHandle<LayoutInfo> & old)3361 JSHandle<LayoutInfo> ObjectFactory::CopyLayoutInfo(const JSHandle<LayoutInfo> &old)
3362 {
3363     uint32_t newLength = old->GetLength();
3364     return JSHandle<LayoutInfo>(CopyArray(
3365         JSHandle<TaggedArray>::Cast(old), newLength, newLength, JSTaggedValue::Hole(),
3366         old.GetTaggedValue().IsInSharedHeap() ? MemSpaceType::SHARED_OLD_SPACE : MemSpaceType::SEMI_SPACE));
3367 }
3368 
CopyAndReSort(const JSHandle<LayoutInfo> & old,int end,int capacity)3369 JSHandle<LayoutInfo> ObjectFactory::CopyAndReSort(const JSHandle<LayoutInfo> &old, int end, int capacity)
3370 {
3371     ASSERT(capacity >= end);
3372     JSHandle<LayoutInfo> newArr = CreateLayoutInfo(capacity);
3373     Span<struct Properties> sp(old->GetProperties(), end);
3374     void *propertiesObj = reinterpret_cast<void *>(old->GetProperties());
3375     size_t keyOffset = 0;
3376     size_t attrOffset = sizeof(JSTaggedType);
3377     if (g_isEnableCMCGC) {
3378         for (int i = 0; i < end; i++) {
3379             JSTaggedValue propKey(Barriers::GetTaggedValue<RBMode::FAST_CMC_RB>(
3380                 thread_, ToUintPtr(propertiesObj) + i * sizeof(Properties) + keyOffset));
3381             JSTaggedValue propValue(Barriers::GetTaggedValue<RBMode::FAST_CMC_RB>(
3382                 thread_, ToUintPtr(propertiesObj) + i * sizeof(Properties) + attrOffset));
3383             sp[i].key_ = propKey;
3384             sp[i].attr_ = propValue;
3385             newArr->AddKey(thread_, i, sp[i].key_, PropertyAttributes(sp[i].attr_));
3386         }
3387     } else {
3388         for (int i = 0; i < end; i++) {
3389             JSTaggedValue propKey(Barriers::GetTaggedValue<RBMode::FAST_NO_RB>(
3390                 thread_, ToUintPtr(propertiesObj) + i * sizeof(Properties) + keyOffset));
3391             JSTaggedValue propValue(Barriers::GetTaggedValue<RBMode::FAST_NO_RB>(
3392                 thread_, ToUintPtr(propertiesObj) + i * sizeof(Properties) + attrOffset));
3393             sp[i].key_ = propKey;
3394             sp[i].attr_ = propValue;
3395             newArr->AddKey(thread_, i, sp[i].key_, PropertyAttributes(sp[i].attr_));
3396         }
3397     }
3398 
3399     return newArr;
3400 }
3401 
NewConstantPool(uint32_t capacity)3402 JSHandle<ConstantPool> ObjectFactory::NewConstantPool(uint32_t capacity)
3403 {
3404     NewObjectHook();
3405     size_t size = ConstantPool::ComputeSize(capacity);
3406     auto header = heap_->AllocateOldOrHugeObject(
3407         JSHClass::Cast(thread_->GlobalConstants()->GetConstantPoolClass().GetTaggedObject()), size);
3408     JSHandle<ConstantPool> array(thread_, header);
3409     array->InitializeWithSpecialValue(thread_, JSTaggedValue::Hole(), capacity);
3410     return array;
3411 }
3412 
NewProgram()3413 JSHandle<Program> ObjectFactory::NewProgram()
3414 {
3415     NewObjectHook();
3416     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
3417         JSHClass::Cast(thread_->GlobalConstants()->GetProgramClass().GetTaggedObject()));
3418     JSHandle<Program> p(thread_, header);
3419     p->InitializeHash();
3420     p->SetMainFunction<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3421     return p;
3422 }
3423 
NewModuleNamespace()3424 JSHandle<ModuleNamespace> ObjectFactory::NewModuleNamespace()
3425 {
3426     NewObjectHook();
3427     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3428     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetModuleNamespaceClass());
3429     JSHandle<JSObject> obj = NewJSObject(hclass);
3430 
3431     JSHandle<ModuleNamespace> moduleNamespace = JSHandle<ModuleNamespace>::Cast(obj);
3432     moduleNamespace->SetModule<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3433     moduleNamespace->SetExports<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3434     moduleNamespace->SetDeregisterProcession<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3435     return moduleNamespace;
3436 }
3437 
NewNativeModuleFailureInfo()3438 JSHandle<NativeModuleFailureInfo> ObjectFactory::NewNativeModuleFailureInfo()
3439 {
3440     NewObjectHook();
3441     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3442     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetNativeModuleFailureInfoClass());
3443     JSHandle<JSObject> obj = NewJSObject(hclass);
3444 
3445     JSHandle<NativeModuleFailureInfo> nativeModuleFailureInfo = JSHandle<NativeModuleFailureInfo>::Cast(obj);
3446     nativeModuleFailureInfo->SetArkNativeModuleFailureInfo<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3447     return nativeModuleFailureInfo;
3448 }
3449 
NewCjsModule()3450 JSHandle<CjsModule> ObjectFactory::NewCjsModule()
3451 {
3452     NewObjectHook();
3453     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3454     JSHandle<JSFunction> moduleObj(env->GetCjsModuleFunction());
3455     JSHandle<CjsModule> cjsModule = JSHandle<CjsModule>(NewJSObjectByConstructor(moduleObj));
3456     return cjsModule;
3457 }
3458 
NewCjsExports()3459 JSHandle<CjsExports> ObjectFactory::NewCjsExports()
3460 {
3461     NewObjectHook();
3462     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3463     JSHandle<JSFunction> exportsObj(env->GetCjsExportsFunction());
3464     JSHandle<CjsExports> cjsExports = JSHandle<CjsExports>(NewJSObjectByConstructor(exportsObj));
3465     return cjsExports;
3466 }
3467 
NewCjsRequire()3468 JSHandle<CjsRequire> ObjectFactory::NewCjsRequire()
3469 {
3470     NewObjectHook();
3471     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3472     JSHandle<JSFunction> requireObj(env->GetCjsRequireFunction());
3473     JSHandle<CjsRequire> cjsRequire = JSHandle<CjsRequire>(NewJSObjectByConstructor(requireObj));
3474     return cjsRequire;
3475 }
3476 
GetEmptyString() const3477 JSHandle<EcmaString> ObjectFactory::GetEmptyString() const
3478 {
3479     return JSHandle<EcmaString>(thread_->GlobalConstants()->GetHandledEmptyString());
3480 }
3481 
EmptyArray() const3482 JSHandle<TaggedArray> ObjectFactory::EmptyArray() const
3483 {
3484     return JSHandle<TaggedArray>(thread_->GlobalConstants()->GetHandledEmptyArray());
3485 }
3486 
EmptyMutantArray() const3487 JSHandle<MutantTaggedArray> ObjectFactory::EmptyMutantArray() const
3488 {
3489     return JSHandle<MutantTaggedArray>(thread_->GlobalConstants()->GetHandledEmptyArray());
3490 }
3491 
GetStringFromStringTable(const uint8_t * utf8Data,uint32_t utf8Len,bool canBeCompress) const3492 JSHandle<EcmaString> ObjectFactory::GetStringFromStringTable(const uint8_t *utf8Data, uint32_t utf8Len,
3493                                                              bool canBeCompress) const
3494 {
3495     NewObjectHook();
3496     if (utf8Len == 0) {
3497         return GetEmptyString();
3498     }
3499     auto stringTable = vm_->GetEcmaStringTable();
3500     return JSHandle<EcmaString>(thread_, stringTable->GetOrInternString(vm_, utf8Data, utf8Len, canBeCompress));
3501 }
3502 
GetCompressedSubStringFromStringTable(const JSHandle<EcmaString> & string,uint32_t offset,uint32_t utf8Len) const3503 JSHandle<EcmaString> ObjectFactory::GetCompressedSubStringFromStringTable(const JSHandle<EcmaString> &string,
3504                                                                           uint32_t offset, uint32_t utf8Len) const
3505 {
3506     NewObjectHook();
3507     if (UNLIKELY(utf8Len == 0)) {
3508         return GetEmptyString();
3509     }
3510     auto *stringTable = vm_->GetEcmaStringTable();
3511     return JSHandle<EcmaString>(thread_,
3512         stringTable->GetOrInternStringFromCompressedSubString(vm_, string, offset, utf8Len));
3513 }
3514 
GetStringFromStringTableReadOnly(const uint8_t * utf8Data,uint32_t utf8Len,bool canBeCompress) const3515 JSHandle<EcmaString> ObjectFactory::GetStringFromStringTableReadOnly(const uint8_t *utf8Data, uint32_t utf8Len,
3516                                                                      bool canBeCompress) const
3517 {
3518     NewObjectHook();
3519     if (utf8Len == 0) {
3520         return GetEmptyString();
3521     }
3522     auto stringTable = vm_->GetEcmaStringTable();
3523     return JSHandle<EcmaString>(thread_, stringTable->GetOrInternString(vm_, utf8Data, utf8Len, canBeCompress,
3524                                                                         MemSpaceType::SHARED_READ_ONLY_SPACE));
3525 }
3526 
GetStringFromStringTable(const uint16_t * utf16Data,uint32_t utf16Len,bool canBeCompress) const3527 JSHandle<EcmaString> ObjectFactory::GetStringFromStringTable(const uint16_t *utf16Data, uint32_t utf16Len,
3528                                                              bool canBeCompress) const
3529 {
3530     NewObjectHook();
3531     if (utf16Len == 0) {
3532         return GetEmptyString();
3533     }
3534     auto stringTable = vm_->GetEcmaStringTable();
3535     return JSHandle<EcmaString>(thread_, stringTable->GetOrInternString(vm_, utf16Data, utf16Len, canBeCompress));
3536 }
3537 
3538 // NB! don't do special case for C0 80, it means '\u0000', so don't convert to UTF-8
GetRawStringFromStringTable(StringData sd,MemSpaceType type) const3539 EcmaString *ObjectFactory::GetRawStringFromStringTable(StringData sd, MemSpaceType type) const
3540 {
3541     NewObjectHook();
3542     uint32_t utf16Len = sd.utf16_length;
3543     if (UNLIKELY(utf16Len == 0)) {
3544         return *GetEmptyString();
3545     }
3546 
3547     bool canBeCompressed = sd.is_ascii;
3548     const uint8_t *mutf8Data = sd.data;
3549     if (canBeCompressed) {
3550         return vm_->GetEcmaStringTable()->GetOrInternString(vm_, mutf8Data, utf16Len, true, type);
3551     }
3552     return vm_->GetEcmaStringTable()->GetOrInternString(vm_, mutf8Data, utf16Len, type);
3553 }
3554 
3555 // used in jit thread, which unsupport create jshandle
GetRawStringFromStringTableWithoutJSHandle(StringData sd,MemSpaceType type) const3556 EcmaString *ObjectFactory::GetRawStringFromStringTableWithoutJSHandle(StringData sd, MemSpaceType type) const
3557 {
3558     NewObjectHook();
3559     uint32_t utf16Len = sd.utf16_length;
3560     if (UNLIKELY(utf16Len == 0)) {
3561         return *GetEmptyString();
3562     }
3563 
3564     bool canBeCompressed = sd.is_ascii;
3565     const uint8_t *mutf8Data = sd.data;
3566     if (canBeCompressed) {
3567         return vm_->GetEcmaStringTable()->GetOrInternStringWithoutJSHandleForJit(vm_, mutf8Data, utf16Len, true, type);
3568     }
3569     return vm_->GetEcmaStringTable()->GetOrInternStringWithoutJSHandleForJit(vm_, mutf8Data, utf16Len, type);
3570 }
3571 
NewPropertyBox(const JSHandle<JSTaggedValue> & value)3572 JSHandle<PropertyBox> ObjectFactory::NewPropertyBox(const JSHandle<JSTaggedValue> &value)
3573 {
3574     NewObjectHook();
3575     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
3576         JSHClass::Cast(thread_->GlobalConstants()->GetPropertyBoxClass().GetTaggedObject()));
3577     JSHandle<PropertyBox> box(thread_, header);
3578     box->SetValue(thread_, value);
3579     return box;
3580 }
3581 
NewEnumCache()3582 JSHandle<EnumCache> ObjectFactory::NewEnumCache()
3583 {
3584     NewObjectHook();
3585     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
3586         JSHClass::Cast(thread_->GlobalConstants()->GetEnumCacheClass().GetTaggedObject()));
3587     JSHandle<EnumCache> enumCache(thread_, header);
3588     JSObject::SetEnumCacheKind(thread_, enumCache, EnumCacheKind::NONE);
3589     enumCache->SetEnumCacheAll(thread_, JSTaggedValue::Null());
3590     enumCache->SetEnumCacheOwn(thread_, JSTaggedValue::Null());
3591     enumCache->SetProtoChainInfoEnumCache(thread_, JSTaggedValue::Null());
3592     return enumCache;
3593 }
3594 
NewProtoChangeMarker()3595 JSHandle<ProtoChangeMarker> ObjectFactory::NewProtoChangeMarker()
3596 {
3597     NewObjectHook();
3598     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
3599         JSHClass::Cast(thread_->GlobalConstants()->GetProtoChangeMarkerClass().GetTaggedObject()));
3600     JSHandle<ProtoChangeMarker> marker(thread_, header);
3601     marker->ClearBitField();
3602     return marker;
3603 }
3604 
NewMarkerCell()3605 JSHandle<MarkerCell> ObjectFactory::NewMarkerCell()
3606 {
3607     NewObjectHook();
3608     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
3609         JSHClass::Cast(thread_->GlobalConstants()->GetMarkerCellClass().GetTaggedObject()));
3610     JSHandle<MarkerCell> marker(thread_, header);
3611     marker->ClearBitField();
3612     return marker;
3613 }
3614 
NewProtoChangeDetails()3615 JSHandle<ProtoChangeDetails> ObjectFactory::NewProtoChangeDetails()
3616 {
3617     NewObjectHook();
3618     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
3619         JSHClass::Cast(thread_->GlobalConstants()->GetProtoChangeDetailsClass().GetTaggedObject()));
3620     JSHandle<ProtoChangeDetails> protoInfo(thread_, header);
3621     protoInfo->SetChangeListener<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3622     protoInfo->SetRegisterIndex(ProtoChangeDetails::UNREGISTERED);
3623     return protoInfo;
3624 }
3625 
NewProfileTypeInfo(uint32_t icSlotSize)3626 JSHandle<ProfileTypeInfo> ObjectFactory::NewProfileTypeInfo(uint32_t icSlotSize)
3627 {
3628     NewObjectHook();
3629     size_t size = ProfileTypeInfo::ComputeSize(icSlotSize);
3630     auto header = heap_->AllocateYoungOrHugeObject(
3631         JSHClass::Cast(thread_->GlobalConstants()->GetProfileTypeInfoClass().GetTaggedObject()), size);
3632     JSHandle<ProfileTypeInfo> array(thread_, header);
3633     array->InitializeWithSpecialValue(JSTaggedValue::Undefined(), icSlotSize);
3634     if (vm_->IsEnableFastJit()) {
3635         uint16_t threshold = vm_->GetJSOptions().GetJitHotnessThreshold();
3636         ASSERT(threshold != ProfileTypeInfo::JIT_DISABLE_FLAG);
3637         array->SetJitHotnessThreshold(threshold);
3638         threshold = vm_->GetJSOptions().GetOsrHotnessThreshold();
3639         array->SetOsrHotnessThreshold(threshold);
3640         uint16_t jitCallThreshold = vm_->GetJSOptions().GetJitCallThreshold();
3641         array->SetJitCallThreshold(jitCallThreshold);
3642     }
3643     if (vm_->IsEnableBaselineJit()) {
3644         uint16_t threshold = vm_->GetJSOptions().GetBaselineJitHotnessThreshold();
3645         array->SetBaselineJitHotnessThreshold(threshold);
3646     }
3647     return array;
3648 }
3649 
3650 // static
NewObjectHook() const3651 void ObjectFactory::NewObjectHook() const
3652 {
3653     CHECK_NO_HEAP_ALLOC;
3654 #ifndef NDEBUG
3655     if (vm_->GetJSOptions().EnableForceGC() && vm_->IsInitialized() &&
3656         !thread_->InGlobalEnvInitialize() && Runtime::GetInstance()->SharedConstInited() &&
3657         !heap_->InSensitiveStatus() && heap_->TriggerCollectionOnNewObjectEnabled()) {
3658         if (vm_->GetJSOptions().ForceFullGC()) {
3659             if (g_isEnableCMCGC) {
3660                 common::BaseRuntime::RequestGC(common::GC_REASON_USER, true, common::GC_TYPE_FULL);
3661             } else {
3662                 vm_->CollectGarbage(TriggerGCType::YOUNG_GC);
3663                 vm_->CollectGarbage(TriggerGCType::OLD_GC);
3664                 vm_->CollectGarbage(TriggerGCType::FULL_GC);
3665             }
3666         } else {
3667             vm_->CollectGarbage(TriggerGCType::YOUNG_GC);
3668             vm_->CollectGarbage(TriggerGCType::OLD_GC);
3669         }
3670     }
3671 #endif
3672 }
3673 
NewTaggedQueue(uint32_t length)3674 JSHandle<TaggedQueue> ObjectFactory::NewTaggedQueue(uint32_t length)
3675 {
3676     uint32_t queueLength = TaggedQueue::QueueToArrayIndex(length);
3677     auto queue = JSHandle<TaggedQueue>::Cast(NewTaggedArray(queueLength, JSTaggedValue::Hole()));
3678     queue->SetStart(thread_, JSTaggedValue(0));  // equal to 0 when add 1.
3679     queue->SetEnd(thread_, JSTaggedValue(0));
3680     queue->SetCapacity(thread_, JSTaggedValue(length));
3681 
3682     return queue;
3683 }
3684 
GetEmptyTaggedQueue() const3685 JSHandle<TaggedQueue> ObjectFactory::GetEmptyTaggedQueue() const
3686 {
3687     return JSHandle<TaggedQueue>(thread_->GlobalConstants()->GetHandledEmptyTaggedQueue());
3688 }
3689 
NewJSSetIterator(const JSHandle<JSSharedSet> & set,IterationKind kind)3690 JSHandle<JSSharedSetIterator> ObjectFactory::NewJSSetIterator(const JSHandle<JSSharedSet> &set, IterationKind kind)
3691 {
3692     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3693     JSHandle<JSTaggedValue> protoValue = env->GetSharedSetIteratorPrototype();
3694     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3695     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSSharedSetIteratorClass());
3696     hclassHandle->SetPrototype(thread_, protoValue);
3697     JSHandle<JSSharedSetIterator> iter(NewJSObject(hclassHandle));
3698     iter->GetJSHClass()->SetExtensible(true);
3699     iter->SetIteratedSet(thread_, set.GetTaggedValue());
3700     iter->SetNextIndex(0);
3701     iter->SetIterationKind(kind);
3702     ASSERT(iter.GetTaggedValue().IsJSSharedSetIterator());
3703     return iter;
3704 }
3705 
NewJSSetIterator(const JSHandle<JSSet> & set,IterationKind kind)3706 JSHandle<JSSetIterator> ObjectFactory::NewJSSetIterator(const JSHandle<JSSet> &set, IterationKind kind)
3707 {
3708     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3709     JSHandle<JSTaggedValue> protoValue = env->GetSetIteratorPrototype();
3710     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3711     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSSetIteratorClass());
3712     hclassHandle->SetPrototype(thread_, protoValue);
3713     JSHandle<JSSetIterator> iter(NewJSObject(hclassHandle));
3714     iter->GetJSHClass()->SetExtensible(true);
3715     iter->SetIteratedSet(thread_, set->GetLinkedSet(thread_));
3716     iter->SetNextIndex(0);
3717     iter->SetIterationKind(kind);
3718     return iter;
3719 }
3720 
NewJSRegExpIterator(const JSHandle<JSTaggedValue> & matcher,const JSHandle<EcmaString> & inputStr,bool global,bool fullUnicode)3721 JSHandle<JSRegExpIterator> ObjectFactory::NewJSRegExpIterator(const JSHandle<JSTaggedValue> &matcher,
3722                                                               const JSHandle<EcmaString> &inputStr, bool global,
3723                                                               bool fullUnicode)
3724 {
3725     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3726     JSHandle<JSTaggedValue> protoValue = env->GetRegExpIteratorPrototype();
3727     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3728     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSRegExpIteratorClass());
3729     hclassHandle->SetPrototype(thread_, protoValue);
3730     JSHandle<JSRegExpIterator> iter(NewJSObject(hclassHandle));
3731     iter->GetJSHClass()->SetExtensible(true);
3732     iter->SetIteratingRegExp(thread_, matcher.GetTaggedValue());
3733     iter->SetIteratedString(thread_, inputStr.GetTaggedValue());
3734     iter->SetGlobal(global);
3735     iter->SetUnicode(fullUnicode);
3736     iter->SetDone(false);
3737     return iter;
3738 }
3739 
NewJSMapIterator(const JSHandle<JSMap> & map,IterationKind kind)3740 JSHandle<JSMapIterator> ObjectFactory::NewJSMapIterator(const JSHandle<JSMap> &map, IterationKind kind)
3741 {
3742     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3743     JSHandle<JSTaggedValue> protoValue = env->GetMapIteratorPrototype();
3744     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3745     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSMapIteratorClass());
3746     hclassHandle->SetPrototype(thread_, protoValue);
3747     JSHandle<JSMapIterator> iter(NewJSObject(hclassHandle));
3748     iter->GetJSHClass()->SetExtensible(true);
3749     iter->SetIteratedMap(thread_, map->GetLinkedMap(thread_));
3750     iter->SetNextIndex(0);
3751     iter->SetIterationKind(kind);
3752     return iter;
3753 }
3754 
NewJSMapIterator(const JSHandle<JSSharedMap> & map,IterationKind kind)3755 JSHandle<JSSharedMapIterator> ObjectFactory::NewJSMapIterator(const JSHandle<JSSharedMap> &map, IterationKind kind)
3756 {
3757     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3758     JSHandle<JSTaggedValue> protoValue = env->GetSharedMapIteratorPrototype();
3759     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3760     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSSharedMapIteratorClass());
3761     hclassHandle->SetPrototype(thread_, protoValue);
3762     JSHandle<JSSharedMapIterator> iter(NewJSObject(hclassHandle));
3763     iter->GetJSHClass()->SetExtensible(true);
3764     iter->SetIteratedMap(thread_, map.GetTaggedValue());
3765     iter->SetNextIndex(0);
3766     iter->SetIterationKind(kind);
3767     ASSERT(iter.GetTaggedValue().IsJSSharedMapIterator());
3768     return iter;
3769 }
3770 
NewJSAPIHashMapIterator(const JSHandle<JSAPIHashMap> & hashMap,IterationKind kind)3771 JSHandle<JSAPIHashMapIterator> ObjectFactory::NewJSAPIHashMapIterator(const JSHandle<JSAPIHashMap> &hashMap,
3772                                                                       IterationKind kind)
3773 {
3774     NewObjectHook();
3775     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3776     JSHandle<JSTaggedValue> holeHandle = globalConst->GetHandledHole();
3777     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
3778     JSHandle<JSTaggedValue> proto(env->GetHashMapIteratorPrototype());
3779     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIHashMapIteratorClass());
3780     hclassHandle->SetPrototype(thread_, proto);
3781     JSHandle<JSAPIHashMapIterator> iter(NewJSObject(hclassHandle));
3782     iter->GetJSHClass()->SetExtensible(true);
3783     iter->SetCurrentNodeResult(thread_, holeHandle);
3784     iter->SetIteratedHashMap(thread_, hashMap);
3785     iter->SetNextIndex(0);
3786     iter->SetTaggedQueue<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3787     JSHandle<TaggedQueue> queue = NewTaggedQueue(0);
3788     iter->SetTaggedQueue(thread_, queue);
3789     iter->SetIterationKind(kind);
3790     return iter;
3791 }
3792 
NewJSAPIHashSetIterator(const JSHandle<JSAPIHashSet> & hashSet,IterationKind kind)3793 JSHandle<JSAPIHashSetIterator> ObjectFactory::NewJSAPIHashSetIterator(const JSHandle<JSAPIHashSet> &hashSet,
3794                                                                       IterationKind kind)
3795 {
3796     NewObjectHook();
3797     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3798     JSHandle<JSTaggedValue> holeHandle = globalConst->GetHandledHole();
3799     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
3800     JSHandle<JSTaggedValue> proto = env->GetHashSetIteratorPrototype();
3801     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIHashSetIteratorClass());
3802     hclassHandle->SetPrototype(thread_, proto);
3803     JSHandle<JSAPIHashSetIterator> iter(NewJSObject(hclassHandle));
3804     iter->GetJSHClass()->SetExtensible(true);
3805     iter->SetCurrentNodeResult(thread_, holeHandle);
3806     iter->SetIteratedHashSet(thread_, hashSet);
3807     iter->SetNextIndex(0);
3808     iter->SetTaggedQueue<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3809     JSHandle<TaggedQueue> queue = NewTaggedQueue(0);
3810     iter->SetTaggedQueue(thread_, queue);
3811     iter->SetIterationKind(kind);
3812     return iter;
3813 }
3814 
NewJSArrayIterator(const JSHandle<JSObject> & array,IterationKind kind)3815 JSHandle<JSArrayIterator> ObjectFactory::NewJSArrayIterator(const JSHandle<JSObject> &array, IterationKind kind)
3816 {
3817     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3818     JSHandle<JSTaggedValue> protoValue = env->GetArrayIteratorPrototype();
3819     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3820     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSArrayIteratorClass());
3821     hclassHandle->SetPrototype(thread_, protoValue);
3822     JSHandle<JSArrayIterator> iter(NewJSObject(hclassHandle));
3823     iter->GetJSHClass()->SetExtensible(true);
3824     iter->SetIteratedArray(thread_, array);
3825     iter->SetNextIndex(0);
3826     iter->SetIterationKind(kind);
3827     return iter;
3828 }
3829 
NewJSSharedArrayIterator(const JSHandle<JSObject> & array,IterationKind kind)3830 JSHandle<JSSharedArrayIterator> ObjectFactory::NewJSSharedArrayIterator(const JSHandle<JSObject> &array,
3831                                                                         IterationKind kind)
3832 {
3833     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3834     JSHandle<JSTaggedValue> protoValue = env->GetSharedArrayIteratorPrototype();
3835     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
3836     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSSharedArrayIteratorClass());
3837     hclassHandle->SetPrototype(thread_, protoValue);
3838     JSHandle<JSSharedArrayIterator> iter(NewJSObject(hclassHandle));
3839     iter->GetJSHClass()->SetExtensible(true);
3840     iter->SetIteratedArray(thread_, array);
3841     iter->SetNextIndex(0);
3842     iter->SetIterationKind(kind);
3843     return iter;
3844 }
3845 
CreateJSPromiseReactionsFunction(MethodIndex idx)3846 JSHandle<JSPromiseReactionsFunction> ObjectFactory::CreateJSPromiseReactionsFunction(MethodIndex idx)
3847 {
3848     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3849     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseReactionFunctionClass());
3850 
3851     JSHandle<JSPromiseReactionsFunction> reactionsFunction =
3852         JSHandle<JSPromiseReactionsFunction>::Cast(NewJSObject(hclass));
3853     reactionsFunction->SetPromise<SKIP_BARRIER>(thread_, JSTaggedValue::Hole());
3854     reactionsFunction->SetAlreadyResolved<SKIP_BARRIER>(thread_, JSTaggedValue::Hole());
3855     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(reactionsFunction);
3856     JSFunction::InitializeJSBuiltinFunction(thread_, env, function);
3857     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(idx));
3858     reactionsFunction->SetMethod(thread_, method);
3859     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(reactionsFunction), method);
3860     JSFunction::SetFunctionLength(thread_, function, JSTaggedValue(1));
3861     return reactionsFunction;
3862 }
3863 
CreateJSPromiseExecutorFunction()3864 JSHandle<JSPromiseExecutorFunction> ObjectFactory::CreateJSPromiseExecutorFunction()
3865 {
3866     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3867     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseExecutorFunctionClass());
3868     JSHandle<JSPromiseExecutorFunction> executorFunction =
3869         JSHandle<JSPromiseExecutorFunction>::Cast(NewJSObject(hclass));
3870     executorFunction->SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3871     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(executorFunction);
3872     JSFunction::InitializeJSBuiltinFunction(thread_, env, function);
3873     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_EXECUTOR));
3874     executorFunction->SetMethod(thread_, method);
3875     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(executorFunction), method);
3876     JSFunction::SetFunctionLength(thread_, function, JSTaggedValue(FunctionLength::TWO));
3877     return executorFunction;
3878 }
3879 
CreateJSAsyncModuleFulfilledFunction()3880 JSHandle<JSAsyncModuleFulfilledFunction> ObjectFactory::CreateJSAsyncModuleFulfilledFunction()
3881 {
3882     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3883     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetAsyncModuleFulfilledFunctionClass());
3884     JSHandle<JSAsyncModuleFulfilledFunction> fulfilledFunction =
3885         JSHandle<JSAsyncModuleFulfilledFunction>::Cast(NewJSObject(hclass));
3886     fulfilledFunction->SetModule<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3887     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(fulfilledFunction);
3888     JSFunction::InitializeJSBuiltinFunction(thread_, env, function);
3889     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_ASYNC_MODULE_FULFILLED_FUNCTION));
3890     fulfilledFunction->SetMethod(thread_, method);
3891     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(fulfilledFunction), method);
3892     JSFunction::SetFunctionLength(thread_, function, JSTaggedValue(FunctionLength::ONE));
3893     return fulfilledFunction;
3894 }
3895 
CreateJSAsyncModuleRejectedFunction()3896 JSHandle<JSAsyncModuleRejectedFunction> ObjectFactory::CreateJSAsyncModuleRejectedFunction()
3897 {
3898     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3899     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetAsyncModuleRejectedFunctionClass());
3900     JSHandle<JSAsyncModuleRejectedFunction> rejectedFunction =
3901         JSHandle<JSAsyncModuleRejectedFunction>::Cast(NewJSObject(hclass));
3902     rejectedFunction->SetModule<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3903     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(rejectedFunction);
3904     JSFunction::InitializeJSBuiltinFunction(thread_, env, function);
3905     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_ASYNC_MODULE_REJECTED_FUNCTION));
3906     rejectedFunction->SetMethod(thread_, method);
3907     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(rejectedFunction), method);
3908     JSFunction::SetFunctionLength(thread_, function, JSTaggedValue(FunctionLength::ONE));
3909     return rejectedFunction;
3910 }
3911 
NewJSPromiseAllResolveElementFunction()3912 JSHandle<JSPromiseAllResolveElementFunction> ObjectFactory::NewJSPromiseAllResolveElementFunction()
3913 {
3914     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3915     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseAllResolveElementFunctionClass());
3916     JSHandle<JSPromiseAllResolveElementFunction> function =
3917         JSHandle<JSPromiseAllResolveElementFunction>::Cast(NewJSObject(hclass));
3918     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
3919     JSHandle<Method> method(thread_,
3920                             vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_RESOLVE_ELEMENT_FUNCTION));
3921     function->SetMethod(thread_, method);
3922     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
3923     function->SetIndex<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3924     function->SetValues<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3925     function->SetCapabilities<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3926     function->SetRemainingElements<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3927     function->SetAlreadyCalled<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3928     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
3929     return function;
3930 }
3931 
NewJSPromiseAnyRejectElementFunction()3932 JSHandle<JSPromiseAnyRejectElementFunction> ObjectFactory::NewJSPromiseAnyRejectElementFunction()
3933 {
3934     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3935     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseAnyRejectElementFunctionClass());
3936     JSHandle<JSPromiseAnyRejectElementFunction> function =
3937         JSHandle<JSPromiseAnyRejectElementFunction>::Cast(NewJSObject(hclass));
3938     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
3939     JSHandle<Method> method(thread_,
3940                             vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_ANY_REJECT_ELEMENT_FUNCTION));
3941     function->SetMethod(thread_, method);
3942     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
3943     function->SetIndex(0);
3944     function->SetErrors<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3945     function->SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3946     function->SetRemainingElements<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3947     function->SetAlreadyCalled<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3948     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
3949     return function;
3950 }
3951 
NewJSPromiseAllSettledResolveElementFunction()3952 JSHandle<JSPromiseAllSettledElementFunction> ObjectFactory::NewJSPromiseAllSettledResolveElementFunction()
3953 {
3954     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3955     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseAllSettledElementFunctionClass());
3956     JSHandle<JSPromiseAllSettledElementFunction> function =
3957         JSHandle<JSPromiseAllSettledElementFunction>::Cast(NewJSObject(hclass));
3958     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
3959     JSHandle<Method> method(thread_,
3960         vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_ALL_SETTLED_RESOLVE_ELEMENT_FUNCTION));
3961     function->SetMethod(thread_, method);
3962     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
3963     function->SetIndex(0);
3964     function->SetValues<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3965     function->SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3966     function->SetRemainingElements<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3967     function->SetAlreadyCalled<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3968     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
3969     return function;
3970 }
3971 
NewJSPromiseAllSettledRejectElementFunction()3972 JSHandle<JSPromiseAllSettledElementFunction> ObjectFactory::NewJSPromiseAllSettledRejectElementFunction()
3973 {
3974     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3975     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseAllSettledElementFunctionClass());
3976     JSHandle<JSPromiseAllSettledElementFunction> function =
3977         JSHandle<JSPromiseAllSettledElementFunction>::Cast(NewJSObject(hclass));
3978     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
3979     JSHandle<Method> method(thread_,
3980         vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_ALL_SETTLED_REJECT_ELEMENT_FUNCTION));
3981     function->SetMethod(thread_, method);
3982     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
3983     function->SetIndex(0);
3984     function->SetValues<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3985     function->SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3986     function->SetRemainingElements<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3987     function->SetAlreadyCalled<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
3988     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
3989     return function;
3990 }
3991 
NewJSPromiseThenFinallyFunction()3992 JSHandle<JSPromiseFinallyFunction> ObjectFactory::NewJSPromiseThenFinallyFunction()
3993 {
3994     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
3995     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseFinallyFunctionClass());
3996     JSHandle<JSPromiseFinallyFunction> function =
3997         JSHandle<JSPromiseFinallyFunction>::Cast(NewJSObject(hclass));
3998     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
3999     JSHandle<Method> method(thread_,
4000                             vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_THEN_FINALLY_FUNCTION));
4001     function->SetMethod(thread_, method);
4002     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
4003     function->SetConstructor<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4004     function->SetOnFinally<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4005     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
4006     return function;
4007 }
4008 
NewJSPromiseCatchFinallyFunction()4009 JSHandle<JSPromiseFinallyFunction> ObjectFactory::NewJSPromiseCatchFinallyFunction()
4010 {
4011     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4012     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseFinallyFunctionClass());
4013     JSHandle<JSPromiseFinallyFunction> function =
4014         JSHandle<JSPromiseFinallyFunction>::Cast(NewJSObject(hclass));
4015     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
4016     JSHandle<Method> method(thread_,
4017                             vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_CATCH_FINALLY_FUNCTION));
4018     function->SetMethod(thread_, method);
4019     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
4020     function->SetConstructor<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4021     function->SetOnFinally<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4022     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
4023     return function;
4024 }
4025 
NewJSAsyGenResNextRetProRstFulfilledFtn()4026 JSHandle<JSAsyncGeneratorResNextRetProRstFtn> ObjectFactory::NewJSAsyGenResNextRetProRstFulfilledFtn()
4027 {
4028     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4029     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(
4030         env->GetAsyncGeneratorResNextRetProRstFtnClass());
4031     JSHandle<JSAsyncGeneratorResNextRetProRstFtn> function =
4032         JSHandle<JSAsyncGeneratorResNextRetProRstFtn>::Cast(NewJSObject(hclass));
4033     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
4034     JSHandle<Method> method(thread_,
4035                             vm_->GetMethodByIndex(MethodIndex::BUILTINS_ASYNC_GENERATOR_NEXT_FULFILLED_FUNCTION));
4036     function->SetMethod(thread_, method);
4037     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
4038     function->SetAsyncGeneratorObject<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4039     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
4040     return function;
4041 }
4042 
NewJSAsyncFromSyncIterUnwarpFunction()4043 JSHandle<JSAsyncFromSyncIterUnwarpFunction> ObjectFactory::NewJSAsyncFromSyncIterUnwarpFunction()
4044 {
4045     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4046     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetAsyncFromSyncIterUnwarpClass());
4047     JSHandle<JSAsyncFromSyncIterUnwarpFunction> function =
4048         JSHandle<JSAsyncFromSyncIterUnwarpFunction>::Cast(NewJSObject(hclass));
4049     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
4050     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_ASYNC_FROM_SYNC_ITERATOR_FUNCTION));
4051     function->SetMethod(thread_, method);
4052     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
4053     function->SetDone<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4054     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
4055     return function;
4056 }
4057 
NewJSAsyGenResNextRetProRstRejectedFtn()4058 JSHandle<JSAsyncGeneratorResNextRetProRstFtn> ObjectFactory::NewJSAsyGenResNextRetProRstRejectedFtn()
4059 {
4060     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4061     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(
4062         env->GetAsyncGeneratorResNextRetProRstFtnClass());
4063     JSHandle<JSAsyncGeneratorResNextRetProRstFtn> function =
4064         JSHandle<JSAsyncGeneratorResNextRetProRstFtn>::Cast(NewJSObject(hclass));
4065     JSFunction::InitializeJSFunction(thread_, JSHandle<JSFunction>::Cast(function));
4066     JSHandle<Method> method(thread_,
4067                             vm_->GetMethodByIndex(MethodIndex::BUILTINS_ASYNC_GENERATOR_NEXT_REJECTED_FUNCTION));
4068     function->SetMethod(thread_, method);
4069     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
4070     function->SetAsyncGeneratorObject<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4071     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(1));
4072     return function;
4073 }
4074 
NewJSPromiseValueThunkFunction()4075 JSHandle<JSPromiseValueThunkOrThrowerFunction> ObjectFactory::NewJSPromiseValueThunkFunction()
4076 {
4077     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4078     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseValueThunkOrThrowerFunctionClass());
4079     JSHandle<JSPromiseValueThunkOrThrowerFunction> function =
4080         JSHandle<JSPromiseValueThunkOrThrowerFunction>::Cast(NewJSObject(hclass));
4081     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
4082     JSHandle<Method> method(thread_,
4083                             vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_VALUE_THUNK_FUNCTION));
4084     function->SetMethod(thread_, method);
4085     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
4086     function->SetResult<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4087     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(0));
4088     return function;
4089 }
4090 
NewJSPromiseThrowerFunction()4091 JSHandle<JSPromiseValueThunkOrThrowerFunction> ObjectFactory::NewJSPromiseThrowerFunction()
4092 {
4093     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4094     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetPromiseValueThunkOrThrowerFunctionClass());
4095     JSHandle<JSPromiseValueThunkOrThrowerFunction> function =
4096         JSHandle<JSPromiseValueThunkOrThrowerFunction>::Cast(NewJSObject(hclass));
4097     JSFunction::InitializeJSBuiltinFunction(thread_, env, JSHandle<JSFunction>::Cast(function));
4098     JSHandle<Method> method(thread_, vm_->GetMethodByIndex(MethodIndex::BUILTINS_PROMISE_HANDLER_THROWER_FUNCTION));
4099     function->SetMethod(thread_, method);
4100     SetNativePointerToFunctionFromMethod(JSHandle<JSFunctionBase>::Cast(function), method);
4101     function->SetResult<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4102     JSFunction::SetFunctionLength(thread_, JSHandle<JSFunction>::Cast(function), JSTaggedValue(0));
4103     return function;
4104 }
4105 
InternString(const JSHandle<JSTaggedValue> & key)4106 EcmaString *ObjectFactory::InternString(const JSHandle<JSTaggedValue> &key)
4107 {
4108     EcmaString *str = EcmaString::Cast(key->GetTaggedObject());
4109     if (EcmaStringAccessor(str).IsInternString()) {
4110         return str;
4111     }
4112 
4113     EcmaStringTable *stringTable = vm_->GetEcmaStringTable();
4114     return stringTable->GetOrInternString(vm_, str);
4115 }
4116 
NewTransitionHandler()4117 JSHandle<TransitionHandler> ObjectFactory::NewTransitionHandler()
4118 {
4119     NewObjectHook();
4120     TransitionHandler *handler = TransitionHandler::Cast(heap_->AllocateYoungOrHugeObject(
4121         JSHClass::Cast(thread_->GlobalConstants()->GetTransitionHandlerClass().GetTaggedObject())));
4122     handler->SetHandlerInfo<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4123     handler->SetTransitionHClass<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4124     return JSHandle<TransitionHandler>(thread_, handler);
4125 }
4126 
NewPrototypeHandler()4127 JSHandle<PrototypeHandler> ObjectFactory::NewPrototypeHandler()
4128 {
4129     NewObjectHook();
4130     PrototypeHandler *header =
4131         PrototypeHandler::Cast(heap_->AllocateYoungOrHugeObject(
4132             JSHClass::Cast(thread_->GlobalConstants()->GetPrototypeHandlerClass().GetTaggedObject())));
4133     JSHandle<PrototypeHandler> handler(thread_, header);
4134     handler->SetHandlerInfo<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4135     handler->SetProtoCell<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4136     handler->SetHolder<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4137     handler->SetAccessorJSFunction<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4138     handler->SetAccessorMethodId(0);
4139     return handler;
4140 }
4141 
NewTransWithProtoHandler()4142 JSHandle<TransWithProtoHandler> ObjectFactory::NewTransWithProtoHandler()
4143 {
4144     NewObjectHook();
4145     TransWithProtoHandler *header =
4146         TransWithProtoHandler::Cast(heap_->AllocateYoungOrHugeObject(
4147             JSHClass::Cast(thread_->GlobalConstants()->GetTransWithProtoHandlerClass().GetTaggedObject())));
4148     JSHandle<TransWithProtoHandler> handler(thread_, header);
4149     handler->SetHandlerInfo<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4150     handler->SetProtoCell<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4151     handler->SetTransitionHClass<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4152     return handler;
4153 }
4154 
NewStoreAOTHandler()4155 JSHandle<StoreAOTHandler> ObjectFactory::NewStoreAOTHandler()
4156 {
4157     NewObjectHook();
4158     StoreAOTHandler *header =
4159         StoreAOTHandler::Cast(heap_->AllocateYoungOrHugeObject(
4160             JSHClass::Cast(thread_->GlobalConstants()->GetStoreAOTHandlerClass().GetTaggedObject())));
4161     JSHandle<StoreAOTHandler> handler(thread_, header);
4162     handler->SetHandlerInfo<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4163     handler->SetProtoCell<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4164     handler->SetHolder<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4165     return handler;
4166 }
4167 
NewPromiseRecord()4168 JSHandle<PromiseRecord> ObjectFactory::NewPromiseRecord()
4169 {
4170     NewObjectHook();
4171     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
4172         JSHClass::Cast(thread_->GlobalConstants()->GetPromiseRecordClass().GetTaggedObject()));
4173     JSHandle<PromiseRecord> obj(thread_, header);
4174     obj->SetValue<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4175     return obj;
4176 }
4177 
NewResolvingFunctionsRecord()4178 JSHandle<ResolvingFunctionsRecord> ObjectFactory::NewResolvingFunctionsRecord()
4179 {
4180     NewObjectHook();
4181     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
4182         JSHClass::Cast(thread_->GlobalConstants()->GetPromiseResolvingFunctionsRecordClass().GetTaggedObject()));
4183     JSHandle<ResolvingFunctionsRecord> obj(thread_, header);
4184     obj->SetResolveFunction<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4185     obj->SetRejectFunction<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
4186     return obj;
4187 }
4188 
CreateObjectClass(const JSHandle<GlobalEnv> & env,const JSHandle<TaggedArray> & properties,size_t length)4189 JSHandle<JSHClass> ObjectFactory::CreateObjectClass(const JSHandle<GlobalEnv> &env,
4190                                                     const JSHandle<TaggedArray> &properties, size_t length)
4191 {
4192     JSHandle<JSTaggedValue> proto = env->GetObjectFunctionPrototype();
4193 
4194     uint32_t fieldOrder = 0;
4195     JSMutableHandle<JSTaggedValue> key(thread_, JSTaggedValue::Undefined());
4196     JSHandle<LayoutInfo> layoutInfoHandle = CreateLayoutInfo(length);
4197     while (fieldOrder < length) {
4198         key.Update(properties->Get(thread_, fieldOrder * 2));  // 2: Meaning to double
4199         ASSERT_PRINT(JSTaggedValue::IsPropertyKey(key), "Key is not a property key");
4200         PropertyAttributes attributes = PropertyAttributes::Default();
4201 
4202         if (properties->Get(thread_, fieldOrder * 2 + 1).IsAccessor()) {  // 2: Meaning to double
4203             attributes.SetIsAccessor(true);
4204         }
4205 
4206         attributes.SetIsInlinedProps(true);
4207         attributes.SetRepresentation(Representation::TAGGED);
4208         attributes.SetOffset(fieldOrder);
4209         layoutInfoHandle->AddKey(thread_, fieldOrder, key.GetTaggedValue(), attributes);
4210         fieldOrder++;
4211     }
4212     ASSERT(fieldOrder <= PropertyAttributes::MAX_FAST_PROPS_CAPACITY);
4213     JSHandle<JSHClass> objClass = NewEcmaHClass(JSObject::SIZE, JSType::JS_OBJECT, fieldOrder);
4214     objClass->SetPrototype(thread_, proto.GetTaggedValue());
4215     {
4216         objClass->SetExtensible(true);
4217         objClass->SetLayout(thread_, layoutInfoHandle);
4218         objClass->SetNumberOfProps(fieldOrder);
4219     }
4220     return objClass;
4221 }
4222 
SetLayoutInObjHClass(const JSHandle<TaggedArray> & properties,size_t length,const JSHandle<JSHClass> & objClass)4223 JSHandle<JSHClass> ObjectFactory::SetLayoutInObjHClass(const JSHandle<TaggedArray> &properties, size_t length,
4224                                                        const JSHandle<JSHClass> &objClass)
4225 {
4226     JSMutableHandle<JSTaggedValue> key(thread_, JSTaggedValue::Undefined());
4227     JSHandle<JSHClass> newObjHClass(objClass);
4228 
4229     for (size_t fieldOffset = 0; fieldOffset < length; fieldOffset++) {
4230         key.Update(properties->Get(thread_, fieldOffset * 2)); // 2 : pair of key and value
4231         ASSERT_PRINT(JSTaggedValue::IsPropertyKey(key), "Key is not a property key");
4232         PropertyAttributes attributes = PropertyAttributes::Default();
4233         auto value = properties->Get(thread_, fieldOffset * 2 + 1);
4234         if (value.IsAccessor()) {  // 2: Meaning to double
4235             attributes.SetIsAccessor(true);
4236         }
4237         attributes.SetIsInlinedProps(true);
4238         attributes.SetRepresentation(Representation::TAGGED);
4239         attributes.SetOffset(fieldOffset);
4240         attributes.SetRepresentation(Representation::TAGGED);
4241         auto rep = PropertyAttributes::TranslateToRep(value);
4242         newObjHClass = JSHClass::SetPropertyOfObjHClass(thread_, newObjHClass, key, attributes, rep);
4243     }
4244     return newObjHClass;
4245 }
4246 
CanObjectLiteralHClassCache(size_t length)4247 bool ObjectFactory::CanObjectLiteralHClassCache(size_t length)
4248 {
4249     return length <= PropertyAttributes::MAX_LITERAL_HCLASS_CACHE_SIZE;
4250 }
4251 
CreateObjectLiteralRootHClass(size_t length)4252 JSHandle<JSHClass> ObjectFactory::CreateObjectLiteralRootHClass(size_t length)
4253 {
4254     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4255     JSHandle<JSTaggedValue> proto = env->GetObjectFunctionPrototype();
4256     JSHandle<JSHClass> hclass = NewEcmaHClass(JSObject::SIZE, JSType::JS_OBJECT, length);
4257     hclass->SetPrototype(thread_, proto.GetTaggedValue());
4258     {
4259         hclass->SetNumberOfProps(0);
4260         hclass->SetExtensible(true);
4261     }
4262     return hclass;
4263 }
4264 
GetObjectLiteralRootHClass(size_t literalLength,size_t maxPropsNum)4265 JSHandle<JSHClass> ObjectFactory::GetObjectLiteralRootHClass(size_t literalLength, size_t maxPropsNum)
4266 {
4267     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4268     JSHandle<JSTaggedValue> maybeCache = env->GetObjectLiteralHClassCache();
4269     if (UNLIKELY(maybeCache->IsHole())) {
4270         JSHandle<TaggedArray> cacheArr = NewTaggedArray(PropertyAttributes::MAX_LITERAL_HCLASS_CACHE_SIZE + 1);
4271         env->SetObjectLiteralHClassCache(thread_, cacheArr.GetTaggedValue());
4272         JSHandle<JSHClass> objHClass = CreateObjectLiteralRootHClass(maxPropsNum);
4273         cacheArr->Set(thread_, literalLength, objHClass);
4274         return objHClass;
4275     }
4276     JSHandle<TaggedArray> hclassCacheArr = JSHandle<TaggedArray>::Cast(maybeCache);
4277     JSTaggedValue maybeHClass = hclassCacheArr->Get(thread_, literalLength);
4278     if (UNLIKELY(maybeHClass.IsHole())) {
4279         JSHandle<JSHClass> objHClass = CreateObjectLiteralRootHClass(maxPropsNum);
4280         hclassCacheArr->Set(thread_, literalLength, objHClass);
4281         return objHClass;
4282     }
4283     return JSHandle<JSHClass>(thread_, maybeHClass);
4284 }
4285 
GetObjectLiteralHClass(const JSHandle<TaggedArray> & properties,size_t length)4286 JSHandle<JSHClass> ObjectFactory::GetObjectLiteralHClass(const JSHandle<TaggedArray> &properties, size_t length)
4287 {
4288     ASSERT(length <= PropertyAttributes::MAX_FAST_PROPS_CAPACITY);
4289     // 64 : If object literal gets too many properties, create hclass directly.
4290     if (!CanObjectLiteralHClassCache(length)) {
4291         JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4292         return CreateObjectClass(env, properties, length);
4293     }
4294     JSHandle<JSHClass> rootHClass = GetObjectLiteralRootHClass(length, length);
4295     return SetLayoutInObjHClass(properties, length, rootHClass);
4296 }
4297 
NewOldSpaceObjLiteralByHClass(const JSHandle<JSHClass> & hclass)4298 JSHandle<JSObject> ObjectFactory::NewOldSpaceObjLiteralByHClass(const JSHandle<JSHClass> &hclass)
4299 {
4300     JSHandle<JSObject> obj = NewOldSpaceJSObject(hclass);
4301     InitializeJSObject(obj, hclass);
4302     return obj;
4303 }
4304 
NewEmptyJSObject(uint32_t inlinedProps)4305 JSHandle<JSObject> ObjectFactory::NewEmptyJSObject(uint32_t inlinedProps)
4306 {
4307     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
4308     JSHandle<JSFunction> builtinObj(env->GetObjectFunction());
4309     return NewJSObjectByConstructor(builtinObj, inlinedProps);
4310 }
4311 
NewEmptyJSObject(const JSHandle<GlobalEnv> & env,uint32_t inlinedProps)4312 JSHandle<JSObject> ObjectFactory::NewEmptyJSObject(const JSHandle<GlobalEnv> &env, uint32_t inlinedProps)
4313 {
4314     JSHandle<JSFunction> builtinObj(env->GetObjectFunction());
4315     return NewJSObjectByConstructor(env, builtinObj, inlinedProps);
4316 }
4317 
CreateNullJSObject()4318 JSHandle<JSObject> ObjectFactory::CreateNullJSObject()
4319 {
4320     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4321     JSHandle<JSTaggedValue> nullValue = globalConst->GetHandledNull();
4322     return OrdinaryNewJSObjectCreate(nullValue);
4323 }
4324 
NewSpaceBySnapshotAllocator(size_t size)4325 uintptr_t ObjectFactory::NewSpaceBySnapshotAllocator(size_t size)
4326 {
4327     NewObjectHook();
4328     return heap_->AllocateSnapshotSpace(size);
4329 }
4330 
NewMachineCodeObject(size_t length,MachineCodeDesc & desc)4331 TaggedObject *ObjectFactory::NewMachineCodeObject(size_t length,
4332     MachineCodeDesc &desc)
4333 {
4334     NewObjectHook();
4335     TaggedObject *obj = heap_->AllocateMachineCodeObject(
4336         JSHClass::Cast(thread_->GlobalConstants()->GetMachineCodeClass().GetTaggedObject()),
4337         length + MachineCode::SIZE, &desc);
4338     return (obj);
4339 }
4340 
NewMachineCodeObject(size_t length,const MachineCodeDesc & desc,JSHandle<Method> & method)4341 JSHandle<MachineCode> ObjectFactory::NewMachineCodeObject(size_t length,
4342     const MachineCodeDesc &desc, JSHandle<Method> &method)
4343 {
4344     NewObjectHook();
4345     TaggedObject *obj = heap_->AllocateMachineCodeObject(
4346         JSHClass::Cast(thread_->GlobalConstants()->GetMachineCodeClass().GetTaggedObject()),
4347         length + MachineCode::SIZE);
4348     return SetMachineCodeObjectData(obj, length, desc, method);
4349 }
4350 
SetMachineCodeObjectData(TaggedObject * obj,size_t length,const MachineCodeDesc & desc,JSHandle<Method> & method)4351 JSHandle<MachineCode> ObjectFactory::SetMachineCodeObjectData(TaggedObject *obj, size_t length,
4352     const MachineCodeDesc &desc, JSHandle<Method> &method)
4353 {
4354     MachineCode *code = MachineCode::Cast(obj);
4355     if (code == nullptr) {
4356         LOG_FULL(FATAL) << "machine code cast failed";
4357         UNREACHABLE();
4358     }
4359     if (code->SetData(thread_, desc, method, length)) {
4360         JSHandle<MachineCode> codeObj(thread_, code);
4361         if (g_isEnableCMCGC) {
4362             uintptr_t start = code->GetText();
4363             uintptr_t end = start + code->GetTextSize();
4364             heap_->SetMachineCodeObject(start, end, reinterpret_cast<uintptr_t>(code));
4365         }
4366         return codeObj;
4367     } else {
4368         if (g_isEnableCMCGC) {
4369             uintptr_t start = code->GetText();
4370             uintptr_t end = start + code->GetTextSize();
4371             heap_->SetMachineCodeObject(start, end, reinterpret_cast<uintptr_t>(code));
4372         }
4373         JSHandle<MachineCode> codeObj;
4374         return codeObj;
4375     }
4376 }
4377 
NewClassInfoExtractor(JSHandle<JSTaggedValue> method)4378 JSHandle<ClassInfoExtractor> ObjectFactory::NewClassInfoExtractor(JSHandle<JSTaggedValue> method)
4379 {
4380     NewObjectHook();
4381     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
4382         JSHClass::Cast(thread_->GlobalConstants()->GetClassInfoExtractorHClass().GetTaggedObject()));
4383     JSHandle<ClassInfoExtractor> obj(thread_, header);
4384     obj->ClearBitField();
4385     obj->SetConstructorMethod(thread_, method.GetTaggedValue());
4386     JSHandle<TaggedArray> emptyArray = EmptyArray();
4387     obj->SetNonStaticKeys<SKIP_BARRIER>(thread_, emptyArray);
4388     obj->SetNonStaticProperties<SKIP_BARRIER>(thread_, emptyArray);
4389     obj->SetNonStaticElements<SKIP_BARRIER>(thread_, emptyArray);
4390     obj->SetStaticKeys<SKIP_BARRIER>(thread_, emptyArray);
4391     obj->SetStaticProperties<SKIP_BARRIER>(thread_, emptyArray);
4392     obj->SetStaticElements<SKIP_BARRIER>(thread_, emptyArray);
4393     return obj;
4394 }
4395 
4396 // ----------------------------------- new string ----------------------------------------
NewFromASCII(std::string_view data)4397 JSHandle<EcmaString> ObjectFactory::NewFromASCII(std::string_view data)
4398 {
4399     auto utf8Data = reinterpret_cast<const uint8_t *>(data.data());
4400     ASSERT(EcmaStringAccessor::CanBeCompressed(utf8Data, data.length()));
4401     return GetStringFromStringTable(utf8Data, data.length(), true);
4402 }
4403 
4404 // At this situation, Create string directly without using a StringTable.
NewFromASCIISkippingStringTable(std::string_view data)4405 JSHandle<EcmaString> ObjectFactory::NewFromASCIISkippingStringTable(std::string_view data)
4406 {
4407     auto utf8Data = reinterpret_cast<const uint8_t *>(data.data());
4408     ASSERT(EcmaStringAccessor::CanBeCompressed(utf8Data, data.length()));
4409     EcmaString *str = EcmaStringAccessor::CreateFromUtf8(vm_, utf8Data, data.length(), true);
4410     return JSHandle<EcmaString>(thread_, str);
4411 }
4412 
NewFromASCIIReadOnly(std::string_view data)4413 JSHandle<EcmaString> ObjectFactory::NewFromASCIIReadOnly(std::string_view data)
4414 {
4415     auto utf8Data = reinterpret_cast<const uint8_t *>(data.data());
4416     ASSERT(EcmaStringAccessor::CanBeCompressed(utf8Data, data.length()));
4417     return GetStringFromStringTableReadOnly(utf8Data, data.length());
4418 }
4419 
NewFromUtf8WithoutStringTable(std::string_view data)4420 JSHandle<EcmaString> ObjectFactory::NewFromUtf8WithoutStringTable(std::string_view data)
4421 {
4422     auto utf8Data = reinterpret_cast<const uint8_t *>(data.data());
4423     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf8Data, data.length());
4424     uint32_t utf8Len = data.length();
4425     NewObjectHook();
4426     if (utf8Len == 0) {
4427         return GetEmptyString();
4428     }
4429     EcmaString *str =
4430         EcmaStringAccessor::CreateFromUtf8(vm_, utf8Data, utf8Len, canBeCompress, MemSpaceType::SHARED_OLD_SPACE);
4431     uint32_t hashCode = EcmaStringAccessor::ComputeHashcodeUtf8(utf8Data, utf8Len, canBeCompress);
4432     str->SetMixHashcode(hashCode);
4433     return JSHandle<EcmaString>(thread_, str);
4434 }
4435 
NewFromUtf8(std::string_view data)4436 JSHandle<EcmaString> ObjectFactory::NewFromUtf8(std::string_view data)
4437 {
4438     auto utf8Data = reinterpret_cast<const uint8_t *>(data.data());
4439     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf8Data, data.length());
4440     return GetStringFromStringTable(utf8Data, data.length(), canBeCompress);
4441 }
4442 
NewFromUtf8(std::string_view data,bool canBeCompress)4443 JSHandle<EcmaString> ObjectFactory::NewFromUtf8(std::string_view data, bool canBeCompress)
4444 {
4445     auto utf8Data = reinterpret_cast<const uint8_t *>(data.data());
4446     ASSERT(canBeCompress == EcmaStringAccessor::CanBeCompressed(utf8Data, data.length()));
4447     return GetStringFromStringTable(utf8Data, data.length(), canBeCompress);
4448 }
4449 
NewFromUtf8ReadOnly(std::string_view data)4450 JSHandle<EcmaString> ObjectFactory::NewFromUtf8ReadOnly(std::string_view data)
4451 {
4452     auto utf8Data = reinterpret_cast<const uint8_t *>(data.data());
4453     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf8Data, data.length());
4454     return GetStringFromStringTableReadOnly(utf8Data, data.length(), canBeCompress);
4455 }
4456 
NewFromUtf16WithoutStringTable(std::u16string_view data)4457 JSHandle<EcmaString> ObjectFactory::NewFromUtf16WithoutStringTable(std::u16string_view data)
4458 {
4459     uint32_t utf16Len = data.length();
4460     auto utf16Data = reinterpret_cast<const uint16_t *>(data.data());
4461     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len);
4462     NewObjectHook();
4463     if (utf16Len == 0) {
4464         return GetEmptyString();
4465     }
4466     EcmaString *str =
4467         EcmaStringAccessor::CreateFromUtf16(vm_, utf16Data, utf16Len, canBeCompress, MemSpaceType::SHARED_OLD_SPACE);
4468     uint32_t hashCode = EcmaStringAccessor::ComputeHashcodeUtf16(const_cast<uint16_t *>(utf16Data), utf16Len);
4469     str->SetMixHashcode(hashCode);
4470     return JSHandle<EcmaString>(thread_, str);
4471 }
4472 
NewFromUtf16(std::u16string_view data)4473 JSHandle<EcmaString> ObjectFactory::NewFromUtf16(std::u16string_view data)
4474 {
4475     uint32_t length = data.length();
4476     auto utf16Data = reinterpret_cast<const uint16_t *>(data.data());
4477     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf16Data, length);
4478     return GetStringFromStringTable(utf16Data, length, canBeCompress);
4479 }
4480 
NewFromStdString(const std::string & data)4481 JSHandle<EcmaString> ObjectFactory::NewFromStdString(const std::string &data)
4482 {
4483     auto utf8Data = reinterpret_cast<const uint8_t *>(data.c_str());
4484     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf8Data, data.length());
4485     return GetStringFromStringTable(utf8Data, data.size(), canBeCompress);
4486 }
4487 
NewFromUtf8WithoutStringTable(const uint8_t * utf8Data,uint32_t utf8Len)4488 JSHandle<EcmaString> ObjectFactory::NewFromUtf8WithoutStringTable(const uint8_t *utf8Data, uint32_t utf8Len)
4489 {
4490     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf8Data, utf8Len);
4491     NewObjectHook();
4492     if (utf8Len == 0) {
4493         return GetEmptyString();
4494     }
4495     EcmaString *str =
4496         EcmaStringAccessor::CreateFromUtf8(vm_, utf8Data, utf8Len, canBeCompress, MemSpaceType::SHARED_OLD_SPACE);
4497     uint32_t hashCode = EcmaStringAccessor::ComputeHashcodeUtf8(utf8Data, utf8Len, canBeCompress);
4498     str->SetMixHashcode(hashCode);
4499     return JSHandle<EcmaString>(thread_, str);
4500 }
4501 
NewFromUtf8(const uint8_t * utf8Data,uint32_t utf8Len)4502 JSHandle<EcmaString> ObjectFactory::NewFromUtf8(const uint8_t *utf8Data, uint32_t utf8Len)
4503 {
4504     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf8Data, utf8Len);
4505     return GetStringFromStringTable(utf8Data, utf8Len, canBeCompress);
4506 }
4507 
NewFromUtf16WithoutStringTable(const uint16_t * utf16Data,uint32_t utf16Len)4508 JSHandle<EcmaString> ObjectFactory::NewFromUtf16WithoutStringTable(const uint16_t *utf16Data, uint32_t utf16Len)
4509 {
4510     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len);
4511     NewObjectHook();
4512     if (utf16Len == 0) {
4513         return GetEmptyString();
4514     }
4515     EcmaString *str =
4516         EcmaStringAccessor::CreateFromUtf16(vm_, utf16Data, utf16Len, canBeCompress, MemSpaceType::SHARED_OLD_SPACE);
4517     uint32_t hashCode = EcmaStringAccessor::ComputeHashcodeUtf16(const_cast<uint16_t *>(utf16Data), utf16Len);
4518     str->SetMixHashcode(hashCode);
4519     return JSHandle<EcmaString>(thread_, str);
4520 }
4521 
NewFromUtf16(const uint16_t * utf16Data,uint32_t utf16Len)4522 JSHandle<EcmaString> ObjectFactory::NewFromUtf16(const uint16_t *utf16Data, uint32_t utf16Len)
4523 {
4524     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len);
4525     return GetStringFromStringTable(utf16Data, utf16Len, canBeCompress);
4526 }
4527 
NewFromUtf16Compress(const uint16_t * utf16Data,uint32_t utf16Len)4528 JSHandle<EcmaString> ObjectFactory::NewFromUtf16Compress(const uint16_t *utf16Data, uint32_t utf16Len)
4529 {
4530     ASSERT(EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len));
4531     return GetStringFromStringTable(utf16Data, utf16Len, true);
4532 }
4533 
NewFromUtf16NotCompress(const uint16_t * utf16Data,uint32_t utf16Len)4534 JSHandle<EcmaString> ObjectFactory::NewFromUtf16NotCompress(const uint16_t *utf16Data, uint32_t utf16Len)
4535 {
4536     ASSERT(!EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len));
4537     return GetStringFromStringTable(utf16Data, utf16Len, false);
4538 }
4539 
NewFromUtf8Literal(const uint8_t * utf8Data,uint32_t utf8Len)4540 JSHandle<EcmaString> ObjectFactory::NewFromUtf8Literal(const uint8_t *utf8Data, uint32_t utf8Len)
4541 {
4542     NewObjectHook();
4543     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf8Data, utf8Len);
4544     return JSHandle<EcmaString>(thread_, EcmaStringAccessor::CreateFromUtf8(vm_, utf8Data, utf8Len, canBeCompress));
4545 }
4546 
NewFromUtf8LiteralCompress(const uint8_t * utf8Data,uint32_t utf8Len)4547 JSHandle<EcmaString> ObjectFactory::NewFromUtf8LiteralCompress(const uint8_t *utf8Data, uint32_t utf8Len)
4548 {
4549     NewObjectHook();
4550     ASSERT(EcmaStringAccessor::CanBeCompressed(utf8Data, utf8Len));
4551     return JSHandle<EcmaString>(thread_, EcmaStringAccessor::CreateFromUtf8(vm_, utf8Data, utf8Len, true));
4552 }
4553 
NewFromUtf8LiteralCompressSubString(const JSHandle<EcmaString> & string,uint32_t offset,uint32_t utf8Len)4554 JSHandle<EcmaString> ObjectFactory::NewFromUtf8LiteralCompressSubString(const JSHandle<EcmaString> &string,
4555                                                                         uint32_t offset, uint32_t utf8Len)
4556 {
4557     NewObjectHook();
4558     ASSERT(EcmaStringAccessor::CanBeCompressed(EcmaStringAccessor(string).GetDataUtf8() + offset, utf8Len));
4559     return JSHandle<EcmaString>(thread_, EcmaStringAccessor::CreateFromUtf8CompressedSubString(vm_, string,
4560         offset, utf8Len));
4561 }
4562 
NewCompressedUtf8(const uint8_t * utf8Data,uint32_t utf8Len)4563 JSHandle<EcmaString> ObjectFactory::NewCompressedUtf8(const uint8_t *utf8Data, uint32_t utf8Len)
4564 {
4565     NewObjectHook();
4566     ASSERT(EcmaStringAccessor::CanBeCompressed(utf8Data, utf8Len));
4567     return GetStringFromStringTable(utf8Data, utf8Len, true);
4568 }
4569 
NewCompressedUtf8SubString(const JSHandle<EcmaString> & string,uint32_t offset,uint32_t utf8Len)4570 JSHandle<EcmaString> ObjectFactory::NewCompressedUtf8SubString(const JSHandle<EcmaString> &string,
4571                                                                uint32_t offset, uint32_t utf8Len)
4572 {
4573     NewObjectHook();
4574     ASSERT(EcmaStringAccessor::CanBeCompressed(EcmaStringAccessor(string).GetDataUtf8() + offset, utf8Len));
4575     return GetCompressedSubStringFromStringTable(string, offset, utf8Len);
4576 }
4577 
NewFromUtf16Literal(const uint16_t * utf16Data,uint32_t utf16Len)4578 JSHandle<EcmaString> ObjectFactory::NewFromUtf16Literal(const uint16_t *utf16Data, uint32_t utf16Len)
4579 {
4580     NewObjectHook();
4581     bool canBeCompress = EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len);
4582     return JSHandle<EcmaString>(thread_, EcmaStringAccessor::CreateFromUtf16(vm_, utf16Data, utf16Len, canBeCompress));
4583 }
4584 
NewFromUtf16LiteralCompress(const uint16_t * utf16Data,uint32_t utf16Len)4585 JSHandle<EcmaString> ObjectFactory::NewFromUtf16LiteralCompress(const uint16_t *utf16Data, uint32_t utf16Len)
4586 {
4587     NewObjectHook();
4588     ASSERT(EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len));
4589     return JSHandle<EcmaString>(thread_, EcmaStringAccessor::CreateFromUtf16(vm_, utf16Data, utf16Len, true));
4590 }
4591 
NewFromUtf16LiteralNotCompress(const uint16_t * utf16Data,uint32_t utf16Len)4592 JSHandle<EcmaString> ObjectFactory::NewFromUtf16LiteralNotCompress(const uint16_t *utf16Data, uint32_t utf16Len)
4593 {
4594     NewObjectHook();
4595     ASSERT(!EcmaStringAccessor::CanBeCompressed(utf16Data, utf16Len));
4596     return JSHandle<EcmaString>(thread_, EcmaStringAccessor::CreateFromUtf16(vm_, utf16Data, utf16Len, false));
4597 }
4598 
ConcatFromString(const JSHandle<EcmaString> & firstString,const JSHandle<EcmaString> & secondString)4599 JSHandle<EcmaString> ObjectFactory::ConcatFromString(const JSHandle<EcmaString> &firstString,
4600                                                      const JSHandle<EcmaString> &secondString)
4601 {
4602     if (EcmaStringAccessor(firstString).GetLength() == 0) {
4603         return secondString;
4604     }
4605     if (EcmaStringAccessor(secondString).GetLength() == 0) {
4606         return firstString;
4607     }
4608     return GetStringFromStringTable(firstString, secondString);
4609 }
4610 
GetStringFromStringTable(const JSHandle<EcmaString> & firstString,const JSHandle<EcmaString> & secondString)4611 JSHandle<EcmaString> ObjectFactory::GetStringFromStringTable(const JSHandle<EcmaString> &firstString,
4612                                                              const JSHandle<EcmaString> &secondString)
4613 {
4614     auto stringTable = vm_->GetEcmaStringTable();
4615     return JSHandle<EcmaString>(thread_, stringTable->GetOrInternString(vm_, firstString, secondString));
4616 }
4617 
NewJSAPIArrayList(uint32_t capacity)4618 JSHandle<JSAPIArrayList> ObjectFactory::NewJSAPIArrayList(uint32_t capacity)
4619 {
4620     NewObjectHook();
4621     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4622     JSHandle<JSFunction> builtinObj = JSHandle<JSFunction>::Cast(env->GetArrayListFunction());
4623     JSHandle<JSAPIArrayList> obj = JSHandle<JSAPIArrayList>(NewJSObjectByConstructor(builtinObj));
4624     ObjectFactory *factory = thread_->GetEcmaVM()->GetFactory();
4625     JSHandle<TaggedArray> elements = factory->NewTaggedArray(capacity);
4626     obj->SetElements(thread_, elements);
4627 
4628     return obj;
4629 }
4630 
NewJSAPIArrayListIterator(const JSHandle<JSAPIArrayList> & arrayList)4631 JSHandle<JSAPIArrayListIterator> ObjectFactory::NewJSAPIArrayListIterator(const JSHandle<JSAPIArrayList> &arrayList)
4632 {
4633     NewObjectHook();
4634     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4635     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4636     JSHandle<JSTaggedValue> protoValue = env->GetArrayListIteratorPrototype();
4637     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIArrayListIteratorClass());
4638     hclassHandle->SetPrototype(thread_, protoValue);
4639     JSHandle<JSAPIArrayListIterator> iter(NewJSObject(hclassHandle));
4640     iter->GetJSHClass()->SetExtensible(true);
4641     iter->SetIteratedArrayList(thread_, arrayList);
4642     iter->SetNextIndex(0);
4643     return iter;
4644 }
4645 
NewJSAPILightWeightMapIterator(const JSHandle<JSAPILightWeightMap> & obj,IterationKind kind)4646 JSHandle<JSAPILightWeightMapIterator> ObjectFactory::NewJSAPILightWeightMapIterator(
4647     const JSHandle<JSAPILightWeightMap> &obj, IterationKind kind)
4648 {
4649     NewObjectHook();
4650     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4651     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4652     JSHandle<JSTaggedValue> protoValue = env->GetLightWeightMapIteratorPrototype();
4653     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPILightWeightMapIteratorClass());
4654     hclassHandle->SetPrototype(thread_, protoValue);
4655     JSHandle<JSAPILightWeightMapIterator> iter(NewJSObject(hclassHandle));
4656     iter->GetJSHClass()->SetExtensible(true);
4657     iter->SetIteratedLightWeightMap(thread_, obj);
4658     iter->SetNextIndex(0);
4659     iter->SetIterationKind(kind);
4660     return iter;
4661 }
4662 
NewJSAPILightWeightSetIterator(const JSHandle<JSAPILightWeightSet> & obj,IterationKind kind)4663 JSHandle<JSAPILightWeightSetIterator> ObjectFactory::NewJSAPILightWeightSetIterator(
4664     const JSHandle<JSAPILightWeightSet> &obj, IterationKind kind)
4665 {
4666     NewObjectHook();
4667     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4668     JSHandle<JSTaggedValue> protoValue = env->GetLightWeightSetIteratorPrototype();
4669     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4670     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPILightWeightSetIteratorClass());
4671     hclassHandle->SetPrototype(thread_, protoValue);
4672     JSHandle<JSAPILightWeightSetIterator> iter(NewJSObject(hclassHandle));
4673     iter->GetJSHClass()->SetExtensible(true);
4674     iter->SetIteratedLightWeightSet(thread_, obj);
4675     iter->SetNextIndex(0);
4676     iter->SetIterationKind(kind);
4677     return iter;
4678 }
4679 
NewJSAPIPlainArray(uint32_t capacity)4680 JSHandle<JSAPIPlainArray> ObjectFactory::NewJSAPIPlainArray(uint32_t capacity)
4681 {
4682     NewObjectHook();
4683     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4684     JSHandle<JSFunction> builtinObj = JSHandle<JSFunction>::Cast(env->GetPlainArrayFunction());
4685     JSHandle<JSAPIPlainArray> obj = JSHandle<JSAPIPlainArray>(NewJSObjectByConstructor(builtinObj));
4686     ObjectFactory *factory = thread_->GetEcmaVM()->GetFactory();
4687     JSHandle<TaggedArray> keyArray = factory->NewTaggedArray(capacity);
4688     JSHandle<TaggedArray> valueArray = factory->NewTaggedArray(capacity);
4689     obj->SetKeys(thread_, keyArray);
4690     obj->SetValues(thread_, valueArray);
4691 
4692     return obj;
4693 }
4694 
NewJSAPIPlainArrayIterator(const JSHandle<JSAPIPlainArray> & plainarray,IterationKind kind)4695 JSHandle<JSAPIPlainArrayIterator> ObjectFactory::NewJSAPIPlainArrayIterator(const JSHandle<JSAPIPlainArray> &plainarray,
4696                                                                             IterationKind kind)
4697 {
4698     NewObjectHook();
4699     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4700     JSHandle<JSTaggedValue> protoValue = env->GetPlainArrayIteratorPrototype();
4701     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4702     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIPlainArrayIteratorClass());
4703     hclassHandle->SetPrototype(thread_, protoValue);
4704     JSHandle<JSAPIPlainArrayIterator> iter(NewJSObject(hclassHandle));
4705     iter->GetJSHClass()->SetExtensible(true);
4706     iter->SetIteratedPlainArray(thread_, plainarray);
4707     iter->SetNextIndex(0);
4708     iter->SetIterationKind(kind);
4709     return iter;
4710 }
4711 
NewJSAPIStackIterator(const JSHandle<JSAPIStack> & stack)4712 JSHandle<JSAPIStackIterator> ObjectFactory::NewJSAPIStackIterator(const JSHandle<JSAPIStack> &stack)
4713 {
4714     NewObjectHook();
4715     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4716     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4717     JSHandle<JSTaggedValue> protoValue = env->GetStackIteratorPrototype();
4718     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIStackIteratorClass());
4719     hclassHandle->SetPrototype(thread_, protoValue);
4720     JSHandle<JSAPIStackIterator> iter(NewJSObject(hclassHandle));
4721     iter->GetJSHClass()->SetExtensible(true);
4722     iter->SetIteratedStack(thread_, stack);
4723     iter->SetNextIndex(0);
4724     return iter;
4725 }
4726 
CopyDeque(const JSHandle<TaggedArray> & old,uint32_t newLength,uint32_t oldLength,uint32_t first,uint32_t last)4727 JSHandle<TaggedArray> ObjectFactory::CopyDeque(const JSHandle<TaggedArray> &old, uint32_t newLength,
4728                                                [[maybe_unused]] uint32_t oldLength, uint32_t first, uint32_t last)
4729 {
4730     NewObjectHook();
4731     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), newLength);
4732     auto header = heap_->AllocateYoungOrHugeObject(
4733         JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject()), size);
4734     JSHandle<TaggedArray> newArray(thread_, header);
4735     newArray->InitializeWithSpecialValue(JSTaggedValue::Hole(), newLength, old->GetExtraLength());
4736 
4737     uint32_t curIndex = first;
4738     // newIndex use in new TaggedArray, 0 : New TaggedArray index
4739     uint32_t newIndex = 0;
4740     uint32_t oldCapacity = old->GetLength();
4741     while (curIndex != last) {
4742         JSTaggedValue value = old->Get(thread_, curIndex);
4743         newArray->Set(thread_, newIndex, value);
4744         ASSERT(oldCapacity != 0);
4745         curIndex = (curIndex + 1) % oldCapacity;
4746         newIndex = newIndex + 1;
4747     }
4748     return newArray;
4749 }
4750 
NewJSAPIDequeIterator(const JSHandle<JSAPIDeque> & deque)4751 JSHandle<JSAPIDequeIterator> ObjectFactory::NewJSAPIDequeIterator(const JSHandle<JSAPIDeque> &deque)
4752 {
4753     NewObjectHook();
4754     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4755     JSHandle<JSTaggedValue> protoValue = env->GetDequeIteratorPrototype();
4756     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4757     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIDequeIteratorClass());
4758     hclassHandle->SetPrototype(thread_, protoValue);
4759     JSHandle<JSAPIDequeIterator> iter(NewJSObject(hclassHandle));
4760     iter->GetJSHClass()->SetExtensible(true);
4761     iter->SetIteratedDeque(thread_, deque);
4762     iter->SetNextIndex(deque->GetFirst());
4763     return iter;
4764 }
4765 
CopyQueue(const JSHandle<TaggedArray> & old,uint32_t newLength,uint32_t front,uint32_t tail)4766 JSHandle<TaggedArray> ObjectFactory::CopyQueue(const JSHandle<TaggedArray> &old, uint32_t newLength,
4767                                                uint32_t front, uint32_t tail)
4768 {
4769     NewObjectHook();
4770     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), newLength);
4771     auto header = heap_->AllocateYoungOrHugeObject(
4772         JSHClass::Cast(thread_->GlobalConstants()->GetTaggedArrayClass().GetTaggedObject()), size);
4773     JSHandle<TaggedArray> newArray(thread_, header);
4774     newArray->InitializeWithSpecialValue(JSTaggedValue::Hole(), newLength, old->GetExtraLength());
4775 
4776     uint32_t curIndex = front;
4777     // newIndex use in new TaggedArray, 0 : New TaggedArray index
4778     uint32_t newIndex = 0;
4779     uint32_t oldCapacity = old->GetLength();
4780     while (curIndex != tail) {
4781         JSTaggedValue value = old->Get(thread_, curIndex);
4782         newArray->Set(thread_, newIndex, value);
4783         ASSERT(oldCapacity != 0);
4784         curIndex = (curIndex + 1) % oldCapacity;
4785         newIndex = newIndex + 1;
4786     }
4787     return newArray;
4788 }
4789 
NewJSAPIQueueIterator(const JSHandle<JSAPIQueue> & queue)4790 JSHandle<JSAPIQueueIterator> ObjectFactory::NewJSAPIQueueIterator(const JSHandle<JSAPIQueue> &queue)
4791 {
4792     NewObjectHook();
4793     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4794     JSHandle<JSTaggedValue> protoValue = env->GetQueueIteratorPrototype();
4795     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4796     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIQueueIteratorClass());
4797     hclassHandle->SetPrototype(thread_, protoValue);
4798     JSHandle<JSAPIQueueIterator> iter(NewJSObject(hclassHandle));
4799     iter->GetJSHClass()->SetExtensible(true);
4800     iter->SetIteratedQueue(thread_, queue); // IteratedQueue
4801     iter->SetNextIndex(0);
4802     return iter;
4803 }
4804 
NewJSAPITreeMapIterator(const JSHandle<JSAPITreeMap> & map,IterationKind kind)4805 JSHandle<JSAPITreeMapIterator> ObjectFactory::NewJSAPITreeMapIterator(const JSHandle<JSAPITreeMap> &map,
4806                                                                       IterationKind kind)
4807 {
4808     NewObjectHook();
4809     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4810     JSHandle<JSTaggedValue> proto = env->GetTreeMapIteratorPrototype();
4811     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4812     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPITreeMapIteratorClass());
4813     hclassHandle->SetPrototype(thread_, proto);
4814     JSHandle<JSAPITreeMapIterator> iter(NewJSObject(hclassHandle));
4815     iter->GetJSHClass()->SetExtensible(true);
4816     iter->SetIteratedMap(thread_, map);
4817     iter->SetNextIndex(0);
4818     iter->SetEntries<SKIP_BARRIER>(thread_, JSTaggedValue::Hole());
4819     iter->SetIterationKind(kind);
4820     return iter;
4821 }
4822 
NewJSAPITreeSetIterator(const JSHandle<JSAPITreeSet> & set,IterationKind kind)4823 JSHandle<JSAPITreeSetIterator> ObjectFactory::NewJSAPITreeSetIterator(const JSHandle<JSAPITreeSet> &set,
4824                                                                       IterationKind kind)
4825 {
4826     NewObjectHook();
4827     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4828     JSHandle<JSTaggedValue> proto = env->GetTreeSetIteratorPrototype();
4829     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4830     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPITreeSetIteratorClass());
4831     hclassHandle->SetPrototype(thread_, proto);
4832     JSHandle<JSAPITreeSetIterator> iter(NewJSObject(hclassHandle));
4833     iter->GetJSHClass()->SetExtensible(true);
4834     iter->SetIteratedSet(thread_, set);
4835     iter->SetNextIndex(0);
4836     iter->SetEntries<SKIP_BARRIER>(thread_, JSTaggedValue::Hole());
4837     iter->SetIterationKind(kind);
4838     return iter;
4839 }
4840 
NewJSAPIVector(uint32_t capacity)4841 JSHandle<JSAPIVector> ObjectFactory::NewJSAPIVector(uint32_t capacity)
4842 {
4843     NewObjectHook();
4844     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4845     JSHandle<JSFunction> builtinObj = JSHandle<JSFunction>::Cast(env->GetVectorFunction());
4846     JSHandle<JSAPIVector> obj = JSHandle<JSAPIVector>(NewJSObjectByConstructor(builtinObj));
4847     JSHandle<TaggedArray> newVector = NewTaggedArray(capacity);
4848     obj->SetElements(thread_, newVector);
4849 
4850     return obj;
4851 }
4852 
NewJSAPIVectorIterator(const JSHandle<JSAPIVector> & vector)4853 JSHandle<JSAPIVectorIterator> ObjectFactory::NewJSAPIVectorIterator(const JSHandle<JSAPIVector> &vector)
4854 {
4855     NewObjectHook();
4856     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4857     JSHandle<JSTaggedValue> proto = env->GetVectorIteratorPrototype();
4858     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4859     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIVectorIteratorClass());
4860     hclassHandle->SetPrototype(thread_, proto);
4861     JSHandle<JSAPIVectorIterator> iter(NewJSObject(hclassHandle));
4862     iter->GetJSHClass()->SetExtensible(true);
4863     iter->SetIteratedVector(thread_, vector);
4864     iter->SetNextIndex(0);
4865     return iter;
4866 }
4867 
NewJSAPIBitVector(uint32_t capacity)4868 JSHandle<JSAPIBitVector> ObjectFactory::NewJSAPIBitVector(uint32_t capacity)
4869 {
4870     NewObjectHook();
4871     JSHandle<JSFunction> builtinObj(thread_->GetEcmaVM()->GetGlobalEnv()->GetBitVectorFunction());
4872     JSHandle<JSAPIBitVector> obj = JSHandle<JSAPIBitVector>(NewJSObjectByConstructor(builtinObj));
4873     uint32_t taggedArrayCapacity = (capacity >> JSAPIBitVector::TAGGED_VALUE_BIT_SIZE) + 1;
4874     auto *newBitSetVector = new std::vector<std::bitset<JSAPIBitVector::BIT_SET_LENGTH>>();
4875     newBitSetVector->resize(taggedArrayCapacity, 0);
4876     auto deleter = []([[maybe_unused]] void *env, void *pointer, [[maybe_unused]] void *data) {
4877         if (pointer == nullptr) {
4878             return;
4879         }
4880         delete reinterpret_cast<std::vector<std::bitset<JSAPIBitVector::BIT_SET_LENGTH>> *>(pointer);
4881     };
4882     JSHandle<JSNativePointer> pointer = NewSJSNativePointer(newBitSetVector, deleter, newBitSetVector);
4883     obj->SetNativePointer(thread_, pointer);
4884 
4885     return obj;
4886 }
4887 
4888 // Creaete a fastbuffer without alloc arraybuffer under TypedArray.
NewJSAPIBufferWithoutInit()4889 JSHandle<JSAPIFastBuffer> ObjectFactory::NewJSAPIBufferWithoutInit()
4890 {
4891     NewObjectHook();
4892     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4893     JSHandle<JSTaggedValue> handleTagValFunc = env->GetUint8ArrayFunction();
4894     JSHandle<JSObject> obj = NewJSObjectByConstructor(JSHandle<JSFunction>(handleTagValFunc), handleTagValFunc);
4895     JSHandle<JSTypedArray> handleUint8Array = JSHandle<JSTypedArray>::Cast(obj);
4896 
4897     handleUint8Array->SetByteLength(0);
4898     handleUint8Array->SetByteOffset(0);
4899     handleUint8Array->SetArrayLength(0);
4900     handleUint8Array->SetContentType(ContentType::Number);
4901     JSHandle<JSFunction> builtinObj(thread_->GetEcmaVM()->GetGlobalEnv()->GetBufferFunction());
4902     JSHandle<JSAPIFastBuffer> buffer = JSHandle<JSAPIFastBuffer>(NewJSObjectByConstructor(builtinObj));
4903     buffer->SetFastBufferData(thread_, handleUint8Array);
4904     buffer->SetLength(0);
4905 
4906     return buffer;
4907 }
4908 
4909 // create fastbuffer shared same arraybufer under typedArray
NewJSAPIBuffer(JSHandle<JSTypedArray> typedArrayHandle)4910 JSHandle<JSAPIFastBuffer> ObjectFactory::NewJSAPIBuffer(JSHandle<JSTypedArray> typedArrayHandle)
4911 {
4912     NewObjectHook();
4913     JSHandle<JSFunction> builtinObj(thread_->GetEcmaVM()->GetGlobalEnv()->GetBufferFunction());
4914     JSHandle<JSAPIFastBuffer> buffer = JSHandle<JSAPIFastBuffer>(NewJSObjectByConstructor(builtinObj));
4915     buffer->SetFastBufferData(thread_, typedArrayHandle);
4916     buffer->SetLength(typedArrayHandle->GetByteLength());
4917     return buffer;
4918 }
4919 
4920 // Create a fastbuffer with length and byteOffset
NewJSAPIBuffer(uint32_t length,uint32_t byteOffset)4921 JSHandle<JSAPIFastBuffer> ObjectFactory::NewJSAPIBuffer(uint32_t length, uint32_t byteOffset)
4922 {
4923     NewObjectHook();
4924     JSHandle<JSTypedArray> handleUint8Array = JSAPIFastBuffer::NewUint8Array(thread_, length);
4925     JSHandle<JSFunction> builtinObj(thread_->GetEcmaVM()->GetGlobalEnv()->GetBufferFunction());
4926     JSHandle<JSAPIFastBuffer> buffer = JSHandle<JSAPIFastBuffer>(NewJSObjectByConstructor(builtinObj));
4927     buffer->SetFastBufferData(thread_, handleUint8Array);
4928     buffer->SetLength(length);
4929     buffer->SetOffset(byteOffset);
4930     return buffer;
4931 }
4932 
NewJSAPIBitVectorIterator(const JSHandle<JSAPIBitVector> & bitVector)4933 JSHandle<JSAPIBitVectorIterator> ObjectFactory::NewJSAPIBitVectorIterator(const JSHandle<JSAPIBitVector> &bitVector)
4934 {
4935     NewObjectHook();
4936     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4937     JSHandle<JSTaggedValue> proto(env->GetBitVectorIteratorPrototype());
4938     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4939     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIBitVectorIteratorClass());
4940     hclassHandle->SetPrototype(thread_, proto);
4941     JSHandle<JSAPIBitVectorIterator> iter(NewJSObject(hclassHandle));
4942     iter->GetJSHClass()->SetExtensible(true);
4943     iter->SetIteratedBitVector(thread_, bitVector);
4944     iter->SetNextIndex(0);
4945     return iter;
4946 }
4947 
NewJSAPILinkedListIterator(const JSHandle<JSAPILinkedList> & linkedList)4948 JSHandle<JSAPILinkedListIterator> ObjectFactory::NewJSAPILinkedListIterator(const JSHandle<JSAPILinkedList> &linkedList)
4949 {
4950     NewObjectHook();
4951     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4952     JSHandle<JSTaggedValue> proto = env->GetLinkedListIteratorPrototype();
4953     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4954     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPILinkedListIteratorClass());
4955     hclassHandle->SetPrototype(thread_, proto);
4956     JSHandle<JSAPILinkedListIterator> iter(NewJSObject(hclassHandle));
4957     iter->GetJSHClass()->SetExtensible(true);
4958     iter->SetIteratedLinkedList(thread_, linkedList->GetDoubleList(thread_));
4959     iter->SetNextIndex(0);
4960     const uint32_t linkedListElementStartIndex = 4;
4961     iter->SetDataIndex(linkedListElementStartIndex);
4962     return iter;
4963 }
4964 
NewJSAPIListIterator(const JSHandle<JSAPIList> & List)4965 JSHandle<JSAPIListIterator> ObjectFactory::NewJSAPIListIterator(const JSHandle<JSAPIList> &List)
4966 {
4967     NewObjectHook();
4968     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4969     JSHandle<JSTaggedValue> proto = env->GetListIteratorPrototype();
4970     const GlobalEnvConstants *globalConst = thread_->GlobalConstants();
4971     JSHandle<JSHClass> hclassHandle(globalConst->GetHandledJSAPIListIteratorClass());
4972     hclassHandle->SetPrototype(thread_, proto);
4973     JSHandle<JSAPIListIterator> iter(NewJSObject(hclassHandle));
4974     iter->GetJSHClass()->SetExtensible(true);
4975     iter->SetIteratedList(thread_, List->GetSingleList(thread_));
4976     iter->SetNextIndex(0);
4977     const uint32_t linkedListElementStartIndex = 4;
4978     iter->SetDataIndex(linkedListElementStartIndex);
4979     return iter;
4980 }
4981 
NewJSAPIList()4982 JSHandle<JSAPIList> ObjectFactory::NewJSAPIList()
4983 {
4984     NewObjectHook();
4985     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4986     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(env->GetListFunction());
4987     return JSHandle<JSAPIList>::Cast(NewJSObjectByConstructor(function));
4988 }
4989 
NewJSAPILinkedList()4990 JSHandle<JSAPILinkedList> ObjectFactory::NewJSAPILinkedList()
4991 {
4992     NewObjectHook();
4993     JSHandle<GlobalEnv> env = thread_->GetEcmaVM()->GetGlobalEnv();
4994     JSHandle<JSFunction> function = JSHandle<JSFunction>::Cast(env->GetLinkedListFunction());
4995     return JSHandle<JSAPILinkedList>::Cast(NewJSObjectByConstructor(function));
4996 }
4997 
NewImportEntry()4998 JSHandle<ImportEntry> ObjectFactory::NewImportEntry()
4999 {
5000     JSHandle<JSTaggedValue> defautValue = thread_->GlobalConstants()->GetHandledUndefined();
5001     return NewImportEntry(0, defautValue, defautValue, SharedTypes::UNSENDABLE_MODULE); // 0: random number
5002 }
5003 
NewImportEntry(const uint32_t moduleRequestIdx,const JSHandle<JSTaggedValue> & importName,const JSHandle<JSTaggedValue> & localName,SharedTypes sharedTypes)5004 JSHandle<ImportEntry> ObjectFactory::NewImportEntry(const uint32_t moduleRequestIdx,
5005                                                     const JSHandle<JSTaggedValue> &importName,
5006                                                     const JSHandle<JSTaggedValue> &localName,
5007                                                     SharedTypes sharedTypes)
5008 {
5009     if (sharedTypes == SharedTypes::SHARED_MODULE) {
5010         return NewSImportEntry(moduleRequestIdx, importName, localName);
5011     }
5012     NewObjectHook();
5013     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5014         JSHClass::Cast(thread_->GlobalConstants()->GetImportEntryClass().GetTaggedObject()));
5015     JSHandle<ImportEntry> obj(thread_, header);
5016     obj->SetImportName(thread_, importName);
5017     obj->SetLocalName(thread_, localName);
5018     obj->SetModuleRequestIndex(moduleRequestIdx);
5019     return obj;
5020 }
5021 
NewLocalExportEntry()5022 JSHandle<LocalExportEntry> ObjectFactory::NewLocalExportEntry()
5023 {
5024     JSHandle<JSTaggedValue> defautValue = thread_->GlobalConstants()->GetHandledUndefined();
5025     return NewLocalExportEntry(defautValue, defautValue, LocalExportEntry::LOCAL_DEFAULT_INDEX,
5026                                SharedTypes::UNSENDABLE_MODULE);
5027 }
5028 
NewLocalExportEntry(const JSHandle<JSTaggedValue> & exportName,const JSHandle<JSTaggedValue> & localName,const uint32_t index,SharedTypes sharedTypes)5029 JSHandle<LocalExportEntry> ObjectFactory::NewLocalExportEntry(const JSHandle<JSTaggedValue> &exportName,
5030     const JSHandle<JSTaggedValue> &localName, const uint32_t index, SharedTypes sharedTypes)
5031 {
5032     if (sharedTypes == SharedTypes::SHARED_MODULE) {
5033         return NewSLocalExportEntry(exportName, localName, index);
5034     }
5035     NewObjectHook();
5036     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5037         JSHClass::Cast(thread_->GlobalConstants()->GetLocalExportEntryClass().GetTaggedObject()));
5038     JSHandle<LocalExportEntry> obj(thread_, header);
5039     obj->SetExportName(thread_, exportName);
5040     obj->SetLocalName(thread_, localName);
5041     obj->SetLocalIndex(index);
5042     return obj;
5043 }
5044 
NewIndirectExportEntry()5045 JSHandle<IndirectExportEntry> ObjectFactory::NewIndirectExportEntry()
5046 {
5047     JSHandle<JSTaggedValue> defautValue = thread_->GlobalConstants()->GetHandledUndefined();
5048     return NewIndirectExportEntry(defautValue, 0, defautValue, SharedTypes::UNSENDABLE_MODULE);
5049 }
5050 
NewIndirectExportEntry(const JSHandle<JSTaggedValue> & exportName,const uint32_t moduleRequestIdx,const JSHandle<JSTaggedValue> & importName,SharedTypes sharedTypes)5051 JSHandle<IndirectExportEntry> ObjectFactory::NewIndirectExportEntry(const JSHandle<JSTaggedValue> &exportName,
5052                                                                     const uint32_t moduleRequestIdx,
5053                                                                     const JSHandle<JSTaggedValue> &importName,
5054                                                                     SharedTypes sharedTypes)
5055 {
5056     if (sharedTypes == SharedTypes::SHARED_MODULE) {
5057         return NewSIndirectExportEntry(exportName, moduleRequestIdx, importName);
5058     }
5059     NewObjectHook();
5060     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5061         JSHClass::Cast(thread_->GlobalConstants()->GetIndirectExportEntryClass().GetTaggedObject()));
5062     JSHandle<IndirectExportEntry> obj(thread_, header);
5063     obj->SetExportName(thread_, exportName);
5064     obj->SetModuleRequestIndex(moduleRequestIdx);
5065     obj->SetImportName(thread_, importName);
5066     return obj;
5067 }
5068 
NewStarExportEntry()5069 JSHandle<StarExportEntry> ObjectFactory::NewStarExportEntry()
5070 {
5071     return NewStarExportEntry(0, SharedTypes::UNSENDABLE_MODULE);
5072 }
5073 
NewStarExportEntry(const uint32_t moduleRequestIdx,SharedTypes sharedTypes)5074 JSHandle<StarExportEntry> ObjectFactory::NewStarExportEntry(const uint32_t moduleRequestIdx,
5075                                                             SharedTypes sharedTypes)
5076 {
5077     if (sharedTypes == SharedTypes::SHARED_MODULE) {
5078         return NewSStarExportEntry(moduleRequestIdx);
5079     }
5080     NewObjectHook();
5081     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5082         JSHClass::Cast(thread_->GlobalConstants()->GetStarExportEntryClass().GetTaggedObject()));
5083     JSHandle<StarExportEntry> obj(thread_, header);
5084     obj->SetModuleRequestIndex(moduleRequestIdx);
5085     return obj;
5086 }
5087 
NewSourceTextModule()5088 JSHandle<SourceTextModule> ObjectFactory::NewSourceTextModule()
5089 {
5090     NewObjectHook();
5091     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5092         JSHClass::Cast(thread_->GlobalConstants()->GetSourceTextModuleClass().GetTaggedObject()));
5093     JSHandle<SourceTextModule> obj(thread_, header);
5094     JSTaggedValue undefinedValue = thread_->GlobalConstants()->GetUndefined();
5095     obj->SetEnvironment(thread_, undefinedValue);
5096     obj->SetNamespace(thread_, undefinedValue);
5097     obj->SetModuleRequests(thread_, undefinedValue);
5098     obj->SetRequestedModules(thread_, undefinedValue);
5099     obj->SetImportEntries(thread_, undefinedValue);
5100     obj->SetLocalExportEntries(thread_, undefinedValue);
5101     obj->SetIndirectExportEntries(thread_, undefinedValue);
5102     obj->SetStarExportEntries(thread_, undefinedValue);
5103     obj->SetNameDictionary(thread_, undefinedValue);
5104     // [[CycleRoot]]: For a module not in a cycle, this would be the module itself.
5105     obj->SetCycleRoot(thread_, obj);
5106     obj->SetTopLevelCapability(thread_, undefinedValue);
5107     obj->SetAsyncParentModules(thread_, undefinedValue);
5108     obj->SetHasTLA(false);
5109     obj->SetAsyncEvaluatingOrdinal(SourceTextModule::NOT_ASYNC_EVALUATED);
5110     obj->SetPendingAsyncDependencies(SourceTextModule::UNDEFINED_INDEX);
5111     obj->SetDFSIndex(SourceTextModule::UNDEFINED_INDEX);
5112     obj->SetDFSAncestorIndex(SourceTextModule::UNDEFINED_INDEX);
5113     obj->SetException<SKIP_BARRIER>(thread_, JSTaggedValue::Hole());
5114     obj->SetStatus(ModuleStatus::UNINSTANTIATED);
5115     obj->SetTypes(ModuleTypes::UNKNOWN);
5116     obj->SetIsNewBcVersion(false);
5117     obj->SetRegisterCounts(UINT16_MAX);
5118     obj->SetLazyImportStatus(ToUintPtr(nullptr));
5119     obj->SetEcmaModuleFilename(ToUintPtr(nullptr));
5120     obj->SetEcmaModuleRecordName(ToUintPtr(nullptr));
5121     obj->SetSharedType(SharedTypes::UNSENDABLE_MODULE);
5122     obj->SetSendableEnv(thread_, undefinedValue);
5123     return obj;
5124 }
5125 
NewResolvedBindingRecord()5126 JSHandle<ResolvedBinding> ObjectFactory::NewResolvedBindingRecord()
5127 {
5128     JSHandle<JSTaggedValue> undefinedValue = thread_->GlobalConstants()->GetHandledUndefined();
5129     JSHandle<SourceTextModule> ecmaModule(undefinedValue);
5130     JSHandle<JSTaggedValue> bindingName(undefinedValue);
5131     return NewResolvedBindingRecord(ecmaModule, bindingName);
5132 }
5133 
NewResolvedBindingRecord(const JSHandle<SourceTextModule> & module,const JSHandle<JSTaggedValue> & bindingName)5134 JSHandle<ResolvedBinding> ObjectFactory::NewResolvedBindingRecord(const JSHandle<SourceTextModule> &module,
5135                                                                   const JSHandle<JSTaggedValue> &bindingName)
5136 {
5137     NewObjectHook();
5138     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5139         JSHClass::Cast(thread_->GlobalConstants()->GetResolvedBindingClass().GetTaggedObject()));
5140     JSHandle<ResolvedBinding> obj(thread_, header);
5141     obj->SetModule(thread_, module);
5142     obj->SetBindingName(thread_, bindingName);
5143     return obj;
5144 }
5145 
NewResolvedIndexBindingRecord()5146 JSHandle<ResolvedIndexBinding> ObjectFactory::NewResolvedIndexBindingRecord()
5147 {
5148     JSHandle<JSTaggedValue> undefinedValue = thread_->GlobalConstants()->GetHandledUndefined();
5149     JSHandle<SourceTextModule> ecmaModule(undefinedValue);
5150     int32_t index = 0;
5151     return NewResolvedIndexBindingRecord(ecmaModule, index);
5152 }
5153 
NewResolvedIndexBindingRecord(const JSHandle<SourceTextModule> & module,int32_t index)5154 JSHandle<ResolvedIndexBinding> ObjectFactory::NewResolvedIndexBindingRecord(const JSHandle<SourceTextModule> &module,
5155                                                                             int32_t index)
5156 {
5157     NewObjectHook();
5158     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5159         JSHClass::Cast(thread_->GlobalConstants()->GetResolvedIndexBindingClass().GetTaggedObject()));
5160     JSHandle<ResolvedIndexBinding> obj(thread_, header);
5161     obj->SetModule(thread_, module);
5162     obj->SetIndex(index);
5163     obj->SetIsUpdatedFromResolvedBinding(false);
5164     return obj;
5165 }
5166 
NewCellRecord()5167 JSHandle<CellRecord> ObjectFactory::NewCellRecord()
5168 {
5169     NewObjectHook();
5170     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5171         JSHClass::Cast(thread_->GlobalConstants()->GetCellRecordClass().GetTaggedObject()));
5172     JSHandle<CellRecord> obj(thread_, header);
5173     obj->SetWeakRefTarget(thread_, JSTaggedValue::Undefined());
5174     obj->SetHeldValue(thread_, JSTaggedValue::Undefined());
5175     return obj;
5176 }
5177 
CreateIteratorResultInstanceClass(const JSHandle<GlobalEnv> & env)5178 JSHandle<JSHClass> ObjectFactory::CreateIteratorResultInstanceClass(const JSHandle<GlobalEnv> &env)
5179 {
5180     auto globalConst = thread_->GlobalConstants();
5181     JSHandle<JSTaggedValue> proto = env->GetObjectFunctionPrototype();
5182     JSHandle<JSHClass> iterResultClass = NewEcmaHClass(JSObject::SIZE, JSType::JS_OBJECT, proto);
5183 
5184     uint32_t fieldOrder = 0;
5185     JSHandle<LayoutInfo> layoutInfoHandle = CreateLayoutInfo(2); // 2 means two field
5186     {
5187         ASSERT(JSIterator::VALUE_INLINE_PROPERTY_INDEX == fieldOrder);
5188         PropertyAttributes attributes = PropertyAttributes::Default();
5189         attributes.SetIsInlinedProps(true);
5190         attributes.SetRepresentation(Representation::TAGGED);
5191         attributes.SetOffset(fieldOrder);
5192         layoutInfoHandle->AddKey(thread_, fieldOrder++, globalConst->GetValueString(), attributes);
5193     }
5194     {
5195         ASSERT(JSIterator::DONE_INLINE_PROPERTY_INDEX == fieldOrder);
5196         PropertyAttributes attributes = PropertyAttributes::Default();
5197         attributes.SetIsInlinedProps(true);
5198         attributes.SetRepresentation(Representation::TAGGED);
5199         attributes.SetOffset(fieldOrder);
5200         layoutInfoHandle->AddKey(thread_, fieldOrder++, globalConst->GetDoneString(), attributes);
5201     }
5202 
5203     {
5204         iterResultClass->SetLayout(thread_, layoutInfoHandle);
5205         iterResultClass->SetNumberOfProps(fieldOrder);
5206     }
5207     return iterResultClass;
5208 }
5209 
NewOldSpaceObject(const JSHandle<JSHClass> & hclass)5210 TaggedObject *ObjectFactory::NewOldSpaceObject(const JSHandle<JSHClass> &hclass)
5211 {
5212     NewObjectHook();
5213     TaggedObject *header = heap_->AllocateOldOrHugeObject(*hclass);
5214     uint32_t inobjPropCount = hclass->GetInlinedProperties();
5215     if (inobjPropCount > 0) {
5216         InitializeExtraProperties(hclass, header, inobjPropCount);
5217     }
5218     return header;
5219 }
5220 
NewOldSpaceJSObject(const JSHandle<JSHClass> & jshclass)5221 JSHandle<JSObject> ObjectFactory::NewOldSpaceJSObject(const JSHandle<JSHClass> &jshclass)
5222 {
5223     JSHandle<JSObject> obj(thread_, JSObject::Cast(NewOldSpaceObject(jshclass)));
5224     JSHandle<TaggedArray> emptyArray = EmptyArray();
5225     obj->InitializeHash();
5226     obj->SetElements(thread_, emptyArray);
5227     obj->SetProperties(thread_, emptyArray);
5228     return obj;
5229 }
5230 
NewOldSpaceTaggedArray(uint32_t length,JSTaggedValue initVal)5231 JSHandle<TaggedArray> ObjectFactory::NewOldSpaceTaggedArray(uint32_t length, JSTaggedValue initVal)
5232 {
5233     return NewTaggedArray(length, initVal, MemSpaceType::OLD_SPACE);
5234 }
5235 
NewJSStableArrayWithElements(const JSHandle<TaggedArray> & elements)5236 JSHandle<JSArray> ObjectFactory::NewJSStableArrayWithElements(const JSHandle<TaggedArray> &elements)
5237 {
5238     JSHandle<JSHClass> cls(
5239         thread_, JSHandle<JSFunction>::Cast(vm_->GetGlobalEnv()->GetArrayFunction())->GetProtoOrHClass(thread_));
5240     JSHandle<JSArray> array = JSHandle<JSArray>::Cast(NewJSObject(cls));
5241     array->SetElements(thread_, elements);
5242     array->SetLength(elements->GetLength());
5243     array->SetTrackInfo(thread_, JSTaggedValue::Undefined());
5244     auto accessor = thread_->GlobalConstants()->GetArrayLengthAccessor();
5245     array->SetPropertyInlinedProps(thread_, JSArray::LENGTH_INLINE_PROPERTY_INDEX, accessor);
5246     return array;
5247 }
5248 
NewJSAsyncGeneratorFunction(const JSHandle<Method> & method)5249 JSHandle<JSFunction> ObjectFactory::NewJSAsyncGeneratorFunction(const JSHandle<Method> &method)
5250 {
5251     NewObjectHook();
5252     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
5253 
5254     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetAsyncGeneratorFunctionClass());
5255     JSHandle<JSFunction> asyncGeneratorFunc = JSHandle<JSFunction>::Cast(NewJSObject(hclass));
5256     JSFunction::InitializeJSFunction(thread_, asyncGeneratorFunc, FunctionKind::ASYNC_GENERATOR_FUNCTION);
5257     asyncGeneratorFunc->SetMethod(thread_, method);
5258     return asyncGeneratorFunc;
5259 }
5260 
NewAsyncGeneratorRequest()5261 JSHandle<AsyncGeneratorRequest> ObjectFactory::NewAsyncGeneratorRequest()
5262 {
5263     NewObjectHook();
5264     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5265         JSHClass::Cast(thread_->GlobalConstants()->GetAsyncGeneratorRequestRecordClass().GetTaggedObject()));
5266     JSHandle<AsyncGeneratorRequest> obj(thread_, header);
5267     obj->SetCompletion<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
5268     obj->SetCapability<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
5269     return obj;
5270 }
5271 
NewAsyncIteratorRecord(const JSHandle<JSTaggedValue> & itor,const JSHandle<JSTaggedValue> & next,bool done)5272 JSHandle<AsyncIteratorRecord> ObjectFactory::NewAsyncIteratorRecord(const JSHandle<JSTaggedValue> &itor,
5273                                                                     const JSHandle<JSTaggedValue> &next, bool done)
5274 {
5275     NewObjectHook();
5276     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5277         JSHClass::Cast(thread_->GlobalConstants()->GetAsyncIteratorRecordClass().GetTaggedObject()));
5278     JSHandle<AsyncIteratorRecord> obj(thread_, header);
5279     obj->SetIterator(thread_, itor.GetTaggedValue());
5280     obj->SetNextMethod(thread_, next.GetTaggedValue());
5281     obj->SetDone(done);
5282     return obj;
5283 }
5284 
NewAOTLiteralInfo(uint32_t length,JSTaggedValue initVal)5285 JSHandle<AOTLiteralInfo> ObjectFactory::NewAOTLiteralInfo(uint32_t length, JSTaggedValue initVal)
5286 {
5287     NewObjectHook();
5288     size_t size = AOTLiteralInfo::ComputeSize(length);
5289     auto header = heap_->AllocateYoungOrHugeObject(
5290         JSHClass::Cast(thread_->GlobalConstants()->GetAOTLiteralInfoClass().GetTaggedObject()), size);
5291 
5292     JSHandle<AOTLiteralInfo> aotLiteralInfo(thread_, header);
5293     aotLiteralInfo->InitializeWithSpecialValue(initVal, length);
5294     return aotLiteralInfo;
5295 }
5296 
NewExtraProfileTypeInfo()5297 JSHandle<ExtraProfileTypeInfo> ObjectFactory::NewExtraProfileTypeInfo()
5298 {
5299     NewObjectHook();
5300     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5301         JSHClass::Cast(thread_->GlobalConstants()->GetExtraProfileTypeInfoClass().GetTaggedObject()));
5302     JSHandle<ExtraProfileTypeInfo> extraProfileTypeInfo(thread_, header);
5303     extraProfileTypeInfo->SetReceiverObject(thread_, JSTaggedValue::Undefined());
5304     extraProfileTypeInfo->SetHolderObject(thread_, JSTaggedValue::Undefined());
5305     return extraProfileTypeInfo;
5306 }
5307 
NewProfileTypeInfoCell(const JSHandle<JSTaggedValue> & value)5308 JSHandle<ProfileTypeInfoCell> ObjectFactory::NewProfileTypeInfoCell(const JSHandle<JSTaggedValue> &value)
5309 {
5310     NewObjectHook();
5311     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5312         JSHClass::Cast(thread_->GlobalConstants()->GetProfileTypeInfoCell0Class().GetTaggedObject()));
5313     JSHandle<ProfileTypeInfoCell> profileTypeInfoCell(thread_, header);
5314     profileTypeInfoCell->SetValue(thread_, value.GetTaggedValue());
5315     profileTypeInfoCell->SetMachineCode<SKIP_BARRIER>(thread_, JSTaggedValue::Hole());
5316     profileTypeInfoCell->SetHandle<SKIP_BARRIER>(thread_, JSTaggedValue::Undefined());
5317     return profileTypeInfoCell;
5318 }
5319 
NewFunctionTemplate(const JSHandle<Method> & method,const JSHandle<JSTaggedValue> & module,int32_t length)5320 JSHandle<FunctionTemplate> ObjectFactory::NewFunctionTemplate(
5321     const JSHandle<Method> &method, const JSHandle<JSTaggedValue> &module, int32_t length)
5322 {
5323     NewObjectHook();
5324     auto globalConstants = thread_->GlobalConstants();
5325     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5326         JSHClass::Cast(globalConstants->GetFunctionTemplateClass().GetTaggedObject()));
5327     JSHandle<FunctionTemplate> funcTemp(thread_, header);
5328     funcTemp->SetMethod(thread_, method);
5329     funcTemp->SetModule(thread_, module);
5330     funcTemp->SetRawProfileTypeInfo<SKIP_BARRIER>(thread_, globalConstants->GetEmptyProfileTypeInfoCell());
5331     funcTemp->SetLength(length);
5332     return funcTemp;
5333 }
5334 
NewVTable(uint32_t length,JSTaggedValue initVal)5335 JSHandle<VTable> ObjectFactory::NewVTable(uint32_t length, JSTaggedValue initVal)
5336 {
5337     NewObjectHook();
5338     size_t size = TaggedArray::ComputeSize(JSTaggedValue::TaggedTypeSize(), length * VTable::TUPLE_SIZE);
5339     auto header = heap_->AllocateYoungOrHugeObject(
5340         JSHClass::Cast(thread_->GlobalConstants()->GetVTableClass().GetTaggedObject()), size);
5341 
5342     JSHandle<VTable> vtable(thread_, header);
5343     vtable->InitializeWithSpecialValue(initVal, length * VTable::TUPLE_SIZE);
5344     return vtable;
5345 }
5346 
NewClassLiteral()5347 JSHandle<ClassLiteral> ObjectFactory::NewClassLiteral()
5348 {
5349     NewObjectHook();
5350 
5351     TaggedObject *header = heap_->AllocateYoungOrHugeObject(
5352         JSHClass::Cast(thread_->GlobalConstants()->GetClassLiteralClass().GetTaggedObject()));
5353     JSHandle<TaggedArray> emptyArray = EmptyArray();
5354 
5355     JSHandle<ClassLiteral> classLiteral(thread_, header);
5356     classLiteral->SetArray(thread_, emptyArray);
5357     classLiteral->SetIsAOTUsed(false);
5358 
5359     return classLiteral;
5360 }
5361 
NewJSFunction(const JSHandle<Method> & methodHandle)5362 JSHandle<JSFunction> ObjectFactory::NewJSFunction(const JSHandle<Method> &methodHandle)
5363 {
5364     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
5365     FunctionKind kind = methodHandle->GetFunctionKind();
5366     JSHandle<JSHClass> hclass;
5367     switch (kind) {
5368         case FunctionKind::NORMAL_FUNCTION:
5369         case FunctionKind::BASE_CONSTRUCTOR: {
5370             hclass = JSHandle<JSHClass>::Cast(env->GetFunctionClassWithProto());
5371             break;
5372         }
5373         case FunctionKind::ARROW_FUNCTION: {
5374             hclass = JSHandle<JSHClass>::Cast(env->GetFunctionClassWithoutProto());
5375             break;
5376         }
5377         case FunctionKind::GENERATOR_FUNCTION: {
5378             hclass = JSHandle<JSHClass>::Cast(env->GetGeneratorFunctionClass());
5379             break;
5380         }
5381         case FunctionKind::CONCURRENT_FUNCTION:
5382         case FunctionKind::ASYNC_ARROW_FUNCTION:
5383         case FunctionKind::ASYNC_FUNCTION: {
5384             hclass = JSHandle<JSHClass>::Cast(env->GetAsyncFunctionClass());
5385             break;
5386         }
5387         case FunctionKind::ASYNC_GENERATOR_FUNCTION: {
5388             hclass = JSHandle<JSHClass>::Cast(env->GetAsyncGeneratorFunctionClass());
5389             break;
5390         }
5391         default:
5392             LOG_ECMA(FATAL) << "this branch is unreachable";
5393             UNREACHABLE();
5394     }
5395 
5396     JSHandle<JSFunction> jsfunc = NewJSFunctionByHClass(methodHandle, hclass);
5397     ASSERT_NO_ABRUPT_COMPLETION(thread_);
5398     return jsfunc;
5399 }
5400 
NewJSFunction(const JSHandle<Method> & methodHandle,const JSHandle<JSTaggedValue> & homeObject)5401 JSHandle<JSFunction> ObjectFactory::NewJSFunction(const JSHandle<Method> &methodHandle,
5402                                                   const JSHandle<JSTaggedValue> &homeObject)
5403 {
5404     ASSERT(homeObject->IsECMAObject());
5405     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
5406     JSHandle<JSHClass> hclass = JSHandle<JSHClass>::Cast(env->GetFunctionClassWithoutProto());
5407 
5408     JSHandle<JSFunction> jsFunc = NewJSFunctionByHClass(methodHandle, hclass);
5409     jsFunc->SetHomeObject(thread_, homeObject);
5410     ASSERT_NO_ABRUPT_COMPLETION(thread_);
5411     return jsFunc;
5412 }
5413 
CreateJSObjectWithProperties(size_t propertyCount,const Local<JSValueRef> * keys,const PropertyDescriptor * descs)5414 JSHandle<JSTaggedValue> ObjectFactory::CreateJSObjectWithProperties(size_t propertyCount,
5415                                                                     const Local<JSValueRef> *keys,
5416                                                                     const PropertyDescriptor *descs)
5417 {
5418     if (!CanObjectLiteralHClassCache(propertyCount)) {
5419         return CreateLargeJSObjectWithProperties(propertyCount, keys, descs);
5420     }
5421 
5422     // At least 4 inlined slot
5423     int inlineProps = std::max(static_cast<int>(propertyCount), JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS);
5424     JSMutableHandle<JSHClass> hclassHandle(thread_, GetObjectLiteralRootHClass(inlineProps, inlineProps));
5425     for (size_t i = 0; i < propertyCount; ++i) {
5426         JSMutableHandle<JSTaggedValue> key(JSNApiHelper::ToJSMutableHandle(keys[i]));
5427         if (key->IsString() && !EcmaStringAccessor(key.GetTaggedValue()).IsInternString()) {
5428             // update string stable
5429             key.Update(JSTaggedValue(InternString(key)));
5430         }
5431         ASSERT(EcmaStringAccessor(key->GetTaggedObject()).IsInternString());
5432         if (UNLIKELY(!JSTaggedValue::IsPureString(thread_, key.GetTaggedValue()))) {
5433             THROW_TYPE_ERROR_AND_RETURN(thread_, "property key must be string and can not convert into element index",
5434                                         JSHandle<JSTaggedValue>());
5435         }
5436         PropertyAttributes attr(descs[i]);
5437         attr.SetIsInlinedProps(true);
5438         attr.SetOffset(i);
5439         attr.SetRepresentation(Representation::TAGGED);
5440         auto value = descs[i].GetValue().GetTaggedValue();
5441         auto rep = PropertyAttributes::TranslateToRep(value);
5442         hclassHandle.Update(JSHClass::SetPropertyOfObjHClass<true>(thread_, hclassHandle, key, attr, rep));
5443         RETURN_VALUE_IF_ABRUPT_COMPLETION(thread_, JSHandle<JSTaggedValue>());
5444     }
5445     JSHandle<JSObject> object = NewJSObject(hclassHandle);
5446 
5447     for (size_t i = 0; i < propertyCount; ++i) {
5448         object->SetPropertyInlinedProps<true>(thread_, i, descs[i].GetValue().GetTaggedValue());
5449     }
5450     return JSHandle<JSTaggedValue>(object);
5451 }
5452 
CreateLargeJSObjectWithProperties(size_t propertyCount,const Local<JSValueRef> * keys,const PropertyDescriptor * descs)5453 JSHandle<JSTaggedValue> ObjectFactory::CreateLargeJSObjectWithProperties(size_t propertyCount,
5454                                                                          const Local<JSValueRef> *keys,
5455                                                                          const PropertyDescriptor *descs)
5456 {
5457     ASSERT(!CanObjectLiteralHClassCache(propertyCount));
5458     if (UNLIKELY(propertyCount > PropertyAttributes::MAX_FAST_PROPS_CAPACITY)) {
5459         return CreateDictionaryJSObjectWithProperties(propertyCount, keys, descs);
5460     }
5461     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
5462     JSHandle<JSTaggedValue> objFuncProto = env->GetObjectFunctionPrototype();
5463 
5464     JSHandle<JSHClass> hClassHandle = NewEcmaHClass(JSObject::SIZE, propertyCount, JSType::JS_OBJECT, objFuncProto);
5465     JSHandle<LayoutInfo> layoutHandle = CreateLayoutInfo(propertyCount);
5466     JSHandle<JSObject> object = NewJSObject(hClassHandle);
5467 
5468     for (size_t i = 0; i < propertyCount; ++i) {
5469         JSMutableHandle<JSTaggedValue> key(JSNApiHelper::ToJSMutableHandle(keys[i]));
5470         if (key->IsString() && !EcmaStringAccessor(key.GetTaggedValue()).IsInternString()) {
5471             // update string stable
5472             key.Update(JSTaggedValue(InternString(key)));
5473         }
5474         ASSERT(EcmaStringAccessor(key->GetTaggedObject()).IsInternString());
5475         if (UNLIKELY(!JSTaggedValue::IsPureString(thread_, key.GetTaggedValue()))) {
5476             THROW_TYPE_ERROR_AND_RETURN(thread_, "property key must be string and can not convert into element index",
5477                                         JSHandle<JSTaggedValue>());
5478         }
5479         PropertyAttributes attr(descs[i]);
5480         attr.SetIsInlinedProps(true);
5481         attr.SetOffset(i);
5482         LayoutInfo *layout = LayoutInfo::Cast(layoutHandle.GetTaggedValue().GetTaggedObject());
5483         layout->AddKey<true>(thread_, i, key.GetTaggedValue(), attr);
5484         RETURN_VALUE_IF_ABRUPT_COMPLETION(thread_, JSHandle<JSTaggedValue>());
5485         object->SetPropertyInlinedProps<true>(thread_, i, descs[i].GetValue().GetTaggedValue());
5486     }
5487     hClassHandle->SetNumberOfProps(propertyCount);
5488     hClassHandle->SetLayout(thread_, layoutHandle);
5489     return JSHandle<JSTaggedValue>(object);
5490 }
5491 
CreateDictionaryJSObjectWithProperties(size_t propertyCount,const Local<JSValueRef> * keys,const PropertyDescriptor * descs)5492 JSHandle<JSTaggedValue> ObjectFactory::CreateDictionaryJSObjectWithProperties(size_t propertyCount,
5493                                                                               const Local<JSValueRef> *keys,
5494                                                                               const PropertyDescriptor *descs)
5495 {
5496     ASSERT(propertyCount > PropertyAttributes::MAX_FAST_PROPS_CAPACITY);
5497     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
5498     JSHandle<JSTaggedValue> objFuncProto = env->GetObjectFunctionPrototype();
5499     JSHandle<JSHClass> hClassHandle = NewEcmaHClass(JSObject::SIZE, 0, JSType::JS_OBJECT, objFuncProto);
5500     hClassHandle->SetNumberOfProps(0);
5501     hClassHandle->SetIsDictionaryMode(true);
5502     JSHandle<JSObject> object = NewJSObject(hClassHandle);
5503 
5504     JSMutableHandle<NameDictionary> dict(
5505         thread_, NameDictionary::Create(thread_, NameDictionary::ComputeHashTableSize(propertyCount)));
5506     for (size_t i = 0; i < propertyCount; ++i) {
5507         JSMutableHandle<JSTaggedValue> key(JSNApiHelper::ToJSMutableHandle(keys[i]));
5508         if (key->IsString() && !EcmaStringAccessor(key.GetTaggedValue()).IsInternString()) {
5509             // update string stable
5510             key.Update(JSTaggedValue(InternString(key)));
5511         }
5512         ASSERT(EcmaStringAccessor(key->GetTaggedObject()).IsInternString());
5513         if (UNLIKELY(!JSTaggedValue::IsPureString(thread_, key.GetTaggedValue()))) {
5514             THROW_TYPE_ERROR_AND_RETURN(thread_, "property key must be string and can not convert into element index",
5515                                         JSHandle<JSTaggedValue>());
5516         }
5517         PropertyAttributes attr(descs[i]);
5518         dict.Update(NameDictionary::PutIfAbsent(thread_, dict, key, descs[i].GetValue(), attr));
5519     }
5520     if (UNLIKELY(dict->EntriesCount() != static_cast<int>(propertyCount))) {
5521         THROW_TYPE_ERROR_AND_RETURN(thread_, "property keys can not duplicate", JSHandle<JSTaggedValue>());
5522     }
5523     object->SetProperties(thread_, dict);
5524     return JSHandle<JSTaggedValue>(object);
5525 }
5526 
CreateJSObjectWithNamedProperties(size_t propertyCount,const char ** keys,const Local<JSValueRef> * values)5527 JSHandle<JSTaggedValue> ObjectFactory::CreateJSObjectWithNamedProperties(size_t propertyCount, const char **keys,
5528                                                                          const Local<JSValueRef> *values)
5529 {
5530     if (!CanObjectLiteralHClassCache(propertyCount)) {
5531         return CreateLargeJSObjectWithNamedProperties(propertyCount, keys, values);
5532     }
5533 
5534     // At least 4 inlined slot
5535     int inlineProps = std::max(static_cast<int>(propertyCount), JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS);
5536     JSMutableHandle<JSHClass> hclassHandle(thread_, GetObjectLiteralRootHClass(inlineProps, inlineProps));
5537     for (size_t i = 0; i < propertyCount; ++i) {
5538         JSHandle<JSTaggedValue> key(NewFromUtf8(keys[i]));
5539         ASSERT(EcmaStringAccessor(key->GetTaggedObject()).IsInternString());
5540         if (UNLIKELY(!JSTaggedValue::IsPureString(thread_, key.GetTaggedValue()))) {
5541             THROW_TYPE_ERROR_AND_RETURN(thread_, "property key must be string and can not convert into element index",
5542                                         JSHandle<JSTaggedValue>());
5543         }
5544         PropertyAttributes attr(PropertyAttributes::GetDefaultAttributes());
5545         attr.SetIsInlinedProps(true);
5546         attr.SetOffset(i);
5547         attr.SetRepresentation(Representation::TAGGED);
5548         auto value = JSNApiHelper::ToJSHandle(values[i]).GetTaggedValue();
5549         auto rep = PropertyAttributes::TranslateToRep(value);
5550         hclassHandle.Update(JSHClass::SetPropertyOfObjHClass<true>(thread_, hclassHandle, key, attr, rep));
5551         RETURN_VALUE_IF_ABRUPT_COMPLETION(thread_, JSHandle<JSTaggedValue>());
5552     }
5553     JSHandle<JSObject> object = NewJSObject(hclassHandle);
5554 
5555     for (size_t i = 0; i < propertyCount; ++i) {
5556         object->SetPropertyInlinedProps<true>(thread_, i, JSNApiHelper::ToJSHandle(values[i]).GetTaggedValue());
5557     }
5558     return JSHandle<JSTaggedValue>(object);
5559 }
5560 
CreateLargeJSObjectWithNamedProperties(size_t propertyCount,const char ** keys,const Local<JSValueRef> * values)5561 JSHandle<JSTaggedValue> ObjectFactory::CreateLargeJSObjectWithNamedProperties(size_t propertyCount, const char **keys,
5562                                                                               const Local<JSValueRef> *values)
5563 {
5564     ASSERT(!CanObjectLiteralHClassCache(propertyCount));
5565     if (UNLIKELY(propertyCount > PropertyAttributes::MAX_FAST_PROPS_CAPACITY)) {
5566         return CreateDictionaryJSObjectWithNamedProperties(propertyCount, keys, values);
5567     }
5568     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
5569     JSHandle<JSTaggedValue> objFuncProto = env->GetObjectFunctionPrototype();
5570 
5571     JSHandle<JSHClass> hClassHandle = NewEcmaHClass(JSObject::SIZE, propertyCount, JSType::JS_OBJECT, objFuncProto);
5572     JSHandle<LayoutInfo> layoutHandle = CreateLayoutInfo(propertyCount);
5573     JSHandle<JSObject> object = NewJSObject(hClassHandle);
5574 
5575     for (size_t i = 0; i < propertyCount; ++i) {
5576         JSHandle<JSTaggedValue> key(NewFromUtf8(keys[i]));
5577         ASSERT(EcmaStringAccessor(key->GetTaggedObject()).IsInternString());
5578         if (UNLIKELY(!JSTaggedValue::IsPureString(thread_, key.GetTaggedValue()))) {
5579             THROW_TYPE_ERROR_AND_RETURN(thread_, "property key must be string and can not convert into element index",
5580                                         JSHandle<JSTaggedValue>());
5581         }
5582         PropertyAttributes attr(PropertyAttributes::GetDefaultAttributes());
5583         attr.SetIsInlinedProps(true);
5584         attr.SetOffset(i);
5585         LayoutInfo *layout = LayoutInfo::Cast(layoutHandle.GetTaggedValue().GetTaggedObject());
5586         layout->AddKey<true>(thread_, i, key.GetTaggedValue(), attr);
5587         RETURN_VALUE_IF_ABRUPT_COMPLETION(thread_, JSHandle<JSTaggedValue>());
5588         object->SetPropertyInlinedProps<true>(thread_, i, JSNApiHelper::ToJSHandle(values[i]).GetTaggedValue());
5589     }
5590     hClassHandle->SetNumberOfProps(propertyCount);
5591     hClassHandle->SetLayout(thread_, layoutHandle);
5592     return JSHandle<JSTaggedValue>(object);
5593 }
5594 
CreateDictionaryJSObjectWithNamedProperties(size_t propertyCount,const char ** keys,const Local<JSValueRef> * values)5595 JSHandle<JSTaggedValue> ObjectFactory::CreateDictionaryJSObjectWithNamedProperties(size_t propertyCount,
5596                                                                                    const char **keys,
5597                                                                                    const Local<JSValueRef> *values)
5598 {
5599     ASSERT(propertyCount > PropertyAttributes::MAX_FAST_PROPS_CAPACITY);
5600     JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
5601     JSHandle<JSTaggedValue> objFuncProto = env->GetObjectFunctionPrototype();
5602     JSHandle<JSHClass> hClassHandle = NewEcmaHClass(JSObject::SIZE, 0, JSType::JS_OBJECT, objFuncProto);
5603     hClassHandle->SetNumberOfProps(0);
5604     hClassHandle->SetIsDictionaryMode(true);
5605     JSHandle<JSObject> object = NewJSObject(hClassHandle);
5606 
5607     JSMutableHandle<NameDictionary> dict(
5608         thread_, NameDictionary::Create(thread_, NameDictionary::ComputeHashTableSize(propertyCount)));
5609     for (size_t i = 0; i < propertyCount; ++i) {
5610         JSHandle<JSTaggedValue> key(NewFromUtf8(keys[i]));
5611         ASSERT(EcmaStringAccessor(key->GetTaggedObject()).IsInternString());
5612         if (UNLIKELY(!JSTaggedValue::IsPureString(thread_, key.GetTaggedValue()))) {
5613             THROW_TYPE_ERROR_AND_RETURN(thread_, "property key must be string and can not convert into element index",
5614                                         JSHandle<JSTaggedValue>());
5615         }
5616         PropertyAttributes attr(PropertyAttributes::GetDefaultAttributes());
5617         dict.Update(NameDictionary::PutIfAbsent(thread_, dict, key, JSNApiHelper::ToJSHandle(values[i]), attr));
5618     }
5619     if (UNLIKELY(dict->EntriesCount() != static_cast<int>(propertyCount))) {
5620         THROW_TYPE_ERROR_AND_RETURN(thread_, "property keys can not duplicate", JSHandle<JSTaggedValue>());
5621     }
5622     object->SetProperties(thread_, dict);
5623     return JSHandle<JSTaggedValue>(object);
5624 }
5625 
CreateClassFuncProtoHClass(const JSThread * thread,size_t inlNonStaticPropCount)5626 JSHandle<JSHClass> ObjectFactory::CreateClassFuncProtoHClass(const JSThread *thread, size_t inlNonStaticPropCount)
5627 {
5628     size_t inlinedProps = inlNonStaticPropCount + JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS;
5629     JSHandle<GlobalEnv> env = thread->GetGlobalEnv();
5630     JSHandle<JSTaggedValue> objFuncProto = env->GetObjectFunctionPrototype();
5631     JSHandle<JSHClass> classPrototypeHClass =
5632         NewEcmaHClass(JSObject::SIZE, inlinedProps, JSType::JS_OBJECT, objFuncProto);
5633     JSHandle<LayoutInfo> layoutInfoHandle = CreateLayoutInfo(static_cast<int>(inlinedProps));
5634     // Check if need grow LayoutInfo capacity
5635     classPrototypeHClass->SetLayout(thread_, layoutInfoHandle);
5636     return classPrototypeHClass;
5637 }
5638 
CreateClassFuncHClass(const JSThread * thread,size_t inlinedStaticPropCount)5639 JSHandle<JSHClass> ObjectFactory::CreateClassFuncHClass(const JSThread *thread, size_t inlinedStaticPropCount)
5640 {
5641     JSHandle<GlobalEnv> env = thread->GetGlobalEnv();
5642     size_t inlinedProps = inlinedStaticPropCount + JSHClass::DEFAULT_CAPACITY_OF_IN_OBJECTS;
5643     return CreateFunctionClass(ecmascript::FunctionKind::CLASS_CONSTRUCTOR, JSFunction::SIZE, JSType::JS_FUNCTION,
5644                                env->GetFunctionPrototype(), inlinedProps);
5645 }
5646 
FillFreeMemoryRange(uintptr_t start,uintptr_t end)5647 void ObjectFactory::FillFreeMemoryRange(uintptr_t start, uintptr_t end)
5648 {
5649     ASSERT(start <= end);
5650     ASSERT(start % static_cast<uint8_t>(MemAlignment::MEM_ALIGN_OBJECT) == 0);
5651     ASSERT(end % static_cast<uint8_t>(MemAlignment::MEM_ALIGN_OBJECT) == 0);
5652     while (start < end) {
5653         Barriers::SetPrimitive<JSTaggedType>(reinterpret_cast<void*>(start), 0, FREE_MEMMORY_ADDRESS_ZAM_VALUE);
5654         start += sizeof(JSTaggedType);
5655     }
5656 }
5657 }  // namespace panda::ecmascript
5658