-
Notifications
You must be signed in to change notification settings - Fork 0
/
LogicalDylib.h
155 lines (125 loc) · 4.94 KB
/
LogicalDylib.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
//===--- LogicalDylib.h - Simulates dylib-style symbol lookup ---*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// Simulates symbol resolution inside a dylib.
//
//===----------------------------------------------------------------------===//
#ifndef LLVM_EXECUTIONENGINE_ORC_LOGICALDYLIB_H
#define LLVM_EXECUTIONENGINE_ORC_LOGICALDYLIB_H
#include "JITSymbol.h"
#include <string>
#include <vector>
#include "llvm/IR/Mangler.h"
#include "llvm/Support/raw_ostream.h"
namespace llvm {
namespace orc {
template <typename BaseLayerT,
typename LogicalModuleResources,
typename LogicalDylibResources>
class LogicalDylib {
public:
typedef typename BaseLayerT::ModuleSetHandleT BaseLayerModuleSetHandleT;
private:
typedef std::vector<BaseLayerModuleSetHandleT> BaseLayerHandleList;
struct LogicalModule {
// Make this move-only to ensure they don't get duplicated across moves of
// LogicalDylib or anything like that.
LogicalModule(LogicalModule &&RHS)
: Resources(std::move(RHS.Resources)),
BaseLayerHandles(std::move(RHS.BaseLayerHandles)) {}
LogicalModule() = default;
LogicalModuleResources Resources;
BaseLayerHandleList BaseLayerHandles;
};
typedef std::vector<LogicalModule> LogicalModuleList;
public:
typedef typename BaseLayerHandleList::iterator BaseLayerHandleIterator;
typedef typename LogicalModuleList::iterator LogicalModuleHandle;
LogicalDylib(BaseLayerT &BaseLayer) : BaseLayer(BaseLayer) {}
~LogicalDylib() {
for (auto &LM : LogicalModules)
for (auto BLH : LM.BaseLayerHandles)
BaseLayer.removeModuleSet(BLH);
}
// If possible, remove this and ~LogicalDylib once the work in the dtor is
// moved to members (eg: self-unregistering base layer handles).
LogicalDylib(LogicalDylib &&RHS)
: BaseLayer(std::move(RHS.BaseLayer)),
LogicalModules(std::move(RHS.LogicalModules)),
DylibResources(std::move(RHS.DylibResources)) {}
LogicalModuleHandle createLogicalModule() {
LogicalModules.push_back(LogicalModule());
return std::prev(LogicalModules.end());
}
void addToLogicalModule(LogicalModuleHandle LMH,
BaseLayerModuleSetHandleT BaseLayerHandle) {
LMH->BaseLayerHandles.push_back(BaseLayerHandle);
}
LogicalModuleResources& getLogicalModuleResources(LogicalModuleHandle LMH) {
return LMH->Resources;
}
static std::string mangle(StringRef Name, const DataLayout &DL) {
std::string MangledName;
{
raw_string_ostream MangledNameStream(MangledName);
Mangler::getNameWithPrefix(MangledNameStream, Name, DL);
}
return MangledName;
}
LogicalModuleResources* getLogicalModuleResourcesForSymbol(const std::string &Name, bool ExportedSymbolsOnly) {
for (auto LMI = LogicalModules.begin(), LME = LogicalModules.end();
LMI != LME; ++LMI)
if (auto Sym = findSymbolInLogicalModule(LMI, mangle(Name,LMI->Resources.SourceModule->getResource().getDataLayout()), ExportedSymbolsOnly))
return &LMI->Resources;
return nullptr;
}
BaseLayerHandleIterator moduleHandlesBegin(LogicalModuleHandle LMH) {
return LMH->BaseLayerHandles.begin();
}
BaseLayerHandleIterator moduleHandlesEnd(LogicalModuleHandle LMH) {
return LMH->BaseLayerHandles.end();
}
JITSymbol findSymbolInLogicalModule(LogicalModuleHandle LMH,
const std::string &Name,
bool ExportedSymbolsOnly) {
if (auto StubSym = LMH->Resources.findSymbol(Name, ExportedSymbolsOnly))
return StubSym;
for (auto BLH : LMH->BaseLayerHandles)
if (auto Symbol = BaseLayer.findSymbolIn(BLH, Name, ExportedSymbolsOnly))
return Symbol;
return nullptr;
}
JITSymbol findSymbolInternally(LogicalModuleHandle LMH,
const std::string &Name) {
if (auto Symbol = findSymbolInLogicalModule(LMH, Name, false))
return Symbol;
for (auto LMI = LogicalModules.begin(), LME = LogicalModules.end();
LMI != LME; ++LMI) {
if (LMI != LMH)
if (auto Symbol = findSymbolInLogicalModule(LMI, Name, false))
return Symbol;
}
return nullptr;
}
JITSymbol findSymbol(const std::string &Name, bool ExportedSymbolsOnly) {
for (auto LMI = LogicalModules.begin(), LME = LogicalModules.end();
LMI != LME; ++LMI)
if (auto Sym = findSymbolInLogicalModule(LMI, Name, ExportedSymbolsOnly))
return Sym;
return nullptr;
}
LogicalDylibResources& getDylibResources() { return DylibResources; }
protected:
BaseLayerT BaseLayer;
LogicalModuleList LogicalModules;
LogicalDylibResources DylibResources;
};
} // End namespace orc.
} // End namespace llvm.
#endif // LLVM_EXECUTIONENGINE_ORC_LOGICALDYLIB_H