clang  8.0.0svn
ObjectFilePCHContainerOperations.cpp
Go to the documentation of this file.
1 //===--- ObjectFilePCHContainerOperations.cpp -----------------------------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
11 #include "CGDebugInfo.h"
12 #include "CodeGenModule.h"
13 #include "clang/AST/ASTContext.h"
14 #include "clang/AST/DeclObjC.h"
15 #include "clang/AST/Expr.h"
18 #include "clang/Basic/Diagnostic.h"
19 #include "clang/Basic/TargetInfo.h"
22 #include "clang/Lex/HeaderSearch.h"
23 #include "clang/Lex/Preprocessor.h"
24 #include "llvm/ADT/StringRef.h"
25 #include "llvm/Bitcode/BitstreamReader.h"
26 #include "llvm/DebugInfo/DWARF/DWARFContext.h"
27 #include "llvm/IR/Constants.h"
28 #include "llvm/IR/DataLayout.h"
29 #include "llvm/IR/LLVMContext.h"
30 #include "llvm/IR/Module.h"
31 #include "llvm/Object/COFF.h"
32 #include "llvm/Object/ObjectFile.h"
33 #include "llvm/Support/Path.h"
34 #include "llvm/Support/TargetRegistry.h"
35 #include <memory>
36 #include <utility>
37 
38 using namespace clang;
39 
40 #define DEBUG_TYPE "pchcontainer"
41 
42 namespace {
43 class PCHContainerGenerator : public ASTConsumer {
44  DiagnosticsEngine &Diags;
45  const std::string MainFileName;
46  const std::string OutputFileName;
47  ASTContext *Ctx;
48  ModuleMap &MMap;
49  const HeaderSearchOptions &HeaderSearchOpts;
50  const PreprocessorOptions &PreprocessorOpts;
51  CodeGenOptions CodeGenOpts;
52  const TargetOptions TargetOpts;
53  const LangOptions LangOpts;
54  std::unique_ptr<llvm::LLVMContext> VMContext;
55  std::unique_ptr<llvm::Module> M;
56  std::unique_ptr<CodeGen::CodeGenModule> Builder;
57  std::unique_ptr<raw_pwrite_stream> OS;
58  std::shared_ptr<PCHBuffer> Buffer;
59 
60  /// Visit every type and emit debug info for it.
61  struct DebugTypeVisitor : public RecursiveASTVisitor<DebugTypeVisitor> {
63  ASTContext &Ctx;
64  DebugTypeVisitor(clang::CodeGen::CGDebugInfo &DI, ASTContext &Ctx)
65  : DI(DI), Ctx(Ctx) {}
66 
67  /// Determine whether this type can be represented in DWARF.
68  static bool CanRepresent(const Type *Ty) {
69  return !Ty->isDependentType() && !Ty->isUndeducedType();
70  }
71 
72  bool VisitImportDecl(ImportDecl *D) {
73  if (!D->getImportedOwningModule())
74  DI.EmitImportDecl(*D);
75  return true;
76  }
77 
78  bool VisitTypeDecl(TypeDecl *D) {
79  // TagDecls may be deferred until after all decls have been merged and we
80  // know the complete type. Pure forward declarations will be skipped, but
81  // they don't need to be emitted into the module anyway.
82  if (auto *TD = dyn_cast<TagDecl>(D))
83  if (!TD->isCompleteDefinition())
84  return true;
85 
86  QualType QualTy = Ctx.getTypeDeclType(D);
87  if (!QualTy.isNull() && CanRepresent(QualTy.getTypePtr()))
88  DI.getOrCreateStandaloneType(QualTy, D->getLocation());
89  return true;
90  }
91 
92  bool VisitObjCInterfaceDecl(ObjCInterfaceDecl *D) {
93  QualType QualTy(D->getTypeForDecl(), 0);
94  if (!QualTy.isNull() && CanRepresent(QualTy.getTypePtr()))
95  DI.getOrCreateStandaloneType(QualTy, D->getLocation());
96  return true;
97  }
98 
99  bool VisitFunctionDecl(FunctionDecl *D) {
100  if (isa<CXXMethodDecl>(D))
101  // This is not yet supported. Constructing the `this' argument
102  // mandates a CodeGenFunction.
103  return true;
104 
105  SmallVector<QualType, 16> ArgTypes;
106  for (auto i : D->parameters())
107  ArgTypes.push_back(i->getType());
108  QualType RetTy = D->getReturnType();
109  QualType FnTy = Ctx.getFunctionType(RetTy, ArgTypes,
111  if (CanRepresent(FnTy.getTypePtr()))
112  DI.EmitFunctionDecl(D, D->getLocation(), FnTy);
113  return true;
114  }
115 
116  bool VisitObjCMethodDecl(ObjCMethodDecl *D) {
117  if (!D->getClassInterface())
118  return true;
119 
120  bool selfIsPseudoStrong, selfIsConsumed;
121  SmallVector<QualType, 16> ArgTypes;
122  ArgTypes.push_back(D->getSelfType(Ctx, D->getClassInterface(),
123  selfIsPseudoStrong, selfIsConsumed));
124  ArgTypes.push_back(Ctx.getObjCSelType());
125  for (auto i : D->parameters())
126  ArgTypes.push_back(i->getType());
127  QualType RetTy = D->getReturnType();
128  QualType FnTy = Ctx.getFunctionType(RetTy, ArgTypes,
130  if (CanRepresent(FnTy.getTypePtr()))
131  DI.EmitFunctionDecl(D, D->getLocation(), FnTy);
132  return true;
133  }
134  };
135 
136 public:
137  PCHContainerGenerator(CompilerInstance &CI, const std::string &MainFileName,
138  const std::string &OutputFileName,
139  std::unique_ptr<raw_pwrite_stream> OS,
140  std::shared_ptr<PCHBuffer> Buffer)
141  : Diags(CI.getDiagnostics()), MainFileName(MainFileName),
142  OutputFileName(OutputFileName), Ctx(nullptr),
144  HeaderSearchOpts(CI.getHeaderSearchOpts()),
145  PreprocessorOpts(CI.getPreprocessorOpts()),
146  TargetOpts(CI.getTargetOpts()), LangOpts(CI.getLangOpts()),
147  OS(std::move(OS)), Buffer(std::move(Buffer)) {
148  // The debug info output isn't affected by CodeModel and
149  // ThreadModel, but the backend expects them to be nonempty.
150  CodeGenOpts.CodeModel = "default";
151  CodeGenOpts.ThreadModel = "single";
152  CodeGenOpts.DebugTypeExtRefs = true;
153  // When building a module MainFileName is the name of the modulemap file.
154  CodeGenOpts.MainFileName =
155  LangOpts.CurrentModule.empty() ? MainFileName : LangOpts.CurrentModule;
156  CodeGenOpts.setDebugInfo(codegenoptions::FullDebugInfo);
157  CodeGenOpts.setDebuggerTuning(CI.getCodeGenOpts().getDebuggerTuning());
158  CodeGenOpts.DebugPrefixMap =
160  }
161 
162  ~PCHContainerGenerator() override = default;
163 
164  void Initialize(ASTContext &Context) override {
165  assert(!Ctx && "initialized multiple times");
166 
167  Ctx = &Context;
168  VMContext.reset(new llvm::LLVMContext());
169  M.reset(new llvm::Module(MainFileName, *VMContext));
170  M->setDataLayout(Ctx->getTargetInfo().getDataLayout());
171  Builder.reset(new CodeGen::CodeGenModule(
172  *Ctx, HeaderSearchOpts, PreprocessorOpts, CodeGenOpts, *M, Diags));
173 
174  // Prepare CGDebugInfo to emit debug info for a clang module.
175  auto *DI = Builder->getModuleDebugInfo();
176  StringRef ModuleName = llvm::sys::path::filename(MainFileName);
177  DI->setPCHDescriptor({ModuleName, "", OutputFileName,
178  ASTFileSignature{{{~0U, ~0U, ~0U, ~0U, ~1U}}}});
179  DI->setModuleMap(MMap);
180  }
181 
182  bool HandleTopLevelDecl(DeclGroupRef D) override {
183  if (Diags.hasErrorOccurred())
184  return true;
185 
186  // Collect debug info for all decls in this group.
187  for (auto *I : D)
188  if (!I->isFromASTFile()) {
189  DebugTypeVisitor DTV(*Builder->getModuleDebugInfo(), *Ctx);
190  DTV.TraverseDecl(I);
191  }
192  return true;
193  }
194 
195  void HandleTopLevelDeclInObjCContainer(DeclGroupRef D) override {
196  HandleTopLevelDecl(D);
197  }
198 
199  void HandleTagDeclDefinition(TagDecl *D) override {
200  if (Diags.hasErrorOccurred())
201  return;
202 
203  if (D->isFromASTFile())
204  return;
205 
206  // Anonymous tag decls are deferred until we are building their declcontext.
207  if (D->getName().empty())
208  return;
209 
210  // Defer tag decls until their declcontext is complete.
211  auto *DeclCtx = D->getDeclContext();
212  while (DeclCtx) {
213  if (auto *D = dyn_cast<TagDecl>(DeclCtx))
214  if (!D->isCompleteDefinition())
215  return;
216  DeclCtx = DeclCtx->getParent();
217  }
218 
219  DebugTypeVisitor DTV(*Builder->getModuleDebugInfo(), *Ctx);
220  DTV.TraverseDecl(D);
221  Builder->UpdateCompletedType(D);
222  }
223 
224  void HandleTagDeclRequiredDefinition(const TagDecl *D) override {
225  if (Diags.hasErrorOccurred())
226  return;
227 
228  if (const RecordDecl *RD = dyn_cast<RecordDecl>(D))
229  Builder->getModuleDebugInfo()->completeRequiredType(RD);
230  }
231 
232  void HandleImplicitImportDecl(ImportDecl *D) override {
233  if (!D->getImportedOwningModule())
234  Builder->getModuleDebugInfo()->EmitImportDecl(*D);
235  }
236 
237  /// Emit a container holding the serialized AST.
238  void HandleTranslationUnit(ASTContext &Ctx) override {
239  assert(M && VMContext && Builder);
240  // Delete these on function exit.
241  std::unique_ptr<llvm::LLVMContext> VMContext = std::move(this->VMContext);
242  std::unique_ptr<llvm::Module> M = std::move(this->M);
243  std::unique_ptr<CodeGen::CodeGenModule> Builder = std::move(this->Builder);
244 
245  if (Diags.hasErrorOccurred())
246  return;
247 
248  M->setTargetTriple(Ctx.getTargetInfo().getTriple().getTriple());
249  M->setDataLayout(Ctx.getTargetInfo().getDataLayout());
250 
251  // PCH files don't have a signature field in the control block,
252  // but LLVM detects DWO CUs by looking for a non-zero DWO id.
253  // We use the lower 64 bits for debug info.
254  uint64_t Signature =
255  Buffer->Signature
256  ? (uint64_t)Buffer->Signature[1] << 32 | Buffer->Signature[0]
257  : ~1ULL;
258  Builder->getModuleDebugInfo()->setDwoId(Signature);
259 
260  // Finalize the Builder.
261  if (Builder)
262  Builder->Release();
263 
264  // Ensure the target exists.
265  std::string Error;
266  auto Triple = Ctx.getTargetInfo().getTriple();
267  if (!llvm::TargetRegistry::lookupTarget(Triple.getTriple(), Error))
268  llvm::report_fatal_error(Error);
269 
270  // Emit the serialized Clang AST into its own section.
271  assert(Buffer->IsComplete && "serialization did not complete");
272  auto &SerializedAST = Buffer->Data;
273  auto Size = SerializedAST.size();
274  auto Int8Ty = llvm::Type::getInt8Ty(*VMContext);
275  auto *Ty = llvm::ArrayType::get(Int8Ty, Size);
276  auto *Data = llvm::ConstantDataArray::getString(
277  *VMContext, StringRef(SerializedAST.data(), Size),
278  /*AddNull=*/false);
279  auto *ASTSym = new llvm::GlobalVariable(
280  *M, Ty, /*constant*/ true, llvm::GlobalVariable::InternalLinkage, Data,
281  "__clang_ast");
282  // The on-disk hashtable needs to be aligned.
283  ASTSym->setAlignment(8);
284 
285  // Mach-O also needs a segment name.
286  if (Triple.isOSBinFormatMachO())
287  ASTSym->setSection("__CLANG,__clangast");
288  // COFF has an eight character length limit.
289  else if (Triple.isOSBinFormatCOFF())
290  ASTSym->setSection("clangast");
291  else
292  ASTSym->setSection("__clangast");
293 
294  LLVM_DEBUG({
295  // Print the IR for the PCH container to the debug output.
296  llvm::SmallString<0> Buffer;
298  Diags, HeaderSearchOpts, CodeGenOpts, TargetOpts, LangOpts,
299  Ctx.getTargetInfo().getDataLayout(), M.get(),
301  llvm::make_unique<llvm::raw_svector_ostream>(Buffer));
302  llvm::dbgs() << Buffer;
303  });
304 
305  // Use the LLVM backend to emit the pch container.
306  clang::EmitBackendOutput(Diags, HeaderSearchOpts, CodeGenOpts, TargetOpts,
307  LangOpts, Ctx.getTargetInfo().getDataLayout(),
309  std::move(OS));
310 
311  // Free the memory for the temporary buffer.
313  SerializedAST = std::move(Empty);
314  }
315 };
316 
317 } // anonymous namespace
318 
319 std::unique_ptr<ASTConsumer>
320 ObjectFilePCHContainerWriter::CreatePCHContainerGenerator(
321  CompilerInstance &CI, const std::string &MainFileName,
322  const std::string &OutputFileName,
323  std::unique_ptr<llvm::raw_pwrite_stream> OS,
324  std::shared_ptr<PCHBuffer> Buffer) const {
325  return llvm::make_unique<PCHContainerGenerator>(
326  CI, MainFileName, OutputFileName, std::move(OS), Buffer);
327 }
328 
329 StringRef
330 ObjectFilePCHContainerReader::ExtractPCH(llvm::MemoryBufferRef Buffer) const {
331  StringRef PCH;
332  auto OFOrErr = llvm::object::ObjectFile::createObjectFile(Buffer);
333  if (OFOrErr) {
334  auto &OF = OFOrErr.get();
335  bool IsCOFF = isa<llvm::object::COFFObjectFile>(*OF);
336  // Find the clang AST section in the container.
337  for (auto &Section : OF->sections()) {
338  StringRef Name;
339  Section.getName(Name);
340  if ((!IsCOFF && Name == "__clangast") || (IsCOFF && Name == "clangast")) {
341  Section.getContents(PCH);
342  return PCH;
343  }
344  }
345  }
346  handleAllErrors(OFOrErr.takeError(), [&](const llvm::ErrorInfoBase &EIB) {
347  if (EIB.convertToErrorCode() ==
348  llvm::object::object_error::invalid_file_type)
349  // As a fallback, treat the buffer as a raw AST.
350  PCH = Buffer.getBuffer();
351  else
352  EIB.log(llvm::errs());
353  });
354  return PCH;
355 }
Defines the clang::ASTContext interface.
LangOptions & getLangOpts()
const Type * getTypeForDecl() const
Definition: DeclObjC.h:1911
Represents a function declaration or definition.
Definition: Decl.h:1739
CompilerInvocation & getInvocation()
PreprocessorOptions & getPreprocessorOpts()
bool hasErrorOccurred() const
Definition: Diagnostic.h:744
A (possibly-)qualified type.
Definition: Type.h:638
ObjCInterfaceDecl * getClassInterface()
Definition: DeclObjC.cpp:1144
ASTConsumer - This is an abstract interface that should be implemented by clients that read ASTs...
Definition: ASTConsumer.h:34
Emit human-readable LLVM assembly.
Definition: BackendUtil.h:34
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
Definition: TargetInfo.h:949
The base class of the type hierarchy.
Definition: Type.h:1411
const TargetInfo & getTargetInfo() const
Definition: ASTContext.h:689
PreprocessorOptions - This class is used for passing the various options used in preprocessor initial...
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
Definition: Decl.h:3178
QualType getReturnType() const
Definition: Decl.h:2303
Options for controlling the target.
Definition: TargetOptions.h:27
Extra information about a function prototype.
Definition: Type.h:3771
This class gathers all debug information during compilation and is responsible for emitting to llvm g...
Definition: CGDebugInfo.h:54
ObjCMethodDecl - Represents an instance or class method declaration.
Definition: DeclObjC.h:139
ModuleMap & getModuleMap()
Retrieve the module map.
Definition: HeaderSearch.h:655
Represents a struct/union/class.
Definition: Decl.h:3602
std::map< std::string, std::string > DebugPrefixMap
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:154
void EmitImportDecl(const ImportDecl &ID)
Emit an declaration.
CodeGenOptions & getCodeGenOpts()
The signature of a module, which is a hash of the AST content.
Definition: Module.h:55
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
Definition: LangOptions.h:50
std::string CodeModel
The code model to use (-mcmodel).
ArrayRef< ParmVarDecl * > parameters() const
Definition: Decl.h:2263
CodeGenOptions & getCodeGenOpts()
HeaderSearch & getHeaderSearchInfo() const
Definition: Preprocessor.h:821
Concrete class used by the front-end to report problems and issues.
Definition: Diagnostic.h:149
Represents a declaration of a type.
Definition: Decl.h:2883
Defines the Diagnostic-related interfaces.
const Type * getTypePtr() const
Retrieves a pointer to the underlying (unqualified) type.
Definition: Type.h:6076
HeaderSearchOptions & getHeaderSearchOpts()
A class that does preorder or postorder depth-first traversal on the entire Clang AST and visits each...
Represents an ObjC class declaration.
Definition: DeclObjC.h:1164
QualType getReturnType() const
Definition: DeclObjC.h:323
std::string ThreadModel
The thread model to use.
std::string CurrentModule
The name of the current module, of which the main source file is a part.
Definition: LangOptions.h:227
Module * getImportedOwningModule() const
Get the imported owning module, if this decl is from an imported (non-local) module.
Definition: DeclBase.h:722
Defines the clang::Preprocessor interface.
DeclContext * getDeclContext()
Definition: DeclBase.h:427
Emit native object files.
Definition: BackendUtil.h:37
DeclContext * getParent()
getParent - Returns the containing DeclContext.
Definition: DeclBase.h:1752
QualType getFunctionType(QualType ResultTy, ArrayRef< QualType > Args, const FunctionProtoType::ExtProtoInfo &EPI) const
Return a normal function type with a typed argument list.
Definition: ASTContext.h:1379
QualType getTypeDeclType(const TypeDecl *Decl, const TypeDecl *PrevDecl=nullptr) const
Return the unique reference to the type for the specified type declaration.
Definition: ASTContext.h:1395
bool isNull() const
Return true if this QualType doesn&#39;t point to a type yet.
Definition: Type.h:703
void EmitFunctionDecl(GlobalDecl GD, SourceLocation Loc, QualType FnType)
Emit debug info for a function declaration.
QualType getSelfType(ASTContext &Context, const ObjCInterfaceDecl *OID, bool &selfIsPseudoStrong, bool &selfIsConsumed)
Definition: DeclObjC.cpp:1078
CompilerInstance - Helper class for managing a single instance of the Clang compiler.
Limit generated debug info to reduce size (-fno-standalone-debug).
Represents the declaration of a struct/union/class/enum.
Definition: Decl.h:3073
QualType getObjCSelType() const
Retrieve the type that corresponds to the predefined Objective-C &#39;SEL&#39; type.
Definition: ASTContext.h:1858
const llvm::DataLayout & getDataLayout() const
Definition: TargetInfo.h:953
bool isFromASTFile() const
Determine whether this declaration came from an AST file (such as a precompiled header or module) rat...
Definition: DeclBase.h:695
Describes a module import declaration, which makes the contents of the named module visible in the cu...
Definition: Decl.h:4158
This class organizes the cross-function state that is used while generating LLVM code.
Dataflow Directional Tag Classes.
void EmitBackendOutput(DiagnosticsEngine &Diags, const HeaderSearchOptions &, const CodeGenOptions &CGOpts, const TargetOptions &TOpts, const LangOptions &LOpts, const llvm::DataLayout &TDesc, llvm::Module *M, BackendAction Action, std::unique_ptr< raw_pwrite_stream > OS)
bool isUndeducedType() const
Determine whether this type is an undeduced type, meaning that it somehow involves a C++11 &#39;auto&#39; typ...
Definition: Type.h:6667
llvm::DIType * getOrCreateStandaloneType(QualType Ty, SourceLocation Loc)
Emit standalone debug info for a type.
CodeGenOptions - Track various options which control how the code is optimized and passed to the back...
Internal linkage, which indicates that the entity can be referred to from within the translation unit...
Definition: Linkage.h:32
Preprocessor & getPreprocessor() const
Return the current preprocessor.
std::string MainFileName
The user provided name for the "main file", if non-empty.
Defines the clang::TargetInfo interface.
DiagnosticsEngine & getDiagnostics() const
Get the current diagnostics engine.
StringRef getName() const
Get the name of identifier for this declaration as a StringRef.
Definition: Decl.h:275
HeaderSearchOptions - Helper class for storing options related to the initialization of the HeaderSea...
bool isDependentType() const
Whether this type is a dependent type, meaning that its definition somehow depends on a template para...
Definition: Type.h:2083
TargetOptions & getTargetOpts()
SourceLocation getLocation() const
Definition: DeclBase.h:418
ArrayRef< ParmVarDecl * > parameters() const
Definition: DeclObjC.h:367