Parse module or component from file path. See "include/loader/loader.h".
| 65 | |
| 66 | // Parse module or component from file path. See "include/loader/loader.h". |
| 67 | Expect<std::variant<std::unique_ptr<AST::Component::Component>, |
| 68 | std::unique_ptr<AST::Module>>> |
| 69 | Loader::parseWasmUnit(const std::filesystem::path &FilePath) { |
| 70 | std::lock_guard Lock(Mutex); |
| 71 | |
| 72 | // Set path and check the header. |
| 73 | EXPECTED_TRY(FMgr.setPath(FilePath).map_error([&FilePath](auto E) { |
| 74 | spdlog::error(E); |
| 75 | spdlog::error(ErrInfo::InfoFile(FilePath)); |
| 76 | return E; |
| 77 | })); |
| 78 | |
| 79 | auto ReportError = [&FilePath](auto E) { |
| 80 | spdlog::error(ErrInfo::InfoFile(FilePath)); |
| 81 | return E; |
| 82 | }; |
| 83 | |
| 84 | switch (FMgr.getHeaderType()) { |
| 85 | // Filter out the Windows .dll, macOS .dylib, or Linux .so AOT compiled |
| 86 | // shared-library-WASM. |
| 87 | case FileMgr::FileHeader::ELF: |
| 88 | case FileMgr::FileHeader::DLL: |
| 89 | case FileMgr::FileHeader::MachO_32: |
| 90 | case FileMgr::FileHeader::MachO_64: { |
| 91 | // Open the shared library long enough to validate its WasmEdge AOT |
| 92 | // version and extract the embedded WASM bytes. Whether the native |
| 93 | // handle stays alive depends on the configured RunMode. |
| 94 | WASMType = InputType::SharedLibrary; |
| 95 | FMgr.reset(); |
| 96 | std::shared_ptr<SharedLibrary> Library = std::make_shared<SharedLibrary>(); |
| 97 | EXPECTED_TRY(Library->load(FilePath).map_error(ReportError)); |
| 98 | EXPECTED_TRY(auto Version, Library->getVersion().map_error(ReportError)); |
| 99 | if (Version != AOT::kBinaryVersion) { |
| 100 | spdlog::error(ErrInfo::InfoMismatch(AOT::kBinaryVersion, Version)); |
| 101 | spdlog::error(ErrInfo::InfoFile(FilePath)); |
| 102 | return Unexpect(ErrCode::Value::MalformedVersion); |
| 103 | } |
| 104 | |
| 105 | EXPECTED_TRY(auto Code, Library->getWasm().map_error(ReportError)); |
| 106 | |
| 107 | if (Conf.getRuntimeConfigure().getRunMode() != RunMode::AOT) { |
| 108 | // Non-AOT mode: drop the native handle now and re-parse the embedded |
| 109 | // WASM bytes as plain WASM. No AOT function symbol from the shared |
| 110 | // library is resolved or called. |
| 111 | Library.reset(); |
| 112 | return parseWasmUnit(Code); |
| 113 | } |
| 114 | |
| 115 | // AOT mode: keep the library alive and load executable symbols. |
| 116 | EXPECTED_TRY(FMgr.setCode(Code).map_error(ReportError)); |
| 117 | EXPECTED_TRY(auto Unit, loadUnit().map_error(ReportError)); |
| 118 | if (auto Ptr = std::get_if<std::unique_ptr<AST::Module>>(&Unit); |
| 119 | likely(!!Ptr)) { |
| 120 | EXPECTED_TRY(loadExecutable(**Ptr, Library).map_error(ReportError)); |
| 121 | } else { |
| 122 | spdlog::error("Component Module is not supported in AOT."sv); |
| 123 | spdlog::error(ErrInfo::InfoFile(FilePath)); |
| 124 | return Unexpect(ErrCode::Value::IllegalGrammar); |