1 //===--- SimpleExecutorDylibManager.cpp - Executor-side dylib management --===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8
9 #include "llvm/ExecutionEngine/Orc/TargetProcess/SimpleExecutorDylibManager.h"
10
11 #include "llvm/ExecutionEngine/Orc/Shared/OrcRTBridge.h"
12 #include "llvm/Support/FormatVariadic.h"
13
14 #define DEBUG_TYPE "orc"
15
16 namespace llvm {
17 namespace orc {
18 namespace rt_bootstrap {
19
~SimpleExecutorDylibManager()20 SimpleExecutorDylibManager::~SimpleExecutorDylibManager() {
21 assert(Dylibs.empty() && "shutdown not called?");
22 }
23
24 Expected<tpctypes::DylibHandle>
open(const std::string & Path,uint64_t Mode)25 SimpleExecutorDylibManager::open(const std::string &Path, uint64_t Mode) {
26 if (Mode != 0)
27 return make_error<StringError>("open: non-zero mode bits not yet supported",
28 inconvertibleErrorCode());
29
30 const char *PathCStr = Path.empty() ? nullptr : Path.c_str();
31 std::string ErrMsg;
32
33 auto DL = sys::DynamicLibrary::getPermanentLibrary(PathCStr, &ErrMsg);
34 if (!DL.isValid())
35 return make_error<StringError>(std::move(ErrMsg), inconvertibleErrorCode());
36
37 std::lock_guard<std::mutex> Lock(M);
38 auto H = ExecutorAddr::fromPtr(DL.getOSSpecificHandle());
39 Dylibs.insert(DL.getOSSpecificHandle());
40 return H;
41 }
42
43 Expected<std::vector<ExecutorAddr>>
lookup(tpctypes::DylibHandle H,const RemoteSymbolLookupSet & L)44 SimpleExecutorDylibManager::lookup(tpctypes::DylibHandle H,
45 const RemoteSymbolLookupSet &L) {
46 std::vector<ExecutorAddr> Result;
47 auto DL = sys::DynamicLibrary(H.toPtr<void *>());
48
49 for (const auto &E : L) {
50 if (E.Name.empty()) {
51 if (E.Required)
52 return make_error<StringError>("Required address for empty symbol \"\"",
53 inconvertibleErrorCode());
54 else
55 Result.push_back(ExecutorAddr());
56 } else {
57
58 const char *DemangledSymName = E.Name.c_str();
59 #ifdef __APPLE__
60 if (E.Name.front() != '_')
61 return make_error<StringError>(Twine("MachO symbol \"") + E.Name +
62 "\" missing leading '_'",
63 inconvertibleErrorCode());
64 ++DemangledSymName;
65 #endif
66
67 void *Addr = DL.getAddressOfSymbol(DemangledSymName);
68 if (!Addr && E.Required)
69 return make_error<StringError>(Twine("Missing definition for ") +
70 DemangledSymName,
71 inconvertibleErrorCode());
72
73 Result.push_back(ExecutorAddr::fromPtr(Addr));
74 }
75 }
76
77 return Result;
78 }
79
shutdown()80 Error SimpleExecutorDylibManager::shutdown() {
81
82 DylibSet DS;
83 {
84 std::lock_guard<std::mutex> Lock(M);
85 std::swap(DS, Dylibs);
86 }
87
88 // There is no removal of dylibs at the moment, so nothing to do here.
89 return Error::success();
90 }
91
addBootstrapSymbols(StringMap<ExecutorAddr> & M)92 void SimpleExecutorDylibManager::addBootstrapSymbols(
93 StringMap<ExecutorAddr> &M) {
94 M[rt::SimpleExecutorDylibManagerInstanceName] = ExecutorAddr::fromPtr(this);
95 M[rt::SimpleExecutorDylibManagerOpenWrapperName] =
96 ExecutorAddr::fromPtr(&openWrapper);
97 M[rt::SimpleExecutorDylibManagerLookupWrapperName] =
98 ExecutorAddr::fromPtr(&lookupWrapper);
99 }
100
101 llvm::orc::shared::CWrapperFunctionResult
openWrapper(const char * ArgData,size_t ArgSize)102 SimpleExecutorDylibManager::openWrapper(const char *ArgData, size_t ArgSize) {
103 return shared::
104 WrapperFunction<rt::SPSSimpleExecutorDylibManagerOpenSignature>::handle(
105 ArgData, ArgSize,
106 shared::makeMethodWrapperHandler(
107 &SimpleExecutorDylibManager::open))
108 .release();
109 }
110
111 llvm::orc::shared::CWrapperFunctionResult
lookupWrapper(const char * ArgData,size_t ArgSize)112 SimpleExecutorDylibManager::lookupWrapper(const char *ArgData, size_t ArgSize) {
113 return shared::
114 WrapperFunction<rt::SPSSimpleExecutorDylibManagerLookupSignature>::handle(
115 ArgData, ArgSize,
116 shared::makeMethodWrapperHandler(
117 &SimpleExecutorDylibManager::lookup))
118 .release();
119 }
120
121 } // namespace rt_bootstrap
122 } // end namespace orc
123 } // end namespace llvm
124