• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2025 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #ifndef ECMASCRIPT_MODULE_JS_MODULE_SOURCE_TEXT_H
17 #define ECMASCRIPT_MODULE_JS_MODULE_SOURCE_TEXT_H
18 
19 #include "ecmascript/base/string_helper.h"
20 #include "ecmascript/mem/c_containers.h"
21 #include "ecmascript/module/js_module_record.h"
22 #include "ecmascript/module/js_module_entry.h"
23 #include "ecmascript/tagged_array.h"
24 #include "ecmascript/sendable_env.h"
25 
26 namespace panda::ecmascript {
27 using ResolvedMultiMap = CUnorderedMultiMap<CString *, JSHandle<JSTaggedValue>>;
28 struct StateVisit;
29 enum class ModuleStatus : uint8_t {
30     // don't change order
31     UNINSTANTIATED = 0x0,
32     PREINSTANTIATING,
33     INSTANTIATING,
34     INSTANTIATED,
35     EVALUATING,
36     EVALUATING_ASYNC,
37     EVALUATED,
38     ERRORED
39 };
40 
41 enum class ModuleTypes : uint8_t {
42     ECMA_MODULE = 0x01,
43     CJS_MODULE,
44     JSON_MODULE,
45     NATIVE_MODULE,
46     OHOS_MODULE,
47     APP_MODULE,
48     INTERNAL_MODULE,
49     UNKNOWN,
50     STATIC_MODULE
51 };
52 
53 enum class LoadingTypes : uint8_t {
54     STABLE_MODULE = 0x01,
55     DYNAMITC_MODULE,
56     OTHERS
57 };
58 
59 enum class SharedTypes : uint8_t {
60     UNSENDABLE_MODULE = 0x01,
61     SENDABLE_FUNCTION_MODULE,
62     SHARED_MODULE,
63     TOTAL_KINDS,
64 };
65 
66 class SourceTextModule final : public ModuleRecord {
67 public:
68     static constexpr int UNDEFINED_INDEX = -1;
69     static constexpr int MODULE_ERROR = 1;
70     static constexpr size_t DEFAULT_DICTIONART_CAPACITY = 2;
71     static constexpr size_t DEFAULT_ARRAY_CAPACITY = 2;
72     static constexpr uint8_t DEREGISTER_MODULE_TAG = 1;
73     static constexpr uint32_t FIRST_ASYNC_EVALUATING_ORDINAL = 2;
74     static constexpr uint32_t NOT_ASYNC_EVALUATED = 0;
75     static constexpr uint32_t ASYNC_EVALUATE_DID_FINISH = 1;
76     static constexpr bool SHARED_MODULE_TAG = true;
77 
78     struct AsyncEvaluatingOrdinalCompare {
operatorAsyncEvaluatingOrdinalCompare79         bool operator()(const JSHandle<SourceTextModule> &lhs, const JSHandle<SourceTextModule> &rhs) const
80         {
81             return lhs->GetAsyncEvaluatingOrdinal() < rhs->GetAsyncEvaluatingOrdinal();
82         }
83     };
84     struct MutableFields {
85         JSTaggedValue TopLevelCapability;
86         JSTaggedValue NameDictionary;
87         JSTaggedValue CycleRoot;
88         JSTaggedValue AsyncParentModules;
89         JSTaggedValue SendableEnv;
90         JSTaggedValue Exception;
91         JSTaggedValue Namespace;
92     };
93     using AsyncParentCompletionSet =
94       CSet<JSHandle<SourceTextModule>, AsyncEvaluatingOrdinalCompare>;
95 
96     CAST_CHECK(SourceTextModule, IsSourceTextModule);
97 
98     static void StoreAndResetMutableFields(JSThread *thread, JSHandle<SourceTextModule> module, MutableFields &fields);
99     static void RestoreMutableFields(JSThread *thread, JSHandle<SourceTextModule> module, MutableFields &fields);
100     // 15.2.1.16.2 GetExportedNames(exportStarSet)
101     static CVector<std::string> GetExportedNames(JSThread *thread, const JSHandle<SourceTextModule> &module,
102                                                  const JSHandle<TaggedArray> &exportStarSet);
103 
104     // 15.2.1.16.3 ResolveExport(exportName, resolvedMap)
105     static JSHandle<JSTaggedValue> ResolveExport(JSThread *thread, const JSHandle<SourceTextModule> &module,
106         const JSHandle<JSTaggedValue> &exportName, ResolvedMultiMap &resolvedMap);
107     static JSHandle<JSTaggedValue> ResolveExportObject(JSThread *thread, const JSHandle<SourceTextModule> &module,
108                                                        const JSHandle<JSTaggedValue> &exportObject,
109                                                        const JSHandle<JSTaggedValue> &exportName);
110     static JSHandle<JSTaggedValue> ResolveNativeStarExport(JSThread *thread,
111                                                            const JSHandle<SourceTextModule> &nativeModule,
112                                                            const JSHandle<JSTaggedValue> &exportName);
113     static JSHandle<JSTaggedValue> ResolveCjsStarExport(JSThread *thread,
114                                                         const JSHandle<SourceTextModule> &cjsModule,
115                                                         const JSHandle<JSTaggedValue> &exportName);
116 
117     // 15.2.1.16.4.2 ModuleDeclarationEnvironmentSetup ( module )
118     static void ModuleDeclarationEnvironmentSetup(JSThread *thread, const JSHandle<SourceTextModule> &module);
119     static void ModuleDeclarationArrayEnvironmentSetup(JSThread *thread, const JSHandle<SourceTextModule> &module);
120 
121     // 15.2.1.16.5.1 InnerModuleEvaluation ( module, stack, index )
122     static int InnerModuleEvaluation(JSThread *thread, JSHandle<SourceTextModule> &moduleRecord,
123         CVector<JSHandle<SourceTextModule>> &stack, CVector<JSHandle<SourceTextModule>> &errorStack,
124         int index, const void *buffer = nullptr, size_t size = 0,
125         const ExecuteTypes &executeType = ExecuteTypes::STATIC);
126 
127     static int InnerModuleEvaluationUnsafe(JSThread *thread,
128         JSHandle<SourceTextModule> &module, CVector<JSHandle<SourceTextModule>> &stack,
129         CVector<JSHandle<SourceTextModule>> &errorStack, int index, const void *buffer,
130         size_t size, const ExecuteTypes &executeType);
131     // 15.2.1.16.5.2 ModuleExecution ( module )
132     static Expected<JSTaggedValue, bool> ModuleExecution(JSThread *thread, const JSHandle<SourceTextModule> &module,
133                                  const void *buffer = nullptr, size_t size = 0,
134                                  const ExecuteTypes &executeType = ExecuteTypes::STATIC);
135 
136     // 16.2.1.5.3.2 ExecuteAsyncModule ( module )
137     static void ExecuteAsyncModule(JSThread *thread, const JSHandle<SourceTextModule> &module,
138                                    const void *buffer = nullptr, size_t size = 0,
139                                    const ExecuteTypes &executeType = ExecuteTypes::STATIC);
140 
141     // 16.2.1.5.3.3 GatherAvailableAncestors ( module, execList )
142     static void GatherAvailableAncestors(JSThread *thread, const JSHandle<SourceTextModule> &module,
143                                          AsyncParentCompletionSet &execList);
144 
145     // 16.2.1.5.3.4 AsyncModuleExecutionFulfilled ( module )
146     static void AsyncModuleExecutionFulfilled(JSThread *thread, const JSHandle<SourceTextModule> &module);
147 
148     // 16.2.1.5.3.5 AsyncModuleExecutionRejected ( module, error )
149     static void AsyncModuleExecutionRejected(JSThread *thread, const JSHandle<SourceTextModule> &module,
150                                              JSTaggedValue error);
151 
152     static JSTaggedValue AsyncModuleFulfilledFunc(EcmaRuntimeCallInfo *argv);
153     static JSTaggedValue AsyncModuleRejectedFunc(EcmaRuntimeCallInfo *argv);
154     static void AddAsyncParentModule(JSThread *thread, JSHandle<SourceTextModule> &module,
155                                      JSHandle<SourceTextModule> &parent);
156     // 15.2.1.18 Runtime Semantics: GetModuleNamespace ( module )
157     static JSHandle<JSTaggedValue> GetModuleNamespace(JSThread *thread, const JSHandle<SourceTextModule> &module);
158 
159     static void AddImportEntry(JSThread *thread, const JSHandle<SourceTextModule> &module,
160                                const JSHandle<ImportEntry> &importEntry, size_t idx, uint32_t len);
161     static void AddLocalExportEntry(JSThread *thread, const JSHandle<SourceTextModule> &module,
162                                     const JSHandle<LocalExportEntry> &exportEntry, size_t idx, uint32_t len);
163     static void AddIndirectExportEntry(JSThread *thread, const JSHandle<SourceTextModule> &module,
164                                        const JSHandle<IndirectExportEntry> &exportEntry, size_t idx, uint32_t len);
165     static void AddStarExportEntry(JSThread *thread, const JSHandle<SourceTextModule> &module,
166                                    const JSHandle<StarExportEntry> &exportEntry, size_t idx, uint32_t len);
167     static bool IsNativeModule(const CString &moduleRequestName);
168     static ModuleTypes GetNativeModuleType(const CString &moduleRequestName);
169     static JSHandle<JSTaggedValue> GetRequireNativeModuleFunc(EcmaVM *vm, ModuleTypes moduleType);
170     static EcmaRuntimeCallInfo* MakeNormalizedAppArgs(const EcmaVM *vm, JSHandle<JSTaggedValue> func,
171         const CString &soPath, const CString &moduleName);
172     static EcmaRuntimeCallInfo* MakeAppArgs(const EcmaVM *vm, JSHandle<JSTaggedValue> func, const CString &soPath,
173         const CString &moduleName, const CString &requestName);
174     static EcmaRuntimeCallInfo* MakeInternalArgs(const EcmaVM *vm, JSHandle<JSTaggedValue> func, const CString &soPath,
175         const CString &moduleRequestName);
176     static JSHandle<JSTaggedValue> LoadNativeModuleCallFunc(EcmaVM *vm, EcmaRuntimeCallInfo* info);
177     static JSHandle<JSTaggedValue> LoadNativeModuleImpl(EcmaVM *vm, JSThread *thread,
178         const JSHandle<SourceTextModule> &requiredModule, ModuleTypes moduleType);
179     static JSHandle<JSTaggedValue> LoadNativeModuleMayThrowError(JSThread *thread,
180         const JSHandle<SourceTextModule> &requiredModule, ModuleTypes moduleType);
181     static bool LoadNativeModule(JSThread *thread, const JSHandle<SourceTextModule> &requiredModule,
182                                  ModuleTypes moduleType);
183     bool CheckAndThrowModuleError(JSThread *thread);
IsNativeModule(ModuleTypes moduleType)184     inline static bool IsNativeModule(ModuleTypes moduleType)
185     {
186         return moduleType == ModuleTypes::OHOS_MODULE ||
187                moduleType == ModuleTypes::APP_MODULE ||
188                moduleType == ModuleTypes::NATIVE_MODULE ||
189                moduleType == ModuleTypes::INTERNAL_MODULE;
190     }
191 
GetResolveErrorReason(const JSHandle<JSTaggedValue> & resolution)192     inline static CString GetResolveErrorReason(const JSHandle<JSTaggedValue> &resolution)
193     {
194         ASSERT(resolution->IsNull() || resolution->IsString());
195         return resolution->IsNull() ? "' does not provide an export name '"
196                                     : "' provide an ambiguous export name '";
197     }
198 
IsCjsModule(ModuleTypes moduleType)199     inline static bool IsCjsModule(ModuleTypes moduleType)
200     {
201         return moduleType == ModuleTypes::CJS_MODULE;
202     }
203 
IsJsonModule(ModuleTypes moduleType)204     inline static bool IsJsonModule(ModuleTypes moduleType)
205     {
206         return moduleType == ModuleTypes::JSON_MODULE;
207     }
208 
IsModuleInSharedHeap(JSHandle<SourceTextModule> currentModule)209     inline static bool IsModuleInSharedHeap(JSHandle<SourceTextModule> currentModule)
210     {
211         return currentModule->GetSharedType() > SharedTypes::UNSENDABLE_MODULE;
212     }
213 
IsSharedModule(JSHandle<SourceTextModule> currentModule)214     inline static bool IsSharedModule(JSHandle<SourceTextModule> currentModule)
215     {
216         return currentModule->GetSharedType() == SharedTypes::SHARED_MODULE;
217     }
218 
219     static bool IsEvaluatedModule(JSThread *thread, StateVisit &stateVisit,
220         const JSHandle<SourceTextModule> &module);
221 
222     static ModuleStatus GetModuleEvaluatingType(JSThread *thread, StateVisit &stateVisit,
223         const JSHandle<SourceTextModule> &module);
224 
IsSendableFunctionModule(JSTaggedValue currentModule)225     inline static bool IsSendableFunctionModule(JSTaggedValue currentModule)
226     {
227         return SourceTextModule::Cast(currentModule.GetTaggedObject())->GetSharedType() ==
228             SharedTypes::SENDABLE_FUNCTION_MODULE;
229     }
230 
GetLazyImportStatusArray()231     inline bool *GetLazyImportStatusArray()
232     {
233         return reinterpret_cast<bool *>(GetLazyImportStatus());
234     }
235 
SetLazyImportArray(bool * lazyImportArray)236     inline void SetLazyImportArray(bool *lazyImportArray)
237     {
238         if (lazyImportArray != nullptr) {
239             DestoryLazyImportArray();
240         }
241         SetLazyImportStatus(ToUintPtr(lazyImportArray));
242     }
243 
DestoryLazyImportArray()244     inline void DestoryLazyImportArray()
245     {
246         delete GetLazyImportStatusArray();
247         SetLazyImportStatus(ToUintPtr(nullptr));
248     }
249 
IsLazyImportModule(size_t index)250     inline bool IsLazyImportModule(size_t index)
251     {
252         bool *lazyArray = GetLazyImportStatusArray();
253         if (lazyArray == nullptr) {
254             return false;
255         }
256         return lazyArray[index];
257     }
258 
GetEcmaModuleFilenameString()259     inline CString GetEcmaModuleFilenameString() const
260     {
261         CString *fileName = reinterpret_cast<CString *>(GetEcmaModuleFilename());
262         if (fileName == nullptr) {
263             return CString();
264         }
265         return *fileName;
266     }
267 
GetEcmaModuleRecordNameString()268     inline CString GetEcmaModuleRecordNameString() const
269     {
270         CString *recordName = reinterpret_cast<CString *>(GetEcmaModuleRecordName());
271         if (recordName == nullptr) {
272             return CString();
273         }
274         return *recordName;
275     }
276 
GetModuleName(const JSHandle<SourceTextModule> & module)277     static inline CString* GetModuleName(const JSHandle<SourceTextModule> &module)
278     {
279         CString* moduleName = reinterpret_cast<CString *>(module->GetEcmaModuleRecordName());
280         if (UNLIKELY(moduleName == nullptr)) {
281             return reinterpret_cast<CString *>(module->GetEcmaModuleFilename());
282         }
283         return moduleName;
284     }
285 
SetEcmaModuleFilenameString(const CString & fileName)286     inline void SetEcmaModuleFilenameString(const CString &fileName)
287     {
288         CString *ptr = new CString(fileName);
289         DestoryEcmaModuleFilenameString();
290         SetEcmaModuleFilename(ToUintPtr(ptr));
291     }
292 
SetEcmaModuleRecordNameString(const CString & recordName)293     inline void SetEcmaModuleRecordNameString(const CString &recordName)
294     {
295         CString *ptr = new CString(recordName);
296         DestoryEcmaModuleRecordNameString();
297         SetEcmaModuleRecordName(ToUintPtr(ptr));
298     }
299 
DestoryEcmaModuleFilenameString()300     inline void DestoryEcmaModuleFilenameString()
301     {
302         CString *ptr = reinterpret_cast<CString *>(GetEcmaModuleFilename());
303         delete ptr;
304         SetEcmaModuleFilename(ToUintPtr(nullptr));
305     }
306 
DestoryEcmaModuleRecordNameString()307     inline void DestoryEcmaModuleRecordNameString()
308     {
309         CString *ptr = reinterpret_cast<CString *>(GetEcmaModuleRecordName());
310         delete ptr;
311         SetEcmaModuleRecordName(ToUintPtr(nullptr));
312     }
313 
SetLazyImportArrayForDeserialize(bool * lazyImportArray)314     inline void SetLazyImportArrayForDeserialize(bool *lazyImportArray)
315     {
316         SetLazyImportStatus(ToUintPtr(lazyImportArray));
317     }
318 
SetEcmaModuleFilenameStringForDeserialize(const CString & fileName)319     inline void SetEcmaModuleFilenameStringForDeserialize(const CString &fileName)
320     {
321         CString *ptr = new CString(fileName);
322         SetEcmaModuleFilename(ToUintPtr(ptr));
323     }
324 
SetEcmaModuleRecordNameStringForDeserialize(const CString & recordName)325     inline void SetEcmaModuleRecordNameStringForDeserialize(const CString &recordName)
326     {
327         CString *ptr = new CString(recordName);
328         SetEcmaModuleRecordName(ToUintPtr(ptr));
329     }
330 
331     static constexpr size_t SOURCE_TEXT_MODULE_OFFSET = ModuleRecord::SIZE;
332     ACCESSORS(Environment, SOURCE_TEXT_MODULE_OFFSET, NAMESPACE_OFFSET);
333     ACCESSORS(Namespace, NAMESPACE_OFFSET, MODULE_REQUESTS_OFFSET);
334     ACCESSORS(ModuleRequests, MODULE_REQUESTS_OFFSET, REQUESTED_MODULES_OFFSET);
335     ACCESSORS(RequestedModules, REQUESTED_MODULES_OFFSET, IMPORT_ENTRIES_OFFSET);
336     ACCESSORS(ImportEntries, IMPORT_ENTRIES_OFFSET, LOCAL_EXPORT_ENTTRIES_OFFSET);
337     ACCESSORS(LocalExportEntries, LOCAL_EXPORT_ENTTRIES_OFFSET, INDIRECT_EXPORT_ENTTRIES_OFFSET);
338     ACCESSORS(IndirectExportEntries, INDIRECT_EXPORT_ENTTRIES_OFFSET, START_EXPORT_ENTTRIES_OFFSET);
339     ACCESSORS(StarExportEntries, START_EXPORT_ENTTRIES_OFFSET, NAME_DICTIONARY_OFFSET);
340     ACCESSORS(NameDictionary, NAME_DICTIONARY_OFFSET, CYCLE_ROOT_OFFSET);
341     ACCESSORS(CycleRoot, CYCLE_ROOT_OFFSET, TOP_LEVEL_CAPABILITY_OFFSET);
342     ACCESSORS(TopLevelCapability, TOP_LEVEL_CAPABILITY_OFFSET, ASYNC_PARENT_MODULES_OFFSET);
343     ACCESSORS(AsyncParentModules, ASYNC_PARENT_MODULES_OFFSET, SENDABLE_ENV_OFFSET);
344     ACCESSORS(SendableEnv, SENDABLE_ENV_OFFSET, EXCEPTION_OFFSET);
345     ACCESSORS(Exception, EXCEPTION_OFFSET, DFS_ANCESTOR_INDEX_OFFSET);
346     ACCESSORS_PRIMITIVE_FIELD(DFSAncestorIndex, int32_t, DFS_ANCESTOR_INDEX_OFFSET, DFS_INDEX_OFFSET);
347     ACCESSORS_PRIMITIVE_FIELD(DFSIndex, int32_t, DFS_INDEX_OFFSET, ASYNC_EVALUATION_OFFSET);
348     ACCESSORS_PRIMITIVE_FIELD(AsyncEvaluatingOrdinal, uint32_t, ASYNC_EVALUATION_OFFSET, PENDING_DEPENDENCIES_OFFSET);
349     ACCESSORS_PRIMITIVE_FIELD(PendingAsyncDependencies,
350         int32_t, PENDING_DEPENDENCIES_OFFSET, LAYZ_IMPORT_STATUS_OFFSET);
351     ACCESSORS_PRIMITIVE_FIELD(LazyImportStatus, uintptr_t, LAYZ_IMPORT_STATUS_OFFSET, ECMA_MODULE_FILENAME);
352     ACCESSORS_PRIMITIVE_FIELD(EcmaModuleFilename, uintptr_t, ECMA_MODULE_FILENAME, ECMA_MODULE_RECORDNAME);
353     ACCESSORS_PRIMITIVE_FIELD(EcmaModuleRecordName, uintptr_t, ECMA_MODULE_RECORDNAME, BIT_FIELD_OFFSET);
354     ACCESSORS_BIT_FIELD(BitField, BIT_FIELD_OFFSET, LAST_OFFSET)
355 
356     DEFINE_ALIGN_SIZE(LAST_OFFSET);
357 
358     // define BitField
359     static constexpr size_t STATUS_BITS = 3;
360     static constexpr size_t MODULE_TYPE_BITS = 4;
361     static constexpr size_t IS_NEW_BC_VERSION_BITS = 1;
362     static constexpr size_t HASTLA_BITS = 1;
363     static constexpr size_t LOADING_TYPE_BITS = 3;
364     static constexpr uint16_t REGISTER_COUNTS = 16;
365     static constexpr size_t IS_SHARED_TYPE_BITS = 2;
366     static constexpr size_t SHARED_TYPES_SHIFT = STATUS_BITS + MODULE_TYPE_BITS + IS_NEW_BC_VERSION_BITS +
367                                                  HASTLA_BITS + LOADING_TYPE_BITS + REGISTER_COUNTS;
368 
369     FIRST_BIT_FIELD(BitField, Status, ModuleStatus, STATUS_BITS)
370     NEXT_BIT_FIELD(BitField, Types, ModuleTypes, MODULE_TYPE_BITS, Status)
371     NEXT_BIT_FIELD(BitField, IsNewBcVersion, bool, IS_NEW_BC_VERSION_BITS, Types)
372     NEXT_BIT_FIELD(BitField, HasTLA, bool, HASTLA_BITS, IsNewBcVersion)
373     NEXT_BIT_FIELD(BitField, LoadingTypes, LoadingTypes, LOADING_TYPE_BITS, HasTLA)
374     NEXT_BIT_FIELD(BitField, RegisterCounts, uint16_t, REGISTER_COUNTS, LoadingTypes)
375     NEXT_BIT_FIELD(BitField, SharedType, SharedTypes, IS_SHARED_TYPE_BITS, RegisterCounts)
376 
377     static_assert(static_cast<size_t>(SharedTypes::TOTAL_KINDS) <= (1 << IS_SHARED_TYPE_BITS));
378 
379     DECL_DUMP()
380     DECL_VISIT_OBJECT(SOURCE_TEXT_MODULE_OFFSET, DFS_ANCESTOR_INDEX_OFFSET)
381 
382     // 15.2.1.16.5 Evaluate()
383     static JSTaggedValue Evaluate(JSThread *thread, const JSHandle<SourceTextModule> &module,
384                          const void *buffer = nullptr, size_t size = 0,
385                          const ExecuteTypes &executeType = ExecuteTypes::STATIC);
386 
387     // 15.2.1.16.4 Instantiate()
388     static int PUBLIC_API Instantiate(JSThread *thread,
389                                       const JSHandle<JSTaggedValue> &moduleHdl,
390                                       const ExecuteTypes &executeType = ExecuteTypes::STATIC);
391 
392     static bool EvaluateNativeModule(JSThread *thread, JSHandle<SourceTextModule> nativeModule,
393                                      ModuleTypes moduleType);
394 
395     JSTaggedValue GetModuleValue(JSThread *thread, int32_t index, bool isThrow);
396     static void StoreModuleValue(JSThread *thread, const JSHandle<SourceTextModule> &module, int32_t index,
397                                  const JSHandle<JSTaggedValue> &value);
398 
399     JSTaggedValue GetModuleValue(JSThread *thread, JSTaggedValue key, bool isThrow);
400     static void StoreModuleValue(JSThread *thread, const JSHandle<SourceTextModule> &module,
401                                  const JSHandle<JSTaggedValue> &key, const JSHandle<JSTaggedValue> &value);
402 
403     static JSTaggedValue GetValueFromExportObject(JSThread *thread, JSHandle<JSTaggedValue> &exportObject,
404         int32_t index);
405 
406     static JSHandle<JSTaggedValue> ResolveIndirectExport(JSThread *thread,
407                                                          const JSHandle<JSTaggedValue> &exportEntry,
408                                                          const JSHandle<JSTaggedValue> &exportName,
409                                                          const JSHandle<SourceTextModule> &module,
410                                                          ResolvedMultiMap &resolvedMap);
411     static CString GetModuleName(JSTaggedValue currentModule);
412 
413     static bool IsDynamicModule(LoadingTypes types);
414 
415     // taskpool
416     static std::optional<std::set<uint32_t>> GetConcurrentRequestedModules(JSThread *thread,
417         const JSHandle<Method> &method);
418     static int EvaluateForConcurrent(JSThread *thread, const JSHandle<SourceTextModule> &module,
419                                      const JSHandle<Method> &method);
420     static int ModuleEvaluation(JSThread *thread, const JSHandle<SourceTextModule> &module,
421                                 int index, const JSHandle<Method> &method);
422     static void CheckCircularImportTool(JSThread *thread, const CString &circularModuleRecordName,
423                                         CList<CString> &referenceList, bool printOtherCircular = false);
424 
425     static void CheckResolvedBinding(JSThread *thread, const JSHandle<SourceTextModule> &module);
426     static bool IsCircular(const CList<CString> &referenceList, const CString &requiredModuleName);
427     static void PrintCircular(const CList<CString> &referenceList, Level level);
428     static void SearchCircularImport(JSThread *thread, const CString &circularModuleRecordName,
429                                      const JSHandle<SourceTextModule> &module, CList<CString> &referenceList,
430                                      CString &requiredModuleName, bool printOtherCircular);
431     static void CheckResolvedIndexBinding(JSThread *thread, const JSHandle<SourceTextModule> &module);
432     static void SetExportName(JSThread *thread, const JSHandle<SourceTextModule> requestedModule,
433                               CVector<std::string> &exportedNames, JSHandle<TaggedArray> &newExportStarSet);
434     static void RecordEvaluatedOrError(JSThread *thread, JSHandle<SourceTextModule> module);
435     static JSHandle<SourceTextModule> GetModuleFromCacheOrResolveNewOne(JSThread *thread,
436         const JSHandle<SourceTextModule> module, const JSHandle<TaggedArray> requestedModules, uint32_t idx);
437     static bool PreModuleInstantiation(JSThread *thread,
438                                        JSHandle<SourceTextModule> module,
439                                        const ExecuteTypes &executeType);
440     static int FinishModuleInstantiation(JSThread *thread,
441                                          JSHandle<SourceTextModule> module,
442                                          CVector<JSHandle<SourceTextModule>> &stack,
443                                          int index, JSHandle<JSTaggedValue> exception);
444     static JSHandle<JSTaggedValue> CreateBindingByIndexBinding(JSThread* thread,
445                                                                JSHandle<ResolvedIndexBinding> binding,
446                                                                bool isShared);
447 
448     // Find function in JsModuleSourceText For Hook
449     static JSHandle<JSTaggedValue> FindFuncInModuleForHook(JSThread* thread, const std::string &recordName,
450                                                            const std::string &namespaceName,
451                                                            const std::string &className,
452                                                            const std::string &funcName);
453 
454 private:
455     static JSHandle<JSTaggedValue> GetStarResolution(JSThread *thread,
456                                                      const JSHandle<JSTaggedValue> &exportName,
457                                                      const JSHandle<SourceTextModule> importedModule,
458                                                      JSMutableHandle<JSTaggedValue> &starResolution,
459                                                      ResolvedMultiMap &resolvedMap);
460     template <typename T>
461     static void AddExportName(JSThread *thread, const JSTaggedValue &exportEntry, CVector<std::string> &exportedNames);
462     static JSHandle<JSTaggedValue> ResolveLocalExport(JSThread *thread, const JSHandle<JSTaggedValue> &exportEntry,
463                                                       const JSHandle<JSTaggedValue> &exportName,
464                                                       const JSHandle<SourceTextModule> &module);
465     static JSHandle<JSTaggedValue> ResolveElementOfObject(JSThread *thread,
466                                                          const JSHandle<JSHClass> &hclass,
467                                                          const JSHandle<JSTaggedValue> &exportName,
468                                                          const JSHandle<SourceTextModule> &module);
469     static bool CheckCircularImport(JSThread *thread,
470                                     const JSHandle<SourceTextModule> &module,
471                                     const JSHandle<JSTaggedValue> &exportName,
472                                     ResolvedMultiMap &resolvedMap);
473     static JSTaggedValue FindByExport(JSThread *thread, const JSTaggedValue &exportEntriesTv, const JSTaggedValue &key,
474                                       const JSTaggedValue &dictionary);
475     static void DFSModuleInstantiation(JSThread *thread,
476                                        JSHandle<SourceTextModule> &module,
477                                        CVector<JSHandle<SourceTextModule>> &stack);
478     static int HandleInstantiateException(JSHandle<SourceTextModule> &module,
479                                           const CVector<JSHandle<SourceTextModule>> &stack, int result);
480     static void HandleEvaluateResult(JSThread *thread, JSHandle<SourceTextModule> &module,
481                                      JSHandle<JSPromise> &capability,
482                                      const CVector<JSHandle<SourceTextModule>> &stack,
483                                      const CVector<JSHandle<SourceTextModule>> &errorStack);
484     static void HandleConcurrentEvaluateResult(JSThread *thread, JSHandle<SourceTextModule> &module,
485                                                const CVector<JSHandle<SourceTextModule>> &stack,
486                                                const CVector<JSHandle<SourceTextModule>> &errorStack);
487     bool IsAsyncEvaluating();
488     static void HandleEvaluateException(JSThread *thread,
489                                         const CVector<JSHandle<SourceTextModule>> &stack,
490                                         JSHandle<JSTaggedValue> exception);
491     static void HandleErrorStack(JSThread *thread, const CVector<JSHandle<SourceTextModule>> &errorStack);
492     static void SetExceptionToModule(JSThread *thread, JSHandle<SourceTextModule> module,
493                                      JSTaggedValue exception);
494     static JSHandle<JSTaggedValue> GetRequestedModuleMayThrowError(JSThread *thread,
495                                                                    const JSHandle<SourceTextModule> module,
496                                                                    uint32_t idx,
497                                                                    const JSHandle<TaggedArray> requestedModules,
498                                                                    JSHandle<JSTaggedValue> exception);
499     static void SetRequestedModules(JSThread *thread, JSHandle<TaggedArray> requestedModules,
500                                     uint32_t idx, JSHandle<JSTaggedValue> requiredModule, bool isShared);
501 
502     static JSHandle<JSTaggedValue> GetBindingNameByIndex(JSThread *thread,
503                                                          const JSHandle<SourceTextModule> module,
504                                                          const int index);
505 
506     friend class EcmaModuleTest;
507     friend class SharedModuleManager;
508 };
509 
510 class ResolvedBinding final : public Record {
511 public:
512     CAST_CHECK(ResolvedBinding, IsResolvedBinding);
513 
514     static constexpr size_t MODULE_OFFSET = Record::SIZE;
515     ACCESSORS(Module, MODULE_OFFSET, BINDING_NAME_OFFSET);
516     ACCESSORS(BindingName, BINDING_NAME_OFFSET, SIZE);
517 
518     DECL_DUMP()
519     DECL_VISIT_OBJECT(MODULE_OFFSET, SIZE)
520 };
521 class ResolvedIndexBinding final : public Record {
522 public:
523     CAST_CHECK(ResolvedIndexBinding, IsResolvedIndexBinding);
524 
525     static constexpr size_t MODULE_OFFSET = Record::SIZE;
526     ACCESSORS(Module, MODULE_OFFSET, INDEX_OFFSET);
527     ACCESSORS_PRIMITIVE_FIELD(Index, int32_t, INDEX_OFFSET, BIT_FIELD_OFFSET);
528     ACCESSORS_BIT_FIELD(BitField, BIT_FIELD_OFFSET, END_OFFSET)
529     DEFINE_ALIGN_SIZE(END_OFFSET);
530 
531     static constexpr size_t IS_UPDATED_FROM_RESOLVED_BINDING_BITS = 1;
532     FIRST_BIT_FIELD(BitField, IsUpdatedFromResolvedBinding, bool, IS_UPDATED_FROM_RESOLVED_BINDING_BITS)
533     DECL_DUMP()
534     DECL_VISIT_OBJECT(MODULE_OFFSET, INDEX_OFFSET)
535 };
536 }  // namespace panda::ecmascript
537 #endif  // ECMASCRIPT_MODULE_JS_MODULE_SOURCE_TEXT_H
538