1717#ifndef SWIFT_TBDGEN_REQUESTS_H
1818#define SWIFT_TBDGEN_REQUESTS_H
1919
20+ #include " llvm/ExecutionEngine/JITSymbol.h"
21+
2022#include " swift/AST/ASTTypeIDs.h"
2123#include " swift/AST/SimpleRequest.h"
2224#include " swift/IRGen/Linking.h"
@@ -148,6 +150,10 @@ class SymbolSource {
148150 // / A symbol introduced when emitting a SIL decl.
149151 SIL,
150152
153+ // / A symbol introduced when emitting a SIL global variable.
154+ // / Only used in piecewise compilation for Immediate mode.
155+ Global,
156+
151157 // / A symbol introduced when emitting LLVM IR.
152158 IR,
153159
@@ -162,13 +168,17 @@ class SymbolSource {
162168
163169private:
164170 union {
171+ VarDecl *Global;
165172 SILDeclRef silDeclRef;
166173 irgen::LinkEntity irEntity;
167174 };
168175
169176 explicit SymbolSource (SILDeclRef ref) : kind(Kind::SIL) {
170177 silDeclRef = ref;
171178 }
179+
180+ SymbolSource (VarDecl *Global) : kind(Kind::Global), Global(Global) {}
181+
172182 explicit SymbolSource (irgen::LinkEntity entity) : kind(Kind::IR) {
173183 irEntity = entity;
174184 }
@@ -180,6 +190,9 @@ class SymbolSource {
180190 static SymbolSource forSILDeclRef (SILDeclRef ref) {
181191 return SymbolSource{ref};
182192 }
193+
194+ static SymbolSource forGlobal (VarDecl *Global) { return Global; }
195+
183196 static SymbolSource forIRLinkEntity (irgen::LinkEntity entity) {
184197 return SymbolSource{entity};
185198 }
@@ -198,49 +211,93 @@ class SymbolSource {
198211 assert (kind == Kind::SIL);
199212 return silDeclRef;
200213 }
214+
215+ VarDecl *getGlobal () const {
216+ assert (kind == Kind::Global);
217+ return Global;
218+ }
219+
201220 irgen::LinkEntity getIRLinkEntity () const {
202221 assert (kind == Kind::IR);
203222 return irEntity;
204223 }
205- };
206-
207- // / Maps a symbol back to its source for lazy compilation.
208- class SymbolSourceMap {
209- friend class SymbolSourceMapRequest ;
210-
211- using Storage = llvm::StringMap<SymbolSource>;
212- const Storage *storage;
213224
214- explicit SymbolSourceMap (const Storage *storage) : storage(storage) {
215- assert (storage);
225+ // / Typecheck the entity wrapped by this `SymbolSource`
226+ void typecheck () const {
227+ switch (kind) {
228+ case Kind::SIL: {
229+ if (auto *AFD = silDeclRef.getAbstractFunctionDecl ())
230+ // If this entity is a `SILFunction`, check its body
231+ AFD->getTypecheckedBody ();
232+ break ;
233+ }
234+ case Kind::Global:
235+ case Kind::IR:
236+ case Kind::LinkerDirective:
237+ case Kind::Unknown:
238+ // Nothing to do
239+ break ;
240+ }
216241 }
217242
218- public:
219- llvm::Optional<SymbolSource> find (StringRef symbol) const {
220- auto result = storage->find (symbol);
221- if (result == storage->end ())
222- return llvm::None;
223- return result->second ;
243+ friend llvm::hash_code hash_value (const SymbolSource &S) {
244+ auto Kind = S.kind ;
245+ switch (Kind) {
246+ case Kind::SIL:
247+ return llvm::hash_combine (Kind, S.silDeclRef );
248+ case Kind::Global:
249+ return llvm::hash_combine (Kind, S.Global );
250+ case Kind::IR:
251+ return llvm::hash_combine (Kind, S.irEntity );
252+ case Kind::LinkerDirective:
253+ case Kind::Unknown:
254+ return llvm::hash_value (Kind);
255+ }
224256 }
225257
226- friend bool operator ==(const SymbolSourceMap &lhs,
227- const SymbolSourceMap &rhs) {
228- return lhs.storage == rhs.storage ;
258+ friend bool operator ==(const SymbolSource &LHS, const SymbolSource &RHS) {
259+ if (LHS.kind != RHS.kind )
260+ return false ;
261+ switch (LHS.kind ) {
262+ case Kind::SIL:
263+ return LHS.silDeclRef == RHS.silDeclRef ;
264+ case Kind::Global:
265+ return LHS.Global == RHS.Global ;
266+ case Kind::IR:
267+ return LHS.irEntity == RHS.irEntity ;
268+ case Kind::LinkerDirective:
269+ case Kind::Unknown:
270+ return true ;
271+ }
229272 }
230- friend bool operator !=( const SymbolSourceMap &lhs,
231- const SymbolSourceMap &rhs ) {
232- return !(lhs == rhs );
273+
274+ friend bool operator !=( const SymbolSource &LHS, const SymbolSource &RHS ) {
275+ return !(LHS == RHS );
233276 }
234277
235- friend void simple_display (llvm::raw_ostream &out, const SymbolSourceMap &) {
236- out << " (symbol storage map)" ;
278+ llvm::JITSymbolFlags getJITSymbolFlags () const {
279+ switch (kind) {
280+ case Kind::SIL:
281+ return llvm::JITSymbolFlags::Callable | llvm::JITSymbolFlags::Exported;
282+ case Kind::Global:
283+ return llvm::JITSymbolFlags::Exported;
284+ case Kind::IR:
285+ llvm_unreachable (" Unimplemented: Symbol flags for LinkEntities" );
286+ case Kind::LinkerDirective:
287+ llvm_unreachable (" Unsupported: Symbol flags for linker directives" );
288+ case Kind::Unknown:
289+ llvm_unreachable (" Unsupported: Symbol flags for unknown source" );
290+ }
237291 }
238292};
239293
294+ // / Maps a symbol back to its source for lazy compilation.
295+ using SymbolSourceMap = llvm::StringMap<SymbolSource>;
296+
240297// / Computes a map of symbols to their SymbolSource for a file or module.
241298class SymbolSourceMapRequest
242299 : public SimpleRequest<SymbolSourceMapRequest,
243- SymbolSourceMap (TBDGenDescriptor),
300+ const SymbolSourceMap * (TBDGenDescriptor),
244301 RequestFlags::Cached> {
245302public:
246303 using SimpleRequest::SimpleRequest;
@@ -249,7 +306,8 @@ class SymbolSourceMapRequest
249306 friend SimpleRequest;
250307
251308 // Evaluation.
252- SymbolSourceMap evaluate (Evaluator &evaluator, TBDGenDescriptor desc) const ;
309+ const SymbolSourceMap *evaluate (Evaluator &evaluator,
310+ TBDGenDescriptor desc) const ;
253311
254312public:
255313 // Cached.
0 commit comments