1 | //===--- ModuleBuilder.cpp - Emit LLVM Code from ASTs ---------------------===// |
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 | // This builds an AST and converts it to LLVM Code. |
10 | // |
11 | //===----------------------------------------------------------------------===// |
12 | |
13 | #include "clang/CodeGen/ModuleBuilder.h" |
14 | #include "CGDebugInfo.h" |
15 | #include "CodeGenModule.h" |
16 | #include "clang/AST/ASTContext.h" |
17 | #include "clang/AST/DeclObjC.h" |
18 | #include "clang/AST/Expr.h" |
19 | #include "clang/Basic/CodeGenOptions.h" |
20 | #include "clang/Basic/Diagnostic.h" |
21 | #include "clang/Basic/TargetInfo.h" |
22 | #include "llvm/ADT/StringRef.h" |
23 | #include "llvm/IR/DataLayout.h" |
24 | #include "llvm/IR/LLVMContext.h" |
25 | #include "llvm/IR/Module.h" |
26 | #include <memory> |
27 | |
28 | using namespace clang; |
29 | using namespace CodeGen; |
30 | |
31 | namespace { |
32 | class CodeGeneratorImpl : public CodeGenerator { |
33 | DiagnosticsEngine &Diags; |
34 | ASTContext *Ctx; |
35 | const HeaderSearchOptions &; // Only used for debug info. |
36 | const PreprocessorOptions &PreprocessorOpts; // Only used for debug info. |
37 | const CodeGenOptions CodeGenOpts; // Intentionally copied in. |
38 | |
39 | unsigned HandlingTopLevelDecls; |
40 | |
41 | /// Use this when emitting decls to block re-entrant decl emission. It will |
42 | /// emit all deferred decls on scope exit. Set EmitDeferred to false if decl |
43 | /// emission must be deferred longer, like at the end of a tag definition. |
44 | struct HandlingTopLevelDeclRAII { |
45 | CodeGeneratorImpl &Self; |
46 | bool EmitDeferred; |
47 | HandlingTopLevelDeclRAII(CodeGeneratorImpl &Self, |
48 | bool EmitDeferred = true) |
49 | : Self(Self), EmitDeferred(EmitDeferred) { |
50 | ++Self.HandlingTopLevelDecls; |
51 | } |
52 | ~HandlingTopLevelDeclRAII() { |
53 | unsigned Level = --Self.HandlingTopLevelDecls; |
54 | if (Level == 0 && EmitDeferred) |
55 | Self.EmitDeferredDecls(); |
56 | } |
57 | }; |
58 | |
59 | CoverageSourceInfo *CoverageInfo; |
60 | |
61 | protected: |
62 | std::unique_ptr<llvm::Module> M; |
63 | std::unique_ptr<CodeGen::CodeGenModule> Builder; |
64 | |
65 | private: |
66 | SmallVector<FunctionDecl *, 8> DeferredInlineMemberFuncDefs; |
67 | |
68 | static llvm::StringRef ExpandModuleName(llvm::StringRef ModuleName, |
69 | const CodeGenOptions &CGO) { |
70 | if (ModuleName == "-" && !CGO.MainFileName.empty()) |
71 | return CGO.MainFileName; |
72 | return ModuleName; |
73 | } |
74 | |
75 | public: |
76 | (DiagnosticsEngine &diags, llvm::StringRef ModuleName, |
77 | const HeaderSearchOptions &HSO, |
78 | const PreprocessorOptions &PPO, const CodeGenOptions &CGO, |
79 | llvm::LLVMContext &C, |
80 | CoverageSourceInfo *CoverageInfo = nullptr) |
81 | : Diags(diags), Ctx(nullptr), HeaderSearchOpts(HSO), |
82 | PreprocessorOpts(PPO), CodeGenOpts(CGO), HandlingTopLevelDecls(0), |
83 | CoverageInfo(CoverageInfo), |
84 | M(new llvm::Module(ExpandModuleName(ModuleName, CGO), C)) { |
85 | C.setDiscardValueNames(CGO.DiscardValueNames); |
86 | } |
87 | |
88 | ~CodeGeneratorImpl() override { |
89 | // There should normally not be any leftover inline method definitions. |
90 | assert(DeferredInlineMemberFuncDefs.empty() || |
91 | Diags.hasErrorOccurred()); |
92 | } |
93 | |
94 | CodeGenModule &CGM() { |
95 | return *Builder; |
96 | } |
97 | |
98 | llvm::Module *GetModule() { |
99 | return M.get(); |
100 | } |
101 | |
102 | CGDebugInfo *getCGDebugInfo() { |
103 | return Builder->getModuleDebugInfo(); |
104 | } |
105 | |
106 | llvm::Module *ReleaseModule() { |
107 | return M.release(); |
108 | } |
109 | |
110 | const Decl *GetDeclForMangledName(StringRef MangledName) { |
111 | GlobalDecl Result; |
112 | if (!Builder->lookupRepresentativeDecl(MangledName, Result)) |
113 | return nullptr; |
114 | const Decl *D = Result.getCanonicalDecl().getDecl(); |
115 | if (auto FD = dyn_cast<FunctionDecl>(D)) { |
116 | if (FD->hasBody(FD)) |
117 | return FD; |
118 | } else if (auto TD = dyn_cast<TagDecl>(D)) { |
119 | if (auto Def = TD->getDefinition()) |
120 | return Def; |
121 | } |
122 | return D; |
123 | } |
124 | |
125 | llvm::Constant *GetAddrOfGlobal(GlobalDecl global, bool isForDefinition) { |
126 | return Builder->GetAddrOfGlobal(global, ForDefinition_t(isForDefinition)); |
127 | } |
128 | |
129 | llvm::Module *StartModule(llvm::StringRef ModuleName, |
130 | llvm::LLVMContext &C) { |
131 | assert(!M && "Replacing existing Module?" ); |
132 | M.reset(new llvm::Module(ExpandModuleName(ModuleName, CodeGenOpts), C)); |
133 | Initialize(*Ctx); |
134 | return M.get(); |
135 | } |
136 | |
137 | void Initialize(ASTContext &Context) override { |
138 | Ctx = &Context; |
139 | |
140 | M->setTargetTriple(Ctx->getTargetInfo().getTriple().getTriple()); |
141 | M->setDataLayout(Ctx->getTargetInfo().getDataLayoutString()); |
142 | const auto &SDKVersion = Ctx->getTargetInfo().getSDKVersion(); |
143 | if (!SDKVersion.empty()) |
144 | M->setSDKVersion(SDKVersion); |
145 | Builder.reset(new CodeGen::CodeGenModule(Context, HeaderSearchOpts, |
146 | PreprocessorOpts, CodeGenOpts, |
147 | *M, Diags, CoverageInfo)); |
148 | |
149 | for (auto &&Lib : CodeGenOpts.DependentLibraries) |
150 | Builder->AddDependentLib(Lib); |
151 | for (auto &&Opt : CodeGenOpts.LinkerOptions) |
152 | Builder->AppendLinkerOptions(Opt); |
153 | } |
154 | |
155 | void HandleCXXStaticMemberVarInstantiation(VarDecl *VD) override { |
156 | if (Diags.hasErrorOccurred()) |
157 | return; |
158 | |
159 | Builder->HandleCXXStaticMemberVarInstantiation(VD); |
160 | } |
161 | |
162 | bool HandleTopLevelDecl(DeclGroupRef DG) override { |
163 | if (Diags.hasErrorOccurred()) |
164 | return true; |
165 | |
166 | HandlingTopLevelDeclRAII HandlingDecl(*this); |
167 | |
168 | // Make sure to emit all elements of a Decl. |
169 | for (DeclGroupRef::iterator I = DG.begin(), E = DG.end(); I != E; ++I) |
170 | Builder->EmitTopLevelDecl(*I); |
171 | |
172 | return true; |
173 | } |
174 | |
175 | void EmitDeferredDecls() { |
176 | if (DeferredInlineMemberFuncDefs.empty()) |
177 | return; |
178 | |
179 | // Emit any deferred inline method definitions. Note that more deferred |
180 | // methods may be added during this loop, since ASTConsumer callbacks |
181 | // can be invoked if AST inspection results in declarations being added. |
182 | HandlingTopLevelDeclRAII HandlingDecl(*this); |
183 | for (unsigned I = 0; I != DeferredInlineMemberFuncDefs.size(); ++I) |
184 | Builder->EmitTopLevelDecl(DeferredInlineMemberFuncDefs[I]); |
185 | DeferredInlineMemberFuncDefs.clear(); |
186 | } |
187 | |
188 | void HandleInlineFunctionDefinition(FunctionDecl *D) override { |
189 | if (Diags.hasErrorOccurred()) |
190 | return; |
191 | |
192 | assert(D->doesThisDeclarationHaveABody()); |
193 | |
194 | // We may want to emit this definition. However, that decision might be |
195 | // based on computing the linkage, and we have to defer that in case we |
196 | // are inside of something that will change the method's final linkage, |
197 | // e.g. |
198 | // typedef struct { |
199 | // void bar(); |
200 | // void foo() { bar(); } |
201 | // } A; |
202 | DeferredInlineMemberFuncDefs.push_back(D); |
203 | |
204 | // Provide some coverage mapping even for methods that aren't emitted. |
205 | // Don't do this for templated classes though, as they may not be |
206 | // instantiable. |
207 | if (!D->getLexicalDeclContext()->isDependentContext()) |
208 | Builder->AddDeferredUnusedCoverageMapping(D); |
209 | } |
210 | |
211 | /// HandleTagDeclDefinition - This callback is invoked each time a TagDecl |
212 | /// to (e.g. struct, union, enum, class) is completed. This allows the |
213 | /// client hack on the type, which can occur at any point in the file |
214 | /// (because these can be defined in declspecs). |
215 | void HandleTagDeclDefinition(TagDecl *D) override { |
216 | if (Diags.hasErrorOccurred()) |
217 | return; |
218 | |
219 | // Don't allow re-entrant calls to CodeGen triggered by PCH |
220 | // deserialization to emit deferred decls. |
221 | HandlingTopLevelDeclRAII HandlingDecl(*this, /*EmitDeferred=*/false); |
222 | |
223 | Builder->UpdateCompletedType(D); |
224 | |
225 | // For MSVC compatibility, treat declarations of static data members with |
226 | // inline initializers as definitions. |
227 | if (Ctx->getTargetInfo().getCXXABI().isMicrosoft()) { |
228 | for (Decl *Member : D->decls()) { |
229 | if (VarDecl *VD = dyn_cast<VarDecl>(Member)) { |
230 | if (Ctx->isMSStaticDataMemberInlineDefinition(VD) && |
231 | Ctx->DeclMustBeEmitted(VD)) { |
232 | Builder->EmitGlobal(VD); |
233 | } |
234 | } |
235 | } |
236 | } |
237 | // For OpenMP emit declare reduction functions, if required. |
238 | if (Ctx->getLangOpts().OpenMP) { |
239 | for (Decl *Member : D->decls()) { |
240 | if (auto *DRD = dyn_cast<OMPDeclareReductionDecl>(Member)) { |
241 | if (Ctx->DeclMustBeEmitted(DRD)) |
242 | Builder->EmitGlobal(DRD); |
243 | } else if (auto *DMD = dyn_cast<OMPDeclareMapperDecl>(Member)) { |
244 | if (Ctx->DeclMustBeEmitted(DMD)) |
245 | Builder->EmitGlobal(DMD); |
246 | } |
247 | } |
248 | } |
249 | } |
250 | |
251 | void HandleTagDeclRequiredDefinition(const TagDecl *D) override { |
252 | if (Diags.hasErrorOccurred()) |
253 | return; |
254 | |
255 | // Don't allow re-entrant calls to CodeGen triggered by PCH |
256 | // deserialization to emit deferred decls. |
257 | HandlingTopLevelDeclRAII HandlingDecl(*this, /*EmitDeferred=*/false); |
258 | |
259 | if (CodeGen::CGDebugInfo *DI = Builder->getModuleDebugInfo()) |
260 | if (const RecordDecl *RD = dyn_cast<RecordDecl>(D)) |
261 | DI->completeRequiredType(RD); |
262 | } |
263 | |
264 | void HandleTranslationUnit(ASTContext &Ctx) override { |
265 | // Release the Builder when there is no error. |
266 | if (!Diags.hasErrorOccurred() && Builder) |
267 | Builder->Release(); |
268 | |
269 | // If there are errors before or when releasing the Builder, reset |
270 | // the module to stop here before invoking the backend. |
271 | if (Diags.hasErrorOccurred()) { |
272 | if (Builder) |
273 | Builder->clear(); |
274 | M.reset(); |
275 | return; |
276 | } |
277 | } |
278 | |
279 | void AssignInheritanceModel(CXXRecordDecl *RD) override { |
280 | if (Diags.hasErrorOccurred()) |
281 | return; |
282 | |
283 | Builder->RefreshTypeCacheForClass(RD); |
284 | } |
285 | |
286 | void CompleteTentativeDefinition(VarDecl *D) override { |
287 | if (Diags.hasErrorOccurred()) |
288 | return; |
289 | |
290 | Builder->EmitTentativeDefinition(D); |
291 | } |
292 | |
293 | void CompleteExternalDeclaration(VarDecl *D) override { |
294 | Builder->EmitExternalDeclaration(D); |
295 | } |
296 | |
297 | void HandleVTable(CXXRecordDecl *RD) override { |
298 | if (Diags.hasErrorOccurred()) |
299 | return; |
300 | |
301 | Builder->EmitVTable(RD); |
302 | } |
303 | }; |
304 | } |
305 | |
306 | void CodeGenerator::anchor() { } |
307 | |
308 | CodeGenModule &CodeGenerator::CGM() { |
309 | return static_cast<CodeGeneratorImpl*>(this)->CGM(); |
310 | } |
311 | |
312 | llvm::Module *CodeGenerator::GetModule() { |
313 | return static_cast<CodeGeneratorImpl*>(this)->GetModule(); |
314 | } |
315 | |
316 | llvm::Module *CodeGenerator::ReleaseModule() { |
317 | return static_cast<CodeGeneratorImpl*>(this)->ReleaseModule(); |
318 | } |
319 | |
320 | CGDebugInfo *CodeGenerator::getCGDebugInfo() { |
321 | return static_cast<CodeGeneratorImpl*>(this)->getCGDebugInfo(); |
322 | } |
323 | |
324 | const Decl *CodeGenerator::GetDeclForMangledName(llvm::StringRef name) { |
325 | return static_cast<CodeGeneratorImpl*>(this)->GetDeclForMangledName(name); |
326 | } |
327 | |
328 | llvm::Constant *CodeGenerator::GetAddrOfGlobal(GlobalDecl global, |
329 | bool isForDefinition) { |
330 | return static_cast<CodeGeneratorImpl*>(this) |
331 | ->GetAddrOfGlobal(global, isForDefinition); |
332 | } |
333 | |
334 | llvm::Module *CodeGenerator::StartModule(llvm::StringRef ModuleName, |
335 | llvm::LLVMContext &C) { |
336 | return static_cast<CodeGeneratorImpl*>(this)->StartModule(ModuleName, C); |
337 | } |
338 | |
339 | CodeGenerator *clang::( |
340 | DiagnosticsEngine &Diags, llvm::StringRef ModuleName, |
341 | const HeaderSearchOptions &, |
342 | const PreprocessorOptions &PreprocessorOpts, const CodeGenOptions &CGO, |
343 | llvm::LLVMContext &C, CoverageSourceInfo *CoverageInfo) { |
344 | return new CodeGeneratorImpl(Diags, ModuleName, HeaderSearchOpts, |
345 | PreprocessorOpts, CGO, C, CoverageInfo); |
346 | } |
347 | |