xref: /minix3/external/bsd/llvm/dist/clang/lib/Serialization/ASTReader.cpp (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1f4a2713aSLionel Sambuc //===--- ASTReader.cpp - AST File Reader ----------------------------------===//
2f4a2713aSLionel Sambuc //
3f4a2713aSLionel Sambuc //                     The LLVM Compiler Infrastructure
4f4a2713aSLionel Sambuc //
5f4a2713aSLionel Sambuc // This file is distributed under the University of Illinois Open Source
6f4a2713aSLionel Sambuc // License. See LICENSE.TXT for details.
7f4a2713aSLionel Sambuc //
8f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
9f4a2713aSLionel Sambuc //
10f4a2713aSLionel Sambuc //  This file defines the ASTReader class, which reads AST files.
11f4a2713aSLionel Sambuc //
12f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
13f4a2713aSLionel Sambuc 
14f4a2713aSLionel Sambuc #include "clang/Serialization/ASTReader.h"
15f4a2713aSLionel Sambuc #include "ASTCommon.h"
16f4a2713aSLionel Sambuc #include "ASTReaderInternals.h"
17f4a2713aSLionel Sambuc #include "clang/AST/ASTConsumer.h"
18f4a2713aSLionel Sambuc #include "clang/AST/ASTContext.h"
19f4a2713aSLionel Sambuc #include "clang/AST/DeclTemplate.h"
20f4a2713aSLionel Sambuc #include "clang/AST/Expr.h"
21f4a2713aSLionel Sambuc #include "clang/AST/ExprCXX.h"
22f4a2713aSLionel Sambuc #include "clang/AST/NestedNameSpecifier.h"
23f4a2713aSLionel Sambuc #include "clang/AST/Type.h"
24f4a2713aSLionel Sambuc #include "clang/AST/TypeLocVisitor.h"
25*0a6a1f1dSLionel Sambuc #include "clang/Basic/DiagnosticOptions.h"
26f4a2713aSLionel Sambuc #include "clang/Basic/FileManager.h"
27f4a2713aSLionel Sambuc #include "clang/Basic/SourceManager.h"
28f4a2713aSLionel Sambuc #include "clang/Basic/SourceManagerInternals.h"
29f4a2713aSLionel Sambuc #include "clang/Basic/TargetInfo.h"
30f4a2713aSLionel Sambuc #include "clang/Basic/TargetOptions.h"
31f4a2713aSLionel Sambuc #include "clang/Basic/Version.h"
32f4a2713aSLionel Sambuc #include "clang/Basic/VersionTuple.h"
33*0a6a1f1dSLionel Sambuc #include "clang/Frontend/Utils.h"
34f4a2713aSLionel Sambuc #include "clang/Lex/HeaderSearch.h"
35f4a2713aSLionel Sambuc #include "clang/Lex/HeaderSearchOptions.h"
36f4a2713aSLionel Sambuc #include "clang/Lex/MacroInfo.h"
37f4a2713aSLionel Sambuc #include "clang/Lex/PreprocessingRecord.h"
38f4a2713aSLionel Sambuc #include "clang/Lex/Preprocessor.h"
39f4a2713aSLionel Sambuc #include "clang/Lex/PreprocessorOptions.h"
40f4a2713aSLionel Sambuc #include "clang/Sema/Scope.h"
41f4a2713aSLionel Sambuc #include "clang/Sema/Sema.h"
42f4a2713aSLionel Sambuc #include "clang/Serialization/ASTDeserializationListener.h"
43f4a2713aSLionel Sambuc #include "clang/Serialization/GlobalModuleIndex.h"
44f4a2713aSLionel Sambuc #include "clang/Serialization/ModuleManager.h"
45f4a2713aSLionel Sambuc #include "clang/Serialization/SerializationDiagnostic.h"
46f4a2713aSLionel Sambuc #include "llvm/ADT/Hashing.h"
47f4a2713aSLionel Sambuc #include "llvm/ADT/StringExtras.h"
48f4a2713aSLionel Sambuc #include "llvm/Bitcode/BitstreamReader.h"
49f4a2713aSLionel Sambuc #include "llvm/Support/ErrorHandling.h"
50f4a2713aSLionel Sambuc #include "llvm/Support/FileSystem.h"
51f4a2713aSLionel Sambuc #include "llvm/Support/MemoryBuffer.h"
52f4a2713aSLionel Sambuc #include "llvm/Support/Path.h"
53f4a2713aSLionel Sambuc #include "llvm/Support/SaveAndRestore.h"
54*0a6a1f1dSLionel Sambuc #include "llvm/Support/raw_ostream.h"
55f4a2713aSLionel Sambuc #include <algorithm>
56f4a2713aSLionel Sambuc #include <cstdio>
57f4a2713aSLionel Sambuc #include <iterator>
58*0a6a1f1dSLionel Sambuc #include <system_error>
59f4a2713aSLionel Sambuc 
60f4a2713aSLionel Sambuc using namespace clang;
61f4a2713aSLionel Sambuc using namespace clang::serialization;
62f4a2713aSLionel Sambuc using namespace clang::serialization::reader;
63f4a2713aSLionel Sambuc using llvm::BitstreamCursor;
64f4a2713aSLionel Sambuc 
65*0a6a1f1dSLionel Sambuc 
66*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===//
67*0a6a1f1dSLionel Sambuc // ChainedASTReaderListener implementation
68*0a6a1f1dSLionel Sambuc //===----------------------------------------------------------------------===//
69*0a6a1f1dSLionel Sambuc 
70*0a6a1f1dSLionel Sambuc bool
ReadFullVersionInformation(StringRef FullVersion)71*0a6a1f1dSLionel Sambuc ChainedASTReaderListener::ReadFullVersionInformation(StringRef FullVersion) {
72*0a6a1f1dSLionel Sambuc   return First->ReadFullVersionInformation(FullVersion) ||
73*0a6a1f1dSLionel Sambuc          Second->ReadFullVersionInformation(FullVersion);
74*0a6a1f1dSLionel Sambuc }
ReadModuleName(StringRef ModuleName)75*0a6a1f1dSLionel Sambuc void ChainedASTReaderListener::ReadModuleName(StringRef ModuleName) {
76*0a6a1f1dSLionel Sambuc   First->ReadModuleName(ModuleName);
77*0a6a1f1dSLionel Sambuc   Second->ReadModuleName(ModuleName);
78*0a6a1f1dSLionel Sambuc }
ReadModuleMapFile(StringRef ModuleMapPath)79*0a6a1f1dSLionel Sambuc void ChainedASTReaderListener::ReadModuleMapFile(StringRef ModuleMapPath) {
80*0a6a1f1dSLionel Sambuc   First->ReadModuleMapFile(ModuleMapPath);
81*0a6a1f1dSLionel Sambuc   Second->ReadModuleMapFile(ModuleMapPath);
82*0a6a1f1dSLionel Sambuc }
83*0a6a1f1dSLionel Sambuc bool
ReadLanguageOptions(const LangOptions & LangOpts,bool Complain,bool AllowCompatibleDifferences)84*0a6a1f1dSLionel Sambuc ChainedASTReaderListener::ReadLanguageOptions(const LangOptions &LangOpts,
85*0a6a1f1dSLionel Sambuc                                               bool Complain,
86*0a6a1f1dSLionel Sambuc                                               bool AllowCompatibleDifferences) {
87*0a6a1f1dSLionel Sambuc   return First->ReadLanguageOptions(LangOpts, Complain,
88*0a6a1f1dSLionel Sambuc                                     AllowCompatibleDifferences) ||
89*0a6a1f1dSLionel Sambuc          Second->ReadLanguageOptions(LangOpts, Complain,
90*0a6a1f1dSLionel Sambuc                                      AllowCompatibleDifferences);
91*0a6a1f1dSLionel Sambuc }
92*0a6a1f1dSLionel Sambuc bool
ReadTargetOptions(const TargetOptions & TargetOpts,bool Complain)93*0a6a1f1dSLionel Sambuc ChainedASTReaderListener::ReadTargetOptions(const TargetOptions &TargetOpts,
94*0a6a1f1dSLionel Sambuc                                             bool Complain) {
95*0a6a1f1dSLionel Sambuc   return First->ReadTargetOptions(TargetOpts, Complain) ||
96*0a6a1f1dSLionel Sambuc          Second->ReadTargetOptions(TargetOpts, Complain);
97*0a6a1f1dSLionel Sambuc }
ReadDiagnosticOptions(IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts,bool Complain)98*0a6a1f1dSLionel Sambuc bool ChainedASTReaderListener::ReadDiagnosticOptions(
99*0a6a1f1dSLionel Sambuc     IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts, bool Complain) {
100*0a6a1f1dSLionel Sambuc   return First->ReadDiagnosticOptions(DiagOpts, Complain) ||
101*0a6a1f1dSLionel Sambuc          Second->ReadDiagnosticOptions(DiagOpts, Complain);
102*0a6a1f1dSLionel Sambuc }
103*0a6a1f1dSLionel Sambuc bool
ReadFileSystemOptions(const FileSystemOptions & FSOpts,bool Complain)104*0a6a1f1dSLionel Sambuc ChainedASTReaderListener::ReadFileSystemOptions(const FileSystemOptions &FSOpts,
105*0a6a1f1dSLionel Sambuc                                                 bool Complain) {
106*0a6a1f1dSLionel Sambuc   return First->ReadFileSystemOptions(FSOpts, Complain) ||
107*0a6a1f1dSLionel Sambuc          Second->ReadFileSystemOptions(FSOpts, Complain);
108*0a6a1f1dSLionel Sambuc }
109*0a6a1f1dSLionel Sambuc 
ReadHeaderSearchOptions(const HeaderSearchOptions & HSOpts,bool Complain)110*0a6a1f1dSLionel Sambuc bool ChainedASTReaderListener::ReadHeaderSearchOptions(
111*0a6a1f1dSLionel Sambuc     const HeaderSearchOptions &HSOpts, bool Complain) {
112*0a6a1f1dSLionel Sambuc   return First->ReadHeaderSearchOptions(HSOpts, Complain) ||
113*0a6a1f1dSLionel Sambuc          Second->ReadHeaderSearchOptions(HSOpts, Complain);
114*0a6a1f1dSLionel Sambuc }
ReadPreprocessorOptions(const PreprocessorOptions & PPOpts,bool Complain,std::string & SuggestedPredefines)115*0a6a1f1dSLionel Sambuc bool ChainedASTReaderListener::ReadPreprocessorOptions(
116*0a6a1f1dSLionel Sambuc     const PreprocessorOptions &PPOpts, bool Complain,
117*0a6a1f1dSLionel Sambuc     std::string &SuggestedPredefines) {
118*0a6a1f1dSLionel Sambuc   return First->ReadPreprocessorOptions(PPOpts, Complain,
119*0a6a1f1dSLionel Sambuc                                         SuggestedPredefines) ||
120*0a6a1f1dSLionel Sambuc          Second->ReadPreprocessorOptions(PPOpts, Complain, SuggestedPredefines);
121*0a6a1f1dSLionel Sambuc }
ReadCounter(const serialization::ModuleFile & M,unsigned Value)122*0a6a1f1dSLionel Sambuc void ChainedASTReaderListener::ReadCounter(const serialization::ModuleFile &M,
123*0a6a1f1dSLionel Sambuc                                            unsigned Value) {
124*0a6a1f1dSLionel Sambuc   First->ReadCounter(M, Value);
125*0a6a1f1dSLionel Sambuc   Second->ReadCounter(M, Value);
126*0a6a1f1dSLionel Sambuc }
needsInputFileVisitation()127*0a6a1f1dSLionel Sambuc bool ChainedASTReaderListener::needsInputFileVisitation() {
128*0a6a1f1dSLionel Sambuc   return First->needsInputFileVisitation() ||
129*0a6a1f1dSLionel Sambuc          Second->needsInputFileVisitation();
130*0a6a1f1dSLionel Sambuc }
needsSystemInputFileVisitation()131*0a6a1f1dSLionel Sambuc bool ChainedASTReaderListener::needsSystemInputFileVisitation() {
132*0a6a1f1dSLionel Sambuc   return First->needsSystemInputFileVisitation() ||
133*0a6a1f1dSLionel Sambuc   Second->needsSystemInputFileVisitation();
134*0a6a1f1dSLionel Sambuc }
visitModuleFile(StringRef Filename)135*0a6a1f1dSLionel Sambuc void ChainedASTReaderListener::visitModuleFile(StringRef Filename) {
136*0a6a1f1dSLionel Sambuc   First->visitModuleFile(Filename);
137*0a6a1f1dSLionel Sambuc   Second->visitModuleFile(Filename);
138*0a6a1f1dSLionel Sambuc }
visitInputFile(StringRef Filename,bool isSystem,bool isOverridden)139*0a6a1f1dSLionel Sambuc bool ChainedASTReaderListener::visitInputFile(StringRef Filename,
140*0a6a1f1dSLionel Sambuc                                               bool isSystem,
141*0a6a1f1dSLionel Sambuc                                               bool isOverridden) {
142*0a6a1f1dSLionel Sambuc   bool Continue = false;
143*0a6a1f1dSLionel Sambuc   if (First->needsInputFileVisitation() &&
144*0a6a1f1dSLionel Sambuc       (!isSystem || First->needsSystemInputFileVisitation()))
145*0a6a1f1dSLionel Sambuc     Continue |= First->visitInputFile(Filename, isSystem, isOverridden);
146*0a6a1f1dSLionel Sambuc   if (Second->needsInputFileVisitation() &&
147*0a6a1f1dSLionel Sambuc       (!isSystem || Second->needsSystemInputFileVisitation()))
148*0a6a1f1dSLionel Sambuc     Continue |= Second->visitInputFile(Filename, isSystem, isOverridden);
149*0a6a1f1dSLionel Sambuc   return Continue;
150*0a6a1f1dSLionel Sambuc }
151*0a6a1f1dSLionel Sambuc 
152f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
153f4a2713aSLionel Sambuc // PCH validator implementation
154f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
155f4a2713aSLionel Sambuc 
~ASTReaderListener()156f4a2713aSLionel Sambuc ASTReaderListener::~ASTReaderListener() {}
157f4a2713aSLionel Sambuc 
158f4a2713aSLionel Sambuc /// \brief Compare the given set of language options against an existing set of
159f4a2713aSLionel Sambuc /// language options.
160f4a2713aSLionel Sambuc ///
161f4a2713aSLionel Sambuc /// \param Diags If non-NULL, diagnostics will be emitted via this engine.
162*0a6a1f1dSLionel Sambuc /// \param AllowCompatibleDifferences If true, differences between compatible
163*0a6a1f1dSLionel Sambuc ///        language options will be permitted.
164f4a2713aSLionel Sambuc ///
165f4a2713aSLionel Sambuc /// \returns true if the languagae options mis-match, false otherwise.
checkLanguageOptions(const LangOptions & LangOpts,const LangOptions & ExistingLangOpts,DiagnosticsEngine * Diags,bool AllowCompatibleDifferences=true)166f4a2713aSLionel Sambuc static bool checkLanguageOptions(const LangOptions &LangOpts,
167f4a2713aSLionel Sambuc                                  const LangOptions &ExistingLangOpts,
168*0a6a1f1dSLionel Sambuc                                  DiagnosticsEngine *Diags,
169*0a6a1f1dSLionel Sambuc                                  bool AllowCompatibleDifferences = true) {
170f4a2713aSLionel Sambuc #define LANGOPT(Name, Bits, Default, Description)                 \
171f4a2713aSLionel Sambuc   if (ExistingLangOpts.Name != LangOpts.Name) {                   \
172f4a2713aSLionel Sambuc     if (Diags)                                                    \
173f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_langopt_mismatch)               \
174f4a2713aSLionel Sambuc         << Description << LangOpts.Name << ExistingLangOpts.Name; \
175f4a2713aSLionel Sambuc     return true;                                                  \
176f4a2713aSLionel Sambuc   }
177f4a2713aSLionel Sambuc 
178f4a2713aSLionel Sambuc #define VALUE_LANGOPT(Name, Bits, Default, Description)   \
179f4a2713aSLionel Sambuc   if (ExistingLangOpts.Name != LangOpts.Name) {           \
180f4a2713aSLionel Sambuc     if (Diags)                                            \
181f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_langopt_value_mismatch) \
182f4a2713aSLionel Sambuc         << Description;                                   \
183f4a2713aSLionel Sambuc     return true;                                          \
184f4a2713aSLionel Sambuc   }
185f4a2713aSLionel Sambuc 
186f4a2713aSLionel Sambuc #define ENUM_LANGOPT(Name, Type, Bits, Default, Description)   \
187f4a2713aSLionel Sambuc   if (ExistingLangOpts.get##Name() != LangOpts.get##Name()) {  \
188f4a2713aSLionel Sambuc     if (Diags)                                                 \
189f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_langopt_value_mismatch)      \
190f4a2713aSLionel Sambuc         << Description;                                        \
191f4a2713aSLionel Sambuc     return true;                                               \
192f4a2713aSLionel Sambuc   }
193f4a2713aSLionel Sambuc 
194*0a6a1f1dSLionel Sambuc #define COMPATIBLE_LANGOPT(Name, Bits, Default, Description)  \
195*0a6a1f1dSLionel Sambuc   if (!AllowCompatibleDifferences)                            \
196*0a6a1f1dSLionel Sambuc     LANGOPT(Name, Bits, Default, Description)
197*0a6a1f1dSLionel Sambuc 
198*0a6a1f1dSLionel Sambuc #define COMPATIBLE_ENUM_LANGOPT(Name, Bits, Default, Description)  \
199*0a6a1f1dSLionel Sambuc   if (!AllowCompatibleDifferences)                                 \
200*0a6a1f1dSLionel Sambuc     ENUM_LANGOPT(Name, Bits, Default, Description)
201*0a6a1f1dSLionel Sambuc 
202f4a2713aSLionel Sambuc #define BENIGN_LANGOPT(Name, Bits, Default, Description)
203f4a2713aSLionel Sambuc #define BENIGN_ENUM_LANGOPT(Name, Type, Bits, Default, Description)
204f4a2713aSLionel Sambuc #include "clang/Basic/LangOptions.def"
205f4a2713aSLionel Sambuc 
206f4a2713aSLionel Sambuc   if (ExistingLangOpts.ObjCRuntime != LangOpts.ObjCRuntime) {
207f4a2713aSLionel Sambuc     if (Diags)
208f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_langopt_value_mismatch)
209f4a2713aSLionel Sambuc       << "target Objective-C runtime";
210f4a2713aSLionel Sambuc     return true;
211f4a2713aSLionel Sambuc   }
212f4a2713aSLionel Sambuc 
213f4a2713aSLionel Sambuc   if (ExistingLangOpts.CommentOpts.BlockCommandNames !=
214f4a2713aSLionel Sambuc       LangOpts.CommentOpts.BlockCommandNames) {
215f4a2713aSLionel Sambuc     if (Diags)
216f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_langopt_value_mismatch)
217f4a2713aSLionel Sambuc         << "block command names";
218f4a2713aSLionel Sambuc     return true;
219f4a2713aSLionel Sambuc   }
220f4a2713aSLionel Sambuc 
221f4a2713aSLionel Sambuc   return false;
222f4a2713aSLionel Sambuc }
223f4a2713aSLionel Sambuc 
224f4a2713aSLionel Sambuc /// \brief Compare the given set of target options against an existing set of
225f4a2713aSLionel Sambuc /// target options.
226f4a2713aSLionel Sambuc ///
227f4a2713aSLionel Sambuc /// \param Diags If non-NULL, diagnostics will be emitted via this engine.
228f4a2713aSLionel Sambuc ///
229f4a2713aSLionel Sambuc /// \returns true if the target options mis-match, false otherwise.
checkTargetOptions(const TargetOptions & TargetOpts,const TargetOptions & ExistingTargetOpts,DiagnosticsEngine * Diags)230f4a2713aSLionel Sambuc static bool checkTargetOptions(const TargetOptions &TargetOpts,
231f4a2713aSLionel Sambuc                                const TargetOptions &ExistingTargetOpts,
232f4a2713aSLionel Sambuc                                DiagnosticsEngine *Diags) {
233f4a2713aSLionel Sambuc #define CHECK_TARGET_OPT(Field, Name)                             \
234f4a2713aSLionel Sambuc   if (TargetOpts.Field != ExistingTargetOpts.Field) {             \
235f4a2713aSLionel Sambuc     if (Diags)                                                    \
236f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_targetopt_mismatch)             \
237f4a2713aSLionel Sambuc         << Name << TargetOpts.Field << ExistingTargetOpts.Field;  \
238f4a2713aSLionel Sambuc     return true;                                                  \
239f4a2713aSLionel Sambuc   }
240f4a2713aSLionel Sambuc 
241f4a2713aSLionel Sambuc   CHECK_TARGET_OPT(Triple, "target");
242f4a2713aSLionel Sambuc   CHECK_TARGET_OPT(CPU, "target CPU");
243f4a2713aSLionel Sambuc   CHECK_TARGET_OPT(ABI, "target ABI");
244f4a2713aSLionel Sambuc #undef CHECK_TARGET_OPT
245f4a2713aSLionel Sambuc 
246f4a2713aSLionel Sambuc   // Compare feature sets.
247f4a2713aSLionel Sambuc   SmallVector<StringRef, 4> ExistingFeatures(
248f4a2713aSLionel Sambuc                                              ExistingTargetOpts.FeaturesAsWritten.begin(),
249f4a2713aSLionel Sambuc                                              ExistingTargetOpts.FeaturesAsWritten.end());
250f4a2713aSLionel Sambuc   SmallVector<StringRef, 4> ReadFeatures(TargetOpts.FeaturesAsWritten.begin(),
251f4a2713aSLionel Sambuc                                          TargetOpts.FeaturesAsWritten.end());
252f4a2713aSLionel Sambuc   std::sort(ExistingFeatures.begin(), ExistingFeatures.end());
253f4a2713aSLionel Sambuc   std::sort(ReadFeatures.begin(), ReadFeatures.end());
254f4a2713aSLionel Sambuc 
255f4a2713aSLionel Sambuc   unsigned ExistingIdx = 0, ExistingN = ExistingFeatures.size();
256f4a2713aSLionel Sambuc   unsigned ReadIdx = 0, ReadN = ReadFeatures.size();
257f4a2713aSLionel Sambuc   while (ExistingIdx < ExistingN && ReadIdx < ReadN) {
258f4a2713aSLionel Sambuc     if (ExistingFeatures[ExistingIdx] == ReadFeatures[ReadIdx]) {
259f4a2713aSLionel Sambuc       ++ExistingIdx;
260f4a2713aSLionel Sambuc       ++ReadIdx;
261f4a2713aSLionel Sambuc       continue;
262f4a2713aSLionel Sambuc     }
263f4a2713aSLionel Sambuc 
264f4a2713aSLionel Sambuc     if (ReadFeatures[ReadIdx] < ExistingFeatures[ExistingIdx]) {
265f4a2713aSLionel Sambuc       if (Diags)
266f4a2713aSLionel Sambuc         Diags->Report(diag::err_pch_targetopt_feature_mismatch)
267f4a2713aSLionel Sambuc           << false << ReadFeatures[ReadIdx];
268f4a2713aSLionel Sambuc       return true;
269f4a2713aSLionel Sambuc     }
270f4a2713aSLionel Sambuc 
271f4a2713aSLionel Sambuc     if (Diags)
272f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_targetopt_feature_mismatch)
273f4a2713aSLionel Sambuc         << true << ExistingFeatures[ExistingIdx];
274f4a2713aSLionel Sambuc     return true;
275f4a2713aSLionel Sambuc   }
276f4a2713aSLionel Sambuc 
277f4a2713aSLionel Sambuc   if (ExistingIdx < ExistingN) {
278f4a2713aSLionel Sambuc     if (Diags)
279f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_targetopt_feature_mismatch)
280f4a2713aSLionel Sambuc         << true << ExistingFeatures[ExistingIdx];
281f4a2713aSLionel Sambuc     return true;
282f4a2713aSLionel Sambuc   }
283f4a2713aSLionel Sambuc 
284f4a2713aSLionel Sambuc   if (ReadIdx < ReadN) {
285f4a2713aSLionel Sambuc     if (Diags)
286f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_targetopt_feature_mismatch)
287f4a2713aSLionel Sambuc         << false << ReadFeatures[ReadIdx];
288f4a2713aSLionel Sambuc     return true;
289f4a2713aSLionel Sambuc   }
290f4a2713aSLionel Sambuc 
291f4a2713aSLionel Sambuc   return false;
292f4a2713aSLionel Sambuc }
293f4a2713aSLionel Sambuc 
294f4a2713aSLionel Sambuc bool
ReadLanguageOptions(const LangOptions & LangOpts,bool Complain,bool AllowCompatibleDifferences)295f4a2713aSLionel Sambuc PCHValidator::ReadLanguageOptions(const LangOptions &LangOpts,
296*0a6a1f1dSLionel Sambuc                                   bool Complain,
297*0a6a1f1dSLionel Sambuc                                   bool AllowCompatibleDifferences) {
298f4a2713aSLionel Sambuc   const LangOptions &ExistingLangOpts = PP.getLangOpts();
299f4a2713aSLionel Sambuc   return checkLanguageOptions(LangOpts, ExistingLangOpts,
300*0a6a1f1dSLionel Sambuc                               Complain ? &Reader.Diags : nullptr,
301*0a6a1f1dSLionel Sambuc                               AllowCompatibleDifferences);
302f4a2713aSLionel Sambuc }
303f4a2713aSLionel Sambuc 
ReadTargetOptions(const TargetOptions & TargetOpts,bool Complain)304f4a2713aSLionel Sambuc bool PCHValidator::ReadTargetOptions(const TargetOptions &TargetOpts,
305f4a2713aSLionel Sambuc                                      bool Complain) {
306f4a2713aSLionel Sambuc   const TargetOptions &ExistingTargetOpts = PP.getTargetInfo().getTargetOpts();
307f4a2713aSLionel Sambuc   return checkTargetOptions(TargetOpts, ExistingTargetOpts,
308*0a6a1f1dSLionel Sambuc                             Complain? &Reader.Diags : nullptr);
309f4a2713aSLionel Sambuc }
310f4a2713aSLionel Sambuc 
311f4a2713aSLionel Sambuc namespace {
312f4a2713aSLionel Sambuc   typedef llvm::StringMap<std::pair<StringRef, bool /*IsUndef*/> >
313f4a2713aSLionel Sambuc     MacroDefinitionsMap;
314f4a2713aSLionel Sambuc   typedef llvm::DenseMap<DeclarationName, SmallVector<NamedDecl *, 8> >
315f4a2713aSLionel Sambuc     DeclsMap;
316f4a2713aSLionel Sambuc }
317f4a2713aSLionel Sambuc 
checkDiagnosticGroupMappings(DiagnosticsEngine & StoredDiags,DiagnosticsEngine & Diags,bool Complain)318*0a6a1f1dSLionel Sambuc static bool checkDiagnosticGroupMappings(DiagnosticsEngine &StoredDiags,
319*0a6a1f1dSLionel Sambuc                                          DiagnosticsEngine &Diags,
320*0a6a1f1dSLionel Sambuc                                          bool Complain) {
321*0a6a1f1dSLionel Sambuc   typedef DiagnosticsEngine::Level Level;
322*0a6a1f1dSLionel Sambuc 
323*0a6a1f1dSLionel Sambuc   // Check current mappings for new -Werror mappings, and the stored mappings
324*0a6a1f1dSLionel Sambuc   // for cases that were explicitly mapped to *not* be errors that are now
325*0a6a1f1dSLionel Sambuc   // errors because of options like -Werror.
326*0a6a1f1dSLionel Sambuc   DiagnosticsEngine *MappingSources[] = { &Diags, &StoredDiags };
327*0a6a1f1dSLionel Sambuc 
328*0a6a1f1dSLionel Sambuc   for (DiagnosticsEngine *MappingSource : MappingSources) {
329*0a6a1f1dSLionel Sambuc     for (auto DiagIDMappingPair : MappingSource->getDiagnosticMappings()) {
330*0a6a1f1dSLionel Sambuc       diag::kind DiagID = DiagIDMappingPair.first;
331*0a6a1f1dSLionel Sambuc       Level CurLevel = Diags.getDiagnosticLevel(DiagID, SourceLocation());
332*0a6a1f1dSLionel Sambuc       if (CurLevel < DiagnosticsEngine::Error)
333*0a6a1f1dSLionel Sambuc         continue; // not significant
334*0a6a1f1dSLionel Sambuc       Level StoredLevel =
335*0a6a1f1dSLionel Sambuc           StoredDiags.getDiagnosticLevel(DiagID, SourceLocation());
336*0a6a1f1dSLionel Sambuc       if (StoredLevel < DiagnosticsEngine::Error) {
337*0a6a1f1dSLionel Sambuc         if (Complain)
338*0a6a1f1dSLionel Sambuc           Diags.Report(diag::err_pch_diagopt_mismatch) << "-Werror=" +
339*0a6a1f1dSLionel Sambuc               Diags.getDiagnosticIDs()->getWarningOptionForDiag(DiagID).str();
340*0a6a1f1dSLionel Sambuc         return true;
341*0a6a1f1dSLionel Sambuc       }
342*0a6a1f1dSLionel Sambuc     }
343*0a6a1f1dSLionel Sambuc   }
344*0a6a1f1dSLionel Sambuc 
345*0a6a1f1dSLionel Sambuc   return false;
346*0a6a1f1dSLionel Sambuc }
347*0a6a1f1dSLionel Sambuc 
isExtHandlingFromDiagsError(DiagnosticsEngine & Diags)348*0a6a1f1dSLionel Sambuc static bool isExtHandlingFromDiagsError(DiagnosticsEngine &Diags) {
349*0a6a1f1dSLionel Sambuc   diag::Severity Ext = Diags.getExtensionHandlingBehavior();
350*0a6a1f1dSLionel Sambuc   if (Ext == diag::Severity::Warning && Diags.getWarningsAsErrors())
351*0a6a1f1dSLionel Sambuc     return true;
352*0a6a1f1dSLionel Sambuc   return Ext >= diag::Severity::Error;
353*0a6a1f1dSLionel Sambuc }
354*0a6a1f1dSLionel Sambuc 
checkDiagnosticMappings(DiagnosticsEngine & StoredDiags,DiagnosticsEngine & Diags,bool IsSystem,bool Complain)355*0a6a1f1dSLionel Sambuc static bool checkDiagnosticMappings(DiagnosticsEngine &StoredDiags,
356*0a6a1f1dSLionel Sambuc                                     DiagnosticsEngine &Diags,
357*0a6a1f1dSLionel Sambuc                                     bool IsSystem, bool Complain) {
358*0a6a1f1dSLionel Sambuc   // Top-level options
359*0a6a1f1dSLionel Sambuc   if (IsSystem) {
360*0a6a1f1dSLionel Sambuc     if (Diags.getSuppressSystemWarnings())
361*0a6a1f1dSLionel Sambuc       return false;
362*0a6a1f1dSLionel Sambuc     // If -Wsystem-headers was not enabled before, be conservative
363*0a6a1f1dSLionel Sambuc     if (StoredDiags.getSuppressSystemWarnings()) {
364*0a6a1f1dSLionel Sambuc       if (Complain)
365*0a6a1f1dSLionel Sambuc         Diags.Report(diag::err_pch_diagopt_mismatch) << "-Wsystem-headers";
366*0a6a1f1dSLionel Sambuc       return true;
367*0a6a1f1dSLionel Sambuc     }
368*0a6a1f1dSLionel Sambuc   }
369*0a6a1f1dSLionel Sambuc 
370*0a6a1f1dSLionel Sambuc   if (Diags.getWarningsAsErrors() && !StoredDiags.getWarningsAsErrors()) {
371*0a6a1f1dSLionel Sambuc     if (Complain)
372*0a6a1f1dSLionel Sambuc       Diags.Report(diag::err_pch_diagopt_mismatch) << "-Werror";
373*0a6a1f1dSLionel Sambuc     return true;
374*0a6a1f1dSLionel Sambuc   }
375*0a6a1f1dSLionel Sambuc 
376*0a6a1f1dSLionel Sambuc   if (Diags.getWarningsAsErrors() && Diags.getEnableAllWarnings() &&
377*0a6a1f1dSLionel Sambuc       !StoredDiags.getEnableAllWarnings()) {
378*0a6a1f1dSLionel Sambuc     if (Complain)
379*0a6a1f1dSLionel Sambuc       Diags.Report(diag::err_pch_diagopt_mismatch) << "-Weverything -Werror";
380*0a6a1f1dSLionel Sambuc     return true;
381*0a6a1f1dSLionel Sambuc   }
382*0a6a1f1dSLionel Sambuc 
383*0a6a1f1dSLionel Sambuc   if (isExtHandlingFromDiagsError(Diags) &&
384*0a6a1f1dSLionel Sambuc       !isExtHandlingFromDiagsError(StoredDiags)) {
385*0a6a1f1dSLionel Sambuc     if (Complain)
386*0a6a1f1dSLionel Sambuc       Diags.Report(diag::err_pch_diagopt_mismatch) << "-pedantic-errors";
387*0a6a1f1dSLionel Sambuc     return true;
388*0a6a1f1dSLionel Sambuc   }
389*0a6a1f1dSLionel Sambuc 
390*0a6a1f1dSLionel Sambuc   return checkDiagnosticGroupMappings(StoredDiags, Diags, Complain);
391*0a6a1f1dSLionel Sambuc }
392*0a6a1f1dSLionel Sambuc 
ReadDiagnosticOptions(IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts,bool Complain)393*0a6a1f1dSLionel Sambuc bool PCHValidator::ReadDiagnosticOptions(
394*0a6a1f1dSLionel Sambuc     IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts, bool Complain) {
395*0a6a1f1dSLionel Sambuc   DiagnosticsEngine &ExistingDiags = PP.getDiagnostics();
396*0a6a1f1dSLionel Sambuc   IntrusiveRefCntPtr<DiagnosticIDs> DiagIDs(ExistingDiags.getDiagnosticIDs());
397*0a6a1f1dSLionel Sambuc   IntrusiveRefCntPtr<DiagnosticsEngine> Diags(
398*0a6a1f1dSLionel Sambuc       new DiagnosticsEngine(DiagIDs, DiagOpts.get()));
399*0a6a1f1dSLionel Sambuc   // This should never fail, because we would have processed these options
400*0a6a1f1dSLionel Sambuc   // before writing them to an ASTFile.
401*0a6a1f1dSLionel Sambuc   ProcessWarningOptions(*Diags, *DiagOpts, /*Report*/false);
402*0a6a1f1dSLionel Sambuc 
403*0a6a1f1dSLionel Sambuc   ModuleManager &ModuleMgr = Reader.getModuleManager();
404*0a6a1f1dSLionel Sambuc   assert(ModuleMgr.size() >= 1 && "what ASTFile is this then");
405*0a6a1f1dSLionel Sambuc 
406*0a6a1f1dSLionel Sambuc   // If the original import came from a file explicitly generated by the user,
407*0a6a1f1dSLionel Sambuc   // don't check the diagnostic mappings.
408*0a6a1f1dSLionel Sambuc   // FIXME: currently this is approximated by checking whether this is not a
409*0a6a1f1dSLionel Sambuc   // module import of an implicitly-loaded module file.
410*0a6a1f1dSLionel Sambuc   // Note: ModuleMgr.rbegin() may not be the current module, but it must be in
411*0a6a1f1dSLionel Sambuc   // the transitive closure of its imports, since unrelated modules cannot be
412*0a6a1f1dSLionel Sambuc   // imported until after this module finishes validation.
413*0a6a1f1dSLionel Sambuc   ModuleFile *TopImport = *ModuleMgr.rbegin();
414*0a6a1f1dSLionel Sambuc   while (!TopImport->ImportedBy.empty())
415*0a6a1f1dSLionel Sambuc     TopImport = TopImport->ImportedBy[0];
416*0a6a1f1dSLionel Sambuc   if (TopImport->Kind != MK_ImplicitModule)
417*0a6a1f1dSLionel Sambuc     return false;
418*0a6a1f1dSLionel Sambuc 
419*0a6a1f1dSLionel Sambuc   StringRef ModuleName = TopImport->ModuleName;
420*0a6a1f1dSLionel Sambuc   assert(!ModuleName.empty() && "diagnostic options read before module name");
421*0a6a1f1dSLionel Sambuc 
422*0a6a1f1dSLionel Sambuc   Module *M = PP.getHeaderSearchInfo().lookupModule(ModuleName);
423*0a6a1f1dSLionel Sambuc   assert(M && "missing module");
424*0a6a1f1dSLionel Sambuc 
425*0a6a1f1dSLionel Sambuc   // FIXME: if the diagnostics are incompatible, save a DiagnosticOptions that
426*0a6a1f1dSLionel Sambuc   // contains the union of their flags.
427*0a6a1f1dSLionel Sambuc   return checkDiagnosticMappings(*Diags, ExistingDiags, M->IsSystem, Complain);
428*0a6a1f1dSLionel Sambuc }
429*0a6a1f1dSLionel Sambuc 
430f4a2713aSLionel Sambuc /// \brief Collect the macro definitions provided by the given preprocessor
431f4a2713aSLionel Sambuc /// options.
432*0a6a1f1dSLionel Sambuc static void
collectMacroDefinitions(const PreprocessorOptions & PPOpts,MacroDefinitionsMap & Macros,SmallVectorImpl<StringRef> * MacroNames=nullptr)433*0a6a1f1dSLionel Sambuc collectMacroDefinitions(const PreprocessorOptions &PPOpts,
434f4a2713aSLionel Sambuc                         MacroDefinitionsMap &Macros,
435*0a6a1f1dSLionel Sambuc                         SmallVectorImpl<StringRef> *MacroNames = nullptr) {
436f4a2713aSLionel Sambuc   for (unsigned I = 0, N = PPOpts.Macros.size(); I != N; ++I) {
437f4a2713aSLionel Sambuc     StringRef Macro = PPOpts.Macros[I].first;
438f4a2713aSLionel Sambuc     bool IsUndef = PPOpts.Macros[I].second;
439f4a2713aSLionel Sambuc 
440f4a2713aSLionel Sambuc     std::pair<StringRef, StringRef> MacroPair = Macro.split('=');
441f4a2713aSLionel Sambuc     StringRef MacroName = MacroPair.first;
442f4a2713aSLionel Sambuc     StringRef MacroBody = MacroPair.second;
443f4a2713aSLionel Sambuc 
444f4a2713aSLionel Sambuc     // For an #undef'd macro, we only care about the name.
445f4a2713aSLionel Sambuc     if (IsUndef) {
446f4a2713aSLionel Sambuc       if (MacroNames && !Macros.count(MacroName))
447f4a2713aSLionel Sambuc         MacroNames->push_back(MacroName);
448f4a2713aSLionel Sambuc 
449f4a2713aSLionel Sambuc       Macros[MacroName] = std::make_pair("", true);
450f4a2713aSLionel Sambuc       continue;
451f4a2713aSLionel Sambuc     }
452f4a2713aSLionel Sambuc 
453f4a2713aSLionel Sambuc     // For a #define'd macro, figure out the actual definition.
454f4a2713aSLionel Sambuc     if (MacroName.size() == Macro.size())
455f4a2713aSLionel Sambuc       MacroBody = "1";
456f4a2713aSLionel Sambuc     else {
457f4a2713aSLionel Sambuc       // Note: GCC drops anything following an end-of-line character.
458f4a2713aSLionel Sambuc       StringRef::size_type End = MacroBody.find_first_of("\n\r");
459f4a2713aSLionel Sambuc       MacroBody = MacroBody.substr(0, End);
460f4a2713aSLionel Sambuc     }
461f4a2713aSLionel Sambuc 
462f4a2713aSLionel Sambuc     if (MacroNames && !Macros.count(MacroName))
463f4a2713aSLionel Sambuc       MacroNames->push_back(MacroName);
464f4a2713aSLionel Sambuc     Macros[MacroName] = std::make_pair(MacroBody, false);
465f4a2713aSLionel Sambuc   }
466f4a2713aSLionel Sambuc }
467f4a2713aSLionel Sambuc 
468f4a2713aSLionel Sambuc /// \brief Check the preprocessor options deserialized from the control block
469f4a2713aSLionel Sambuc /// against the preprocessor options in an existing preprocessor.
470f4a2713aSLionel Sambuc ///
471f4a2713aSLionel Sambuc /// \param Diags If non-null, produce diagnostics for any mismatches incurred.
checkPreprocessorOptions(const PreprocessorOptions & PPOpts,const PreprocessorOptions & ExistingPPOpts,DiagnosticsEngine * Diags,FileManager & FileMgr,std::string & SuggestedPredefines,const LangOptions & LangOpts)472f4a2713aSLionel Sambuc static bool checkPreprocessorOptions(const PreprocessorOptions &PPOpts,
473f4a2713aSLionel Sambuc                                      const PreprocessorOptions &ExistingPPOpts,
474f4a2713aSLionel Sambuc                                      DiagnosticsEngine *Diags,
475f4a2713aSLionel Sambuc                                      FileManager &FileMgr,
476f4a2713aSLionel Sambuc                                      std::string &SuggestedPredefines,
477f4a2713aSLionel Sambuc                                      const LangOptions &LangOpts) {
478f4a2713aSLionel Sambuc   // Check macro definitions.
479f4a2713aSLionel Sambuc   MacroDefinitionsMap ASTFileMacros;
480f4a2713aSLionel Sambuc   collectMacroDefinitions(PPOpts, ASTFileMacros);
481f4a2713aSLionel Sambuc   MacroDefinitionsMap ExistingMacros;
482f4a2713aSLionel Sambuc   SmallVector<StringRef, 4> ExistingMacroNames;
483f4a2713aSLionel Sambuc   collectMacroDefinitions(ExistingPPOpts, ExistingMacros, &ExistingMacroNames);
484f4a2713aSLionel Sambuc 
485f4a2713aSLionel Sambuc   for (unsigned I = 0, N = ExistingMacroNames.size(); I != N; ++I) {
486f4a2713aSLionel Sambuc     // Dig out the macro definition in the existing preprocessor options.
487f4a2713aSLionel Sambuc     StringRef MacroName = ExistingMacroNames[I];
488f4a2713aSLionel Sambuc     std::pair<StringRef, bool> Existing = ExistingMacros[MacroName];
489f4a2713aSLionel Sambuc 
490f4a2713aSLionel Sambuc     // Check whether we know anything about this macro name or not.
491f4a2713aSLionel Sambuc     llvm::StringMap<std::pair<StringRef, bool /*IsUndef*/> >::iterator Known
492f4a2713aSLionel Sambuc       = ASTFileMacros.find(MacroName);
493f4a2713aSLionel Sambuc     if (Known == ASTFileMacros.end()) {
494f4a2713aSLionel Sambuc       // FIXME: Check whether this identifier was referenced anywhere in the
495f4a2713aSLionel Sambuc       // AST file. If so, we should reject the AST file. Unfortunately, this
496f4a2713aSLionel Sambuc       // information isn't in the control block. What shall we do about it?
497f4a2713aSLionel Sambuc 
498f4a2713aSLionel Sambuc       if (Existing.second) {
499f4a2713aSLionel Sambuc         SuggestedPredefines += "#undef ";
500f4a2713aSLionel Sambuc         SuggestedPredefines += MacroName.str();
501f4a2713aSLionel Sambuc         SuggestedPredefines += '\n';
502f4a2713aSLionel Sambuc       } else {
503f4a2713aSLionel Sambuc         SuggestedPredefines += "#define ";
504f4a2713aSLionel Sambuc         SuggestedPredefines += MacroName.str();
505f4a2713aSLionel Sambuc         SuggestedPredefines += ' ';
506f4a2713aSLionel Sambuc         SuggestedPredefines += Existing.first.str();
507f4a2713aSLionel Sambuc         SuggestedPredefines += '\n';
508f4a2713aSLionel Sambuc       }
509f4a2713aSLionel Sambuc       continue;
510f4a2713aSLionel Sambuc     }
511f4a2713aSLionel Sambuc 
512f4a2713aSLionel Sambuc     // If the macro was defined in one but undef'd in the other, we have a
513f4a2713aSLionel Sambuc     // conflict.
514f4a2713aSLionel Sambuc     if (Existing.second != Known->second.second) {
515f4a2713aSLionel Sambuc       if (Diags) {
516f4a2713aSLionel Sambuc         Diags->Report(diag::err_pch_macro_def_undef)
517f4a2713aSLionel Sambuc           << MacroName << Known->second.second;
518f4a2713aSLionel Sambuc       }
519f4a2713aSLionel Sambuc       return true;
520f4a2713aSLionel Sambuc     }
521f4a2713aSLionel Sambuc 
522f4a2713aSLionel Sambuc     // If the macro was #undef'd in both, or if the macro bodies are identical,
523f4a2713aSLionel Sambuc     // it's fine.
524f4a2713aSLionel Sambuc     if (Existing.second || Existing.first == Known->second.first)
525f4a2713aSLionel Sambuc       continue;
526f4a2713aSLionel Sambuc 
527f4a2713aSLionel Sambuc     // The macro bodies differ; complain.
528f4a2713aSLionel Sambuc     if (Diags) {
529f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_macro_def_conflict)
530f4a2713aSLionel Sambuc         << MacroName << Known->second.first << Existing.first;
531f4a2713aSLionel Sambuc     }
532f4a2713aSLionel Sambuc     return true;
533f4a2713aSLionel Sambuc   }
534f4a2713aSLionel Sambuc 
535f4a2713aSLionel Sambuc   // Check whether we're using predefines.
536f4a2713aSLionel Sambuc   if (PPOpts.UsePredefines != ExistingPPOpts.UsePredefines) {
537f4a2713aSLionel Sambuc     if (Diags) {
538f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_undef) << ExistingPPOpts.UsePredefines;
539f4a2713aSLionel Sambuc     }
540f4a2713aSLionel Sambuc     return true;
541f4a2713aSLionel Sambuc   }
542f4a2713aSLionel Sambuc 
543f4a2713aSLionel Sambuc   // Detailed record is important since it is used for the module cache hash.
544f4a2713aSLionel Sambuc   if (LangOpts.Modules &&
545f4a2713aSLionel Sambuc       PPOpts.DetailedRecord != ExistingPPOpts.DetailedRecord) {
546f4a2713aSLionel Sambuc     if (Diags) {
547f4a2713aSLionel Sambuc       Diags->Report(diag::err_pch_pp_detailed_record) << PPOpts.DetailedRecord;
548f4a2713aSLionel Sambuc     }
549f4a2713aSLionel Sambuc     return true;
550f4a2713aSLionel Sambuc   }
551f4a2713aSLionel Sambuc 
552f4a2713aSLionel Sambuc   // Compute the #include and #include_macros lines we need.
553f4a2713aSLionel Sambuc   for (unsigned I = 0, N = ExistingPPOpts.Includes.size(); I != N; ++I) {
554f4a2713aSLionel Sambuc     StringRef File = ExistingPPOpts.Includes[I];
555f4a2713aSLionel Sambuc     if (File == ExistingPPOpts.ImplicitPCHInclude)
556f4a2713aSLionel Sambuc       continue;
557f4a2713aSLionel Sambuc 
558f4a2713aSLionel Sambuc     if (std::find(PPOpts.Includes.begin(), PPOpts.Includes.end(), File)
559f4a2713aSLionel Sambuc           != PPOpts.Includes.end())
560f4a2713aSLionel Sambuc       continue;
561f4a2713aSLionel Sambuc 
562f4a2713aSLionel Sambuc     SuggestedPredefines += "#include \"";
563*0a6a1f1dSLionel Sambuc     SuggestedPredefines += File;
564f4a2713aSLionel Sambuc     SuggestedPredefines += "\"\n";
565f4a2713aSLionel Sambuc   }
566f4a2713aSLionel Sambuc 
567f4a2713aSLionel Sambuc   for (unsigned I = 0, N = ExistingPPOpts.MacroIncludes.size(); I != N; ++I) {
568f4a2713aSLionel Sambuc     StringRef File = ExistingPPOpts.MacroIncludes[I];
569f4a2713aSLionel Sambuc     if (std::find(PPOpts.MacroIncludes.begin(), PPOpts.MacroIncludes.end(),
570f4a2713aSLionel Sambuc                   File)
571f4a2713aSLionel Sambuc         != PPOpts.MacroIncludes.end())
572f4a2713aSLionel Sambuc       continue;
573f4a2713aSLionel Sambuc 
574f4a2713aSLionel Sambuc     SuggestedPredefines += "#__include_macros \"";
575*0a6a1f1dSLionel Sambuc     SuggestedPredefines += File;
576f4a2713aSLionel Sambuc     SuggestedPredefines += "\"\n##\n";
577f4a2713aSLionel Sambuc   }
578f4a2713aSLionel Sambuc 
579f4a2713aSLionel Sambuc   return false;
580f4a2713aSLionel Sambuc }
581f4a2713aSLionel Sambuc 
ReadPreprocessorOptions(const PreprocessorOptions & PPOpts,bool Complain,std::string & SuggestedPredefines)582f4a2713aSLionel Sambuc bool PCHValidator::ReadPreprocessorOptions(const PreprocessorOptions &PPOpts,
583f4a2713aSLionel Sambuc                                            bool Complain,
584f4a2713aSLionel Sambuc                                            std::string &SuggestedPredefines) {
585f4a2713aSLionel Sambuc   const PreprocessorOptions &ExistingPPOpts = PP.getPreprocessorOpts();
586f4a2713aSLionel Sambuc 
587f4a2713aSLionel Sambuc   return checkPreprocessorOptions(PPOpts, ExistingPPOpts,
588*0a6a1f1dSLionel Sambuc                                   Complain? &Reader.Diags : nullptr,
589f4a2713aSLionel Sambuc                                   PP.getFileManager(),
590f4a2713aSLionel Sambuc                                   SuggestedPredefines,
591f4a2713aSLionel Sambuc                                   PP.getLangOpts());
592f4a2713aSLionel Sambuc }
593f4a2713aSLionel Sambuc 
ReadCounter(const ModuleFile & M,unsigned Value)594f4a2713aSLionel Sambuc void PCHValidator::ReadCounter(const ModuleFile &M, unsigned Value) {
595f4a2713aSLionel Sambuc   PP.setCounterValue(Value);
596f4a2713aSLionel Sambuc }
597f4a2713aSLionel Sambuc 
598f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
599f4a2713aSLionel Sambuc // AST reader implementation
600f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
601f4a2713aSLionel Sambuc 
setDeserializationListener(ASTDeserializationListener * Listener,bool TakeOwnership)602*0a6a1f1dSLionel Sambuc void ASTReader::setDeserializationListener(ASTDeserializationListener *Listener,
603*0a6a1f1dSLionel Sambuc                                            bool TakeOwnership) {
604f4a2713aSLionel Sambuc   DeserializationListener = Listener;
605*0a6a1f1dSLionel Sambuc   OwnsDeserializationListener = TakeOwnership;
606f4a2713aSLionel Sambuc }
607f4a2713aSLionel Sambuc 
608f4a2713aSLionel Sambuc 
609f4a2713aSLionel Sambuc 
ComputeHash(Selector Sel)610f4a2713aSLionel Sambuc unsigned ASTSelectorLookupTrait::ComputeHash(Selector Sel) {
611f4a2713aSLionel Sambuc   return serialization::ComputeHash(Sel);
612f4a2713aSLionel Sambuc }
613f4a2713aSLionel Sambuc 
614f4a2713aSLionel Sambuc 
615f4a2713aSLionel Sambuc std::pair<unsigned, unsigned>
ReadKeyDataLength(const unsigned char * & d)616f4a2713aSLionel Sambuc ASTSelectorLookupTrait::ReadKeyDataLength(const unsigned char*& d) {
617*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
618*0a6a1f1dSLionel Sambuc   unsigned KeyLen = endian::readNext<uint16_t, little, unaligned>(d);
619*0a6a1f1dSLionel Sambuc   unsigned DataLen = endian::readNext<uint16_t, little, unaligned>(d);
620f4a2713aSLionel Sambuc   return std::make_pair(KeyLen, DataLen);
621f4a2713aSLionel Sambuc }
622f4a2713aSLionel Sambuc 
623f4a2713aSLionel Sambuc ASTSelectorLookupTrait::internal_key_type
ReadKey(const unsigned char * d,unsigned)624f4a2713aSLionel Sambuc ASTSelectorLookupTrait::ReadKey(const unsigned char* d, unsigned) {
625*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
626f4a2713aSLionel Sambuc   SelectorTable &SelTable = Reader.getContext().Selectors;
627*0a6a1f1dSLionel Sambuc   unsigned N = endian::readNext<uint16_t, little, unaligned>(d);
628*0a6a1f1dSLionel Sambuc   IdentifierInfo *FirstII = Reader.getLocalIdentifier(
629*0a6a1f1dSLionel Sambuc       F, endian::readNext<uint32_t, little, unaligned>(d));
630f4a2713aSLionel Sambuc   if (N == 0)
631f4a2713aSLionel Sambuc     return SelTable.getNullarySelector(FirstII);
632f4a2713aSLionel Sambuc   else if (N == 1)
633f4a2713aSLionel Sambuc     return SelTable.getUnarySelector(FirstII);
634f4a2713aSLionel Sambuc 
635f4a2713aSLionel Sambuc   SmallVector<IdentifierInfo *, 16> Args;
636f4a2713aSLionel Sambuc   Args.push_back(FirstII);
637f4a2713aSLionel Sambuc   for (unsigned I = 1; I != N; ++I)
638*0a6a1f1dSLionel Sambuc     Args.push_back(Reader.getLocalIdentifier(
639*0a6a1f1dSLionel Sambuc         F, endian::readNext<uint32_t, little, unaligned>(d)));
640f4a2713aSLionel Sambuc 
641f4a2713aSLionel Sambuc   return SelTable.getSelector(N, Args.data());
642f4a2713aSLionel Sambuc }
643f4a2713aSLionel Sambuc 
644f4a2713aSLionel Sambuc ASTSelectorLookupTrait::data_type
ReadData(Selector,const unsigned char * d,unsigned DataLen)645f4a2713aSLionel Sambuc ASTSelectorLookupTrait::ReadData(Selector, const unsigned char* d,
646f4a2713aSLionel Sambuc                                  unsigned DataLen) {
647*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
648f4a2713aSLionel Sambuc 
649f4a2713aSLionel Sambuc   data_type Result;
650f4a2713aSLionel Sambuc 
651*0a6a1f1dSLionel Sambuc   Result.ID = Reader.getGlobalSelectorID(
652*0a6a1f1dSLionel Sambuc       F, endian::readNext<uint32_t, little, unaligned>(d));
653*0a6a1f1dSLionel Sambuc   unsigned FullInstanceBits = endian::readNext<uint16_t, little, unaligned>(d);
654*0a6a1f1dSLionel Sambuc   unsigned FullFactoryBits = endian::readNext<uint16_t, little, unaligned>(d);
655*0a6a1f1dSLionel Sambuc   Result.InstanceBits = FullInstanceBits & 0x3;
656*0a6a1f1dSLionel Sambuc   Result.InstanceHasMoreThanOneDecl = (FullInstanceBits >> 2) & 0x1;
657*0a6a1f1dSLionel Sambuc   Result.FactoryBits = FullFactoryBits & 0x3;
658*0a6a1f1dSLionel Sambuc   Result.FactoryHasMoreThanOneDecl = (FullFactoryBits >> 2) & 0x1;
659*0a6a1f1dSLionel Sambuc   unsigned NumInstanceMethods = FullInstanceBits >> 3;
660*0a6a1f1dSLionel Sambuc   unsigned NumFactoryMethods = FullFactoryBits >> 3;
661f4a2713aSLionel Sambuc 
662f4a2713aSLionel Sambuc   // Load instance methods
663f4a2713aSLionel Sambuc   for (unsigned I = 0; I != NumInstanceMethods; ++I) {
664*0a6a1f1dSLionel Sambuc     if (ObjCMethodDecl *Method = Reader.GetLocalDeclAs<ObjCMethodDecl>(
665*0a6a1f1dSLionel Sambuc             F, endian::readNext<uint32_t, little, unaligned>(d)))
666f4a2713aSLionel Sambuc       Result.Instance.push_back(Method);
667f4a2713aSLionel Sambuc   }
668f4a2713aSLionel Sambuc 
669f4a2713aSLionel Sambuc   // Load factory methods
670f4a2713aSLionel Sambuc   for (unsigned I = 0; I != NumFactoryMethods; ++I) {
671*0a6a1f1dSLionel Sambuc     if (ObjCMethodDecl *Method = Reader.GetLocalDeclAs<ObjCMethodDecl>(
672*0a6a1f1dSLionel Sambuc             F, endian::readNext<uint32_t, little, unaligned>(d)))
673f4a2713aSLionel Sambuc       Result.Factory.push_back(Method);
674f4a2713aSLionel Sambuc   }
675f4a2713aSLionel Sambuc 
676f4a2713aSLionel Sambuc   return Result;
677f4a2713aSLionel Sambuc }
678f4a2713aSLionel Sambuc 
ComputeHash(const internal_key_type & a)679f4a2713aSLionel Sambuc unsigned ASTIdentifierLookupTraitBase::ComputeHash(const internal_key_type& a) {
680f4a2713aSLionel Sambuc   return llvm::HashString(a);
681f4a2713aSLionel Sambuc }
682f4a2713aSLionel Sambuc 
683f4a2713aSLionel Sambuc std::pair<unsigned, unsigned>
ReadKeyDataLength(const unsigned char * & d)684f4a2713aSLionel Sambuc ASTIdentifierLookupTraitBase::ReadKeyDataLength(const unsigned char*& d) {
685*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
686*0a6a1f1dSLionel Sambuc   unsigned DataLen = endian::readNext<uint16_t, little, unaligned>(d);
687*0a6a1f1dSLionel Sambuc   unsigned KeyLen = endian::readNext<uint16_t, little, unaligned>(d);
688f4a2713aSLionel Sambuc   return std::make_pair(KeyLen, DataLen);
689f4a2713aSLionel Sambuc }
690f4a2713aSLionel Sambuc 
691f4a2713aSLionel Sambuc ASTIdentifierLookupTraitBase::internal_key_type
ReadKey(const unsigned char * d,unsigned n)692f4a2713aSLionel Sambuc ASTIdentifierLookupTraitBase::ReadKey(const unsigned char* d, unsigned n) {
693f4a2713aSLionel Sambuc   assert(n >= 2 && d[n-1] == '\0');
694f4a2713aSLionel Sambuc   return StringRef((const char*) d, n-1);
695f4a2713aSLionel Sambuc }
696f4a2713aSLionel Sambuc 
697f4a2713aSLionel Sambuc /// \brief Whether the given identifier is "interesting".
isInterestingIdentifier(IdentifierInfo & II)698f4a2713aSLionel Sambuc static bool isInterestingIdentifier(IdentifierInfo &II) {
699f4a2713aSLionel Sambuc   return II.isPoisoned() ||
700f4a2713aSLionel Sambuc          II.isExtensionToken() ||
701f4a2713aSLionel Sambuc          II.getObjCOrBuiltinID() ||
702f4a2713aSLionel Sambuc          II.hasRevertedTokenIDToIdentifier() ||
703f4a2713aSLionel Sambuc          II.hadMacroDefinition() ||
704f4a2713aSLionel Sambuc          II.getFETokenInfo<void>();
705f4a2713aSLionel Sambuc }
706f4a2713aSLionel Sambuc 
ReadData(const internal_key_type & k,const unsigned char * d,unsigned DataLen)707f4a2713aSLionel Sambuc IdentifierInfo *ASTIdentifierLookupTrait::ReadData(const internal_key_type& k,
708f4a2713aSLionel Sambuc                                                    const unsigned char* d,
709f4a2713aSLionel Sambuc                                                    unsigned DataLen) {
710*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
711*0a6a1f1dSLionel Sambuc   unsigned RawID = endian::readNext<uint32_t, little, unaligned>(d);
712f4a2713aSLionel Sambuc   bool IsInteresting = RawID & 0x01;
713f4a2713aSLionel Sambuc 
714f4a2713aSLionel Sambuc   // Wipe out the "is interesting" bit.
715f4a2713aSLionel Sambuc   RawID = RawID >> 1;
716f4a2713aSLionel Sambuc 
717f4a2713aSLionel Sambuc   IdentID ID = Reader.getGlobalIdentifierID(F, RawID);
718f4a2713aSLionel Sambuc   if (!IsInteresting) {
719f4a2713aSLionel Sambuc     // For uninteresting identifiers, just build the IdentifierInfo
720f4a2713aSLionel Sambuc     // and associate it with the persistent ID.
721f4a2713aSLionel Sambuc     IdentifierInfo *II = KnownII;
722f4a2713aSLionel Sambuc     if (!II) {
723f4a2713aSLionel Sambuc       II = &Reader.getIdentifierTable().getOwn(k);
724f4a2713aSLionel Sambuc       KnownII = II;
725f4a2713aSLionel Sambuc     }
726f4a2713aSLionel Sambuc     Reader.SetIdentifierInfo(ID, II);
727f4a2713aSLionel Sambuc     if (!II->isFromAST()) {
728f4a2713aSLionel Sambuc       bool WasInteresting = isInterestingIdentifier(*II);
729f4a2713aSLionel Sambuc       II->setIsFromAST();
730f4a2713aSLionel Sambuc       if (WasInteresting)
731f4a2713aSLionel Sambuc         II->setChangedSinceDeserialization();
732f4a2713aSLionel Sambuc     }
733f4a2713aSLionel Sambuc     Reader.markIdentifierUpToDate(II);
734f4a2713aSLionel Sambuc     return II;
735f4a2713aSLionel Sambuc   }
736f4a2713aSLionel Sambuc 
737*0a6a1f1dSLionel Sambuc   unsigned ObjCOrBuiltinID = endian::readNext<uint16_t, little, unaligned>(d);
738*0a6a1f1dSLionel Sambuc   unsigned Bits = endian::readNext<uint16_t, little, unaligned>(d);
739f4a2713aSLionel Sambuc   bool CPlusPlusOperatorKeyword = Bits & 0x01;
740f4a2713aSLionel Sambuc   Bits >>= 1;
741f4a2713aSLionel Sambuc   bool HasRevertedTokenIDToIdentifier = Bits & 0x01;
742f4a2713aSLionel Sambuc   Bits >>= 1;
743f4a2713aSLionel Sambuc   bool Poisoned = Bits & 0x01;
744f4a2713aSLionel Sambuc   Bits >>= 1;
745f4a2713aSLionel Sambuc   bool ExtensionToken = Bits & 0x01;
746f4a2713aSLionel Sambuc   Bits >>= 1;
747f4a2713aSLionel Sambuc   bool hasSubmoduleMacros = Bits & 0x01;
748f4a2713aSLionel Sambuc   Bits >>= 1;
749f4a2713aSLionel Sambuc   bool hadMacroDefinition = Bits & 0x01;
750f4a2713aSLionel Sambuc   Bits >>= 1;
751f4a2713aSLionel Sambuc 
752f4a2713aSLionel Sambuc   assert(Bits == 0 && "Extra bits in the identifier?");
753f4a2713aSLionel Sambuc   DataLen -= 8;
754f4a2713aSLionel Sambuc 
755f4a2713aSLionel Sambuc   // Build the IdentifierInfo itself and link the identifier ID with
756f4a2713aSLionel Sambuc   // the new IdentifierInfo.
757f4a2713aSLionel Sambuc   IdentifierInfo *II = KnownII;
758f4a2713aSLionel Sambuc   if (!II) {
759f4a2713aSLionel Sambuc     II = &Reader.getIdentifierTable().getOwn(StringRef(k));
760f4a2713aSLionel Sambuc     KnownII = II;
761f4a2713aSLionel Sambuc   }
762f4a2713aSLionel Sambuc   Reader.markIdentifierUpToDate(II);
763f4a2713aSLionel Sambuc   if (!II->isFromAST()) {
764f4a2713aSLionel Sambuc     bool WasInteresting = isInterestingIdentifier(*II);
765f4a2713aSLionel Sambuc     II->setIsFromAST();
766f4a2713aSLionel Sambuc     if (WasInteresting)
767f4a2713aSLionel Sambuc       II->setChangedSinceDeserialization();
768f4a2713aSLionel Sambuc   }
769f4a2713aSLionel Sambuc 
770f4a2713aSLionel Sambuc   // Set or check the various bits in the IdentifierInfo structure.
771f4a2713aSLionel Sambuc   // Token IDs are read-only.
772f4a2713aSLionel Sambuc   if (HasRevertedTokenIDToIdentifier && II->getTokenID() != tok::identifier)
773f4a2713aSLionel Sambuc     II->RevertTokenIDToIdentifier();
774f4a2713aSLionel Sambuc   II->setObjCOrBuiltinID(ObjCOrBuiltinID);
775f4a2713aSLionel Sambuc   assert(II->isExtensionToken() == ExtensionToken &&
776f4a2713aSLionel Sambuc          "Incorrect extension token flag");
777f4a2713aSLionel Sambuc   (void)ExtensionToken;
778f4a2713aSLionel Sambuc   if (Poisoned)
779f4a2713aSLionel Sambuc     II->setIsPoisoned(true);
780f4a2713aSLionel Sambuc   assert(II->isCPlusPlusOperatorKeyword() == CPlusPlusOperatorKeyword &&
781f4a2713aSLionel Sambuc          "Incorrect C++ operator keyword flag");
782f4a2713aSLionel Sambuc   (void)CPlusPlusOperatorKeyword;
783f4a2713aSLionel Sambuc 
784f4a2713aSLionel Sambuc   // If this identifier is a macro, deserialize the macro
785f4a2713aSLionel Sambuc   // definition.
786f4a2713aSLionel Sambuc   if (hadMacroDefinition) {
787*0a6a1f1dSLionel Sambuc     uint32_t MacroDirectivesOffset =
788*0a6a1f1dSLionel Sambuc         endian::readNext<uint32_t, little, unaligned>(d);
789f4a2713aSLionel Sambuc     DataLen -= 4;
790f4a2713aSLionel Sambuc     SmallVector<uint32_t, 8> LocalMacroIDs;
791f4a2713aSLionel Sambuc     if (hasSubmoduleMacros) {
792*0a6a1f1dSLionel Sambuc       while (true) {
793*0a6a1f1dSLionel Sambuc         uint32_t LocalMacroID =
794*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(d);
795f4a2713aSLionel Sambuc         DataLen -= 4;
796*0a6a1f1dSLionel Sambuc         if (LocalMacroID == 0xdeadbeef) break;
797f4a2713aSLionel Sambuc         LocalMacroIDs.push_back(LocalMacroID);
798f4a2713aSLionel Sambuc       }
799f4a2713aSLionel Sambuc     }
800f4a2713aSLionel Sambuc 
801*0a6a1f1dSLionel Sambuc     if (F.Kind == MK_ImplicitModule || F.Kind == MK_ExplicitModule) {
802*0a6a1f1dSLionel Sambuc       // Macro definitions are stored from newest to oldest, so reverse them
803*0a6a1f1dSLionel Sambuc       // before registering them.
804*0a6a1f1dSLionel Sambuc       llvm::SmallVector<unsigned, 8> MacroSizes;
805f4a2713aSLionel Sambuc       for (SmallVectorImpl<uint32_t>::iterator
806*0a6a1f1dSLionel Sambuc              I = LocalMacroIDs.begin(), E = LocalMacroIDs.end(); I != E; /**/) {
807*0a6a1f1dSLionel Sambuc         unsigned Size = 1;
808*0a6a1f1dSLionel Sambuc 
809*0a6a1f1dSLionel Sambuc         static const uint32_t HasOverridesFlag = 0x80000000U;
810*0a6a1f1dSLionel Sambuc         if (I + 1 != E && (I[1] & HasOverridesFlag))
811*0a6a1f1dSLionel Sambuc           Size += 1 + (I[1] & ~HasOverridesFlag);
812*0a6a1f1dSLionel Sambuc 
813*0a6a1f1dSLionel Sambuc         MacroSizes.push_back(Size);
814*0a6a1f1dSLionel Sambuc         I += Size;
815f4a2713aSLionel Sambuc       }
816*0a6a1f1dSLionel Sambuc 
817*0a6a1f1dSLionel Sambuc       SmallVectorImpl<uint32_t>::iterator I = LocalMacroIDs.end();
818*0a6a1f1dSLionel Sambuc       for (SmallVectorImpl<unsigned>::reverse_iterator SI = MacroSizes.rbegin(),
819*0a6a1f1dSLionel Sambuc                                                        SE = MacroSizes.rend();
820*0a6a1f1dSLionel Sambuc            SI != SE; ++SI) {
821*0a6a1f1dSLionel Sambuc         I -= *SI;
822*0a6a1f1dSLionel Sambuc 
823*0a6a1f1dSLionel Sambuc         uint32_t LocalMacroID = *I;
824*0a6a1f1dSLionel Sambuc         ArrayRef<uint32_t> Overrides;
825*0a6a1f1dSLionel Sambuc         if (*SI != 1)
826*0a6a1f1dSLionel Sambuc           Overrides = llvm::makeArrayRef(&I[2], *SI - 2);
827*0a6a1f1dSLionel Sambuc         Reader.addPendingMacroFromModule(II, &F, LocalMacroID, Overrides);
828*0a6a1f1dSLionel Sambuc       }
829*0a6a1f1dSLionel Sambuc       assert(I == LocalMacroIDs.begin());
830f4a2713aSLionel Sambuc     } else {
831f4a2713aSLionel Sambuc       Reader.addPendingMacroFromPCH(II, &F, MacroDirectivesOffset);
832f4a2713aSLionel Sambuc     }
833f4a2713aSLionel Sambuc   }
834f4a2713aSLionel Sambuc 
835f4a2713aSLionel Sambuc   Reader.SetIdentifierInfo(ID, II);
836f4a2713aSLionel Sambuc 
837f4a2713aSLionel Sambuc   // Read all of the declarations visible at global scope with this
838f4a2713aSLionel Sambuc   // name.
839f4a2713aSLionel Sambuc   if (DataLen > 0) {
840f4a2713aSLionel Sambuc     SmallVector<uint32_t, 4> DeclIDs;
841f4a2713aSLionel Sambuc     for (; DataLen > 0; DataLen -= 4)
842*0a6a1f1dSLionel Sambuc       DeclIDs.push_back(Reader.getGlobalDeclID(
843*0a6a1f1dSLionel Sambuc           F, endian::readNext<uint32_t, little, unaligned>(d)));
844f4a2713aSLionel Sambuc     Reader.SetGloballyVisibleDecls(II, DeclIDs);
845f4a2713aSLionel Sambuc   }
846f4a2713aSLionel Sambuc 
847f4a2713aSLionel Sambuc   return II;
848f4a2713aSLionel Sambuc }
849f4a2713aSLionel Sambuc 
850f4a2713aSLionel Sambuc unsigned
ComputeHash(const DeclNameKey & Key) const851f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::ComputeHash(const DeclNameKey &Key) const {
852f4a2713aSLionel Sambuc   llvm::FoldingSetNodeID ID;
853f4a2713aSLionel Sambuc   ID.AddInteger(Key.Kind);
854f4a2713aSLionel Sambuc 
855f4a2713aSLionel Sambuc   switch (Key.Kind) {
856f4a2713aSLionel Sambuc   case DeclarationName::Identifier:
857f4a2713aSLionel Sambuc   case DeclarationName::CXXLiteralOperatorName:
858f4a2713aSLionel Sambuc     ID.AddString(((IdentifierInfo*)Key.Data)->getName());
859f4a2713aSLionel Sambuc     break;
860f4a2713aSLionel Sambuc   case DeclarationName::ObjCZeroArgSelector:
861f4a2713aSLionel Sambuc   case DeclarationName::ObjCOneArgSelector:
862f4a2713aSLionel Sambuc   case DeclarationName::ObjCMultiArgSelector:
863f4a2713aSLionel Sambuc     ID.AddInteger(serialization::ComputeHash(Selector(Key.Data)));
864f4a2713aSLionel Sambuc     break;
865f4a2713aSLionel Sambuc   case DeclarationName::CXXOperatorName:
866f4a2713aSLionel Sambuc     ID.AddInteger((OverloadedOperatorKind)Key.Data);
867f4a2713aSLionel Sambuc     break;
868f4a2713aSLionel Sambuc   case DeclarationName::CXXConstructorName:
869f4a2713aSLionel Sambuc   case DeclarationName::CXXDestructorName:
870f4a2713aSLionel Sambuc   case DeclarationName::CXXConversionFunctionName:
871f4a2713aSLionel Sambuc   case DeclarationName::CXXUsingDirective:
872f4a2713aSLionel Sambuc     break;
873f4a2713aSLionel Sambuc   }
874f4a2713aSLionel Sambuc 
875f4a2713aSLionel Sambuc   return ID.ComputeHash();
876f4a2713aSLionel Sambuc }
877f4a2713aSLionel Sambuc 
878f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::internal_key_type
GetInternalKey(const external_key_type & Name) const879f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::GetInternalKey(
880f4a2713aSLionel Sambuc                                           const external_key_type& Name) const {
881f4a2713aSLionel Sambuc   DeclNameKey Key;
882f4a2713aSLionel Sambuc   Key.Kind = Name.getNameKind();
883f4a2713aSLionel Sambuc   switch (Name.getNameKind()) {
884f4a2713aSLionel Sambuc   case DeclarationName::Identifier:
885f4a2713aSLionel Sambuc     Key.Data = (uint64_t)Name.getAsIdentifierInfo();
886f4a2713aSLionel Sambuc     break;
887f4a2713aSLionel Sambuc   case DeclarationName::ObjCZeroArgSelector:
888f4a2713aSLionel Sambuc   case DeclarationName::ObjCOneArgSelector:
889f4a2713aSLionel Sambuc   case DeclarationName::ObjCMultiArgSelector:
890f4a2713aSLionel Sambuc     Key.Data = (uint64_t)Name.getObjCSelector().getAsOpaquePtr();
891f4a2713aSLionel Sambuc     break;
892f4a2713aSLionel Sambuc   case DeclarationName::CXXOperatorName:
893f4a2713aSLionel Sambuc     Key.Data = Name.getCXXOverloadedOperator();
894f4a2713aSLionel Sambuc     break;
895f4a2713aSLionel Sambuc   case DeclarationName::CXXLiteralOperatorName:
896f4a2713aSLionel Sambuc     Key.Data = (uint64_t)Name.getCXXLiteralIdentifier();
897f4a2713aSLionel Sambuc     break;
898f4a2713aSLionel Sambuc   case DeclarationName::CXXConstructorName:
899f4a2713aSLionel Sambuc   case DeclarationName::CXXDestructorName:
900f4a2713aSLionel Sambuc   case DeclarationName::CXXConversionFunctionName:
901f4a2713aSLionel Sambuc   case DeclarationName::CXXUsingDirective:
902f4a2713aSLionel Sambuc     Key.Data = 0;
903f4a2713aSLionel Sambuc     break;
904f4a2713aSLionel Sambuc   }
905f4a2713aSLionel Sambuc 
906f4a2713aSLionel Sambuc   return Key;
907f4a2713aSLionel Sambuc }
908f4a2713aSLionel Sambuc 
909f4a2713aSLionel Sambuc std::pair<unsigned, unsigned>
ReadKeyDataLength(const unsigned char * & d)910f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::ReadKeyDataLength(const unsigned char*& d) {
911*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
912*0a6a1f1dSLionel Sambuc   unsigned KeyLen = endian::readNext<uint16_t, little, unaligned>(d);
913*0a6a1f1dSLionel Sambuc   unsigned DataLen = endian::readNext<uint16_t, little, unaligned>(d);
914f4a2713aSLionel Sambuc   return std::make_pair(KeyLen, DataLen);
915f4a2713aSLionel Sambuc }
916f4a2713aSLionel Sambuc 
917f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::internal_key_type
ReadKey(const unsigned char * d,unsigned)918f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::ReadKey(const unsigned char* d, unsigned) {
919*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
920f4a2713aSLionel Sambuc 
921f4a2713aSLionel Sambuc   DeclNameKey Key;
922f4a2713aSLionel Sambuc   Key.Kind = (DeclarationName::NameKind)*d++;
923f4a2713aSLionel Sambuc   switch (Key.Kind) {
924f4a2713aSLionel Sambuc   case DeclarationName::Identifier:
925*0a6a1f1dSLionel Sambuc     Key.Data = (uint64_t)Reader.getLocalIdentifier(
926*0a6a1f1dSLionel Sambuc         F, endian::readNext<uint32_t, little, unaligned>(d));
927f4a2713aSLionel Sambuc     break;
928f4a2713aSLionel Sambuc   case DeclarationName::ObjCZeroArgSelector:
929f4a2713aSLionel Sambuc   case DeclarationName::ObjCOneArgSelector:
930f4a2713aSLionel Sambuc   case DeclarationName::ObjCMultiArgSelector:
931f4a2713aSLionel Sambuc     Key.Data =
932*0a6a1f1dSLionel Sambuc         (uint64_t)Reader.getLocalSelector(
933*0a6a1f1dSLionel Sambuc                              F, endian::readNext<uint32_t, little, unaligned>(
934*0a6a1f1dSLionel Sambuc                                     d)).getAsOpaquePtr();
935f4a2713aSLionel Sambuc     break;
936f4a2713aSLionel Sambuc   case DeclarationName::CXXOperatorName:
937f4a2713aSLionel Sambuc     Key.Data = *d++; // OverloadedOperatorKind
938f4a2713aSLionel Sambuc     break;
939f4a2713aSLionel Sambuc   case DeclarationName::CXXLiteralOperatorName:
940*0a6a1f1dSLionel Sambuc     Key.Data = (uint64_t)Reader.getLocalIdentifier(
941*0a6a1f1dSLionel Sambuc         F, endian::readNext<uint32_t, little, unaligned>(d));
942f4a2713aSLionel Sambuc     break;
943f4a2713aSLionel Sambuc   case DeclarationName::CXXConstructorName:
944f4a2713aSLionel Sambuc   case DeclarationName::CXXDestructorName:
945f4a2713aSLionel Sambuc   case DeclarationName::CXXConversionFunctionName:
946f4a2713aSLionel Sambuc   case DeclarationName::CXXUsingDirective:
947f4a2713aSLionel Sambuc     Key.Data = 0;
948f4a2713aSLionel Sambuc     break;
949f4a2713aSLionel Sambuc   }
950f4a2713aSLionel Sambuc 
951f4a2713aSLionel Sambuc   return Key;
952f4a2713aSLionel Sambuc }
953f4a2713aSLionel Sambuc 
954f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::data_type
ReadData(internal_key_type,const unsigned char * d,unsigned DataLen)955f4a2713aSLionel Sambuc ASTDeclContextNameLookupTrait::ReadData(internal_key_type,
956f4a2713aSLionel Sambuc                                         const unsigned char* d,
957f4a2713aSLionel Sambuc                                         unsigned DataLen) {
958*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
959*0a6a1f1dSLionel Sambuc   unsigned NumDecls = endian::readNext<uint16_t, little, unaligned>(d);
960f4a2713aSLionel Sambuc   LE32DeclID *Start = reinterpret_cast<LE32DeclID *>(
961f4a2713aSLionel Sambuc                         const_cast<unsigned char *>(d));
962f4a2713aSLionel Sambuc   return std::make_pair(Start, Start + NumDecls);
963f4a2713aSLionel Sambuc }
964f4a2713aSLionel Sambuc 
ReadDeclContextStorage(ModuleFile & M,BitstreamCursor & Cursor,const std::pair<uint64_t,uint64_t> & Offsets,DeclContextInfo & Info)965f4a2713aSLionel Sambuc bool ASTReader::ReadDeclContextStorage(ModuleFile &M,
966f4a2713aSLionel Sambuc                                        BitstreamCursor &Cursor,
967f4a2713aSLionel Sambuc                                    const std::pair<uint64_t, uint64_t> &Offsets,
968f4a2713aSLionel Sambuc                                        DeclContextInfo &Info) {
969f4a2713aSLionel Sambuc   SavedStreamPosition SavedPosition(Cursor);
970f4a2713aSLionel Sambuc   // First the lexical decls.
971f4a2713aSLionel Sambuc   if (Offsets.first != 0) {
972f4a2713aSLionel Sambuc     Cursor.JumpToBit(Offsets.first);
973f4a2713aSLionel Sambuc 
974f4a2713aSLionel Sambuc     RecordData Record;
975f4a2713aSLionel Sambuc     StringRef Blob;
976f4a2713aSLionel Sambuc     unsigned Code = Cursor.ReadCode();
977f4a2713aSLionel Sambuc     unsigned RecCode = Cursor.readRecord(Code, Record, &Blob);
978f4a2713aSLionel Sambuc     if (RecCode != DECL_CONTEXT_LEXICAL) {
979f4a2713aSLionel Sambuc       Error("Expected lexical block");
980f4a2713aSLionel Sambuc       return true;
981f4a2713aSLionel Sambuc     }
982f4a2713aSLionel Sambuc 
983f4a2713aSLionel Sambuc     Info.LexicalDecls = reinterpret_cast<const KindDeclIDPair*>(Blob.data());
984f4a2713aSLionel Sambuc     Info.NumLexicalDecls = Blob.size() / sizeof(KindDeclIDPair);
985f4a2713aSLionel Sambuc   }
986f4a2713aSLionel Sambuc 
987f4a2713aSLionel Sambuc   // Now the lookup table.
988f4a2713aSLionel Sambuc   if (Offsets.second != 0) {
989f4a2713aSLionel Sambuc     Cursor.JumpToBit(Offsets.second);
990f4a2713aSLionel Sambuc 
991f4a2713aSLionel Sambuc     RecordData Record;
992f4a2713aSLionel Sambuc     StringRef Blob;
993f4a2713aSLionel Sambuc     unsigned Code = Cursor.ReadCode();
994f4a2713aSLionel Sambuc     unsigned RecCode = Cursor.readRecord(Code, Record, &Blob);
995f4a2713aSLionel Sambuc     if (RecCode != DECL_CONTEXT_VISIBLE) {
996f4a2713aSLionel Sambuc       Error("Expected visible lookup table block");
997f4a2713aSLionel Sambuc       return true;
998f4a2713aSLionel Sambuc     }
999*0a6a1f1dSLionel Sambuc     Info.NameLookupTableData = ASTDeclContextNameLookupTable::Create(
1000f4a2713aSLionel Sambuc         (const unsigned char *)Blob.data() + Record[0],
1001*0a6a1f1dSLionel Sambuc         (const unsigned char *)Blob.data() + sizeof(uint32_t),
1002f4a2713aSLionel Sambuc         (const unsigned char *)Blob.data(),
1003f4a2713aSLionel Sambuc         ASTDeclContextNameLookupTrait(*this, M));
1004f4a2713aSLionel Sambuc   }
1005f4a2713aSLionel Sambuc 
1006f4a2713aSLionel Sambuc   return false;
1007f4a2713aSLionel Sambuc }
1008f4a2713aSLionel Sambuc 
Error(StringRef Msg)1009f4a2713aSLionel Sambuc void ASTReader::Error(StringRef Msg) {
1010f4a2713aSLionel Sambuc   Error(diag::err_fe_pch_malformed, Msg);
1011f4a2713aSLionel Sambuc   if (Context.getLangOpts().Modules && !Diags.isDiagnosticInFlight()) {
1012f4a2713aSLionel Sambuc     Diag(diag::note_module_cache_path)
1013f4a2713aSLionel Sambuc       << PP.getHeaderSearchInfo().getModuleCachePath();
1014f4a2713aSLionel Sambuc   }
1015f4a2713aSLionel Sambuc }
1016f4a2713aSLionel Sambuc 
Error(unsigned DiagID,StringRef Arg1,StringRef Arg2)1017f4a2713aSLionel Sambuc void ASTReader::Error(unsigned DiagID,
1018f4a2713aSLionel Sambuc                       StringRef Arg1, StringRef Arg2) {
1019f4a2713aSLionel Sambuc   if (Diags.isDiagnosticInFlight())
1020f4a2713aSLionel Sambuc     Diags.SetDelayedDiagnostic(DiagID, Arg1, Arg2);
1021f4a2713aSLionel Sambuc   else
1022f4a2713aSLionel Sambuc     Diag(DiagID) << Arg1 << Arg2;
1023f4a2713aSLionel Sambuc }
1024f4a2713aSLionel Sambuc 
1025f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
1026f4a2713aSLionel Sambuc // Source Manager Deserialization
1027f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
1028f4a2713aSLionel Sambuc 
1029f4a2713aSLionel Sambuc /// \brief Read the line table in the source manager block.
1030f4a2713aSLionel Sambuc /// \returns true if there was an error.
ParseLineTable(ModuleFile & F,const RecordData & Record)1031f4a2713aSLionel Sambuc bool ASTReader::ParseLineTable(ModuleFile &F,
1032*0a6a1f1dSLionel Sambuc                                const RecordData &Record) {
1033f4a2713aSLionel Sambuc   unsigned Idx = 0;
1034f4a2713aSLionel Sambuc   LineTableInfo &LineTable = SourceMgr.getLineTable();
1035f4a2713aSLionel Sambuc 
1036f4a2713aSLionel Sambuc   // Parse the file names
1037f4a2713aSLionel Sambuc   std::map<int, int> FileIDs;
1038f4a2713aSLionel Sambuc   for (int I = 0, N = Record[Idx++]; I != N; ++I) {
1039f4a2713aSLionel Sambuc     // Extract the file name
1040*0a6a1f1dSLionel Sambuc     auto Filename = ReadPath(F, Record, Idx);
1041f4a2713aSLionel Sambuc     FileIDs[I] = LineTable.getLineTableFilenameID(Filename);
1042f4a2713aSLionel Sambuc   }
1043f4a2713aSLionel Sambuc 
1044f4a2713aSLionel Sambuc   // Parse the line entries
1045f4a2713aSLionel Sambuc   std::vector<LineEntry> Entries;
1046f4a2713aSLionel Sambuc   while (Idx < Record.size()) {
1047f4a2713aSLionel Sambuc     int FID = Record[Idx++];
1048f4a2713aSLionel Sambuc     assert(FID >= 0 && "Serialized line entries for non-local file.");
1049f4a2713aSLionel Sambuc     // Remap FileID from 1-based old view.
1050f4a2713aSLionel Sambuc     FID += F.SLocEntryBaseID - 1;
1051f4a2713aSLionel Sambuc 
1052f4a2713aSLionel Sambuc     // Extract the line entries
1053f4a2713aSLionel Sambuc     unsigned NumEntries = Record[Idx++];
1054f4a2713aSLionel Sambuc     assert(NumEntries && "Numentries is 00000");
1055f4a2713aSLionel Sambuc     Entries.clear();
1056f4a2713aSLionel Sambuc     Entries.reserve(NumEntries);
1057f4a2713aSLionel Sambuc     for (unsigned I = 0; I != NumEntries; ++I) {
1058f4a2713aSLionel Sambuc       unsigned FileOffset = Record[Idx++];
1059f4a2713aSLionel Sambuc       unsigned LineNo = Record[Idx++];
1060f4a2713aSLionel Sambuc       int FilenameID = FileIDs[Record[Idx++]];
1061f4a2713aSLionel Sambuc       SrcMgr::CharacteristicKind FileKind
1062f4a2713aSLionel Sambuc         = (SrcMgr::CharacteristicKind)Record[Idx++];
1063f4a2713aSLionel Sambuc       unsigned IncludeOffset = Record[Idx++];
1064f4a2713aSLionel Sambuc       Entries.push_back(LineEntry::get(FileOffset, LineNo, FilenameID,
1065f4a2713aSLionel Sambuc                                        FileKind, IncludeOffset));
1066f4a2713aSLionel Sambuc     }
1067f4a2713aSLionel Sambuc     LineTable.AddEntry(FileID::get(FID), Entries);
1068f4a2713aSLionel Sambuc   }
1069f4a2713aSLionel Sambuc 
1070f4a2713aSLionel Sambuc   return false;
1071f4a2713aSLionel Sambuc }
1072f4a2713aSLionel Sambuc 
1073f4a2713aSLionel Sambuc /// \brief Read a source manager block
ReadSourceManagerBlock(ModuleFile & F)1074f4a2713aSLionel Sambuc bool ASTReader::ReadSourceManagerBlock(ModuleFile &F) {
1075f4a2713aSLionel Sambuc   using namespace SrcMgr;
1076f4a2713aSLionel Sambuc 
1077f4a2713aSLionel Sambuc   BitstreamCursor &SLocEntryCursor = F.SLocEntryCursor;
1078f4a2713aSLionel Sambuc 
1079f4a2713aSLionel Sambuc   // Set the source-location entry cursor to the current position in
1080f4a2713aSLionel Sambuc   // the stream. This cursor will be used to read the contents of the
1081f4a2713aSLionel Sambuc   // source manager block initially, and then lazily read
1082f4a2713aSLionel Sambuc   // source-location entries as needed.
1083f4a2713aSLionel Sambuc   SLocEntryCursor = F.Stream;
1084f4a2713aSLionel Sambuc 
1085f4a2713aSLionel Sambuc   // The stream itself is going to skip over the source manager block.
1086f4a2713aSLionel Sambuc   if (F.Stream.SkipBlock()) {
1087f4a2713aSLionel Sambuc     Error("malformed block record in AST file");
1088f4a2713aSLionel Sambuc     return true;
1089f4a2713aSLionel Sambuc   }
1090f4a2713aSLionel Sambuc 
1091f4a2713aSLionel Sambuc   // Enter the source manager block.
1092f4a2713aSLionel Sambuc   if (SLocEntryCursor.EnterSubBlock(SOURCE_MANAGER_BLOCK_ID)) {
1093f4a2713aSLionel Sambuc     Error("malformed source manager block record in AST file");
1094f4a2713aSLionel Sambuc     return true;
1095f4a2713aSLionel Sambuc   }
1096f4a2713aSLionel Sambuc 
1097f4a2713aSLionel Sambuc   RecordData Record;
1098f4a2713aSLionel Sambuc   while (true) {
1099f4a2713aSLionel Sambuc     llvm::BitstreamEntry E = SLocEntryCursor.advanceSkippingSubblocks();
1100f4a2713aSLionel Sambuc 
1101f4a2713aSLionel Sambuc     switch (E.Kind) {
1102f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::SubBlock: // Handled for us already.
1103f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Error:
1104f4a2713aSLionel Sambuc       Error("malformed block record in AST file");
1105f4a2713aSLionel Sambuc       return true;
1106f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::EndBlock:
1107f4a2713aSLionel Sambuc       return false;
1108f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Record:
1109f4a2713aSLionel Sambuc       // The interesting case.
1110f4a2713aSLionel Sambuc       break;
1111f4a2713aSLionel Sambuc     }
1112f4a2713aSLionel Sambuc 
1113f4a2713aSLionel Sambuc     // Read a record.
1114f4a2713aSLionel Sambuc     Record.clear();
1115f4a2713aSLionel Sambuc     StringRef Blob;
1116f4a2713aSLionel Sambuc     switch (SLocEntryCursor.readRecord(E.ID, Record, &Blob)) {
1117f4a2713aSLionel Sambuc     default:  // Default behavior: ignore.
1118f4a2713aSLionel Sambuc       break;
1119f4a2713aSLionel Sambuc 
1120f4a2713aSLionel Sambuc     case SM_SLOC_FILE_ENTRY:
1121f4a2713aSLionel Sambuc     case SM_SLOC_BUFFER_ENTRY:
1122f4a2713aSLionel Sambuc     case SM_SLOC_EXPANSION_ENTRY:
1123f4a2713aSLionel Sambuc       // Once we hit one of the source location entries, we're done.
1124f4a2713aSLionel Sambuc       return false;
1125f4a2713aSLionel Sambuc     }
1126f4a2713aSLionel Sambuc   }
1127f4a2713aSLionel Sambuc }
1128f4a2713aSLionel Sambuc 
1129f4a2713aSLionel Sambuc /// \brief If a header file is not found at the path that we expect it to be
1130f4a2713aSLionel Sambuc /// and the PCH file was moved from its original location, try to resolve the
1131f4a2713aSLionel Sambuc /// file by assuming that header+PCH were moved together and the header is in
1132f4a2713aSLionel Sambuc /// the same place relative to the PCH.
1133f4a2713aSLionel Sambuc static std::string
resolveFileRelativeToOriginalDir(const std::string & Filename,const std::string & OriginalDir,const std::string & CurrDir)1134f4a2713aSLionel Sambuc resolveFileRelativeToOriginalDir(const std::string &Filename,
1135f4a2713aSLionel Sambuc                                  const std::string &OriginalDir,
1136f4a2713aSLionel Sambuc                                  const std::string &CurrDir) {
1137f4a2713aSLionel Sambuc   assert(OriginalDir != CurrDir &&
1138f4a2713aSLionel Sambuc          "No point trying to resolve the file if the PCH dir didn't change");
1139f4a2713aSLionel Sambuc   using namespace llvm::sys;
1140f4a2713aSLionel Sambuc   SmallString<128> filePath(Filename);
1141f4a2713aSLionel Sambuc   fs::make_absolute(filePath);
1142f4a2713aSLionel Sambuc   assert(path::is_absolute(OriginalDir));
1143f4a2713aSLionel Sambuc   SmallString<128> currPCHPath(CurrDir);
1144f4a2713aSLionel Sambuc 
1145f4a2713aSLionel Sambuc   path::const_iterator fileDirI = path::begin(path::parent_path(filePath)),
1146f4a2713aSLionel Sambuc                        fileDirE = path::end(path::parent_path(filePath));
1147f4a2713aSLionel Sambuc   path::const_iterator origDirI = path::begin(OriginalDir),
1148f4a2713aSLionel Sambuc                        origDirE = path::end(OriginalDir);
1149f4a2713aSLionel Sambuc   // Skip the common path components from filePath and OriginalDir.
1150f4a2713aSLionel Sambuc   while (fileDirI != fileDirE && origDirI != origDirE &&
1151f4a2713aSLionel Sambuc          *fileDirI == *origDirI) {
1152f4a2713aSLionel Sambuc     ++fileDirI;
1153f4a2713aSLionel Sambuc     ++origDirI;
1154f4a2713aSLionel Sambuc   }
1155f4a2713aSLionel Sambuc   for (; origDirI != origDirE; ++origDirI)
1156f4a2713aSLionel Sambuc     path::append(currPCHPath, "..");
1157f4a2713aSLionel Sambuc   path::append(currPCHPath, fileDirI, fileDirE);
1158f4a2713aSLionel Sambuc   path::append(currPCHPath, path::filename(Filename));
1159f4a2713aSLionel Sambuc   return currPCHPath.str();
1160f4a2713aSLionel Sambuc }
1161f4a2713aSLionel Sambuc 
ReadSLocEntry(int ID)1162f4a2713aSLionel Sambuc bool ASTReader::ReadSLocEntry(int ID) {
1163f4a2713aSLionel Sambuc   if (ID == 0)
1164f4a2713aSLionel Sambuc     return false;
1165f4a2713aSLionel Sambuc 
1166f4a2713aSLionel Sambuc   if (unsigned(-ID) - 2 >= getTotalNumSLocs() || ID > 0) {
1167f4a2713aSLionel Sambuc     Error("source location entry ID out-of-range for AST file");
1168f4a2713aSLionel Sambuc     return true;
1169f4a2713aSLionel Sambuc   }
1170f4a2713aSLionel Sambuc 
1171f4a2713aSLionel Sambuc   ModuleFile *F = GlobalSLocEntryMap.find(-ID)->second;
1172f4a2713aSLionel Sambuc   F->SLocEntryCursor.JumpToBit(F->SLocEntryOffsets[ID - F->SLocEntryBaseID]);
1173f4a2713aSLionel Sambuc   BitstreamCursor &SLocEntryCursor = F->SLocEntryCursor;
1174f4a2713aSLionel Sambuc   unsigned BaseOffset = F->SLocEntryBaseOffset;
1175f4a2713aSLionel Sambuc 
1176f4a2713aSLionel Sambuc   ++NumSLocEntriesRead;
1177f4a2713aSLionel Sambuc   llvm::BitstreamEntry Entry = SLocEntryCursor.advance();
1178f4a2713aSLionel Sambuc   if (Entry.Kind != llvm::BitstreamEntry::Record) {
1179f4a2713aSLionel Sambuc     Error("incorrectly-formatted source location entry in AST file");
1180f4a2713aSLionel Sambuc     return true;
1181f4a2713aSLionel Sambuc   }
1182f4a2713aSLionel Sambuc 
1183f4a2713aSLionel Sambuc   RecordData Record;
1184f4a2713aSLionel Sambuc   StringRef Blob;
1185f4a2713aSLionel Sambuc   switch (SLocEntryCursor.readRecord(Entry.ID, Record, &Blob)) {
1186f4a2713aSLionel Sambuc   default:
1187f4a2713aSLionel Sambuc     Error("incorrectly-formatted source location entry in AST file");
1188f4a2713aSLionel Sambuc     return true;
1189f4a2713aSLionel Sambuc 
1190f4a2713aSLionel Sambuc   case SM_SLOC_FILE_ENTRY: {
1191f4a2713aSLionel Sambuc     // We will detect whether a file changed and return 'Failure' for it, but
1192f4a2713aSLionel Sambuc     // we will also try to fail gracefully by setting up the SLocEntry.
1193f4a2713aSLionel Sambuc     unsigned InputID = Record[4];
1194f4a2713aSLionel Sambuc     InputFile IF = getInputFile(*F, InputID);
1195f4a2713aSLionel Sambuc     const FileEntry *File = IF.getFile();
1196f4a2713aSLionel Sambuc     bool OverriddenBuffer = IF.isOverridden();
1197f4a2713aSLionel Sambuc 
1198f4a2713aSLionel Sambuc     // Note that we only check if a File was returned. If it was out-of-date
1199f4a2713aSLionel Sambuc     // we have complained but we will continue creating a FileID to recover
1200f4a2713aSLionel Sambuc     // gracefully.
1201f4a2713aSLionel Sambuc     if (!File)
1202f4a2713aSLionel Sambuc       return true;
1203f4a2713aSLionel Sambuc 
1204f4a2713aSLionel Sambuc     SourceLocation IncludeLoc = ReadSourceLocation(*F, Record[1]);
1205f4a2713aSLionel Sambuc     if (IncludeLoc.isInvalid() && F->Kind != MK_MainFile) {
1206f4a2713aSLionel Sambuc       // This is the module's main file.
1207f4a2713aSLionel Sambuc       IncludeLoc = getImportLocation(F);
1208f4a2713aSLionel Sambuc     }
1209f4a2713aSLionel Sambuc     SrcMgr::CharacteristicKind
1210f4a2713aSLionel Sambuc       FileCharacter = (SrcMgr::CharacteristicKind)Record[2];
1211f4a2713aSLionel Sambuc     FileID FID = SourceMgr.createFileID(File, IncludeLoc, FileCharacter,
1212f4a2713aSLionel Sambuc                                         ID, BaseOffset + Record[0]);
1213f4a2713aSLionel Sambuc     SrcMgr::FileInfo &FileInfo =
1214f4a2713aSLionel Sambuc           const_cast<SrcMgr::FileInfo&>(SourceMgr.getSLocEntry(FID).getFile());
1215f4a2713aSLionel Sambuc     FileInfo.NumCreatedFIDs = Record[5];
1216f4a2713aSLionel Sambuc     if (Record[3])
1217f4a2713aSLionel Sambuc       FileInfo.setHasLineDirectives();
1218f4a2713aSLionel Sambuc 
1219f4a2713aSLionel Sambuc     const DeclID *FirstDecl = F->FileSortedDecls + Record[6];
1220f4a2713aSLionel Sambuc     unsigned NumFileDecls = Record[7];
1221f4a2713aSLionel Sambuc     if (NumFileDecls) {
1222f4a2713aSLionel Sambuc       assert(F->FileSortedDecls && "FILE_SORTED_DECLS not encountered yet ?");
1223f4a2713aSLionel Sambuc       FileDeclIDs[FID] = FileDeclsInfo(F, llvm::makeArrayRef(FirstDecl,
1224f4a2713aSLionel Sambuc                                                              NumFileDecls));
1225f4a2713aSLionel Sambuc     }
1226f4a2713aSLionel Sambuc 
1227f4a2713aSLionel Sambuc     const SrcMgr::ContentCache *ContentCache
1228f4a2713aSLionel Sambuc       = SourceMgr.getOrCreateContentCache(File,
1229f4a2713aSLionel Sambuc                               /*isSystemFile=*/FileCharacter != SrcMgr::C_User);
1230f4a2713aSLionel Sambuc     if (OverriddenBuffer && !ContentCache->BufferOverridden &&
1231f4a2713aSLionel Sambuc         ContentCache->ContentsEntry == ContentCache->OrigEntry) {
1232f4a2713aSLionel Sambuc       unsigned Code = SLocEntryCursor.ReadCode();
1233f4a2713aSLionel Sambuc       Record.clear();
1234f4a2713aSLionel Sambuc       unsigned RecCode = SLocEntryCursor.readRecord(Code, Record, &Blob);
1235f4a2713aSLionel Sambuc 
1236f4a2713aSLionel Sambuc       if (RecCode != SM_SLOC_BUFFER_BLOB) {
1237f4a2713aSLionel Sambuc         Error("AST record has invalid code");
1238f4a2713aSLionel Sambuc         return true;
1239f4a2713aSLionel Sambuc       }
1240f4a2713aSLionel Sambuc 
1241*0a6a1f1dSLionel Sambuc       std::unique_ptr<llvm::MemoryBuffer> Buffer
1242f4a2713aSLionel Sambuc         = llvm::MemoryBuffer::getMemBuffer(Blob.drop_back(1), File->getName());
1243*0a6a1f1dSLionel Sambuc       SourceMgr.overrideFileContents(File, std::move(Buffer));
1244f4a2713aSLionel Sambuc     }
1245f4a2713aSLionel Sambuc 
1246f4a2713aSLionel Sambuc     break;
1247f4a2713aSLionel Sambuc   }
1248f4a2713aSLionel Sambuc 
1249f4a2713aSLionel Sambuc   case SM_SLOC_BUFFER_ENTRY: {
1250f4a2713aSLionel Sambuc     const char *Name = Blob.data();
1251f4a2713aSLionel Sambuc     unsigned Offset = Record[0];
1252f4a2713aSLionel Sambuc     SrcMgr::CharacteristicKind
1253f4a2713aSLionel Sambuc       FileCharacter = (SrcMgr::CharacteristicKind)Record[2];
1254f4a2713aSLionel Sambuc     SourceLocation IncludeLoc = ReadSourceLocation(*F, Record[1]);
1255*0a6a1f1dSLionel Sambuc     if (IncludeLoc.isInvalid() &&
1256*0a6a1f1dSLionel Sambuc         (F->Kind == MK_ImplicitModule || F->Kind == MK_ExplicitModule)) {
1257f4a2713aSLionel Sambuc       IncludeLoc = getImportLocation(F);
1258f4a2713aSLionel Sambuc     }
1259f4a2713aSLionel Sambuc     unsigned Code = SLocEntryCursor.ReadCode();
1260f4a2713aSLionel Sambuc     Record.clear();
1261f4a2713aSLionel Sambuc     unsigned RecCode
1262f4a2713aSLionel Sambuc       = SLocEntryCursor.readRecord(Code, Record, &Blob);
1263f4a2713aSLionel Sambuc 
1264f4a2713aSLionel Sambuc     if (RecCode != SM_SLOC_BUFFER_BLOB) {
1265f4a2713aSLionel Sambuc       Error("AST record has invalid code");
1266f4a2713aSLionel Sambuc       return true;
1267f4a2713aSLionel Sambuc     }
1268f4a2713aSLionel Sambuc 
1269*0a6a1f1dSLionel Sambuc     std::unique_ptr<llvm::MemoryBuffer> Buffer =
1270*0a6a1f1dSLionel Sambuc         llvm::MemoryBuffer::getMemBuffer(Blob.drop_back(1), Name);
1271*0a6a1f1dSLionel Sambuc     SourceMgr.createFileID(std::move(Buffer), FileCharacter, ID,
1272f4a2713aSLionel Sambuc                            BaseOffset + Offset, IncludeLoc);
1273f4a2713aSLionel Sambuc     break;
1274f4a2713aSLionel Sambuc   }
1275f4a2713aSLionel Sambuc 
1276f4a2713aSLionel Sambuc   case SM_SLOC_EXPANSION_ENTRY: {
1277f4a2713aSLionel Sambuc     SourceLocation SpellingLoc = ReadSourceLocation(*F, Record[1]);
1278f4a2713aSLionel Sambuc     SourceMgr.createExpansionLoc(SpellingLoc,
1279f4a2713aSLionel Sambuc                                      ReadSourceLocation(*F, Record[2]),
1280f4a2713aSLionel Sambuc                                      ReadSourceLocation(*F, Record[3]),
1281f4a2713aSLionel Sambuc                                      Record[4],
1282f4a2713aSLionel Sambuc                                      ID,
1283f4a2713aSLionel Sambuc                                      BaseOffset + Record[0]);
1284f4a2713aSLionel Sambuc     break;
1285f4a2713aSLionel Sambuc   }
1286f4a2713aSLionel Sambuc   }
1287f4a2713aSLionel Sambuc 
1288f4a2713aSLionel Sambuc   return false;
1289f4a2713aSLionel Sambuc }
1290f4a2713aSLionel Sambuc 
getModuleImportLoc(int ID)1291f4a2713aSLionel Sambuc std::pair<SourceLocation, StringRef> ASTReader::getModuleImportLoc(int ID) {
1292f4a2713aSLionel Sambuc   if (ID == 0)
1293f4a2713aSLionel Sambuc     return std::make_pair(SourceLocation(), "");
1294f4a2713aSLionel Sambuc 
1295f4a2713aSLionel Sambuc   if (unsigned(-ID) - 2 >= getTotalNumSLocs() || ID > 0) {
1296f4a2713aSLionel Sambuc     Error("source location entry ID out-of-range for AST file");
1297f4a2713aSLionel Sambuc     return std::make_pair(SourceLocation(), "");
1298f4a2713aSLionel Sambuc   }
1299f4a2713aSLionel Sambuc 
1300f4a2713aSLionel Sambuc   // Find which module file this entry lands in.
1301f4a2713aSLionel Sambuc   ModuleFile *M = GlobalSLocEntryMap.find(-ID)->second;
1302*0a6a1f1dSLionel Sambuc   if (M->Kind != MK_ImplicitModule && M->Kind != MK_ExplicitModule)
1303f4a2713aSLionel Sambuc     return std::make_pair(SourceLocation(), "");
1304f4a2713aSLionel Sambuc 
1305f4a2713aSLionel Sambuc   // FIXME: Can we map this down to a particular submodule? That would be
1306f4a2713aSLionel Sambuc   // ideal.
1307*0a6a1f1dSLionel Sambuc   return std::make_pair(M->ImportLoc, StringRef(M->ModuleName));
1308f4a2713aSLionel Sambuc }
1309f4a2713aSLionel Sambuc 
1310f4a2713aSLionel Sambuc /// \brief Find the location where the module F is imported.
getImportLocation(ModuleFile * F)1311f4a2713aSLionel Sambuc SourceLocation ASTReader::getImportLocation(ModuleFile *F) {
1312f4a2713aSLionel Sambuc   if (F->ImportLoc.isValid())
1313f4a2713aSLionel Sambuc     return F->ImportLoc;
1314f4a2713aSLionel Sambuc 
1315f4a2713aSLionel Sambuc   // Otherwise we have a PCH. It's considered to be "imported" at the first
1316f4a2713aSLionel Sambuc   // location of its includer.
1317f4a2713aSLionel Sambuc   if (F->ImportedBy.empty() || !F->ImportedBy[0]) {
1318*0a6a1f1dSLionel Sambuc     // Main file is the importer.
1319*0a6a1f1dSLionel Sambuc     assert(!SourceMgr.getMainFileID().isInvalid() && "missing main file");
1320*0a6a1f1dSLionel Sambuc     return SourceMgr.getLocForStartOfFile(SourceMgr.getMainFileID());
1321f4a2713aSLionel Sambuc   }
1322f4a2713aSLionel Sambuc   return F->ImportedBy[0]->FirstLoc;
1323f4a2713aSLionel Sambuc }
1324f4a2713aSLionel Sambuc 
1325f4a2713aSLionel Sambuc /// ReadBlockAbbrevs - Enter a subblock of the specified BlockID with the
1326f4a2713aSLionel Sambuc /// specified cursor.  Read the abbreviations that are at the top of the block
1327f4a2713aSLionel Sambuc /// and then leave the cursor pointing into the block.
ReadBlockAbbrevs(BitstreamCursor & Cursor,unsigned BlockID)1328f4a2713aSLionel Sambuc bool ASTReader::ReadBlockAbbrevs(BitstreamCursor &Cursor, unsigned BlockID) {
1329f4a2713aSLionel Sambuc   if (Cursor.EnterSubBlock(BlockID)) {
1330f4a2713aSLionel Sambuc     Error("malformed block record in AST file");
1331f4a2713aSLionel Sambuc     return Failure;
1332f4a2713aSLionel Sambuc   }
1333f4a2713aSLionel Sambuc 
1334f4a2713aSLionel Sambuc   while (true) {
1335f4a2713aSLionel Sambuc     uint64_t Offset = Cursor.GetCurrentBitNo();
1336f4a2713aSLionel Sambuc     unsigned Code = Cursor.ReadCode();
1337f4a2713aSLionel Sambuc 
1338f4a2713aSLionel Sambuc     // We expect all abbrevs to be at the start of the block.
1339f4a2713aSLionel Sambuc     if (Code != llvm::bitc::DEFINE_ABBREV) {
1340f4a2713aSLionel Sambuc       Cursor.JumpToBit(Offset);
1341f4a2713aSLionel Sambuc       return false;
1342f4a2713aSLionel Sambuc     }
1343f4a2713aSLionel Sambuc     Cursor.ReadAbbrevRecord();
1344f4a2713aSLionel Sambuc   }
1345f4a2713aSLionel Sambuc }
1346f4a2713aSLionel Sambuc 
ReadToken(ModuleFile & F,const RecordDataImpl & Record,unsigned & Idx)1347f4a2713aSLionel Sambuc Token ASTReader::ReadToken(ModuleFile &F, const RecordDataImpl &Record,
1348f4a2713aSLionel Sambuc                            unsigned &Idx) {
1349f4a2713aSLionel Sambuc   Token Tok;
1350f4a2713aSLionel Sambuc   Tok.startToken();
1351f4a2713aSLionel Sambuc   Tok.setLocation(ReadSourceLocation(F, Record, Idx));
1352f4a2713aSLionel Sambuc   Tok.setLength(Record[Idx++]);
1353f4a2713aSLionel Sambuc   if (IdentifierInfo *II = getLocalIdentifier(F, Record[Idx++]))
1354f4a2713aSLionel Sambuc     Tok.setIdentifierInfo(II);
1355f4a2713aSLionel Sambuc   Tok.setKind((tok::TokenKind)Record[Idx++]);
1356f4a2713aSLionel Sambuc   Tok.setFlag((Token::TokenFlags)Record[Idx++]);
1357f4a2713aSLionel Sambuc   return Tok;
1358f4a2713aSLionel Sambuc }
1359f4a2713aSLionel Sambuc 
ReadMacroRecord(ModuleFile & F,uint64_t Offset)1360f4a2713aSLionel Sambuc MacroInfo *ASTReader::ReadMacroRecord(ModuleFile &F, uint64_t Offset) {
1361f4a2713aSLionel Sambuc   BitstreamCursor &Stream = F.MacroCursor;
1362f4a2713aSLionel Sambuc 
1363f4a2713aSLionel Sambuc   // Keep track of where we are in the stream, then jump back there
1364f4a2713aSLionel Sambuc   // after reading this macro.
1365f4a2713aSLionel Sambuc   SavedStreamPosition SavedPosition(Stream);
1366f4a2713aSLionel Sambuc 
1367f4a2713aSLionel Sambuc   Stream.JumpToBit(Offset);
1368f4a2713aSLionel Sambuc   RecordData Record;
1369f4a2713aSLionel Sambuc   SmallVector<IdentifierInfo*, 16> MacroArgs;
1370*0a6a1f1dSLionel Sambuc   MacroInfo *Macro = nullptr;
1371f4a2713aSLionel Sambuc 
1372f4a2713aSLionel Sambuc   while (true) {
1373f4a2713aSLionel Sambuc     // Advance to the next record, but if we get to the end of the block, don't
1374f4a2713aSLionel Sambuc     // pop it (removing all the abbreviations from the cursor) since we want to
1375f4a2713aSLionel Sambuc     // be able to reseek within the block and read entries.
1376f4a2713aSLionel Sambuc     unsigned Flags = BitstreamCursor::AF_DontPopBlockAtEnd;
1377f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = Stream.advanceSkippingSubblocks(Flags);
1378f4a2713aSLionel Sambuc 
1379f4a2713aSLionel Sambuc     switch (Entry.Kind) {
1380f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::SubBlock: // Handled for us already.
1381f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Error:
1382f4a2713aSLionel Sambuc       Error("malformed block record in AST file");
1383f4a2713aSLionel Sambuc       return Macro;
1384f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::EndBlock:
1385f4a2713aSLionel Sambuc       return Macro;
1386f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Record:
1387f4a2713aSLionel Sambuc       // The interesting case.
1388f4a2713aSLionel Sambuc       break;
1389f4a2713aSLionel Sambuc     }
1390f4a2713aSLionel Sambuc 
1391f4a2713aSLionel Sambuc     // Read a record.
1392f4a2713aSLionel Sambuc     Record.clear();
1393f4a2713aSLionel Sambuc     PreprocessorRecordTypes RecType =
1394f4a2713aSLionel Sambuc       (PreprocessorRecordTypes)Stream.readRecord(Entry.ID, Record);
1395f4a2713aSLionel Sambuc     switch (RecType) {
1396f4a2713aSLionel Sambuc     case PP_MACRO_DIRECTIVE_HISTORY:
1397f4a2713aSLionel Sambuc       return Macro;
1398f4a2713aSLionel Sambuc 
1399f4a2713aSLionel Sambuc     case PP_MACRO_OBJECT_LIKE:
1400f4a2713aSLionel Sambuc     case PP_MACRO_FUNCTION_LIKE: {
1401f4a2713aSLionel Sambuc       // If we already have a macro, that means that we've hit the end
1402f4a2713aSLionel Sambuc       // of the definition of the macro we were looking for. We're
1403f4a2713aSLionel Sambuc       // done.
1404f4a2713aSLionel Sambuc       if (Macro)
1405f4a2713aSLionel Sambuc         return Macro;
1406f4a2713aSLionel Sambuc 
1407f4a2713aSLionel Sambuc       unsigned NextIndex = 1; // Skip identifier ID.
1408f4a2713aSLionel Sambuc       SubmoduleID SubModID = getGlobalSubmoduleID(F, Record[NextIndex++]);
1409f4a2713aSLionel Sambuc       SourceLocation Loc = ReadSourceLocation(F, Record, NextIndex);
1410f4a2713aSLionel Sambuc       MacroInfo *MI = PP.AllocateDeserializedMacroInfo(Loc, SubModID);
1411f4a2713aSLionel Sambuc       MI->setDefinitionEndLoc(ReadSourceLocation(F, Record, NextIndex));
1412f4a2713aSLionel Sambuc       MI->setIsUsed(Record[NextIndex++]);
1413*0a6a1f1dSLionel Sambuc       MI->setUsedForHeaderGuard(Record[NextIndex++]);
1414f4a2713aSLionel Sambuc 
1415f4a2713aSLionel Sambuc       if (RecType == PP_MACRO_FUNCTION_LIKE) {
1416f4a2713aSLionel Sambuc         // Decode function-like macro info.
1417f4a2713aSLionel Sambuc         bool isC99VarArgs = Record[NextIndex++];
1418f4a2713aSLionel Sambuc         bool isGNUVarArgs = Record[NextIndex++];
1419f4a2713aSLionel Sambuc         bool hasCommaPasting = Record[NextIndex++];
1420f4a2713aSLionel Sambuc         MacroArgs.clear();
1421f4a2713aSLionel Sambuc         unsigned NumArgs = Record[NextIndex++];
1422f4a2713aSLionel Sambuc         for (unsigned i = 0; i != NumArgs; ++i)
1423f4a2713aSLionel Sambuc           MacroArgs.push_back(getLocalIdentifier(F, Record[NextIndex++]));
1424f4a2713aSLionel Sambuc 
1425f4a2713aSLionel Sambuc         // Install function-like macro info.
1426f4a2713aSLionel Sambuc         MI->setIsFunctionLike();
1427f4a2713aSLionel Sambuc         if (isC99VarArgs) MI->setIsC99Varargs();
1428f4a2713aSLionel Sambuc         if (isGNUVarArgs) MI->setIsGNUVarargs();
1429f4a2713aSLionel Sambuc         if (hasCommaPasting) MI->setHasCommaPasting();
1430f4a2713aSLionel Sambuc         MI->setArgumentList(MacroArgs.data(), MacroArgs.size(),
1431f4a2713aSLionel Sambuc                             PP.getPreprocessorAllocator());
1432f4a2713aSLionel Sambuc       }
1433f4a2713aSLionel Sambuc 
1434f4a2713aSLionel Sambuc       // Remember that we saw this macro last so that we add the tokens that
1435f4a2713aSLionel Sambuc       // form its body to it.
1436f4a2713aSLionel Sambuc       Macro = MI;
1437f4a2713aSLionel Sambuc 
1438f4a2713aSLionel Sambuc       if (NextIndex + 1 == Record.size() && PP.getPreprocessingRecord() &&
1439f4a2713aSLionel Sambuc           Record[NextIndex]) {
1440f4a2713aSLionel Sambuc         // We have a macro definition. Register the association
1441f4a2713aSLionel Sambuc         PreprocessedEntityID
1442f4a2713aSLionel Sambuc             GlobalID = getGlobalPreprocessedEntityID(F, Record[NextIndex]);
1443f4a2713aSLionel Sambuc         PreprocessingRecord &PPRec = *PP.getPreprocessingRecord();
1444f4a2713aSLionel Sambuc         PreprocessingRecord::PPEntityID
1445f4a2713aSLionel Sambuc           PPID = PPRec.getPPEntityID(GlobalID-1, /*isLoaded=*/true);
1446f4a2713aSLionel Sambuc         MacroDefinition *PPDef =
1447f4a2713aSLionel Sambuc           cast_or_null<MacroDefinition>(PPRec.getPreprocessedEntity(PPID));
1448f4a2713aSLionel Sambuc         if (PPDef)
1449f4a2713aSLionel Sambuc           PPRec.RegisterMacroDefinition(Macro, PPDef);
1450f4a2713aSLionel Sambuc       }
1451f4a2713aSLionel Sambuc 
1452f4a2713aSLionel Sambuc       ++NumMacrosRead;
1453f4a2713aSLionel Sambuc       break;
1454f4a2713aSLionel Sambuc     }
1455f4a2713aSLionel Sambuc 
1456f4a2713aSLionel Sambuc     case PP_TOKEN: {
1457f4a2713aSLionel Sambuc       // If we see a TOKEN before a PP_MACRO_*, then the file is
1458f4a2713aSLionel Sambuc       // erroneous, just pretend we didn't see this.
1459*0a6a1f1dSLionel Sambuc       if (!Macro) break;
1460f4a2713aSLionel Sambuc 
1461f4a2713aSLionel Sambuc       unsigned Idx = 0;
1462f4a2713aSLionel Sambuc       Token Tok = ReadToken(F, Record, Idx);
1463f4a2713aSLionel Sambuc       Macro->AddTokenToBody(Tok);
1464f4a2713aSLionel Sambuc       break;
1465f4a2713aSLionel Sambuc     }
1466f4a2713aSLionel Sambuc     }
1467f4a2713aSLionel Sambuc   }
1468f4a2713aSLionel Sambuc }
1469f4a2713aSLionel Sambuc 
1470f4a2713aSLionel Sambuc PreprocessedEntityID
getGlobalPreprocessedEntityID(ModuleFile & M,unsigned LocalID) const1471f4a2713aSLionel Sambuc ASTReader::getGlobalPreprocessedEntityID(ModuleFile &M, unsigned LocalID) const {
1472f4a2713aSLionel Sambuc   ContinuousRangeMap<uint32_t, int, 2>::const_iterator
1473f4a2713aSLionel Sambuc     I = M.PreprocessedEntityRemap.find(LocalID - NUM_PREDEF_PP_ENTITY_IDS);
1474f4a2713aSLionel Sambuc   assert(I != M.PreprocessedEntityRemap.end()
1475f4a2713aSLionel Sambuc          && "Invalid index into preprocessed entity index remap");
1476f4a2713aSLionel Sambuc 
1477f4a2713aSLionel Sambuc   return LocalID + I->second;
1478f4a2713aSLionel Sambuc }
1479f4a2713aSLionel Sambuc 
ComputeHash(internal_key_ref ikey)1480f4a2713aSLionel Sambuc unsigned HeaderFileInfoTrait::ComputeHash(internal_key_ref ikey) {
1481f4a2713aSLionel Sambuc   return llvm::hash_combine(ikey.Size, ikey.ModTime);
1482f4a2713aSLionel Sambuc }
1483f4a2713aSLionel Sambuc 
1484f4a2713aSLionel Sambuc HeaderFileInfoTrait::internal_key_type
GetInternalKey(const FileEntry * FE)1485f4a2713aSLionel Sambuc HeaderFileInfoTrait::GetInternalKey(const FileEntry *FE) {
1486f4a2713aSLionel Sambuc   internal_key_type ikey = { FE->getSize(), FE->getModificationTime(),
1487*0a6a1f1dSLionel Sambuc                              FE->getName(), /*Imported*/false };
1488f4a2713aSLionel Sambuc   return ikey;
1489f4a2713aSLionel Sambuc }
1490f4a2713aSLionel Sambuc 
EqualKey(internal_key_ref a,internal_key_ref b)1491f4a2713aSLionel Sambuc bool HeaderFileInfoTrait::EqualKey(internal_key_ref a, internal_key_ref b) {
1492f4a2713aSLionel Sambuc   if (a.Size != b.Size || a.ModTime != b.ModTime)
1493f4a2713aSLionel Sambuc     return false;
1494f4a2713aSLionel Sambuc 
1495*0a6a1f1dSLionel Sambuc   if (llvm::sys::path::is_absolute(a.Filename) &&
1496*0a6a1f1dSLionel Sambuc       strcmp(a.Filename, b.Filename) == 0)
1497f4a2713aSLionel Sambuc     return true;
1498f4a2713aSLionel Sambuc 
1499f4a2713aSLionel Sambuc   // Determine whether the actual files are equivalent.
1500f4a2713aSLionel Sambuc   FileManager &FileMgr = Reader.getFileManager();
1501*0a6a1f1dSLionel Sambuc   auto GetFile = [&](const internal_key_type &Key) -> const FileEntry* {
1502*0a6a1f1dSLionel Sambuc     if (!Key.Imported)
1503*0a6a1f1dSLionel Sambuc       return FileMgr.getFile(Key.Filename);
1504*0a6a1f1dSLionel Sambuc 
1505*0a6a1f1dSLionel Sambuc     std::string Resolved = Key.Filename;
1506*0a6a1f1dSLionel Sambuc     Reader.ResolveImportedPath(M, Resolved);
1507*0a6a1f1dSLionel Sambuc     return FileMgr.getFile(Resolved);
1508*0a6a1f1dSLionel Sambuc   };
1509*0a6a1f1dSLionel Sambuc 
1510*0a6a1f1dSLionel Sambuc   const FileEntry *FEA = GetFile(a);
1511*0a6a1f1dSLionel Sambuc   const FileEntry *FEB = GetFile(b);
1512*0a6a1f1dSLionel Sambuc   return FEA && FEA == FEB;
1513f4a2713aSLionel Sambuc }
1514f4a2713aSLionel Sambuc 
1515f4a2713aSLionel Sambuc std::pair<unsigned, unsigned>
ReadKeyDataLength(const unsigned char * & d)1516f4a2713aSLionel Sambuc HeaderFileInfoTrait::ReadKeyDataLength(const unsigned char*& d) {
1517*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
1518*0a6a1f1dSLionel Sambuc   unsigned KeyLen = (unsigned) endian::readNext<uint16_t, little, unaligned>(d);
1519f4a2713aSLionel Sambuc   unsigned DataLen = (unsigned) *d++;
1520f4a2713aSLionel Sambuc   return std::make_pair(KeyLen, DataLen);
1521f4a2713aSLionel Sambuc }
1522f4a2713aSLionel Sambuc 
1523f4a2713aSLionel Sambuc HeaderFileInfoTrait::internal_key_type
ReadKey(const unsigned char * d,unsigned)1524f4a2713aSLionel Sambuc HeaderFileInfoTrait::ReadKey(const unsigned char *d, unsigned) {
1525*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
1526f4a2713aSLionel Sambuc   internal_key_type ikey;
1527*0a6a1f1dSLionel Sambuc   ikey.Size = off_t(endian::readNext<uint64_t, little, unaligned>(d));
1528*0a6a1f1dSLionel Sambuc   ikey.ModTime = time_t(endian::readNext<uint64_t, little, unaligned>(d));
1529f4a2713aSLionel Sambuc   ikey.Filename = (const char *)d;
1530*0a6a1f1dSLionel Sambuc   ikey.Imported = true;
1531f4a2713aSLionel Sambuc   return ikey;
1532f4a2713aSLionel Sambuc }
1533f4a2713aSLionel Sambuc 
1534f4a2713aSLionel Sambuc HeaderFileInfoTrait::data_type
ReadData(internal_key_ref key,const unsigned char * d,unsigned DataLen)1535f4a2713aSLionel Sambuc HeaderFileInfoTrait::ReadData(internal_key_ref key, const unsigned char *d,
1536f4a2713aSLionel Sambuc                               unsigned DataLen) {
1537f4a2713aSLionel Sambuc   const unsigned char *End = d + DataLen;
1538*0a6a1f1dSLionel Sambuc   using namespace llvm::support;
1539f4a2713aSLionel Sambuc   HeaderFileInfo HFI;
1540f4a2713aSLionel Sambuc   unsigned Flags = *d++;
1541f4a2713aSLionel Sambuc   HFI.HeaderRole = static_cast<ModuleMap::ModuleHeaderRole>
1542f4a2713aSLionel Sambuc                    ((Flags >> 6) & 0x03);
1543f4a2713aSLionel Sambuc   HFI.isImport = (Flags >> 5) & 0x01;
1544f4a2713aSLionel Sambuc   HFI.isPragmaOnce = (Flags >> 4) & 0x01;
1545f4a2713aSLionel Sambuc   HFI.DirInfo = (Flags >> 2) & 0x03;
1546f4a2713aSLionel Sambuc   HFI.Resolved = (Flags >> 1) & 0x01;
1547f4a2713aSLionel Sambuc   HFI.IndexHeaderMapHeader = Flags & 0x01;
1548*0a6a1f1dSLionel Sambuc   HFI.NumIncludes = endian::readNext<uint16_t, little, unaligned>(d);
1549*0a6a1f1dSLionel Sambuc   HFI.ControllingMacroID = Reader.getGlobalIdentifierID(
1550*0a6a1f1dSLionel Sambuc       M, endian::readNext<uint32_t, little, unaligned>(d));
1551*0a6a1f1dSLionel Sambuc   if (unsigned FrameworkOffset =
1552*0a6a1f1dSLionel Sambuc           endian::readNext<uint32_t, little, unaligned>(d)) {
1553f4a2713aSLionel Sambuc     // The framework offset is 1 greater than the actual offset,
1554f4a2713aSLionel Sambuc     // since 0 is used as an indicator for "no framework name".
1555f4a2713aSLionel Sambuc     StringRef FrameworkName(FrameworkStrings + FrameworkOffset - 1);
1556f4a2713aSLionel Sambuc     HFI.Framework = HS->getUniqueFrameworkName(FrameworkName);
1557f4a2713aSLionel Sambuc   }
1558f4a2713aSLionel Sambuc 
1559f4a2713aSLionel Sambuc   if (d != End) {
1560*0a6a1f1dSLionel Sambuc     uint32_t LocalSMID = endian::readNext<uint32_t, little, unaligned>(d);
1561f4a2713aSLionel Sambuc     if (LocalSMID) {
1562f4a2713aSLionel Sambuc       // This header is part of a module. Associate it with the module to enable
1563f4a2713aSLionel Sambuc       // implicit module import.
1564f4a2713aSLionel Sambuc       SubmoduleID GlobalSMID = Reader.getGlobalSubmoduleID(M, LocalSMID);
1565f4a2713aSLionel Sambuc       Module *Mod = Reader.getSubmodule(GlobalSMID);
1566f4a2713aSLionel Sambuc       HFI.isModuleHeader = true;
1567f4a2713aSLionel Sambuc       FileManager &FileMgr = Reader.getFileManager();
1568f4a2713aSLionel Sambuc       ModuleMap &ModMap =
1569f4a2713aSLionel Sambuc           Reader.getPreprocessor().getHeaderSearchInfo().getModuleMap();
1570*0a6a1f1dSLionel Sambuc       // FIXME: This information should be propagated through the
1571*0a6a1f1dSLionel Sambuc       // SUBMODULE_HEADER etc records rather than from here.
1572*0a6a1f1dSLionel Sambuc       // FIXME: We don't ever mark excluded headers.
1573*0a6a1f1dSLionel Sambuc       std::string Filename = key.Filename;
1574*0a6a1f1dSLionel Sambuc       if (key.Imported)
1575*0a6a1f1dSLionel Sambuc         Reader.ResolveImportedPath(M, Filename);
1576*0a6a1f1dSLionel Sambuc       Module::Header H = { key.Filename, FileMgr.getFile(Filename) };
1577*0a6a1f1dSLionel Sambuc       ModMap.addHeader(Mod, H, HFI.getHeaderRole());
1578f4a2713aSLionel Sambuc     }
1579f4a2713aSLionel Sambuc   }
1580f4a2713aSLionel Sambuc 
1581f4a2713aSLionel Sambuc   assert(End == d && "Wrong data length in HeaderFileInfo deserialization");
1582f4a2713aSLionel Sambuc   (void)End;
1583f4a2713aSLionel Sambuc 
1584f4a2713aSLionel Sambuc   // This HeaderFileInfo was externally loaded.
1585f4a2713aSLionel Sambuc   HFI.External = true;
1586f4a2713aSLionel Sambuc   return HFI;
1587f4a2713aSLionel Sambuc }
1588f4a2713aSLionel Sambuc 
1589*0a6a1f1dSLionel Sambuc void
addPendingMacroFromModule(IdentifierInfo * II,ModuleFile * M,GlobalMacroID GMacID,ArrayRef<SubmoduleID> Overrides)1590*0a6a1f1dSLionel Sambuc ASTReader::addPendingMacroFromModule(IdentifierInfo *II, ModuleFile *M,
1591f4a2713aSLionel Sambuc                                      GlobalMacroID GMacID,
1592*0a6a1f1dSLionel Sambuc                                      ArrayRef<SubmoduleID> Overrides) {
1593f4a2713aSLionel Sambuc   assert(NumCurrentElementsDeserializing > 0 &&"Missing deserialization guard");
1594*0a6a1f1dSLionel Sambuc   SubmoduleID *OverrideData = nullptr;
1595*0a6a1f1dSLionel Sambuc   if (!Overrides.empty()) {
1596*0a6a1f1dSLionel Sambuc     OverrideData = new (Context) SubmoduleID[Overrides.size() + 1];
1597*0a6a1f1dSLionel Sambuc     OverrideData[0] = Overrides.size();
1598*0a6a1f1dSLionel Sambuc     for (unsigned I = 0; I != Overrides.size(); ++I)
1599*0a6a1f1dSLionel Sambuc       OverrideData[I + 1] = getGlobalSubmoduleID(*M, Overrides[I]);
1600*0a6a1f1dSLionel Sambuc   }
1601*0a6a1f1dSLionel Sambuc   PendingMacroIDs[II].push_back(PendingMacroInfo(M, GMacID, OverrideData));
1602f4a2713aSLionel Sambuc }
1603f4a2713aSLionel Sambuc 
addPendingMacroFromPCH(IdentifierInfo * II,ModuleFile * M,uint64_t MacroDirectivesOffset)1604f4a2713aSLionel Sambuc void ASTReader::addPendingMacroFromPCH(IdentifierInfo *II,
1605f4a2713aSLionel Sambuc                                        ModuleFile *M,
1606f4a2713aSLionel Sambuc                                        uint64_t MacroDirectivesOffset) {
1607f4a2713aSLionel Sambuc   assert(NumCurrentElementsDeserializing > 0 &&"Missing deserialization guard");
1608f4a2713aSLionel Sambuc   PendingMacroIDs[II].push_back(PendingMacroInfo(M, MacroDirectivesOffset));
1609f4a2713aSLionel Sambuc }
1610f4a2713aSLionel Sambuc 
ReadDefinedMacros()1611f4a2713aSLionel Sambuc void ASTReader::ReadDefinedMacros() {
1612f4a2713aSLionel Sambuc   // Note that we are loading defined macros.
1613f4a2713aSLionel Sambuc   Deserializing Macros(this);
1614f4a2713aSLionel Sambuc 
1615f4a2713aSLionel Sambuc   for (ModuleReverseIterator I = ModuleMgr.rbegin(),
1616f4a2713aSLionel Sambuc       E = ModuleMgr.rend(); I != E; ++I) {
1617f4a2713aSLionel Sambuc     BitstreamCursor &MacroCursor = (*I)->MacroCursor;
1618f4a2713aSLionel Sambuc 
1619f4a2713aSLionel Sambuc     // If there was no preprocessor block, skip this file.
1620f4a2713aSLionel Sambuc     if (!MacroCursor.getBitStreamReader())
1621f4a2713aSLionel Sambuc       continue;
1622f4a2713aSLionel Sambuc 
1623f4a2713aSLionel Sambuc     BitstreamCursor Cursor = MacroCursor;
1624f4a2713aSLionel Sambuc     Cursor.JumpToBit((*I)->MacroStartOffset);
1625f4a2713aSLionel Sambuc 
1626f4a2713aSLionel Sambuc     RecordData Record;
1627f4a2713aSLionel Sambuc     while (true) {
1628f4a2713aSLionel Sambuc       llvm::BitstreamEntry E = Cursor.advanceSkippingSubblocks();
1629f4a2713aSLionel Sambuc 
1630f4a2713aSLionel Sambuc       switch (E.Kind) {
1631f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::SubBlock: // Handled for us already.
1632f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::Error:
1633f4a2713aSLionel Sambuc         Error("malformed block record in AST file");
1634f4a2713aSLionel Sambuc         return;
1635f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::EndBlock:
1636f4a2713aSLionel Sambuc         goto NextCursor;
1637f4a2713aSLionel Sambuc 
1638f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::Record:
1639f4a2713aSLionel Sambuc         Record.clear();
1640f4a2713aSLionel Sambuc         switch (Cursor.readRecord(E.ID, Record)) {
1641f4a2713aSLionel Sambuc         default:  // Default behavior: ignore.
1642f4a2713aSLionel Sambuc           break;
1643f4a2713aSLionel Sambuc 
1644f4a2713aSLionel Sambuc         case PP_MACRO_OBJECT_LIKE:
1645f4a2713aSLionel Sambuc         case PP_MACRO_FUNCTION_LIKE:
1646f4a2713aSLionel Sambuc           getLocalIdentifier(**I, Record[0]);
1647f4a2713aSLionel Sambuc           break;
1648f4a2713aSLionel Sambuc 
1649f4a2713aSLionel Sambuc         case PP_TOKEN:
1650f4a2713aSLionel Sambuc           // Ignore tokens.
1651f4a2713aSLionel Sambuc           break;
1652f4a2713aSLionel Sambuc         }
1653f4a2713aSLionel Sambuc         break;
1654f4a2713aSLionel Sambuc       }
1655f4a2713aSLionel Sambuc     }
1656f4a2713aSLionel Sambuc     NextCursor:  ;
1657f4a2713aSLionel Sambuc   }
1658f4a2713aSLionel Sambuc }
1659f4a2713aSLionel Sambuc 
1660f4a2713aSLionel Sambuc namespace {
1661f4a2713aSLionel Sambuc   /// \brief Visitor class used to look up identifirs in an AST file.
1662f4a2713aSLionel Sambuc   class IdentifierLookupVisitor {
1663f4a2713aSLionel Sambuc     StringRef Name;
1664f4a2713aSLionel Sambuc     unsigned PriorGeneration;
1665f4a2713aSLionel Sambuc     unsigned &NumIdentifierLookups;
1666f4a2713aSLionel Sambuc     unsigned &NumIdentifierLookupHits;
1667f4a2713aSLionel Sambuc     IdentifierInfo *Found;
1668f4a2713aSLionel Sambuc 
1669f4a2713aSLionel Sambuc   public:
IdentifierLookupVisitor(StringRef Name,unsigned PriorGeneration,unsigned & NumIdentifierLookups,unsigned & NumIdentifierLookupHits)1670f4a2713aSLionel Sambuc     IdentifierLookupVisitor(StringRef Name, unsigned PriorGeneration,
1671f4a2713aSLionel Sambuc                             unsigned &NumIdentifierLookups,
1672f4a2713aSLionel Sambuc                             unsigned &NumIdentifierLookupHits)
1673f4a2713aSLionel Sambuc       : Name(Name), PriorGeneration(PriorGeneration),
1674f4a2713aSLionel Sambuc         NumIdentifierLookups(NumIdentifierLookups),
1675f4a2713aSLionel Sambuc         NumIdentifierLookupHits(NumIdentifierLookupHits),
1676f4a2713aSLionel Sambuc         Found()
1677f4a2713aSLionel Sambuc     {
1678f4a2713aSLionel Sambuc     }
1679f4a2713aSLionel Sambuc 
visit(ModuleFile & M,void * UserData)1680f4a2713aSLionel Sambuc     static bool visit(ModuleFile &M, void *UserData) {
1681f4a2713aSLionel Sambuc       IdentifierLookupVisitor *This
1682f4a2713aSLionel Sambuc         = static_cast<IdentifierLookupVisitor *>(UserData);
1683f4a2713aSLionel Sambuc 
1684f4a2713aSLionel Sambuc       // If we've already searched this module file, skip it now.
1685f4a2713aSLionel Sambuc       if (M.Generation <= This->PriorGeneration)
1686f4a2713aSLionel Sambuc         return true;
1687f4a2713aSLionel Sambuc 
1688f4a2713aSLionel Sambuc       ASTIdentifierLookupTable *IdTable
1689f4a2713aSLionel Sambuc         = (ASTIdentifierLookupTable *)M.IdentifierLookupTable;
1690f4a2713aSLionel Sambuc       if (!IdTable)
1691f4a2713aSLionel Sambuc         return false;
1692f4a2713aSLionel Sambuc 
1693f4a2713aSLionel Sambuc       ASTIdentifierLookupTrait Trait(IdTable->getInfoObj().getReader(),
1694f4a2713aSLionel Sambuc                                      M, This->Found);
1695f4a2713aSLionel Sambuc       ++This->NumIdentifierLookups;
1696f4a2713aSLionel Sambuc       ASTIdentifierLookupTable::iterator Pos = IdTable->find(This->Name,&Trait);
1697f4a2713aSLionel Sambuc       if (Pos == IdTable->end())
1698f4a2713aSLionel Sambuc         return false;
1699f4a2713aSLionel Sambuc 
1700f4a2713aSLionel Sambuc       // Dereferencing the iterator has the effect of building the
1701f4a2713aSLionel Sambuc       // IdentifierInfo node and populating it with the various
1702f4a2713aSLionel Sambuc       // declarations it needs.
1703f4a2713aSLionel Sambuc       ++This->NumIdentifierLookupHits;
1704f4a2713aSLionel Sambuc       This->Found = *Pos;
1705f4a2713aSLionel Sambuc       return true;
1706f4a2713aSLionel Sambuc     }
1707f4a2713aSLionel Sambuc 
1708f4a2713aSLionel Sambuc     // \brief Retrieve the identifier info found within the module
1709f4a2713aSLionel Sambuc     // files.
getIdentifierInfo() const1710f4a2713aSLionel Sambuc     IdentifierInfo *getIdentifierInfo() const { return Found; }
1711f4a2713aSLionel Sambuc   };
1712f4a2713aSLionel Sambuc }
1713f4a2713aSLionel Sambuc 
updateOutOfDateIdentifier(IdentifierInfo & II)1714f4a2713aSLionel Sambuc void ASTReader::updateOutOfDateIdentifier(IdentifierInfo &II) {
1715f4a2713aSLionel Sambuc   // Note that we are loading an identifier.
1716f4a2713aSLionel Sambuc   Deserializing AnIdentifier(this);
1717f4a2713aSLionel Sambuc 
1718f4a2713aSLionel Sambuc   unsigned PriorGeneration = 0;
1719f4a2713aSLionel Sambuc   if (getContext().getLangOpts().Modules)
1720f4a2713aSLionel Sambuc     PriorGeneration = IdentifierGeneration[&II];
1721f4a2713aSLionel Sambuc 
1722f4a2713aSLionel Sambuc   // If there is a global index, look there first to determine which modules
1723f4a2713aSLionel Sambuc   // provably do not have any results for this identifier.
1724f4a2713aSLionel Sambuc   GlobalModuleIndex::HitSet Hits;
1725*0a6a1f1dSLionel Sambuc   GlobalModuleIndex::HitSet *HitsPtr = nullptr;
1726f4a2713aSLionel Sambuc   if (!loadGlobalIndex()) {
1727f4a2713aSLionel Sambuc     if (GlobalIndex->lookupIdentifier(II.getName(), Hits)) {
1728f4a2713aSLionel Sambuc       HitsPtr = &Hits;
1729f4a2713aSLionel Sambuc     }
1730f4a2713aSLionel Sambuc   }
1731f4a2713aSLionel Sambuc 
1732f4a2713aSLionel Sambuc   IdentifierLookupVisitor Visitor(II.getName(), PriorGeneration,
1733f4a2713aSLionel Sambuc                                   NumIdentifierLookups,
1734f4a2713aSLionel Sambuc                                   NumIdentifierLookupHits);
1735f4a2713aSLionel Sambuc   ModuleMgr.visit(IdentifierLookupVisitor::visit, &Visitor, HitsPtr);
1736f4a2713aSLionel Sambuc   markIdentifierUpToDate(&II);
1737f4a2713aSLionel Sambuc }
1738f4a2713aSLionel Sambuc 
markIdentifierUpToDate(IdentifierInfo * II)1739f4a2713aSLionel Sambuc void ASTReader::markIdentifierUpToDate(IdentifierInfo *II) {
1740f4a2713aSLionel Sambuc   if (!II)
1741f4a2713aSLionel Sambuc     return;
1742f4a2713aSLionel Sambuc 
1743f4a2713aSLionel Sambuc   II->setOutOfDate(false);
1744f4a2713aSLionel Sambuc 
1745f4a2713aSLionel Sambuc   // Update the generation for this identifier.
1746f4a2713aSLionel Sambuc   if (getContext().getLangOpts().Modules)
1747*0a6a1f1dSLionel Sambuc     IdentifierGeneration[II] = getGeneration();
1748*0a6a1f1dSLionel Sambuc }
1749*0a6a1f1dSLionel Sambuc 
1750*0a6a1f1dSLionel Sambuc struct ASTReader::ModuleMacroInfo {
1751*0a6a1f1dSLionel Sambuc   SubmoduleID SubModID;
1752*0a6a1f1dSLionel Sambuc   MacroInfo *MI;
1753*0a6a1f1dSLionel Sambuc   SubmoduleID *Overrides;
1754*0a6a1f1dSLionel Sambuc   // FIXME: Remove this.
1755*0a6a1f1dSLionel Sambuc   ModuleFile *F;
1756*0a6a1f1dSLionel Sambuc 
isDefineASTReader::ModuleMacroInfo1757*0a6a1f1dSLionel Sambuc   bool isDefine() const { return MI; }
1758*0a6a1f1dSLionel Sambuc 
getSubmoduleIDASTReader::ModuleMacroInfo1759*0a6a1f1dSLionel Sambuc   SubmoduleID getSubmoduleID() const { return SubModID; }
1760*0a6a1f1dSLionel Sambuc 
getOverriddenSubmodulesASTReader::ModuleMacroInfo1761*0a6a1f1dSLionel Sambuc   ArrayRef<SubmoduleID> getOverriddenSubmodules() const {
1762*0a6a1f1dSLionel Sambuc     if (!Overrides)
1763*0a6a1f1dSLionel Sambuc       return None;
1764*0a6a1f1dSLionel Sambuc     return llvm::makeArrayRef(Overrides + 1, *Overrides);
1765*0a6a1f1dSLionel Sambuc   }
1766*0a6a1f1dSLionel Sambuc 
importASTReader::ModuleMacroInfo1767*0a6a1f1dSLionel Sambuc   MacroDirective *import(Preprocessor &PP, SourceLocation ImportLoc) const {
1768*0a6a1f1dSLionel Sambuc     if (!MI)
1769*0a6a1f1dSLionel Sambuc       return PP.AllocateUndefMacroDirective(ImportLoc, SubModID,
1770*0a6a1f1dSLionel Sambuc                                             getOverriddenSubmodules());
1771*0a6a1f1dSLionel Sambuc     return PP.AllocateDefMacroDirective(MI, ImportLoc, SubModID,
1772*0a6a1f1dSLionel Sambuc                                         getOverriddenSubmodules());
1773*0a6a1f1dSLionel Sambuc   }
1774*0a6a1f1dSLionel Sambuc };
1775*0a6a1f1dSLionel Sambuc 
1776*0a6a1f1dSLionel Sambuc ASTReader::ModuleMacroInfo *
getModuleMacro(const PendingMacroInfo & PMInfo)1777*0a6a1f1dSLionel Sambuc ASTReader::getModuleMacro(const PendingMacroInfo &PMInfo) {
1778*0a6a1f1dSLionel Sambuc   ModuleMacroInfo Info;
1779*0a6a1f1dSLionel Sambuc 
1780*0a6a1f1dSLionel Sambuc   uint32_t ID = PMInfo.ModuleMacroData.MacID;
1781*0a6a1f1dSLionel Sambuc   if (ID & 1) {
1782*0a6a1f1dSLionel Sambuc     // Macro undefinition.
1783*0a6a1f1dSLionel Sambuc     Info.SubModID = getGlobalSubmoduleID(*PMInfo.M, ID >> 1);
1784*0a6a1f1dSLionel Sambuc     Info.MI = nullptr;
1785*0a6a1f1dSLionel Sambuc   } else {
1786*0a6a1f1dSLionel Sambuc     // Macro definition.
1787*0a6a1f1dSLionel Sambuc     GlobalMacroID GMacID = getGlobalMacroID(*PMInfo.M, ID >> 1);
1788*0a6a1f1dSLionel Sambuc     assert(GMacID);
1789*0a6a1f1dSLionel Sambuc 
1790*0a6a1f1dSLionel Sambuc     // If this macro has already been loaded, don't do so again.
1791*0a6a1f1dSLionel Sambuc     // FIXME: This is highly dubious. Multiple macro definitions can have the
1792*0a6a1f1dSLionel Sambuc     // same MacroInfo (and hence the same GMacID) due to #pragma push_macro etc.
1793*0a6a1f1dSLionel Sambuc     if (MacrosLoaded[GMacID - NUM_PREDEF_MACRO_IDS])
1794*0a6a1f1dSLionel Sambuc       return nullptr;
1795*0a6a1f1dSLionel Sambuc 
1796*0a6a1f1dSLionel Sambuc     Info.MI = getMacro(GMacID);
1797*0a6a1f1dSLionel Sambuc     Info.SubModID = Info.MI->getOwningModuleID();
1798*0a6a1f1dSLionel Sambuc   }
1799*0a6a1f1dSLionel Sambuc   Info.Overrides = PMInfo.ModuleMacroData.Overrides;
1800*0a6a1f1dSLionel Sambuc   Info.F = PMInfo.M;
1801*0a6a1f1dSLionel Sambuc 
1802*0a6a1f1dSLionel Sambuc   return new (Context) ModuleMacroInfo(Info);
1803f4a2713aSLionel Sambuc }
1804f4a2713aSLionel Sambuc 
resolvePendingMacro(IdentifierInfo * II,const PendingMacroInfo & PMInfo)1805f4a2713aSLionel Sambuc void ASTReader::resolvePendingMacro(IdentifierInfo *II,
1806f4a2713aSLionel Sambuc                                     const PendingMacroInfo &PMInfo) {
1807f4a2713aSLionel Sambuc   assert(II);
1808f4a2713aSLionel Sambuc 
1809*0a6a1f1dSLionel Sambuc   if (PMInfo.M->Kind != MK_ImplicitModule &&
1810*0a6a1f1dSLionel Sambuc       PMInfo.M->Kind != MK_ExplicitModule) {
1811f4a2713aSLionel Sambuc     installPCHMacroDirectives(II, *PMInfo.M,
1812f4a2713aSLionel Sambuc                               PMInfo.PCHMacroData.MacroDirectivesOffset);
1813f4a2713aSLionel Sambuc     return;
1814f4a2713aSLionel Sambuc   }
1815f4a2713aSLionel Sambuc 
1816f4a2713aSLionel Sambuc   // Module Macro.
1817f4a2713aSLionel Sambuc 
1818*0a6a1f1dSLionel Sambuc   ModuleMacroInfo *MMI = getModuleMacro(PMInfo);
1819*0a6a1f1dSLionel Sambuc   if (!MMI)
1820f4a2713aSLionel Sambuc     return;
1821f4a2713aSLionel Sambuc 
1822*0a6a1f1dSLionel Sambuc   Module *Owner = getSubmodule(MMI->getSubmoduleID());
1823*0a6a1f1dSLionel Sambuc   if (Owner && Owner->NameVisibility == Module::Hidden) {
1824*0a6a1f1dSLionel Sambuc     // Macros in the owning module are hidden. Just remember this macro to
1825*0a6a1f1dSLionel Sambuc     // install if we make this module visible.
1826*0a6a1f1dSLionel Sambuc     HiddenNamesMap[Owner].HiddenMacros.insert(std::make_pair(II, MMI));
1827*0a6a1f1dSLionel Sambuc   } else {
1828*0a6a1f1dSLionel Sambuc     installImportedMacro(II, MMI, Owner);
1829f4a2713aSLionel Sambuc   }
1830f4a2713aSLionel Sambuc }
1831f4a2713aSLionel Sambuc 
installPCHMacroDirectives(IdentifierInfo * II,ModuleFile & M,uint64_t Offset)1832f4a2713aSLionel Sambuc void ASTReader::installPCHMacroDirectives(IdentifierInfo *II,
1833f4a2713aSLionel Sambuc                                           ModuleFile &M, uint64_t Offset) {
1834*0a6a1f1dSLionel Sambuc   assert(M.Kind != MK_ImplicitModule && M.Kind != MK_ExplicitModule);
1835f4a2713aSLionel Sambuc 
1836f4a2713aSLionel Sambuc   BitstreamCursor &Cursor = M.MacroCursor;
1837f4a2713aSLionel Sambuc   SavedStreamPosition SavedPosition(Cursor);
1838f4a2713aSLionel Sambuc   Cursor.JumpToBit(Offset);
1839f4a2713aSLionel Sambuc 
1840f4a2713aSLionel Sambuc   llvm::BitstreamEntry Entry =
1841f4a2713aSLionel Sambuc       Cursor.advance(BitstreamCursor::AF_DontPopBlockAtEnd);
1842f4a2713aSLionel Sambuc   if (Entry.Kind != llvm::BitstreamEntry::Record) {
1843f4a2713aSLionel Sambuc     Error("malformed block record in AST file");
1844f4a2713aSLionel Sambuc     return;
1845f4a2713aSLionel Sambuc   }
1846f4a2713aSLionel Sambuc 
1847f4a2713aSLionel Sambuc   RecordData Record;
1848f4a2713aSLionel Sambuc   PreprocessorRecordTypes RecType =
1849f4a2713aSLionel Sambuc     (PreprocessorRecordTypes)Cursor.readRecord(Entry.ID, Record);
1850f4a2713aSLionel Sambuc   if (RecType != PP_MACRO_DIRECTIVE_HISTORY) {
1851f4a2713aSLionel Sambuc     Error("malformed block record in AST file");
1852f4a2713aSLionel Sambuc     return;
1853f4a2713aSLionel Sambuc   }
1854f4a2713aSLionel Sambuc 
1855f4a2713aSLionel Sambuc   // Deserialize the macro directives history in reverse source-order.
1856*0a6a1f1dSLionel Sambuc   MacroDirective *Latest = nullptr, *Earliest = nullptr;
1857f4a2713aSLionel Sambuc   unsigned Idx = 0, N = Record.size();
1858f4a2713aSLionel Sambuc   while (Idx < N) {
1859*0a6a1f1dSLionel Sambuc     MacroDirective *MD = nullptr;
1860f4a2713aSLionel Sambuc     SourceLocation Loc = ReadSourceLocation(M, Record, Idx);
1861f4a2713aSLionel Sambuc     MacroDirective::Kind K = (MacroDirective::Kind)Record[Idx++];
1862f4a2713aSLionel Sambuc     switch (K) {
1863f4a2713aSLionel Sambuc     case MacroDirective::MD_Define: {
1864f4a2713aSLionel Sambuc       GlobalMacroID GMacID = getGlobalMacroID(M, Record[Idx++]);
1865f4a2713aSLionel Sambuc       MacroInfo *MI = getMacro(GMacID);
1866*0a6a1f1dSLionel Sambuc       SubmoduleID ImportedFrom = Record[Idx++];
1867*0a6a1f1dSLionel Sambuc       bool IsAmbiguous = Record[Idx++];
1868*0a6a1f1dSLionel Sambuc       llvm::SmallVector<unsigned, 4> Overrides;
1869*0a6a1f1dSLionel Sambuc       if (ImportedFrom) {
1870*0a6a1f1dSLionel Sambuc         Overrides.insert(Overrides.end(),
1871*0a6a1f1dSLionel Sambuc                          &Record[Idx] + 1, &Record[Idx] + 1 + Record[Idx]);
1872*0a6a1f1dSLionel Sambuc         Idx += Overrides.size() + 1;
1873*0a6a1f1dSLionel Sambuc       }
1874f4a2713aSLionel Sambuc       DefMacroDirective *DefMD =
1875*0a6a1f1dSLionel Sambuc           PP.AllocateDefMacroDirective(MI, Loc, ImportedFrom, Overrides);
1876*0a6a1f1dSLionel Sambuc       DefMD->setAmbiguous(IsAmbiguous);
1877f4a2713aSLionel Sambuc       MD = DefMD;
1878f4a2713aSLionel Sambuc       break;
1879f4a2713aSLionel Sambuc     }
1880*0a6a1f1dSLionel Sambuc     case MacroDirective::MD_Undefine: {
1881*0a6a1f1dSLionel Sambuc       SubmoduleID ImportedFrom = Record[Idx++];
1882*0a6a1f1dSLionel Sambuc       llvm::SmallVector<unsigned, 4> Overrides;
1883*0a6a1f1dSLionel Sambuc       if (ImportedFrom) {
1884*0a6a1f1dSLionel Sambuc         Overrides.insert(Overrides.end(),
1885*0a6a1f1dSLionel Sambuc                          &Record[Idx] + 1, &Record[Idx] + 1 + Record[Idx]);
1886*0a6a1f1dSLionel Sambuc         Idx += Overrides.size() + 1;
1887*0a6a1f1dSLionel Sambuc       }
1888*0a6a1f1dSLionel Sambuc       MD = PP.AllocateUndefMacroDirective(Loc, ImportedFrom, Overrides);
1889f4a2713aSLionel Sambuc       break;
1890*0a6a1f1dSLionel Sambuc     }
1891*0a6a1f1dSLionel Sambuc     case MacroDirective::MD_Visibility:
1892f4a2713aSLionel Sambuc       bool isPublic = Record[Idx++];
1893f4a2713aSLionel Sambuc       MD = PP.AllocateVisibilityMacroDirective(Loc, isPublic);
1894f4a2713aSLionel Sambuc       break;
1895f4a2713aSLionel Sambuc     }
1896f4a2713aSLionel Sambuc 
1897f4a2713aSLionel Sambuc     if (!Latest)
1898f4a2713aSLionel Sambuc       Latest = MD;
1899f4a2713aSLionel Sambuc     if (Earliest)
1900f4a2713aSLionel Sambuc       Earliest->setPrevious(MD);
1901f4a2713aSLionel Sambuc     Earliest = MD;
1902f4a2713aSLionel Sambuc   }
1903f4a2713aSLionel Sambuc 
1904f4a2713aSLionel Sambuc   PP.setLoadedMacroDirective(II, Latest);
1905f4a2713aSLionel Sambuc }
1906f4a2713aSLionel Sambuc 
1907f4a2713aSLionel Sambuc /// \brief For the given macro definitions, check if they are both in system
1908f4a2713aSLionel Sambuc /// modules.
areDefinedInSystemModules(MacroInfo * PrevMI,MacroInfo * NewMI,Module * NewOwner,ASTReader & Reader)1909f4a2713aSLionel Sambuc static bool areDefinedInSystemModules(MacroInfo *PrevMI, MacroInfo *NewMI,
1910f4a2713aSLionel Sambuc                                       Module *NewOwner, ASTReader &Reader) {
1911f4a2713aSLionel Sambuc   assert(PrevMI && NewMI);
1912*0a6a1f1dSLionel Sambuc   Module *PrevOwner = nullptr;
1913f4a2713aSLionel Sambuc   if (SubmoduleID PrevModID = PrevMI->getOwningModuleID())
1914f4a2713aSLionel Sambuc     PrevOwner = Reader.getSubmodule(PrevModID);
1915f4a2713aSLionel Sambuc   SourceManager &SrcMgr = Reader.getSourceManager();
1916f4a2713aSLionel Sambuc   bool PrevInSystem
1917f4a2713aSLionel Sambuc     = PrevOwner? PrevOwner->IsSystem
1918f4a2713aSLionel Sambuc                : SrcMgr.isInSystemHeader(PrevMI->getDefinitionLoc());
1919f4a2713aSLionel Sambuc   bool NewInSystem
1920f4a2713aSLionel Sambuc     = NewOwner? NewOwner->IsSystem
1921f4a2713aSLionel Sambuc               : SrcMgr.isInSystemHeader(NewMI->getDefinitionLoc());
1922f4a2713aSLionel Sambuc   if (PrevOwner && PrevOwner == NewOwner)
1923f4a2713aSLionel Sambuc     return false;
1924f4a2713aSLionel Sambuc   return PrevInSystem && NewInSystem;
1925f4a2713aSLionel Sambuc }
1926f4a2713aSLionel Sambuc 
removeOverriddenMacros(IdentifierInfo * II,SourceLocation ImportLoc,AmbiguousMacros & Ambig,ArrayRef<SubmoduleID> Overrides)1927*0a6a1f1dSLionel Sambuc void ASTReader::removeOverriddenMacros(IdentifierInfo *II,
1928*0a6a1f1dSLionel Sambuc                                        SourceLocation ImportLoc,
1929*0a6a1f1dSLionel Sambuc                                        AmbiguousMacros &Ambig,
1930*0a6a1f1dSLionel Sambuc                                        ArrayRef<SubmoduleID> Overrides) {
1931*0a6a1f1dSLionel Sambuc   for (unsigned OI = 0, ON = Overrides.size(); OI != ON; ++OI) {
1932*0a6a1f1dSLionel Sambuc     SubmoduleID OwnerID = Overrides[OI];
1933f4a2713aSLionel Sambuc 
1934*0a6a1f1dSLionel Sambuc     // If this macro is not yet visible, remove it from the hidden names list.
1935*0a6a1f1dSLionel Sambuc     // It won't be there if we're in the middle of making the owner visible.
1936*0a6a1f1dSLionel Sambuc     Module *Owner = getSubmodule(OwnerID);
1937*0a6a1f1dSLionel Sambuc     auto HiddenIt = HiddenNamesMap.find(Owner);
1938*0a6a1f1dSLionel Sambuc     if (HiddenIt != HiddenNamesMap.end()) {
1939*0a6a1f1dSLionel Sambuc       HiddenNames &Hidden = HiddenIt->second;
1940*0a6a1f1dSLionel Sambuc       HiddenMacrosMap::iterator HI = Hidden.HiddenMacros.find(II);
1941*0a6a1f1dSLionel Sambuc       if (HI != Hidden.HiddenMacros.end()) {
1942*0a6a1f1dSLionel Sambuc         // Register the macro now so we don't lose it when we re-export.
1943*0a6a1f1dSLionel Sambuc         PP.appendMacroDirective(II, HI->second->import(PP, ImportLoc));
1944*0a6a1f1dSLionel Sambuc 
1945*0a6a1f1dSLionel Sambuc         auto SubOverrides = HI->second->getOverriddenSubmodules();
1946*0a6a1f1dSLionel Sambuc         Hidden.HiddenMacros.erase(HI);
1947*0a6a1f1dSLionel Sambuc         removeOverriddenMacros(II, ImportLoc, Ambig, SubOverrides);
1948*0a6a1f1dSLionel Sambuc       }
1949*0a6a1f1dSLionel Sambuc     }
1950*0a6a1f1dSLionel Sambuc 
1951*0a6a1f1dSLionel Sambuc     // If this macro is already in our list of conflicts, remove it from there.
1952*0a6a1f1dSLionel Sambuc     Ambig.erase(
1953*0a6a1f1dSLionel Sambuc         std::remove_if(Ambig.begin(), Ambig.end(), [&](DefMacroDirective *MD) {
1954*0a6a1f1dSLionel Sambuc           return MD->getInfo()->getOwningModuleID() == OwnerID;
1955*0a6a1f1dSLionel Sambuc         }),
1956*0a6a1f1dSLionel Sambuc         Ambig.end());
1957*0a6a1f1dSLionel Sambuc   }
1958*0a6a1f1dSLionel Sambuc }
1959*0a6a1f1dSLionel Sambuc 
1960*0a6a1f1dSLionel Sambuc ASTReader::AmbiguousMacros *
removeOverriddenMacros(IdentifierInfo * II,SourceLocation ImportLoc,ArrayRef<SubmoduleID> Overrides)1961*0a6a1f1dSLionel Sambuc ASTReader::removeOverriddenMacros(IdentifierInfo *II,
1962*0a6a1f1dSLionel Sambuc                                   SourceLocation ImportLoc,
1963*0a6a1f1dSLionel Sambuc                                   ArrayRef<SubmoduleID> Overrides) {
1964f4a2713aSLionel Sambuc   MacroDirective *Prev = PP.getMacroDirective(II);
1965*0a6a1f1dSLionel Sambuc   if (!Prev && Overrides.empty())
1966*0a6a1f1dSLionel Sambuc     return nullptr;
1967*0a6a1f1dSLionel Sambuc 
1968*0a6a1f1dSLionel Sambuc   DefMacroDirective *PrevDef = Prev ? Prev->getDefinition().getDirective()
1969*0a6a1f1dSLionel Sambuc                                     : nullptr;
1970*0a6a1f1dSLionel Sambuc   if (PrevDef && PrevDef->isAmbiguous()) {
1971*0a6a1f1dSLionel Sambuc     // We had a prior ambiguity. Check whether we resolve it (or make it worse).
1972*0a6a1f1dSLionel Sambuc     AmbiguousMacros &Ambig = AmbiguousMacroDefs[II];
1973*0a6a1f1dSLionel Sambuc     Ambig.push_back(PrevDef);
1974*0a6a1f1dSLionel Sambuc 
1975*0a6a1f1dSLionel Sambuc     removeOverriddenMacros(II, ImportLoc, Ambig, Overrides);
1976*0a6a1f1dSLionel Sambuc 
1977*0a6a1f1dSLionel Sambuc     if (!Ambig.empty())
1978*0a6a1f1dSLionel Sambuc       return &Ambig;
1979*0a6a1f1dSLionel Sambuc 
1980*0a6a1f1dSLionel Sambuc     AmbiguousMacroDefs.erase(II);
1981*0a6a1f1dSLionel Sambuc   } else {
1982*0a6a1f1dSLionel Sambuc     // There's no ambiguity yet. Maybe we're introducing one.
1983*0a6a1f1dSLionel Sambuc     AmbiguousMacros Ambig;
1984*0a6a1f1dSLionel Sambuc     if (PrevDef)
1985*0a6a1f1dSLionel Sambuc       Ambig.push_back(PrevDef);
1986*0a6a1f1dSLionel Sambuc 
1987*0a6a1f1dSLionel Sambuc     removeOverriddenMacros(II, ImportLoc, Ambig, Overrides);
1988*0a6a1f1dSLionel Sambuc 
1989*0a6a1f1dSLionel Sambuc     if (!Ambig.empty()) {
1990*0a6a1f1dSLionel Sambuc       AmbiguousMacros &Result = AmbiguousMacroDefs[II];
1991*0a6a1f1dSLionel Sambuc       std::swap(Result, Ambig);
1992*0a6a1f1dSLionel Sambuc       return &Result;
1993*0a6a1f1dSLionel Sambuc     }
1994*0a6a1f1dSLionel Sambuc   }
1995*0a6a1f1dSLionel Sambuc 
1996*0a6a1f1dSLionel Sambuc   // We ended up with no ambiguity.
1997*0a6a1f1dSLionel Sambuc   return nullptr;
1998*0a6a1f1dSLionel Sambuc }
1999*0a6a1f1dSLionel Sambuc 
installImportedMacro(IdentifierInfo * II,ModuleMacroInfo * MMI,Module * Owner)2000*0a6a1f1dSLionel Sambuc void ASTReader::installImportedMacro(IdentifierInfo *II, ModuleMacroInfo *MMI,
2001*0a6a1f1dSLionel Sambuc                                      Module *Owner) {
2002*0a6a1f1dSLionel Sambuc   assert(II && Owner);
2003*0a6a1f1dSLionel Sambuc 
2004*0a6a1f1dSLionel Sambuc   SourceLocation ImportLoc = Owner->MacroVisibilityLoc;
2005*0a6a1f1dSLionel Sambuc   if (ImportLoc.isInvalid()) {
2006*0a6a1f1dSLionel Sambuc     // FIXME: If we made macros from this module visible but didn't provide a
2007*0a6a1f1dSLionel Sambuc     // source location for the import, we don't have a location for the macro.
2008*0a6a1f1dSLionel Sambuc     // Use the location at which the containing module file was first imported
2009*0a6a1f1dSLionel Sambuc     // for now.
2010*0a6a1f1dSLionel Sambuc     ImportLoc = MMI->F->DirectImportLoc;
2011*0a6a1f1dSLionel Sambuc     assert(ImportLoc.isValid() && "no import location for a visible macro?");
2012*0a6a1f1dSLionel Sambuc   }
2013*0a6a1f1dSLionel Sambuc 
2014*0a6a1f1dSLionel Sambuc   AmbiguousMacros *Prev =
2015*0a6a1f1dSLionel Sambuc       removeOverriddenMacros(II, ImportLoc, MMI->getOverriddenSubmodules());
2016*0a6a1f1dSLionel Sambuc 
2017*0a6a1f1dSLionel Sambuc   // Create a synthetic macro definition corresponding to the import (or null
2018*0a6a1f1dSLionel Sambuc   // if this was an undefinition of the macro).
2019*0a6a1f1dSLionel Sambuc   MacroDirective *Imported = MMI->import(PP, ImportLoc);
2020*0a6a1f1dSLionel Sambuc   DefMacroDirective *MD = dyn_cast<DefMacroDirective>(Imported);
2021*0a6a1f1dSLionel Sambuc 
2022*0a6a1f1dSLionel Sambuc   // If there's no ambiguity, just install the macro.
2023*0a6a1f1dSLionel Sambuc   if (!Prev) {
2024*0a6a1f1dSLionel Sambuc     PP.appendMacroDirective(II, Imported);
2025*0a6a1f1dSLionel Sambuc     return;
2026*0a6a1f1dSLionel Sambuc   }
2027*0a6a1f1dSLionel Sambuc   assert(!Prev->empty());
2028*0a6a1f1dSLionel Sambuc 
2029*0a6a1f1dSLionel Sambuc   if (!MD) {
2030*0a6a1f1dSLionel Sambuc     // We imported a #undef that didn't remove all prior definitions. The most
2031*0a6a1f1dSLionel Sambuc     // recent prior definition remains, and we install it in the place of the
2032*0a6a1f1dSLionel Sambuc     // imported directive, as if by a local #pragma pop_macro.
2033*0a6a1f1dSLionel Sambuc     MacroInfo *NewMI = Prev->back()->getInfo();
2034*0a6a1f1dSLionel Sambuc     Prev->pop_back();
2035*0a6a1f1dSLionel Sambuc     MD = PP.AllocateDefMacroDirective(NewMI, ImportLoc);
2036*0a6a1f1dSLionel Sambuc 
2037*0a6a1f1dSLionel Sambuc     // Install our #undef first so that we don't lose track of it. We'll replace
2038*0a6a1f1dSLionel Sambuc     // this with whichever macro definition ends up winning.
2039*0a6a1f1dSLionel Sambuc     PP.appendMacroDirective(II, Imported);
2040*0a6a1f1dSLionel Sambuc   }
2041*0a6a1f1dSLionel Sambuc 
2042*0a6a1f1dSLionel Sambuc   // We're introducing a macro definition that creates or adds to an ambiguity.
2043*0a6a1f1dSLionel Sambuc   // We can resolve that ambiguity if this macro is token-for-token identical to
2044*0a6a1f1dSLionel Sambuc   // all of the existing definitions.
2045*0a6a1f1dSLionel Sambuc   MacroInfo *NewMI = MD->getInfo();
2046*0a6a1f1dSLionel Sambuc   assert(NewMI && "macro definition with no MacroInfo?");
2047*0a6a1f1dSLionel Sambuc   while (!Prev->empty()) {
2048*0a6a1f1dSLionel Sambuc     MacroInfo *PrevMI = Prev->back()->getInfo();
2049*0a6a1f1dSLionel Sambuc     assert(PrevMI && "macro definition with no MacroInfo?");
2050*0a6a1f1dSLionel Sambuc 
2051f4a2713aSLionel Sambuc     // Before marking the macros as ambiguous, check if this is a case where
2052f4a2713aSLionel Sambuc     // both macros are in system headers. If so, we trust that the system
2053f4a2713aSLionel Sambuc     // did not get it wrong. This also handles cases where Clang's own
2054f4a2713aSLionel Sambuc     // headers have a different spelling of certain system macros:
2055f4a2713aSLionel Sambuc     //   #define LONG_MAX __LONG_MAX__ (clang's limits.h)
2056f4a2713aSLionel Sambuc     //   #define LONG_MAX 0x7fffffffffffffffL (system's limits.h)
2057*0a6a1f1dSLionel Sambuc     //
2058*0a6a1f1dSLionel Sambuc     // FIXME: Remove the defined-in-system-headers check. clang's limits.h
2059*0a6a1f1dSLionel Sambuc     // overrides the system limits.h's macros, so there's no conflict here.
2060*0a6a1f1dSLionel Sambuc     if (NewMI != PrevMI &&
2061*0a6a1f1dSLionel Sambuc         !PrevMI->isIdenticalTo(*NewMI, PP, /*Syntactically=*/true) &&
2062*0a6a1f1dSLionel Sambuc         !areDefinedInSystemModules(PrevMI, NewMI, Owner, *this))
2063*0a6a1f1dSLionel Sambuc       break;
2064*0a6a1f1dSLionel Sambuc 
2065*0a6a1f1dSLionel Sambuc     // The previous definition is the same as this one (or both are defined in
2066*0a6a1f1dSLionel Sambuc     // system modules so we can assume they're equivalent); we don't need to
2067*0a6a1f1dSLionel Sambuc     // track it any more.
2068*0a6a1f1dSLionel Sambuc     Prev->pop_back();
2069f4a2713aSLionel Sambuc   }
2070f4a2713aSLionel Sambuc 
2071*0a6a1f1dSLionel Sambuc   if (!Prev->empty())
2072*0a6a1f1dSLionel Sambuc     MD->setAmbiguous(true);
2073*0a6a1f1dSLionel Sambuc 
2074f4a2713aSLionel Sambuc   PP.appendMacroDirective(II, MD);
2075f4a2713aSLionel Sambuc }
2076f4a2713aSLionel Sambuc 
2077*0a6a1f1dSLionel Sambuc ASTReader::InputFileInfo
readInputFileInfo(ModuleFile & F,unsigned ID)2078*0a6a1f1dSLionel Sambuc ASTReader::readInputFileInfo(ModuleFile &F, unsigned ID) {
2079*0a6a1f1dSLionel Sambuc   // Go find this input file.
2080*0a6a1f1dSLionel Sambuc   BitstreamCursor &Cursor = F.InputFilesCursor;
2081*0a6a1f1dSLionel Sambuc   SavedStreamPosition SavedPosition(Cursor);
2082*0a6a1f1dSLionel Sambuc   Cursor.JumpToBit(F.InputFileOffsets[ID-1]);
2083*0a6a1f1dSLionel Sambuc 
2084*0a6a1f1dSLionel Sambuc   unsigned Code = Cursor.ReadCode();
2085*0a6a1f1dSLionel Sambuc   RecordData Record;
2086*0a6a1f1dSLionel Sambuc   StringRef Blob;
2087*0a6a1f1dSLionel Sambuc 
2088*0a6a1f1dSLionel Sambuc   unsigned Result = Cursor.readRecord(Code, Record, &Blob);
2089*0a6a1f1dSLionel Sambuc   assert(static_cast<InputFileRecordTypes>(Result) == INPUT_FILE &&
2090*0a6a1f1dSLionel Sambuc          "invalid record type for input file");
2091*0a6a1f1dSLionel Sambuc   (void)Result;
2092*0a6a1f1dSLionel Sambuc 
2093*0a6a1f1dSLionel Sambuc   std::string Filename;
2094*0a6a1f1dSLionel Sambuc   off_t StoredSize;
2095*0a6a1f1dSLionel Sambuc   time_t StoredTime;
2096*0a6a1f1dSLionel Sambuc   bool Overridden;
2097*0a6a1f1dSLionel Sambuc 
2098*0a6a1f1dSLionel Sambuc   assert(Record[0] == ID && "Bogus stored ID or offset");
2099*0a6a1f1dSLionel Sambuc   StoredSize = static_cast<off_t>(Record[1]);
2100*0a6a1f1dSLionel Sambuc   StoredTime = static_cast<time_t>(Record[2]);
2101*0a6a1f1dSLionel Sambuc   Overridden = static_cast<bool>(Record[3]);
2102*0a6a1f1dSLionel Sambuc   Filename = Blob;
2103*0a6a1f1dSLionel Sambuc   ResolveImportedPath(F, Filename);
2104*0a6a1f1dSLionel Sambuc 
2105*0a6a1f1dSLionel Sambuc   InputFileInfo R = { std::move(Filename), StoredSize, StoredTime, Overridden };
2106*0a6a1f1dSLionel Sambuc   return R;
2107*0a6a1f1dSLionel Sambuc }
2108*0a6a1f1dSLionel Sambuc 
getInputFileName(ModuleFile & F,unsigned int ID)2109*0a6a1f1dSLionel Sambuc std::string ASTReader::getInputFileName(ModuleFile &F, unsigned int ID) {
2110*0a6a1f1dSLionel Sambuc   return readInputFileInfo(F, ID).Filename;
2111*0a6a1f1dSLionel Sambuc }
2112*0a6a1f1dSLionel Sambuc 
getInputFile(ModuleFile & F,unsigned ID,bool Complain)2113f4a2713aSLionel Sambuc InputFile ASTReader::getInputFile(ModuleFile &F, unsigned ID, bool Complain) {
2114f4a2713aSLionel Sambuc   // If this ID is bogus, just return an empty input file.
2115f4a2713aSLionel Sambuc   if (ID == 0 || ID > F.InputFilesLoaded.size())
2116f4a2713aSLionel Sambuc     return InputFile();
2117f4a2713aSLionel Sambuc 
2118f4a2713aSLionel Sambuc   // If we've already loaded this input file, return it.
2119f4a2713aSLionel Sambuc   if (F.InputFilesLoaded[ID-1].getFile())
2120f4a2713aSLionel Sambuc     return F.InputFilesLoaded[ID-1];
2121f4a2713aSLionel Sambuc 
2122*0a6a1f1dSLionel Sambuc   if (F.InputFilesLoaded[ID-1].isNotFound())
2123*0a6a1f1dSLionel Sambuc     return InputFile();
2124*0a6a1f1dSLionel Sambuc 
2125f4a2713aSLionel Sambuc   // Go find this input file.
2126f4a2713aSLionel Sambuc   BitstreamCursor &Cursor = F.InputFilesCursor;
2127f4a2713aSLionel Sambuc   SavedStreamPosition SavedPosition(Cursor);
2128f4a2713aSLionel Sambuc   Cursor.JumpToBit(F.InputFileOffsets[ID-1]);
2129f4a2713aSLionel Sambuc 
2130*0a6a1f1dSLionel Sambuc   InputFileInfo FI = readInputFileInfo(F, ID);
2131*0a6a1f1dSLionel Sambuc   off_t StoredSize = FI.StoredSize;
2132*0a6a1f1dSLionel Sambuc   time_t StoredTime = FI.StoredTime;
2133*0a6a1f1dSLionel Sambuc   bool Overridden = FI.Overridden;
2134*0a6a1f1dSLionel Sambuc   StringRef Filename = FI.Filename;
2135f4a2713aSLionel Sambuc 
2136f4a2713aSLionel Sambuc   const FileEntry *File
2137f4a2713aSLionel Sambuc     = Overridden? FileMgr.getVirtualFile(Filename, StoredSize, StoredTime)
2138f4a2713aSLionel Sambuc                 : FileMgr.getFile(Filename, /*OpenFile=*/false);
2139f4a2713aSLionel Sambuc 
2140f4a2713aSLionel Sambuc   // If we didn't find the file, resolve it relative to the
2141f4a2713aSLionel Sambuc   // original directory from which this AST file was created.
2142*0a6a1f1dSLionel Sambuc   if (File == nullptr && !F.OriginalDir.empty() && !CurrentDir.empty() &&
2143f4a2713aSLionel Sambuc       F.OriginalDir != CurrentDir) {
2144f4a2713aSLionel Sambuc     std::string Resolved = resolveFileRelativeToOriginalDir(Filename,
2145f4a2713aSLionel Sambuc                                                             F.OriginalDir,
2146f4a2713aSLionel Sambuc                                                             CurrentDir);
2147f4a2713aSLionel Sambuc     if (!Resolved.empty())
2148f4a2713aSLionel Sambuc       File = FileMgr.getFile(Resolved);
2149f4a2713aSLionel Sambuc   }
2150f4a2713aSLionel Sambuc 
2151f4a2713aSLionel Sambuc   // For an overridden file, create a virtual file with the stored
2152f4a2713aSLionel Sambuc   // size/timestamp.
2153*0a6a1f1dSLionel Sambuc   if (Overridden && File == nullptr) {
2154f4a2713aSLionel Sambuc     File = FileMgr.getVirtualFile(Filename, StoredSize, StoredTime);
2155f4a2713aSLionel Sambuc   }
2156f4a2713aSLionel Sambuc 
2157*0a6a1f1dSLionel Sambuc   if (File == nullptr) {
2158f4a2713aSLionel Sambuc     if (Complain) {
2159f4a2713aSLionel Sambuc       std::string ErrorStr = "could not find file '";
2160f4a2713aSLionel Sambuc       ErrorStr += Filename;
2161f4a2713aSLionel Sambuc       ErrorStr += "' referenced by AST file";
2162f4a2713aSLionel Sambuc       Error(ErrorStr.c_str());
2163f4a2713aSLionel Sambuc     }
2164*0a6a1f1dSLionel Sambuc     // Record that we didn't find the file.
2165*0a6a1f1dSLionel Sambuc     F.InputFilesLoaded[ID-1] = InputFile::getNotFound();
2166f4a2713aSLionel Sambuc     return InputFile();
2167f4a2713aSLionel Sambuc   }
2168f4a2713aSLionel Sambuc 
2169f4a2713aSLionel Sambuc   // Check if there was a request to override the contents of the file
2170f4a2713aSLionel Sambuc   // that was part of the precompiled header. Overridding such a file
2171f4a2713aSLionel Sambuc   // can lead to problems when lexing using the source locations from the
2172f4a2713aSLionel Sambuc   // PCH.
2173f4a2713aSLionel Sambuc   SourceManager &SM = getSourceManager();
2174f4a2713aSLionel Sambuc   if (!Overridden && SM.isFileOverridden(File)) {
2175f4a2713aSLionel Sambuc     if (Complain)
2176f4a2713aSLionel Sambuc       Error(diag::err_fe_pch_file_overridden, Filename);
2177f4a2713aSLionel Sambuc     // After emitting the diagnostic, recover by disabling the override so
2178f4a2713aSLionel Sambuc     // that the original file will be used.
2179f4a2713aSLionel Sambuc     SM.disableFileContentsOverride(File);
2180f4a2713aSLionel Sambuc     // The FileEntry is a virtual file entry with the size of the contents
2181f4a2713aSLionel Sambuc     // that would override the original contents. Set it to the original's
2182f4a2713aSLionel Sambuc     // size/time.
2183f4a2713aSLionel Sambuc     FileMgr.modifyFileEntry(const_cast<FileEntry*>(File),
2184f4a2713aSLionel Sambuc                             StoredSize, StoredTime);
2185f4a2713aSLionel Sambuc   }
2186f4a2713aSLionel Sambuc 
2187f4a2713aSLionel Sambuc   bool IsOutOfDate = false;
2188f4a2713aSLionel Sambuc 
2189f4a2713aSLionel Sambuc   // For an overridden file, there is nothing to validate.
2190*0a6a1f1dSLionel Sambuc   if (!Overridden && //
2191*0a6a1f1dSLionel Sambuc       (StoredSize != File->getSize() ||
2192*0a6a1f1dSLionel Sambuc #if defined(LLVM_ON_WIN32)
2193*0a6a1f1dSLionel Sambuc        false
2194*0a6a1f1dSLionel Sambuc #else
2195f4a2713aSLionel Sambuc        // In our regression testing, the Windows file system seems to
2196f4a2713aSLionel Sambuc        // have inconsistent modification times that sometimes
2197f4a2713aSLionel Sambuc        // erroneously trigger this error-handling path.
2198*0a6a1f1dSLionel Sambuc        //
2199*0a6a1f1dSLionel Sambuc        // This also happens in networked file systems, so disable this
2200*0a6a1f1dSLionel Sambuc        // check if validation is disabled or if we have an explicitly
2201*0a6a1f1dSLionel Sambuc        // built PCM file.
2202*0a6a1f1dSLionel Sambuc        //
2203*0a6a1f1dSLionel Sambuc        // FIXME: Should we also do this for PCH files? They could also
2204*0a6a1f1dSLionel Sambuc        // reasonably get shared across a network during a distributed build.
2205*0a6a1f1dSLionel Sambuc        (StoredTime != File->getModificationTime() && !DisableValidation &&
2206*0a6a1f1dSLionel Sambuc         F.Kind != MK_ExplicitModule)
2207f4a2713aSLionel Sambuc #endif
2208f4a2713aSLionel Sambuc        )) {
2209f4a2713aSLionel Sambuc     if (Complain) {
2210*0a6a1f1dSLionel Sambuc       // Build a list of the PCH imports that got us here (in reverse).
2211*0a6a1f1dSLionel Sambuc       SmallVector<ModuleFile *, 4> ImportStack(1, &F);
2212*0a6a1f1dSLionel Sambuc       while (ImportStack.back()->ImportedBy.size() > 0)
2213*0a6a1f1dSLionel Sambuc         ImportStack.push_back(ImportStack.back()->ImportedBy[0]);
2214*0a6a1f1dSLionel Sambuc 
2215*0a6a1f1dSLionel Sambuc       // The top-level PCH is stale.
2216*0a6a1f1dSLionel Sambuc       StringRef TopLevelPCHName(ImportStack.back()->FileName);
2217*0a6a1f1dSLionel Sambuc       Error(diag::err_fe_pch_file_modified, Filename, TopLevelPCHName);
2218*0a6a1f1dSLionel Sambuc 
2219*0a6a1f1dSLionel Sambuc       // Print the import stack.
2220*0a6a1f1dSLionel Sambuc       if (ImportStack.size() > 1 && !Diags.isDiagnosticInFlight()) {
2221*0a6a1f1dSLionel Sambuc         Diag(diag::note_pch_required_by)
2222*0a6a1f1dSLionel Sambuc           << Filename << ImportStack[0]->FileName;
2223*0a6a1f1dSLionel Sambuc         for (unsigned I = 1; I < ImportStack.size(); ++I)
2224*0a6a1f1dSLionel Sambuc           Diag(diag::note_pch_required_by)
2225*0a6a1f1dSLionel Sambuc             << ImportStack[I-1]->FileName << ImportStack[I]->FileName;
2226f4a2713aSLionel Sambuc       }
2227*0a6a1f1dSLionel Sambuc 
2228*0a6a1f1dSLionel Sambuc       if (!Diags.isDiagnosticInFlight())
2229*0a6a1f1dSLionel Sambuc         Diag(diag::note_pch_rebuild_required) << TopLevelPCHName;
2230f4a2713aSLionel Sambuc     }
2231f4a2713aSLionel Sambuc 
2232f4a2713aSLionel Sambuc     IsOutOfDate = true;
2233f4a2713aSLionel Sambuc   }
2234f4a2713aSLionel Sambuc 
2235f4a2713aSLionel Sambuc   InputFile IF = InputFile(File, Overridden, IsOutOfDate);
2236f4a2713aSLionel Sambuc 
2237f4a2713aSLionel Sambuc   // Note that we've loaded this input file.
2238f4a2713aSLionel Sambuc   F.InputFilesLoaded[ID-1] = IF;
2239f4a2713aSLionel Sambuc   return IF;
2240f4a2713aSLionel Sambuc }
2241*0a6a1f1dSLionel Sambuc 
2242*0a6a1f1dSLionel Sambuc /// \brief If we are loading a relocatable PCH or module file, and the filename
2243*0a6a1f1dSLionel Sambuc /// is not an absolute path, add the system or module root to the beginning of
2244*0a6a1f1dSLionel Sambuc /// the file name.
ResolveImportedPath(ModuleFile & M,std::string & Filename)2245*0a6a1f1dSLionel Sambuc void ASTReader::ResolveImportedPath(ModuleFile &M, std::string &Filename) {
2246*0a6a1f1dSLionel Sambuc   // Resolve relative to the base directory, if we have one.
2247*0a6a1f1dSLionel Sambuc   if (!M.BaseDirectory.empty())
2248*0a6a1f1dSLionel Sambuc     return ResolveImportedPath(Filename, M.BaseDirectory);
2249f4a2713aSLionel Sambuc }
2250f4a2713aSLionel Sambuc 
ResolveImportedPath(std::string & Filename,StringRef Prefix)2251*0a6a1f1dSLionel Sambuc void ASTReader::ResolveImportedPath(std::string &Filename, StringRef Prefix) {
2252f4a2713aSLionel Sambuc   if (Filename.empty() || llvm::sys::path::is_absolute(Filename))
2253f4a2713aSLionel Sambuc     return;
2254f4a2713aSLionel Sambuc 
2255*0a6a1f1dSLionel Sambuc   SmallString<128> Buffer;
2256*0a6a1f1dSLionel Sambuc   llvm::sys::path::append(Buffer, Prefix, Filename);
2257*0a6a1f1dSLionel Sambuc   Filename.assign(Buffer.begin(), Buffer.end());
2258f4a2713aSLionel Sambuc }
2259f4a2713aSLionel Sambuc 
2260f4a2713aSLionel Sambuc ASTReader::ASTReadResult
ReadControlBlock(ModuleFile & F,SmallVectorImpl<ImportedModule> & Loaded,const ModuleFile * ImportedBy,unsigned ClientLoadCapabilities)2261f4a2713aSLionel Sambuc ASTReader::ReadControlBlock(ModuleFile &F,
2262f4a2713aSLionel Sambuc                             SmallVectorImpl<ImportedModule> &Loaded,
2263*0a6a1f1dSLionel Sambuc                             const ModuleFile *ImportedBy,
2264f4a2713aSLionel Sambuc                             unsigned ClientLoadCapabilities) {
2265f4a2713aSLionel Sambuc   BitstreamCursor &Stream = F.Stream;
2266f4a2713aSLionel Sambuc 
2267f4a2713aSLionel Sambuc   if (Stream.EnterSubBlock(CONTROL_BLOCK_ID)) {
2268f4a2713aSLionel Sambuc     Error("malformed block record in AST file");
2269f4a2713aSLionel Sambuc     return Failure;
2270f4a2713aSLionel Sambuc   }
2271f4a2713aSLionel Sambuc 
2272*0a6a1f1dSLionel Sambuc   // Should we allow the configuration of the module file to differ from the
2273*0a6a1f1dSLionel Sambuc   // configuration of the current translation unit in a compatible way?
2274*0a6a1f1dSLionel Sambuc   //
2275*0a6a1f1dSLionel Sambuc   // FIXME: Allow this for files explicitly specified with -include-pch too.
2276*0a6a1f1dSLionel Sambuc   bool AllowCompatibleConfigurationMismatch = F.Kind == MK_ExplicitModule;
2277*0a6a1f1dSLionel Sambuc 
2278f4a2713aSLionel Sambuc   // Read all of the records and blocks in the control block.
2279f4a2713aSLionel Sambuc   RecordData Record;
2280*0a6a1f1dSLionel Sambuc   unsigned NumInputs = 0;
2281*0a6a1f1dSLionel Sambuc   unsigned NumUserInputs = 0;
2282f4a2713aSLionel Sambuc   while (1) {
2283f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = Stream.advance();
2284f4a2713aSLionel Sambuc 
2285f4a2713aSLionel Sambuc     switch (Entry.Kind) {
2286f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Error:
2287f4a2713aSLionel Sambuc       Error("malformed block record in AST file");
2288f4a2713aSLionel Sambuc       return Failure;
2289*0a6a1f1dSLionel Sambuc     case llvm::BitstreamEntry::EndBlock: {
2290*0a6a1f1dSLionel Sambuc       // Validate input files.
2291*0a6a1f1dSLionel Sambuc       const HeaderSearchOptions &HSOpts =
2292*0a6a1f1dSLionel Sambuc           PP.getHeaderSearchInfo().getHeaderSearchOpts();
2293*0a6a1f1dSLionel Sambuc 
2294*0a6a1f1dSLionel Sambuc       // All user input files reside at the index range [0, NumUserInputs), and
2295*0a6a1f1dSLionel Sambuc       // system input files reside at [NumUserInputs, NumInputs).
2296f4a2713aSLionel Sambuc       if (!DisableValidation) {
2297f4a2713aSLionel Sambuc         bool Complain = (ClientLoadCapabilities & ARR_OutOfDate) == 0;
2298*0a6a1f1dSLionel Sambuc 
2299*0a6a1f1dSLionel Sambuc         // If we are reading a module, we will create a verification timestamp,
2300*0a6a1f1dSLionel Sambuc         // so we verify all input files.  Otherwise, verify only user input
2301*0a6a1f1dSLionel Sambuc         // files.
2302*0a6a1f1dSLionel Sambuc 
2303*0a6a1f1dSLionel Sambuc         unsigned N = NumUserInputs;
2304*0a6a1f1dSLionel Sambuc         if (ValidateSystemInputs ||
2305*0a6a1f1dSLionel Sambuc             (HSOpts.ModulesValidateOncePerBuildSession &&
2306*0a6a1f1dSLionel Sambuc              F.InputFilesValidationTimestamp <= HSOpts.BuildSessionTimestamp &&
2307*0a6a1f1dSLionel Sambuc              F.Kind == MK_ImplicitModule))
2308*0a6a1f1dSLionel Sambuc           N = NumInputs;
2309*0a6a1f1dSLionel Sambuc 
2310*0a6a1f1dSLionel Sambuc         for (unsigned I = 0; I < N; ++I) {
2311f4a2713aSLionel Sambuc           InputFile IF = getInputFile(F, I+1, Complain);
2312f4a2713aSLionel Sambuc           if (!IF.getFile() || IF.isOutOfDate())
2313f4a2713aSLionel Sambuc             return OutOfDate;
2314f4a2713aSLionel Sambuc         }
2315f4a2713aSLionel Sambuc       }
2316*0a6a1f1dSLionel Sambuc 
2317*0a6a1f1dSLionel Sambuc       if (Listener)
2318*0a6a1f1dSLionel Sambuc         Listener->visitModuleFile(F.FileName);
2319*0a6a1f1dSLionel Sambuc 
2320*0a6a1f1dSLionel Sambuc       if (Listener && Listener->needsInputFileVisitation()) {
2321*0a6a1f1dSLionel Sambuc         unsigned N = Listener->needsSystemInputFileVisitation() ? NumInputs
2322*0a6a1f1dSLionel Sambuc                                                                 : NumUserInputs;
2323*0a6a1f1dSLionel Sambuc         for (unsigned I = 0; I < N; ++I) {
2324*0a6a1f1dSLionel Sambuc           bool IsSystem = I >= NumUserInputs;
2325*0a6a1f1dSLionel Sambuc           InputFileInfo FI = readInputFileInfo(F, I+1);
2326*0a6a1f1dSLionel Sambuc           Listener->visitInputFile(FI.Filename, IsSystem, FI.Overridden);
2327*0a6a1f1dSLionel Sambuc         }
2328*0a6a1f1dSLionel Sambuc       }
2329*0a6a1f1dSLionel Sambuc 
2330f4a2713aSLionel Sambuc       return Success;
2331*0a6a1f1dSLionel Sambuc     }
2332f4a2713aSLionel Sambuc 
2333f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::SubBlock:
2334f4a2713aSLionel Sambuc       switch (Entry.ID) {
2335f4a2713aSLionel Sambuc       case INPUT_FILES_BLOCK_ID:
2336f4a2713aSLionel Sambuc         F.InputFilesCursor = Stream;
2337f4a2713aSLionel Sambuc         if (Stream.SkipBlock() || // Skip with the main cursor
2338f4a2713aSLionel Sambuc             // Read the abbreviations
2339f4a2713aSLionel Sambuc             ReadBlockAbbrevs(F.InputFilesCursor, INPUT_FILES_BLOCK_ID)) {
2340f4a2713aSLionel Sambuc           Error("malformed block record in AST file");
2341f4a2713aSLionel Sambuc           return Failure;
2342f4a2713aSLionel Sambuc         }
2343f4a2713aSLionel Sambuc         continue;
2344f4a2713aSLionel Sambuc 
2345f4a2713aSLionel Sambuc       default:
2346f4a2713aSLionel Sambuc         if (Stream.SkipBlock()) {
2347f4a2713aSLionel Sambuc           Error("malformed block record in AST file");
2348f4a2713aSLionel Sambuc           return Failure;
2349f4a2713aSLionel Sambuc         }
2350f4a2713aSLionel Sambuc         continue;
2351f4a2713aSLionel Sambuc       }
2352f4a2713aSLionel Sambuc 
2353f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Record:
2354f4a2713aSLionel Sambuc       // The interesting case.
2355f4a2713aSLionel Sambuc       break;
2356f4a2713aSLionel Sambuc     }
2357f4a2713aSLionel Sambuc 
2358f4a2713aSLionel Sambuc     // Read and process a record.
2359f4a2713aSLionel Sambuc     Record.clear();
2360f4a2713aSLionel Sambuc     StringRef Blob;
2361f4a2713aSLionel Sambuc     switch ((ControlRecordTypes)Stream.readRecord(Entry.ID, Record, &Blob)) {
2362f4a2713aSLionel Sambuc     case METADATA: {
2363f4a2713aSLionel Sambuc       if (Record[0] != VERSION_MAJOR && !DisableValidation) {
2364f4a2713aSLionel Sambuc         if ((ClientLoadCapabilities & ARR_VersionMismatch) == 0)
2365*0a6a1f1dSLionel Sambuc           Diag(Record[0] < VERSION_MAJOR? diag::err_pch_version_too_old
2366*0a6a1f1dSLionel Sambuc                                         : diag::err_pch_version_too_new);
2367f4a2713aSLionel Sambuc         return VersionMismatch;
2368f4a2713aSLionel Sambuc       }
2369f4a2713aSLionel Sambuc 
2370f4a2713aSLionel Sambuc       bool hasErrors = Record[5];
2371f4a2713aSLionel Sambuc       if (hasErrors && !DisableValidation && !AllowASTWithCompilerErrors) {
2372f4a2713aSLionel Sambuc         Diag(diag::err_pch_with_compiler_errors);
2373f4a2713aSLionel Sambuc         return HadErrors;
2374f4a2713aSLionel Sambuc       }
2375f4a2713aSLionel Sambuc 
2376f4a2713aSLionel Sambuc       F.RelocatablePCH = Record[4];
2377*0a6a1f1dSLionel Sambuc       // Relative paths in a relocatable PCH are relative to our sysroot.
2378*0a6a1f1dSLionel Sambuc       if (F.RelocatablePCH)
2379*0a6a1f1dSLionel Sambuc         F.BaseDirectory = isysroot.empty() ? "/" : isysroot;
2380f4a2713aSLionel Sambuc 
2381f4a2713aSLionel Sambuc       const std::string &CurBranch = getClangFullRepositoryVersion();
2382f4a2713aSLionel Sambuc       StringRef ASTBranch = Blob;
2383f4a2713aSLionel Sambuc       if (StringRef(CurBranch) != ASTBranch && !DisableValidation) {
2384f4a2713aSLionel Sambuc         if ((ClientLoadCapabilities & ARR_VersionMismatch) == 0)
2385*0a6a1f1dSLionel Sambuc           Diag(diag::err_pch_different_branch) << ASTBranch << CurBranch;
2386f4a2713aSLionel Sambuc         return VersionMismatch;
2387f4a2713aSLionel Sambuc       }
2388f4a2713aSLionel Sambuc       break;
2389f4a2713aSLionel Sambuc     }
2390f4a2713aSLionel Sambuc 
2391*0a6a1f1dSLionel Sambuc     case SIGNATURE:
2392*0a6a1f1dSLionel Sambuc       assert((!F.Signature || F.Signature == Record[0]) && "signature changed");
2393*0a6a1f1dSLionel Sambuc       F.Signature = Record[0];
2394*0a6a1f1dSLionel Sambuc       break;
2395*0a6a1f1dSLionel Sambuc 
2396f4a2713aSLionel Sambuc     case IMPORTS: {
2397f4a2713aSLionel Sambuc       // Load each of the imported PCH files.
2398f4a2713aSLionel Sambuc       unsigned Idx = 0, N = Record.size();
2399f4a2713aSLionel Sambuc       while (Idx < N) {
2400f4a2713aSLionel Sambuc         // Read information about the AST file.
2401f4a2713aSLionel Sambuc         ModuleKind ImportedKind = (ModuleKind)Record[Idx++];
2402f4a2713aSLionel Sambuc         // The import location will be the local one for now; we will adjust
2403f4a2713aSLionel Sambuc         // all import locations of module imports after the global source
2404f4a2713aSLionel Sambuc         // location info are setup.
2405f4a2713aSLionel Sambuc         SourceLocation ImportLoc =
2406f4a2713aSLionel Sambuc             SourceLocation::getFromRawEncoding(Record[Idx++]);
2407f4a2713aSLionel Sambuc         off_t StoredSize = (off_t)Record[Idx++];
2408f4a2713aSLionel Sambuc         time_t StoredModTime = (time_t)Record[Idx++];
2409*0a6a1f1dSLionel Sambuc         ASTFileSignature StoredSignature = Record[Idx++];
2410*0a6a1f1dSLionel Sambuc         auto ImportedFile = ReadPath(F, Record, Idx);
2411f4a2713aSLionel Sambuc 
2412f4a2713aSLionel Sambuc         // Load the AST file.
2413f4a2713aSLionel Sambuc         switch(ReadASTCore(ImportedFile, ImportedKind, ImportLoc, &F, Loaded,
2414*0a6a1f1dSLionel Sambuc                            StoredSize, StoredModTime, StoredSignature,
2415f4a2713aSLionel Sambuc                            ClientLoadCapabilities)) {
2416f4a2713aSLionel Sambuc         case Failure: return Failure;
2417f4a2713aSLionel Sambuc           // If we have to ignore the dependency, we'll have to ignore this too.
2418f4a2713aSLionel Sambuc         case Missing:
2419f4a2713aSLionel Sambuc         case OutOfDate: return OutOfDate;
2420f4a2713aSLionel Sambuc         case VersionMismatch: return VersionMismatch;
2421f4a2713aSLionel Sambuc         case ConfigurationMismatch: return ConfigurationMismatch;
2422f4a2713aSLionel Sambuc         case HadErrors: return HadErrors;
2423f4a2713aSLionel Sambuc         case Success: break;
2424f4a2713aSLionel Sambuc         }
2425f4a2713aSLionel Sambuc       }
2426f4a2713aSLionel Sambuc       break;
2427f4a2713aSLionel Sambuc     }
2428f4a2713aSLionel Sambuc 
2429f4a2713aSLionel Sambuc     case LANGUAGE_OPTIONS: {
2430f4a2713aSLionel Sambuc       bool Complain = (ClientLoadCapabilities & ARR_ConfigurationMismatch) == 0;
2431*0a6a1f1dSLionel Sambuc       // FIXME: The &F == *ModuleMgr.begin() check is wrong for modules.
2432f4a2713aSLionel Sambuc       if (Listener && &F == *ModuleMgr.begin() &&
2433*0a6a1f1dSLionel Sambuc           ParseLanguageOptions(Record, Complain, *Listener,
2434*0a6a1f1dSLionel Sambuc                                AllowCompatibleConfigurationMismatch) &&
2435*0a6a1f1dSLionel Sambuc           !DisableValidation && !AllowConfigurationMismatch)
2436f4a2713aSLionel Sambuc         return ConfigurationMismatch;
2437f4a2713aSLionel Sambuc       break;
2438f4a2713aSLionel Sambuc     }
2439f4a2713aSLionel Sambuc 
2440f4a2713aSLionel Sambuc     case TARGET_OPTIONS: {
2441f4a2713aSLionel Sambuc       bool Complain = (ClientLoadCapabilities & ARR_ConfigurationMismatch)==0;
2442f4a2713aSLionel Sambuc       if (Listener && &F == *ModuleMgr.begin() &&
2443f4a2713aSLionel Sambuc           ParseTargetOptions(Record, Complain, *Listener) &&
2444*0a6a1f1dSLionel Sambuc           !DisableValidation && !AllowConfigurationMismatch)
2445f4a2713aSLionel Sambuc         return ConfigurationMismatch;
2446f4a2713aSLionel Sambuc       break;
2447f4a2713aSLionel Sambuc     }
2448f4a2713aSLionel Sambuc 
2449f4a2713aSLionel Sambuc     case DIAGNOSTIC_OPTIONS: {
2450*0a6a1f1dSLionel Sambuc       bool Complain = (ClientLoadCapabilities & ARR_OutOfDate)==0;
2451f4a2713aSLionel Sambuc       if (Listener && &F == *ModuleMgr.begin() &&
2452*0a6a1f1dSLionel Sambuc           !AllowCompatibleConfigurationMismatch &&
2453f4a2713aSLionel Sambuc           ParseDiagnosticOptions(Record, Complain, *Listener) &&
2454f4a2713aSLionel Sambuc           !DisableValidation)
2455*0a6a1f1dSLionel Sambuc         return OutOfDate;
2456f4a2713aSLionel Sambuc       break;
2457f4a2713aSLionel Sambuc     }
2458f4a2713aSLionel Sambuc 
2459f4a2713aSLionel Sambuc     case FILE_SYSTEM_OPTIONS: {
2460f4a2713aSLionel Sambuc       bool Complain = (ClientLoadCapabilities & ARR_ConfigurationMismatch)==0;
2461f4a2713aSLionel Sambuc       if (Listener && &F == *ModuleMgr.begin() &&
2462*0a6a1f1dSLionel Sambuc           !AllowCompatibleConfigurationMismatch &&
2463f4a2713aSLionel Sambuc           ParseFileSystemOptions(Record, Complain, *Listener) &&
2464*0a6a1f1dSLionel Sambuc           !DisableValidation && !AllowConfigurationMismatch)
2465f4a2713aSLionel Sambuc         return ConfigurationMismatch;
2466f4a2713aSLionel Sambuc       break;
2467f4a2713aSLionel Sambuc     }
2468f4a2713aSLionel Sambuc 
2469f4a2713aSLionel Sambuc     case HEADER_SEARCH_OPTIONS: {
2470f4a2713aSLionel Sambuc       bool Complain = (ClientLoadCapabilities & ARR_ConfigurationMismatch)==0;
2471f4a2713aSLionel Sambuc       if (Listener && &F == *ModuleMgr.begin() &&
2472*0a6a1f1dSLionel Sambuc           !AllowCompatibleConfigurationMismatch &&
2473f4a2713aSLionel Sambuc           ParseHeaderSearchOptions(Record, Complain, *Listener) &&
2474*0a6a1f1dSLionel Sambuc           !DisableValidation && !AllowConfigurationMismatch)
2475f4a2713aSLionel Sambuc         return ConfigurationMismatch;
2476f4a2713aSLionel Sambuc       break;
2477f4a2713aSLionel Sambuc     }
2478f4a2713aSLionel Sambuc 
2479f4a2713aSLionel Sambuc     case PREPROCESSOR_OPTIONS: {
2480f4a2713aSLionel Sambuc       bool Complain = (ClientLoadCapabilities & ARR_ConfigurationMismatch)==0;
2481f4a2713aSLionel Sambuc       if (Listener && &F == *ModuleMgr.begin() &&
2482*0a6a1f1dSLionel Sambuc           !AllowCompatibleConfigurationMismatch &&
2483f4a2713aSLionel Sambuc           ParsePreprocessorOptions(Record, Complain, *Listener,
2484f4a2713aSLionel Sambuc                                    SuggestedPredefines) &&
2485*0a6a1f1dSLionel Sambuc           !DisableValidation && !AllowConfigurationMismatch)
2486f4a2713aSLionel Sambuc         return ConfigurationMismatch;
2487f4a2713aSLionel Sambuc       break;
2488f4a2713aSLionel Sambuc     }
2489f4a2713aSLionel Sambuc 
2490f4a2713aSLionel Sambuc     case ORIGINAL_FILE:
2491f4a2713aSLionel Sambuc       F.OriginalSourceFileID = FileID::get(Record[0]);
2492f4a2713aSLionel Sambuc       F.ActualOriginalSourceFileName = Blob;
2493f4a2713aSLionel Sambuc       F.OriginalSourceFileName = F.ActualOriginalSourceFileName;
2494*0a6a1f1dSLionel Sambuc       ResolveImportedPath(F, F.OriginalSourceFileName);
2495f4a2713aSLionel Sambuc       break;
2496f4a2713aSLionel Sambuc 
2497f4a2713aSLionel Sambuc     case ORIGINAL_FILE_ID:
2498f4a2713aSLionel Sambuc       F.OriginalSourceFileID = FileID::get(Record[0]);
2499f4a2713aSLionel Sambuc       break;
2500f4a2713aSLionel Sambuc 
2501f4a2713aSLionel Sambuc     case ORIGINAL_PCH_DIR:
2502f4a2713aSLionel Sambuc       F.OriginalDir = Blob;
2503f4a2713aSLionel Sambuc       break;
2504f4a2713aSLionel Sambuc 
2505*0a6a1f1dSLionel Sambuc     case MODULE_NAME:
2506*0a6a1f1dSLionel Sambuc       F.ModuleName = Blob;
2507*0a6a1f1dSLionel Sambuc       if (Listener)
2508*0a6a1f1dSLionel Sambuc         Listener->ReadModuleName(F.ModuleName);
2509*0a6a1f1dSLionel Sambuc       break;
2510*0a6a1f1dSLionel Sambuc 
2511*0a6a1f1dSLionel Sambuc     case MODULE_DIRECTORY: {
2512*0a6a1f1dSLionel Sambuc       assert(!F.ModuleName.empty() &&
2513*0a6a1f1dSLionel Sambuc              "MODULE_DIRECTORY found before MODULE_NAME");
2514*0a6a1f1dSLionel Sambuc       // If we've already loaded a module map file covering this module, we may
2515*0a6a1f1dSLionel Sambuc       // have a better path for it (relative to the current build).
2516*0a6a1f1dSLionel Sambuc       Module *M = PP.getHeaderSearchInfo().lookupModule(F.ModuleName);
2517*0a6a1f1dSLionel Sambuc       if (M && M->Directory) {
2518*0a6a1f1dSLionel Sambuc         // If we're implicitly loading a module, the base directory can't
2519*0a6a1f1dSLionel Sambuc         // change between the build and use.
2520*0a6a1f1dSLionel Sambuc         if (F.Kind != MK_ExplicitModule) {
2521*0a6a1f1dSLionel Sambuc           const DirectoryEntry *BuildDir =
2522*0a6a1f1dSLionel Sambuc               PP.getFileManager().getDirectory(Blob);
2523*0a6a1f1dSLionel Sambuc           if (!BuildDir || BuildDir != M->Directory) {
2524*0a6a1f1dSLionel Sambuc             if ((ClientLoadCapabilities & ARR_OutOfDate) == 0)
2525*0a6a1f1dSLionel Sambuc               Diag(diag::err_imported_module_relocated)
2526*0a6a1f1dSLionel Sambuc                   << F.ModuleName << Blob << M->Directory->getName();
2527*0a6a1f1dSLionel Sambuc             return OutOfDate;
2528*0a6a1f1dSLionel Sambuc           }
2529*0a6a1f1dSLionel Sambuc         }
2530*0a6a1f1dSLionel Sambuc         F.BaseDirectory = M->Directory->getName();
2531*0a6a1f1dSLionel Sambuc       } else {
2532*0a6a1f1dSLionel Sambuc         F.BaseDirectory = Blob;
2533*0a6a1f1dSLionel Sambuc       }
2534*0a6a1f1dSLionel Sambuc       break;
2535*0a6a1f1dSLionel Sambuc     }
2536*0a6a1f1dSLionel Sambuc 
2537*0a6a1f1dSLionel Sambuc     case MODULE_MAP_FILE:
2538*0a6a1f1dSLionel Sambuc       if (ASTReadResult Result =
2539*0a6a1f1dSLionel Sambuc               ReadModuleMapFileBlock(Record, F, ImportedBy, ClientLoadCapabilities))
2540*0a6a1f1dSLionel Sambuc         return Result;
2541*0a6a1f1dSLionel Sambuc       break;
2542*0a6a1f1dSLionel Sambuc 
2543f4a2713aSLionel Sambuc     case INPUT_FILE_OFFSETS:
2544*0a6a1f1dSLionel Sambuc       NumInputs = Record[0];
2545*0a6a1f1dSLionel Sambuc       NumUserInputs = Record[1];
2546f4a2713aSLionel Sambuc       F.InputFileOffsets = (const uint32_t *)Blob.data();
2547*0a6a1f1dSLionel Sambuc       F.InputFilesLoaded.resize(NumInputs);
2548f4a2713aSLionel Sambuc       break;
2549f4a2713aSLionel Sambuc     }
2550f4a2713aSLionel Sambuc   }
2551f4a2713aSLionel Sambuc }
2552f4a2713aSLionel Sambuc 
2553*0a6a1f1dSLionel Sambuc ASTReader::ASTReadResult
ReadASTBlock(ModuleFile & F,unsigned ClientLoadCapabilities)2554*0a6a1f1dSLionel Sambuc ASTReader::ReadASTBlock(ModuleFile &F, unsigned ClientLoadCapabilities) {
2555f4a2713aSLionel Sambuc   BitstreamCursor &Stream = F.Stream;
2556f4a2713aSLionel Sambuc 
2557f4a2713aSLionel Sambuc   if (Stream.EnterSubBlock(AST_BLOCK_ID)) {
2558f4a2713aSLionel Sambuc     Error("malformed block record in AST file");
2559*0a6a1f1dSLionel Sambuc     return Failure;
2560f4a2713aSLionel Sambuc   }
2561f4a2713aSLionel Sambuc 
2562f4a2713aSLionel Sambuc   // Read all of the records and blocks for the AST file.
2563f4a2713aSLionel Sambuc   RecordData Record;
2564f4a2713aSLionel Sambuc   while (1) {
2565f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = Stream.advance();
2566f4a2713aSLionel Sambuc 
2567f4a2713aSLionel Sambuc     switch (Entry.Kind) {
2568f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Error:
2569f4a2713aSLionel Sambuc       Error("error at end of module block in AST file");
2570*0a6a1f1dSLionel Sambuc       return Failure;
2571f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::EndBlock: {
2572f4a2713aSLionel Sambuc       // Outside of C++, we do not store a lookup map for the translation unit.
2573f4a2713aSLionel Sambuc       // Instead, mark it as needing a lookup map to be built if this module
2574f4a2713aSLionel Sambuc       // contains any declarations lexically within it (which it always does!).
2575f4a2713aSLionel Sambuc       // This usually has no cost, since we very rarely need the lookup map for
2576f4a2713aSLionel Sambuc       // the translation unit outside C++.
2577f4a2713aSLionel Sambuc       DeclContext *DC = Context.getTranslationUnitDecl();
2578f4a2713aSLionel Sambuc       if (DC->hasExternalLexicalStorage() &&
2579f4a2713aSLionel Sambuc           !getContext().getLangOpts().CPlusPlus)
2580f4a2713aSLionel Sambuc         DC->setMustBuildLookupTable();
2581f4a2713aSLionel Sambuc 
2582*0a6a1f1dSLionel Sambuc       return Success;
2583f4a2713aSLionel Sambuc     }
2584f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::SubBlock:
2585f4a2713aSLionel Sambuc       switch (Entry.ID) {
2586f4a2713aSLionel Sambuc       case DECLTYPES_BLOCK_ID:
2587f4a2713aSLionel Sambuc         // We lazily load the decls block, but we want to set up the
2588f4a2713aSLionel Sambuc         // DeclsCursor cursor to point into it.  Clone our current bitcode
2589f4a2713aSLionel Sambuc         // cursor to it, enter the block and read the abbrevs in that block.
2590f4a2713aSLionel Sambuc         // With the main cursor, we just skip over it.
2591f4a2713aSLionel Sambuc         F.DeclsCursor = Stream;
2592f4a2713aSLionel Sambuc         if (Stream.SkipBlock() ||  // Skip with the main cursor.
2593f4a2713aSLionel Sambuc             // Read the abbrevs.
2594f4a2713aSLionel Sambuc             ReadBlockAbbrevs(F.DeclsCursor, DECLTYPES_BLOCK_ID)) {
2595f4a2713aSLionel Sambuc           Error("malformed block record in AST file");
2596*0a6a1f1dSLionel Sambuc           return Failure;
2597f4a2713aSLionel Sambuc         }
2598f4a2713aSLionel Sambuc         break;
2599f4a2713aSLionel Sambuc 
2600f4a2713aSLionel Sambuc       case PREPROCESSOR_BLOCK_ID:
2601f4a2713aSLionel Sambuc         F.MacroCursor = Stream;
2602f4a2713aSLionel Sambuc         if (!PP.getExternalSource())
2603f4a2713aSLionel Sambuc           PP.setExternalSource(this);
2604f4a2713aSLionel Sambuc 
2605f4a2713aSLionel Sambuc         if (Stream.SkipBlock() ||
2606f4a2713aSLionel Sambuc             ReadBlockAbbrevs(F.MacroCursor, PREPROCESSOR_BLOCK_ID)) {
2607f4a2713aSLionel Sambuc           Error("malformed block record in AST file");
2608*0a6a1f1dSLionel Sambuc           return Failure;
2609f4a2713aSLionel Sambuc         }
2610f4a2713aSLionel Sambuc         F.MacroStartOffset = F.MacroCursor.GetCurrentBitNo();
2611f4a2713aSLionel Sambuc         break;
2612f4a2713aSLionel Sambuc 
2613f4a2713aSLionel Sambuc       case PREPROCESSOR_DETAIL_BLOCK_ID:
2614f4a2713aSLionel Sambuc         F.PreprocessorDetailCursor = Stream;
2615f4a2713aSLionel Sambuc         if (Stream.SkipBlock() ||
2616f4a2713aSLionel Sambuc             ReadBlockAbbrevs(F.PreprocessorDetailCursor,
2617f4a2713aSLionel Sambuc                              PREPROCESSOR_DETAIL_BLOCK_ID)) {
2618f4a2713aSLionel Sambuc               Error("malformed preprocessor detail record in AST file");
2619*0a6a1f1dSLionel Sambuc               return Failure;
2620f4a2713aSLionel Sambuc             }
2621f4a2713aSLionel Sambuc         F.PreprocessorDetailStartOffset
2622f4a2713aSLionel Sambuc         = F.PreprocessorDetailCursor.GetCurrentBitNo();
2623f4a2713aSLionel Sambuc 
2624f4a2713aSLionel Sambuc         if (!PP.getPreprocessingRecord())
2625f4a2713aSLionel Sambuc           PP.createPreprocessingRecord();
2626f4a2713aSLionel Sambuc         if (!PP.getPreprocessingRecord()->getExternalSource())
2627f4a2713aSLionel Sambuc           PP.getPreprocessingRecord()->SetExternalSource(*this);
2628f4a2713aSLionel Sambuc         break;
2629f4a2713aSLionel Sambuc 
2630f4a2713aSLionel Sambuc       case SOURCE_MANAGER_BLOCK_ID:
2631f4a2713aSLionel Sambuc         if (ReadSourceManagerBlock(F))
2632*0a6a1f1dSLionel Sambuc           return Failure;
2633f4a2713aSLionel Sambuc         break;
2634f4a2713aSLionel Sambuc 
2635f4a2713aSLionel Sambuc       case SUBMODULE_BLOCK_ID:
2636*0a6a1f1dSLionel Sambuc         if (ASTReadResult Result = ReadSubmoduleBlock(F, ClientLoadCapabilities))
2637*0a6a1f1dSLionel Sambuc           return Result;
2638f4a2713aSLionel Sambuc         break;
2639f4a2713aSLionel Sambuc 
2640f4a2713aSLionel Sambuc       case COMMENTS_BLOCK_ID: {
2641f4a2713aSLionel Sambuc         BitstreamCursor C = Stream;
2642f4a2713aSLionel Sambuc         if (Stream.SkipBlock() ||
2643f4a2713aSLionel Sambuc             ReadBlockAbbrevs(C, COMMENTS_BLOCK_ID)) {
2644f4a2713aSLionel Sambuc           Error("malformed comments block in AST file");
2645*0a6a1f1dSLionel Sambuc           return Failure;
2646f4a2713aSLionel Sambuc         }
2647f4a2713aSLionel Sambuc         CommentsCursors.push_back(std::make_pair(C, &F));
2648f4a2713aSLionel Sambuc         break;
2649f4a2713aSLionel Sambuc       }
2650f4a2713aSLionel Sambuc 
2651f4a2713aSLionel Sambuc       default:
2652f4a2713aSLionel Sambuc         if (Stream.SkipBlock()) {
2653f4a2713aSLionel Sambuc           Error("malformed block record in AST file");
2654*0a6a1f1dSLionel Sambuc           return Failure;
2655f4a2713aSLionel Sambuc         }
2656f4a2713aSLionel Sambuc         break;
2657f4a2713aSLionel Sambuc       }
2658f4a2713aSLionel Sambuc       continue;
2659f4a2713aSLionel Sambuc 
2660f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Record:
2661f4a2713aSLionel Sambuc       // The interesting case.
2662f4a2713aSLionel Sambuc       break;
2663f4a2713aSLionel Sambuc     }
2664f4a2713aSLionel Sambuc 
2665f4a2713aSLionel Sambuc     // Read and process a record.
2666f4a2713aSLionel Sambuc     Record.clear();
2667f4a2713aSLionel Sambuc     StringRef Blob;
2668f4a2713aSLionel Sambuc     switch ((ASTRecordTypes)Stream.readRecord(Entry.ID, Record, &Blob)) {
2669f4a2713aSLionel Sambuc     default:  // Default behavior: ignore.
2670f4a2713aSLionel Sambuc       break;
2671f4a2713aSLionel Sambuc 
2672f4a2713aSLionel Sambuc     case TYPE_OFFSET: {
2673f4a2713aSLionel Sambuc       if (F.LocalNumTypes != 0) {
2674f4a2713aSLionel Sambuc         Error("duplicate TYPE_OFFSET record in AST file");
2675*0a6a1f1dSLionel Sambuc         return Failure;
2676f4a2713aSLionel Sambuc       }
2677f4a2713aSLionel Sambuc       F.TypeOffsets = (const uint32_t *)Blob.data();
2678f4a2713aSLionel Sambuc       F.LocalNumTypes = Record[0];
2679f4a2713aSLionel Sambuc       unsigned LocalBaseTypeIndex = Record[1];
2680f4a2713aSLionel Sambuc       F.BaseTypeIndex = getTotalNumTypes();
2681f4a2713aSLionel Sambuc 
2682f4a2713aSLionel Sambuc       if (F.LocalNumTypes > 0) {
2683f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for types within this module.
2684f4a2713aSLionel Sambuc         GlobalTypeMap.insert(std::make_pair(getTotalNumTypes(), &F));
2685f4a2713aSLionel Sambuc 
2686f4a2713aSLionel Sambuc         // Introduce the local -> global mapping for types within this module.
2687f4a2713aSLionel Sambuc         F.TypeRemap.insertOrReplace(
2688f4a2713aSLionel Sambuc           std::make_pair(LocalBaseTypeIndex,
2689f4a2713aSLionel Sambuc                          F.BaseTypeIndex - LocalBaseTypeIndex));
2690f4a2713aSLionel Sambuc 
2691f4a2713aSLionel Sambuc         TypesLoaded.resize(TypesLoaded.size() + F.LocalNumTypes);
2692f4a2713aSLionel Sambuc       }
2693f4a2713aSLionel Sambuc       break;
2694f4a2713aSLionel Sambuc     }
2695f4a2713aSLionel Sambuc 
2696f4a2713aSLionel Sambuc     case DECL_OFFSET: {
2697f4a2713aSLionel Sambuc       if (F.LocalNumDecls != 0) {
2698f4a2713aSLionel Sambuc         Error("duplicate DECL_OFFSET record in AST file");
2699*0a6a1f1dSLionel Sambuc         return Failure;
2700f4a2713aSLionel Sambuc       }
2701f4a2713aSLionel Sambuc       F.DeclOffsets = (const DeclOffset *)Blob.data();
2702f4a2713aSLionel Sambuc       F.LocalNumDecls = Record[0];
2703f4a2713aSLionel Sambuc       unsigned LocalBaseDeclID = Record[1];
2704f4a2713aSLionel Sambuc       F.BaseDeclID = getTotalNumDecls();
2705f4a2713aSLionel Sambuc 
2706f4a2713aSLionel Sambuc       if (F.LocalNumDecls > 0) {
2707f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for declarations within this
2708f4a2713aSLionel Sambuc         // module.
2709f4a2713aSLionel Sambuc         GlobalDeclMap.insert(
2710f4a2713aSLionel Sambuc           std::make_pair(getTotalNumDecls() + NUM_PREDEF_DECL_IDS, &F));
2711f4a2713aSLionel Sambuc 
2712f4a2713aSLionel Sambuc         // Introduce the local -> global mapping for declarations within this
2713f4a2713aSLionel Sambuc         // module.
2714f4a2713aSLionel Sambuc         F.DeclRemap.insertOrReplace(
2715f4a2713aSLionel Sambuc           std::make_pair(LocalBaseDeclID, F.BaseDeclID - LocalBaseDeclID));
2716f4a2713aSLionel Sambuc 
2717f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for declarations within this
2718f4a2713aSLionel Sambuc         // module.
2719f4a2713aSLionel Sambuc         F.GlobalToLocalDeclIDs[&F] = LocalBaseDeclID;
2720f4a2713aSLionel Sambuc 
2721f4a2713aSLionel Sambuc         DeclsLoaded.resize(DeclsLoaded.size() + F.LocalNumDecls);
2722f4a2713aSLionel Sambuc       }
2723f4a2713aSLionel Sambuc       break;
2724f4a2713aSLionel Sambuc     }
2725f4a2713aSLionel Sambuc 
2726f4a2713aSLionel Sambuc     case TU_UPDATE_LEXICAL: {
2727f4a2713aSLionel Sambuc       DeclContext *TU = Context.getTranslationUnitDecl();
2728f4a2713aSLionel Sambuc       DeclContextInfo &Info = F.DeclContextInfos[TU];
2729f4a2713aSLionel Sambuc       Info.LexicalDecls = reinterpret_cast<const KindDeclIDPair *>(Blob.data());
2730f4a2713aSLionel Sambuc       Info.NumLexicalDecls
2731f4a2713aSLionel Sambuc         = static_cast<unsigned int>(Blob.size() / sizeof(KindDeclIDPair));
2732f4a2713aSLionel Sambuc       TU->setHasExternalLexicalStorage(true);
2733f4a2713aSLionel Sambuc       break;
2734f4a2713aSLionel Sambuc     }
2735f4a2713aSLionel Sambuc 
2736f4a2713aSLionel Sambuc     case UPDATE_VISIBLE: {
2737f4a2713aSLionel Sambuc       unsigned Idx = 0;
2738f4a2713aSLionel Sambuc       serialization::DeclID ID = ReadDeclID(F, Record, Idx);
2739f4a2713aSLionel Sambuc       ASTDeclContextNameLookupTable *Table =
2740f4a2713aSLionel Sambuc           ASTDeclContextNameLookupTable::Create(
2741f4a2713aSLionel Sambuc               (const unsigned char *)Blob.data() + Record[Idx++],
2742*0a6a1f1dSLionel Sambuc               (const unsigned char *)Blob.data() + sizeof(uint32_t),
2743f4a2713aSLionel Sambuc               (const unsigned char *)Blob.data(),
2744f4a2713aSLionel Sambuc               ASTDeclContextNameLookupTrait(*this, F));
2745*0a6a1f1dSLionel Sambuc       if (Decl *D = GetExistingDecl(ID)) {
2746*0a6a1f1dSLionel Sambuc         auto *DC = cast<DeclContext>(D);
2747*0a6a1f1dSLionel Sambuc         DC->getPrimaryContext()->setHasExternalVisibleStorage(true);
2748*0a6a1f1dSLionel Sambuc         auto *&LookupTable = F.DeclContextInfos[DC].NameLookupTableData;
2749*0a6a1f1dSLionel Sambuc         delete LookupTable;
2750*0a6a1f1dSLionel Sambuc         LookupTable = Table;
2751f4a2713aSLionel Sambuc       } else
2752f4a2713aSLionel Sambuc         PendingVisibleUpdates[ID].push_back(std::make_pair(Table, &F));
2753f4a2713aSLionel Sambuc       break;
2754f4a2713aSLionel Sambuc     }
2755f4a2713aSLionel Sambuc 
2756f4a2713aSLionel Sambuc     case IDENTIFIER_TABLE:
2757f4a2713aSLionel Sambuc       F.IdentifierTableData = Blob.data();
2758f4a2713aSLionel Sambuc       if (Record[0]) {
2759*0a6a1f1dSLionel Sambuc         F.IdentifierLookupTable = ASTIdentifierLookupTable::Create(
2760f4a2713aSLionel Sambuc             (const unsigned char *)F.IdentifierTableData + Record[0],
2761*0a6a1f1dSLionel Sambuc             (const unsigned char *)F.IdentifierTableData + sizeof(uint32_t),
2762f4a2713aSLionel Sambuc             (const unsigned char *)F.IdentifierTableData,
2763f4a2713aSLionel Sambuc             ASTIdentifierLookupTrait(*this, F));
2764f4a2713aSLionel Sambuc 
2765f4a2713aSLionel Sambuc         PP.getIdentifierTable().setExternalIdentifierLookup(this);
2766f4a2713aSLionel Sambuc       }
2767f4a2713aSLionel Sambuc       break;
2768f4a2713aSLionel Sambuc 
2769f4a2713aSLionel Sambuc     case IDENTIFIER_OFFSET: {
2770f4a2713aSLionel Sambuc       if (F.LocalNumIdentifiers != 0) {
2771f4a2713aSLionel Sambuc         Error("duplicate IDENTIFIER_OFFSET record in AST file");
2772*0a6a1f1dSLionel Sambuc         return Failure;
2773f4a2713aSLionel Sambuc       }
2774f4a2713aSLionel Sambuc       F.IdentifierOffsets = (const uint32_t *)Blob.data();
2775f4a2713aSLionel Sambuc       F.LocalNumIdentifiers = Record[0];
2776f4a2713aSLionel Sambuc       unsigned LocalBaseIdentifierID = Record[1];
2777f4a2713aSLionel Sambuc       F.BaseIdentifierID = getTotalNumIdentifiers();
2778f4a2713aSLionel Sambuc 
2779f4a2713aSLionel Sambuc       if (F.LocalNumIdentifiers > 0) {
2780f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for identifiers within this
2781f4a2713aSLionel Sambuc         // module.
2782f4a2713aSLionel Sambuc         GlobalIdentifierMap.insert(std::make_pair(getTotalNumIdentifiers() + 1,
2783f4a2713aSLionel Sambuc                                                   &F));
2784f4a2713aSLionel Sambuc 
2785f4a2713aSLionel Sambuc         // Introduce the local -> global mapping for identifiers within this
2786f4a2713aSLionel Sambuc         // module.
2787f4a2713aSLionel Sambuc         F.IdentifierRemap.insertOrReplace(
2788f4a2713aSLionel Sambuc           std::make_pair(LocalBaseIdentifierID,
2789f4a2713aSLionel Sambuc                          F.BaseIdentifierID - LocalBaseIdentifierID));
2790f4a2713aSLionel Sambuc 
2791f4a2713aSLionel Sambuc         IdentifiersLoaded.resize(IdentifiersLoaded.size()
2792f4a2713aSLionel Sambuc                                  + F.LocalNumIdentifiers);
2793f4a2713aSLionel Sambuc       }
2794f4a2713aSLionel Sambuc       break;
2795f4a2713aSLionel Sambuc     }
2796f4a2713aSLionel Sambuc 
2797*0a6a1f1dSLionel Sambuc     case EAGERLY_DESERIALIZED_DECLS:
2798f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
2799*0a6a1f1dSLionel Sambuc         EagerlyDeserializedDecls.push_back(getGlobalDeclID(F, Record[I]));
2800f4a2713aSLionel Sambuc       break;
2801f4a2713aSLionel Sambuc 
2802f4a2713aSLionel Sambuc     case SPECIAL_TYPES:
2803f4a2713aSLionel Sambuc       if (SpecialTypes.empty()) {
2804f4a2713aSLionel Sambuc         for (unsigned I = 0, N = Record.size(); I != N; ++I)
2805f4a2713aSLionel Sambuc           SpecialTypes.push_back(getGlobalTypeID(F, Record[I]));
2806f4a2713aSLionel Sambuc         break;
2807f4a2713aSLionel Sambuc       }
2808f4a2713aSLionel Sambuc 
2809f4a2713aSLionel Sambuc       if (SpecialTypes.size() != Record.size()) {
2810f4a2713aSLionel Sambuc         Error("invalid special-types record");
2811*0a6a1f1dSLionel Sambuc         return Failure;
2812f4a2713aSLionel Sambuc       }
2813f4a2713aSLionel Sambuc 
2814f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I) {
2815f4a2713aSLionel Sambuc         serialization::TypeID ID = getGlobalTypeID(F, Record[I]);
2816f4a2713aSLionel Sambuc         if (!SpecialTypes[I])
2817f4a2713aSLionel Sambuc           SpecialTypes[I] = ID;
2818f4a2713aSLionel Sambuc         // FIXME: If ID && SpecialTypes[I] != ID, do we need a separate
2819f4a2713aSLionel Sambuc         // merge step?
2820f4a2713aSLionel Sambuc       }
2821f4a2713aSLionel Sambuc       break;
2822f4a2713aSLionel Sambuc 
2823f4a2713aSLionel Sambuc     case STATISTICS:
2824f4a2713aSLionel Sambuc       TotalNumStatements += Record[0];
2825f4a2713aSLionel Sambuc       TotalNumMacros += Record[1];
2826f4a2713aSLionel Sambuc       TotalLexicalDeclContexts += Record[2];
2827f4a2713aSLionel Sambuc       TotalVisibleDeclContexts += Record[3];
2828f4a2713aSLionel Sambuc       break;
2829f4a2713aSLionel Sambuc 
2830f4a2713aSLionel Sambuc     case UNUSED_FILESCOPED_DECLS:
2831f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
2832f4a2713aSLionel Sambuc         UnusedFileScopedDecls.push_back(getGlobalDeclID(F, Record[I]));
2833f4a2713aSLionel Sambuc       break;
2834f4a2713aSLionel Sambuc 
2835f4a2713aSLionel Sambuc     case DELEGATING_CTORS:
2836f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
2837f4a2713aSLionel Sambuc         DelegatingCtorDecls.push_back(getGlobalDeclID(F, Record[I]));
2838f4a2713aSLionel Sambuc       break;
2839f4a2713aSLionel Sambuc 
2840f4a2713aSLionel Sambuc     case WEAK_UNDECLARED_IDENTIFIERS:
2841f4a2713aSLionel Sambuc       if (Record.size() % 4 != 0) {
2842f4a2713aSLionel Sambuc         Error("invalid weak identifiers record");
2843*0a6a1f1dSLionel Sambuc         return Failure;
2844f4a2713aSLionel Sambuc       }
2845f4a2713aSLionel Sambuc 
2846f4a2713aSLionel Sambuc       // FIXME: Ignore weak undeclared identifiers from non-original PCH
2847f4a2713aSLionel Sambuc       // files. This isn't the way to do it :)
2848f4a2713aSLionel Sambuc       WeakUndeclaredIdentifiers.clear();
2849f4a2713aSLionel Sambuc 
2850f4a2713aSLionel Sambuc       // Translate the weak, undeclared identifiers into global IDs.
2851f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I < N; /* in loop */) {
2852f4a2713aSLionel Sambuc         WeakUndeclaredIdentifiers.push_back(
2853f4a2713aSLionel Sambuc           getGlobalIdentifierID(F, Record[I++]));
2854f4a2713aSLionel Sambuc         WeakUndeclaredIdentifiers.push_back(
2855f4a2713aSLionel Sambuc           getGlobalIdentifierID(F, Record[I++]));
2856f4a2713aSLionel Sambuc         WeakUndeclaredIdentifiers.push_back(
2857f4a2713aSLionel Sambuc           ReadSourceLocation(F, Record, I).getRawEncoding());
2858f4a2713aSLionel Sambuc         WeakUndeclaredIdentifiers.push_back(Record[I++]);
2859f4a2713aSLionel Sambuc       }
2860f4a2713aSLionel Sambuc       break;
2861f4a2713aSLionel Sambuc 
2862f4a2713aSLionel Sambuc     case LOCALLY_SCOPED_EXTERN_C_DECLS:
2863f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
2864f4a2713aSLionel Sambuc         LocallyScopedExternCDecls.push_back(getGlobalDeclID(F, Record[I]));
2865f4a2713aSLionel Sambuc       break;
2866f4a2713aSLionel Sambuc 
2867f4a2713aSLionel Sambuc     case SELECTOR_OFFSETS: {
2868f4a2713aSLionel Sambuc       F.SelectorOffsets = (const uint32_t *)Blob.data();
2869f4a2713aSLionel Sambuc       F.LocalNumSelectors = Record[0];
2870f4a2713aSLionel Sambuc       unsigned LocalBaseSelectorID = Record[1];
2871f4a2713aSLionel Sambuc       F.BaseSelectorID = getTotalNumSelectors();
2872f4a2713aSLionel Sambuc 
2873f4a2713aSLionel Sambuc       if (F.LocalNumSelectors > 0) {
2874f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for selectors within this
2875f4a2713aSLionel Sambuc         // module.
2876f4a2713aSLionel Sambuc         GlobalSelectorMap.insert(std::make_pair(getTotalNumSelectors()+1, &F));
2877f4a2713aSLionel Sambuc 
2878f4a2713aSLionel Sambuc         // Introduce the local -> global mapping for selectors within this
2879f4a2713aSLionel Sambuc         // module.
2880f4a2713aSLionel Sambuc         F.SelectorRemap.insertOrReplace(
2881f4a2713aSLionel Sambuc           std::make_pair(LocalBaseSelectorID,
2882f4a2713aSLionel Sambuc                          F.BaseSelectorID - LocalBaseSelectorID));
2883f4a2713aSLionel Sambuc 
2884f4a2713aSLionel Sambuc         SelectorsLoaded.resize(SelectorsLoaded.size() + F.LocalNumSelectors);
2885f4a2713aSLionel Sambuc       }
2886f4a2713aSLionel Sambuc       break;
2887f4a2713aSLionel Sambuc     }
2888f4a2713aSLionel Sambuc 
2889f4a2713aSLionel Sambuc     case METHOD_POOL:
2890f4a2713aSLionel Sambuc       F.SelectorLookupTableData = (const unsigned char *)Blob.data();
2891f4a2713aSLionel Sambuc       if (Record[0])
2892f4a2713aSLionel Sambuc         F.SelectorLookupTable
2893f4a2713aSLionel Sambuc           = ASTSelectorLookupTable::Create(
2894f4a2713aSLionel Sambuc                         F.SelectorLookupTableData + Record[0],
2895f4a2713aSLionel Sambuc                         F.SelectorLookupTableData,
2896f4a2713aSLionel Sambuc                         ASTSelectorLookupTrait(*this, F));
2897f4a2713aSLionel Sambuc       TotalNumMethodPoolEntries += Record[1];
2898f4a2713aSLionel Sambuc       break;
2899f4a2713aSLionel Sambuc 
2900f4a2713aSLionel Sambuc     case REFERENCED_SELECTOR_POOL:
2901f4a2713aSLionel Sambuc       if (!Record.empty()) {
2902f4a2713aSLionel Sambuc         for (unsigned Idx = 0, N = Record.size() - 1; Idx < N; /* in loop */) {
2903f4a2713aSLionel Sambuc           ReferencedSelectorsData.push_back(getGlobalSelectorID(F,
2904f4a2713aSLionel Sambuc                                                                 Record[Idx++]));
2905f4a2713aSLionel Sambuc           ReferencedSelectorsData.push_back(ReadSourceLocation(F, Record, Idx).
2906f4a2713aSLionel Sambuc                                               getRawEncoding());
2907f4a2713aSLionel Sambuc         }
2908f4a2713aSLionel Sambuc       }
2909f4a2713aSLionel Sambuc       break;
2910f4a2713aSLionel Sambuc 
2911f4a2713aSLionel Sambuc     case PP_COUNTER_VALUE:
2912f4a2713aSLionel Sambuc       if (!Record.empty() && Listener)
2913f4a2713aSLionel Sambuc         Listener->ReadCounter(F, Record[0]);
2914f4a2713aSLionel Sambuc       break;
2915f4a2713aSLionel Sambuc 
2916f4a2713aSLionel Sambuc     case FILE_SORTED_DECLS:
2917f4a2713aSLionel Sambuc       F.FileSortedDecls = (const DeclID *)Blob.data();
2918f4a2713aSLionel Sambuc       F.NumFileSortedDecls = Record[0];
2919f4a2713aSLionel Sambuc       break;
2920f4a2713aSLionel Sambuc 
2921f4a2713aSLionel Sambuc     case SOURCE_LOCATION_OFFSETS: {
2922f4a2713aSLionel Sambuc       F.SLocEntryOffsets = (const uint32_t *)Blob.data();
2923f4a2713aSLionel Sambuc       F.LocalNumSLocEntries = Record[0];
2924f4a2713aSLionel Sambuc       unsigned SLocSpaceSize = Record[1];
2925*0a6a1f1dSLionel Sambuc       std::tie(F.SLocEntryBaseID, F.SLocEntryBaseOffset) =
2926f4a2713aSLionel Sambuc           SourceMgr.AllocateLoadedSLocEntries(F.LocalNumSLocEntries,
2927f4a2713aSLionel Sambuc                                               SLocSpaceSize);
2928f4a2713aSLionel Sambuc       // Make our entry in the range map. BaseID is negative and growing, so
2929f4a2713aSLionel Sambuc       // we invert it. Because we invert it, though, we need the other end of
2930f4a2713aSLionel Sambuc       // the range.
2931f4a2713aSLionel Sambuc       unsigned RangeStart =
2932f4a2713aSLionel Sambuc           unsigned(-F.SLocEntryBaseID) - F.LocalNumSLocEntries + 1;
2933f4a2713aSLionel Sambuc       GlobalSLocEntryMap.insert(std::make_pair(RangeStart, &F));
2934f4a2713aSLionel Sambuc       F.FirstLoc = SourceLocation::getFromRawEncoding(F.SLocEntryBaseOffset);
2935f4a2713aSLionel Sambuc 
2936f4a2713aSLionel Sambuc       // SLocEntryBaseOffset is lower than MaxLoadedOffset and decreasing.
2937f4a2713aSLionel Sambuc       assert((F.SLocEntryBaseOffset & (1U << 31U)) == 0);
2938f4a2713aSLionel Sambuc       GlobalSLocOffsetMap.insert(
2939f4a2713aSLionel Sambuc           std::make_pair(SourceManager::MaxLoadedOffset - F.SLocEntryBaseOffset
2940f4a2713aSLionel Sambuc                            - SLocSpaceSize,&F));
2941f4a2713aSLionel Sambuc 
2942f4a2713aSLionel Sambuc       // Initialize the remapping table.
2943f4a2713aSLionel Sambuc       // Invalid stays invalid.
2944*0a6a1f1dSLionel Sambuc       F.SLocRemap.insertOrReplace(std::make_pair(0U, 0));
2945f4a2713aSLionel Sambuc       // This module. Base was 2 when being compiled.
2946*0a6a1f1dSLionel Sambuc       F.SLocRemap.insertOrReplace(std::make_pair(2U,
2947f4a2713aSLionel Sambuc                                   static_cast<int>(F.SLocEntryBaseOffset - 2)));
2948f4a2713aSLionel Sambuc 
2949f4a2713aSLionel Sambuc       TotalNumSLocEntries += F.LocalNumSLocEntries;
2950f4a2713aSLionel Sambuc       break;
2951f4a2713aSLionel Sambuc     }
2952f4a2713aSLionel Sambuc 
2953f4a2713aSLionel Sambuc     case MODULE_OFFSET_MAP: {
2954f4a2713aSLionel Sambuc       // Additional remapping information.
2955f4a2713aSLionel Sambuc       const unsigned char *Data = (const unsigned char*)Blob.data();
2956f4a2713aSLionel Sambuc       const unsigned char *DataEnd = Data + Blob.size();
2957f4a2713aSLionel Sambuc 
2958*0a6a1f1dSLionel Sambuc       // If we see this entry before SOURCE_LOCATION_OFFSETS, add placeholders.
2959*0a6a1f1dSLionel Sambuc       if (F.SLocRemap.find(0) == F.SLocRemap.end()) {
2960*0a6a1f1dSLionel Sambuc         F.SLocRemap.insert(std::make_pair(0U, 0));
2961*0a6a1f1dSLionel Sambuc         F.SLocRemap.insert(std::make_pair(2U, 1));
2962*0a6a1f1dSLionel Sambuc       }
2963*0a6a1f1dSLionel Sambuc 
2964f4a2713aSLionel Sambuc       // Continuous range maps we may be updating in our module.
2965*0a6a1f1dSLionel Sambuc       typedef ContinuousRangeMap<uint32_t, int, 2>::Builder
2966*0a6a1f1dSLionel Sambuc           RemapBuilder;
2967*0a6a1f1dSLionel Sambuc       RemapBuilder SLocRemap(F.SLocRemap);
2968*0a6a1f1dSLionel Sambuc       RemapBuilder IdentifierRemap(F.IdentifierRemap);
2969*0a6a1f1dSLionel Sambuc       RemapBuilder MacroRemap(F.MacroRemap);
2970*0a6a1f1dSLionel Sambuc       RemapBuilder PreprocessedEntityRemap(F.PreprocessedEntityRemap);
2971*0a6a1f1dSLionel Sambuc       RemapBuilder SubmoduleRemap(F.SubmoduleRemap);
2972*0a6a1f1dSLionel Sambuc       RemapBuilder SelectorRemap(F.SelectorRemap);
2973*0a6a1f1dSLionel Sambuc       RemapBuilder DeclRemap(F.DeclRemap);
2974*0a6a1f1dSLionel Sambuc       RemapBuilder TypeRemap(F.TypeRemap);
2975f4a2713aSLionel Sambuc 
2976f4a2713aSLionel Sambuc       while(Data < DataEnd) {
2977*0a6a1f1dSLionel Sambuc         using namespace llvm::support;
2978*0a6a1f1dSLionel Sambuc         uint16_t Len = endian::readNext<uint16_t, little, unaligned>(Data);
2979f4a2713aSLionel Sambuc         StringRef Name = StringRef((const char*)Data, Len);
2980f4a2713aSLionel Sambuc         Data += Len;
2981f4a2713aSLionel Sambuc         ModuleFile *OM = ModuleMgr.lookup(Name);
2982f4a2713aSLionel Sambuc         if (!OM) {
2983f4a2713aSLionel Sambuc           Error("SourceLocation remap refers to unknown module");
2984*0a6a1f1dSLionel Sambuc           return Failure;
2985f4a2713aSLionel Sambuc         }
2986f4a2713aSLionel Sambuc 
2987*0a6a1f1dSLionel Sambuc         uint32_t SLocOffset =
2988*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
2989*0a6a1f1dSLionel Sambuc         uint32_t IdentifierIDOffset =
2990*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
2991*0a6a1f1dSLionel Sambuc         uint32_t MacroIDOffset =
2992*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
2993*0a6a1f1dSLionel Sambuc         uint32_t PreprocessedEntityIDOffset =
2994*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
2995*0a6a1f1dSLionel Sambuc         uint32_t SubmoduleIDOffset =
2996*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
2997*0a6a1f1dSLionel Sambuc         uint32_t SelectorIDOffset =
2998*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
2999*0a6a1f1dSLionel Sambuc         uint32_t DeclIDOffset =
3000*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
3001*0a6a1f1dSLionel Sambuc         uint32_t TypeIndexOffset =
3002*0a6a1f1dSLionel Sambuc             endian::readNext<uint32_t, little, unaligned>(Data);
3003f4a2713aSLionel Sambuc 
3004*0a6a1f1dSLionel Sambuc         uint32_t None = std::numeric_limits<uint32_t>::max();
3005f4a2713aSLionel Sambuc 
3006*0a6a1f1dSLionel Sambuc         auto mapOffset = [&](uint32_t Offset, uint32_t BaseOffset,
3007*0a6a1f1dSLionel Sambuc                              RemapBuilder &Remap) {
3008*0a6a1f1dSLionel Sambuc           if (Offset != None)
3009*0a6a1f1dSLionel Sambuc             Remap.insert(std::make_pair(Offset,
3010*0a6a1f1dSLionel Sambuc                                         static_cast<int>(BaseOffset - Offset)));
3011*0a6a1f1dSLionel Sambuc         };
3012*0a6a1f1dSLionel Sambuc         mapOffset(SLocOffset, OM->SLocEntryBaseOffset, SLocRemap);
3013*0a6a1f1dSLionel Sambuc         mapOffset(IdentifierIDOffset, OM->BaseIdentifierID, IdentifierRemap);
3014*0a6a1f1dSLionel Sambuc         mapOffset(MacroIDOffset, OM->BaseMacroID, MacroRemap);
3015*0a6a1f1dSLionel Sambuc         mapOffset(PreprocessedEntityIDOffset, OM->BasePreprocessedEntityID,
3016*0a6a1f1dSLionel Sambuc                   PreprocessedEntityRemap);
3017*0a6a1f1dSLionel Sambuc         mapOffset(SubmoduleIDOffset, OM->BaseSubmoduleID, SubmoduleRemap);
3018*0a6a1f1dSLionel Sambuc         mapOffset(SelectorIDOffset, OM->BaseSelectorID, SelectorRemap);
3019*0a6a1f1dSLionel Sambuc         mapOffset(DeclIDOffset, OM->BaseDeclID, DeclRemap);
3020*0a6a1f1dSLionel Sambuc         mapOffset(TypeIndexOffset, OM->BaseTypeIndex, TypeRemap);
3021f4a2713aSLionel Sambuc 
3022f4a2713aSLionel Sambuc         // Global -> local mappings.
3023f4a2713aSLionel Sambuc         F.GlobalToLocalDeclIDs[OM] = DeclIDOffset;
3024f4a2713aSLionel Sambuc       }
3025f4a2713aSLionel Sambuc       break;
3026f4a2713aSLionel Sambuc     }
3027f4a2713aSLionel Sambuc 
3028f4a2713aSLionel Sambuc     case SOURCE_MANAGER_LINE_TABLE:
3029f4a2713aSLionel Sambuc       if (ParseLineTable(F, Record))
3030*0a6a1f1dSLionel Sambuc         return Failure;
3031f4a2713aSLionel Sambuc       break;
3032f4a2713aSLionel Sambuc 
3033f4a2713aSLionel Sambuc     case SOURCE_LOCATION_PRELOADS: {
3034f4a2713aSLionel Sambuc       // Need to transform from the local view (1-based IDs) to the global view,
3035f4a2713aSLionel Sambuc       // which is based off F.SLocEntryBaseID.
3036f4a2713aSLionel Sambuc       if (!F.PreloadSLocEntries.empty()) {
3037f4a2713aSLionel Sambuc         Error("Multiple SOURCE_LOCATION_PRELOADS records in AST file");
3038*0a6a1f1dSLionel Sambuc         return Failure;
3039f4a2713aSLionel Sambuc       }
3040f4a2713aSLionel Sambuc 
3041f4a2713aSLionel Sambuc       F.PreloadSLocEntries.swap(Record);
3042f4a2713aSLionel Sambuc       break;
3043f4a2713aSLionel Sambuc     }
3044f4a2713aSLionel Sambuc 
3045f4a2713aSLionel Sambuc     case EXT_VECTOR_DECLS:
3046f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
3047f4a2713aSLionel Sambuc         ExtVectorDecls.push_back(getGlobalDeclID(F, Record[I]));
3048f4a2713aSLionel Sambuc       break;
3049f4a2713aSLionel Sambuc 
3050f4a2713aSLionel Sambuc     case VTABLE_USES:
3051f4a2713aSLionel Sambuc       if (Record.size() % 3 != 0) {
3052f4a2713aSLionel Sambuc         Error("Invalid VTABLE_USES record");
3053*0a6a1f1dSLionel Sambuc         return Failure;
3054f4a2713aSLionel Sambuc       }
3055f4a2713aSLionel Sambuc 
3056f4a2713aSLionel Sambuc       // Later tables overwrite earlier ones.
3057f4a2713aSLionel Sambuc       // FIXME: Modules will have some trouble with this. This is clearly not
3058f4a2713aSLionel Sambuc       // the right way to do this.
3059f4a2713aSLionel Sambuc       VTableUses.clear();
3060f4a2713aSLionel Sambuc 
3061f4a2713aSLionel Sambuc       for (unsigned Idx = 0, N = Record.size(); Idx != N; /* In loop */) {
3062f4a2713aSLionel Sambuc         VTableUses.push_back(getGlobalDeclID(F, Record[Idx++]));
3063f4a2713aSLionel Sambuc         VTableUses.push_back(
3064f4a2713aSLionel Sambuc           ReadSourceLocation(F, Record, Idx).getRawEncoding());
3065f4a2713aSLionel Sambuc         VTableUses.push_back(Record[Idx++]);
3066f4a2713aSLionel Sambuc       }
3067f4a2713aSLionel Sambuc       break;
3068f4a2713aSLionel Sambuc 
3069f4a2713aSLionel Sambuc     case DYNAMIC_CLASSES:
3070f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
3071f4a2713aSLionel Sambuc         DynamicClasses.push_back(getGlobalDeclID(F, Record[I]));
3072f4a2713aSLionel Sambuc       break;
3073f4a2713aSLionel Sambuc 
3074f4a2713aSLionel Sambuc     case PENDING_IMPLICIT_INSTANTIATIONS:
3075f4a2713aSLionel Sambuc       if (PendingInstantiations.size() % 2 != 0) {
3076f4a2713aSLionel Sambuc         Error("Invalid existing PendingInstantiations");
3077*0a6a1f1dSLionel Sambuc         return Failure;
3078f4a2713aSLionel Sambuc       }
3079f4a2713aSLionel Sambuc 
3080f4a2713aSLionel Sambuc       if (Record.size() % 2 != 0) {
3081f4a2713aSLionel Sambuc         Error("Invalid PENDING_IMPLICIT_INSTANTIATIONS block");
3082*0a6a1f1dSLionel Sambuc         return Failure;
3083f4a2713aSLionel Sambuc       }
3084f4a2713aSLionel Sambuc 
3085f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; /* in loop */) {
3086f4a2713aSLionel Sambuc         PendingInstantiations.push_back(getGlobalDeclID(F, Record[I++]));
3087f4a2713aSLionel Sambuc         PendingInstantiations.push_back(
3088f4a2713aSLionel Sambuc           ReadSourceLocation(F, Record, I).getRawEncoding());
3089f4a2713aSLionel Sambuc       }
3090f4a2713aSLionel Sambuc       break;
3091f4a2713aSLionel Sambuc 
3092f4a2713aSLionel Sambuc     case SEMA_DECL_REFS:
3093f4a2713aSLionel Sambuc       if (Record.size() != 2) {
3094f4a2713aSLionel Sambuc         Error("Invalid SEMA_DECL_REFS block");
3095*0a6a1f1dSLionel Sambuc         return Failure;
3096f4a2713aSLionel Sambuc       }
3097f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
3098f4a2713aSLionel Sambuc         SemaDeclRefs.push_back(getGlobalDeclID(F, Record[I]));
3099f4a2713aSLionel Sambuc       break;
3100f4a2713aSLionel Sambuc 
3101f4a2713aSLionel Sambuc     case PPD_ENTITIES_OFFSETS: {
3102f4a2713aSLionel Sambuc       F.PreprocessedEntityOffsets = (const PPEntityOffset *)Blob.data();
3103f4a2713aSLionel Sambuc       assert(Blob.size() % sizeof(PPEntityOffset) == 0);
3104f4a2713aSLionel Sambuc       F.NumPreprocessedEntities = Blob.size() / sizeof(PPEntityOffset);
3105f4a2713aSLionel Sambuc 
3106f4a2713aSLionel Sambuc       unsigned LocalBasePreprocessedEntityID = Record[0];
3107f4a2713aSLionel Sambuc 
3108f4a2713aSLionel Sambuc       unsigned StartingID;
3109f4a2713aSLionel Sambuc       if (!PP.getPreprocessingRecord())
3110f4a2713aSLionel Sambuc         PP.createPreprocessingRecord();
3111f4a2713aSLionel Sambuc       if (!PP.getPreprocessingRecord()->getExternalSource())
3112f4a2713aSLionel Sambuc         PP.getPreprocessingRecord()->SetExternalSource(*this);
3113f4a2713aSLionel Sambuc       StartingID
3114f4a2713aSLionel Sambuc         = PP.getPreprocessingRecord()
3115f4a2713aSLionel Sambuc             ->allocateLoadedEntities(F.NumPreprocessedEntities);
3116f4a2713aSLionel Sambuc       F.BasePreprocessedEntityID = StartingID;
3117f4a2713aSLionel Sambuc 
3118f4a2713aSLionel Sambuc       if (F.NumPreprocessedEntities > 0) {
3119f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for preprocessed entities in
3120f4a2713aSLionel Sambuc         // this module.
3121f4a2713aSLionel Sambuc         GlobalPreprocessedEntityMap.insert(std::make_pair(StartingID, &F));
3122f4a2713aSLionel Sambuc 
3123f4a2713aSLionel Sambuc         // Introduce the local -> global mapping for preprocessed entities in
3124f4a2713aSLionel Sambuc         // this module.
3125f4a2713aSLionel Sambuc         F.PreprocessedEntityRemap.insertOrReplace(
3126f4a2713aSLionel Sambuc           std::make_pair(LocalBasePreprocessedEntityID,
3127f4a2713aSLionel Sambuc             F.BasePreprocessedEntityID - LocalBasePreprocessedEntityID));
3128f4a2713aSLionel Sambuc       }
3129f4a2713aSLionel Sambuc 
3130f4a2713aSLionel Sambuc       break;
3131f4a2713aSLionel Sambuc     }
3132f4a2713aSLionel Sambuc 
3133f4a2713aSLionel Sambuc     case DECL_UPDATE_OFFSETS: {
3134f4a2713aSLionel Sambuc       if (Record.size() % 2 != 0) {
3135f4a2713aSLionel Sambuc         Error("invalid DECL_UPDATE_OFFSETS block in AST file");
3136*0a6a1f1dSLionel Sambuc         return Failure;
3137f4a2713aSLionel Sambuc       }
3138*0a6a1f1dSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; I += 2) {
3139*0a6a1f1dSLionel Sambuc         GlobalDeclID ID = getGlobalDeclID(F, Record[I]);
3140*0a6a1f1dSLionel Sambuc         DeclUpdateOffsets[ID].push_back(std::make_pair(&F, Record[I + 1]));
3141*0a6a1f1dSLionel Sambuc 
3142*0a6a1f1dSLionel Sambuc         // If we've already loaded the decl, perform the updates when we finish
3143*0a6a1f1dSLionel Sambuc         // loading this block.
3144*0a6a1f1dSLionel Sambuc         if (Decl *D = GetExistingDecl(ID))
3145*0a6a1f1dSLionel Sambuc           PendingUpdateRecords.push_back(std::make_pair(ID, D));
3146*0a6a1f1dSLionel Sambuc       }
3147f4a2713aSLionel Sambuc       break;
3148f4a2713aSLionel Sambuc     }
3149f4a2713aSLionel Sambuc 
3150f4a2713aSLionel Sambuc     case DECL_REPLACEMENTS: {
3151f4a2713aSLionel Sambuc       if (Record.size() % 3 != 0) {
3152f4a2713aSLionel Sambuc         Error("invalid DECL_REPLACEMENTS block in AST file");
3153*0a6a1f1dSLionel Sambuc         return Failure;
3154f4a2713aSLionel Sambuc       }
3155f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; I += 3)
3156f4a2713aSLionel Sambuc         ReplacedDecls[getGlobalDeclID(F, Record[I])]
3157f4a2713aSLionel Sambuc           = ReplacedDeclInfo(&F, Record[I+1], Record[I+2]);
3158f4a2713aSLionel Sambuc       break;
3159f4a2713aSLionel Sambuc     }
3160f4a2713aSLionel Sambuc 
3161f4a2713aSLionel Sambuc     case OBJC_CATEGORIES_MAP: {
3162f4a2713aSLionel Sambuc       if (F.LocalNumObjCCategoriesInMap != 0) {
3163f4a2713aSLionel Sambuc         Error("duplicate OBJC_CATEGORIES_MAP record in AST file");
3164*0a6a1f1dSLionel Sambuc         return Failure;
3165f4a2713aSLionel Sambuc       }
3166f4a2713aSLionel Sambuc 
3167f4a2713aSLionel Sambuc       F.LocalNumObjCCategoriesInMap = Record[0];
3168f4a2713aSLionel Sambuc       F.ObjCCategoriesMap = (const ObjCCategoriesInfo *)Blob.data();
3169f4a2713aSLionel Sambuc       break;
3170f4a2713aSLionel Sambuc     }
3171f4a2713aSLionel Sambuc 
3172f4a2713aSLionel Sambuc     case OBJC_CATEGORIES:
3173f4a2713aSLionel Sambuc       F.ObjCCategories.swap(Record);
3174f4a2713aSLionel Sambuc       break;
3175f4a2713aSLionel Sambuc 
3176f4a2713aSLionel Sambuc     case CXX_BASE_SPECIFIER_OFFSETS: {
3177f4a2713aSLionel Sambuc       if (F.LocalNumCXXBaseSpecifiers != 0) {
3178f4a2713aSLionel Sambuc         Error("duplicate CXX_BASE_SPECIFIER_OFFSETS record in AST file");
3179*0a6a1f1dSLionel Sambuc         return Failure;
3180f4a2713aSLionel Sambuc       }
3181f4a2713aSLionel Sambuc 
3182f4a2713aSLionel Sambuc       F.LocalNumCXXBaseSpecifiers = Record[0];
3183f4a2713aSLionel Sambuc       F.CXXBaseSpecifiersOffsets = (const uint32_t *)Blob.data();
3184f4a2713aSLionel Sambuc       NumCXXBaseSpecifiersLoaded += F.LocalNumCXXBaseSpecifiers;
3185f4a2713aSLionel Sambuc       break;
3186f4a2713aSLionel Sambuc     }
3187f4a2713aSLionel Sambuc 
3188f4a2713aSLionel Sambuc     case DIAG_PRAGMA_MAPPINGS:
3189f4a2713aSLionel Sambuc       if (F.PragmaDiagMappings.empty())
3190f4a2713aSLionel Sambuc         F.PragmaDiagMappings.swap(Record);
3191f4a2713aSLionel Sambuc       else
3192f4a2713aSLionel Sambuc         F.PragmaDiagMappings.insert(F.PragmaDiagMappings.end(),
3193f4a2713aSLionel Sambuc                                     Record.begin(), Record.end());
3194f4a2713aSLionel Sambuc       break;
3195f4a2713aSLionel Sambuc 
3196f4a2713aSLionel Sambuc     case CUDA_SPECIAL_DECL_REFS:
3197f4a2713aSLionel Sambuc       // Later tables overwrite earlier ones.
3198f4a2713aSLionel Sambuc       // FIXME: Modules will have trouble with this.
3199f4a2713aSLionel Sambuc       CUDASpecialDeclRefs.clear();
3200f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
3201f4a2713aSLionel Sambuc         CUDASpecialDeclRefs.push_back(getGlobalDeclID(F, Record[I]));
3202f4a2713aSLionel Sambuc       break;
3203f4a2713aSLionel Sambuc 
3204f4a2713aSLionel Sambuc     case HEADER_SEARCH_TABLE: {
3205f4a2713aSLionel Sambuc       F.HeaderFileInfoTableData = Blob.data();
3206f4a2713aSLionel Sambuc       F.LocalNumHeaderFileInfos = Record[1];
3207f4a2713aSLionel Sambuc       if (Record[0]) {
3208f4a2713aSLionel Sambuc         F.HeaderFileInfoTable
3209f4a2713aSLionel Sambuc           = HeaderFileInfoLookupTable::Create(
3210f4a2713aSLionel Sambuc                    (const unsigned char *)F.HeaderFileInfoTableData + Record[0],
3211f4a2713aSLionel Sambuc                    (const unsigned char *)F.HeaderFileInfoTableData,
3212f4a2713aSLionel Sambuc                    HeaderFileInfoTrait(*this, F,
3213f4a2713aSLionel Sambuc                                        &PP.getHeaderSearchInfo(),
3214f4a2713aSLionel Sambuc                                        Blob.data() + Record[2]));
3215f4a2713aSLionel Sambuc 
3216f4a2713aSLionel Sambuc         PP.getHeaderSearchInfo().SetExternalSource(this);
3217f4a2713aSLionel Sambuc         if (!PP.getHeaderSearchInfo().getExternalLookup())
3218f4a2713aSLionel Sambuc           PP.getHeaderSearchInfo().SetExternalLookup(this);
3219f4a2713aSLionel Sambuc       }
3220f4a2713aSLionel Sambuc       break;
3221f4a2713aSLionel Sambuc     }
3222f4a2713aSLionel Sambuc 
3223f4a2713aSLionel Sambuc     case FP_PRAGMA_OPTIONS:
3224f4a2713aSLionel Sambuc       // Later tables overwrite earlier ones.
3225f4a2713aSLionel Sambuc       FPPragmaOptions.swap(Record);
3226f4a2713aSLionel Sambuc       break;
3227f4a2713aSLionel Sambuc 
3228f4a2713aSLionel Sambuc     case OPENCL_EXTENSIONS:
3229f4a2713aSLionel Sambuc       // Later tables overwrite earlier ones.
3230f4a2713aSLionel Sambuc       OpenCLExtensions.swap(Record);
3231f4a2713aSLionel Sambuc       break;
3232f4a2713aSLionel Sambuc 
3233f4a2713aSLionel Sambuc     case TENTATIVE_DEFINITIONS:
3234f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
3235f4a2713aSLionel Sambuc         TentativeDefinitions.push_back(getGlobalDeclID(F, Record[I]));
3236f4a2713aSLionel Sambuc       break;
3237f4a2713aSLionel Sambuc 
3238f4a2713aSLionel Sambuc     case KNOWN_NAMESPACES:
3239f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
3240f4a2713aSLionel Sambuc         KnownNamespaces.push_back(getGlobalDeclID(F, Record[I]));
3241f4a2713aSLionel Sambuc       break;
3242f4a2713aSLionel Sambuc 
3243f4a2713aSLionel Sambuc     case UNDEFINED_BUT_USED:
3244f4a2713aSLionel Sambuc       if (UndefinedButUsed.size() % 2 != 0) {
3245f4a2713aSLionel Sambuc         Error("Invalid existing UndefinedButUsed");
3246*0a6a1f1dSLionel Sambuc         return Failure;
3247f4a2713aSLionel Sambuc       }
3248f4a2713aSLionel Sambuc 
3249f4a2713aSLionel Sambuc       if (Record.size() % 2 != 0) {
3250f4a2713aSLionel Sambuc         Error("invalid undefined-but-used record");
3251*0a6a1f1dSLionel Sambuc         return Failure;
3252f4a2713aSLionel Sambuc       }
3253f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; /* in loop */) {
3254f4a2713aSLionel Sambuc         UndefinedButUsed.push_back(getGlobalDeclID(F, Record[I++]));
3255f4a2713aSLionel Sambuc         UndefinedButUsed.push_back(
3256f4a2713aSLionel Sambuc             ReadSourceLocation(F, Record, I).getRawEncoding());
3257f4a2713aSLionel Sambuc       }
3258f4a2713aSLionel Sambuc       break;
3259f4a2713aSLionel Sambuc 
3260f4a2713aSLionel Sambuc     case IMPORTED_MODULES: {
3261*0a6a1f1dSLionel Sambuc       if (F.Kind != MK_ImplicitModule && F.Kind != MK_ExplicitModule) {
3262f4a2713aSLionel Sambuc         // If we aren't loading a module (which has its own exports), make
3263f4a2713aSLionel Sambuc         // all of the imported modules visible.
3264f4a2713aSLionel Sambuc         // FIXME: Deal with macros-only imports.
3265*0a6a1f1dSLionel Sambuc         for (unsigned I = 0, N = Record.size(); I != N; /**/) {
3266*0a6a1f1dSLionel Sambuc           unsigned GlobalID = getGlobalSubmoduleID(F, Record[I++]);
3267*0a6a1f1dSLionel Sambuc           SourceLocation Loc = ReadSourceLocation(F, Record, I);
3268*0a6a1f1dSLionel Sambuc           if (GlobalID)
3269*0a6a1f1dSLionel Sambuc             ImportedModules.push_back(ImportedSubmodule(GlobalID, Loc));
3270f4a2713aSLionel Sambuc         }
3271f4a2713aSLionel Sambuc       }
3272f4a2713aSLionel Sambuc       break;
3273f4a2713aSLionel Sambuc     }
3274f4a2713aSLionel Sambuc 
3275f4a2713aSLionel Sambuc     case LOCAL_REDECLARATIONS: {
3276f4a2713aSLionel Sambuc       F.RedeclarationChains.swap(Record);
3277f4a2713aSLionel Sambuc       break;
3278f4a2713aSLionel Sambuc     }
3279f4a2713aSLionel Sambuc 
3280f4a2713aSLionel Sambuc     case LOCAL_REDECLARATIONS_MAP: {
3281f4a2713aSLionel Sambuc       if (F.LocalNumRedeclarationsInMap != 0) {
3282f4a2713aSLionel Sambuc         Error("duplicate LOCAL_REDECLARATIONS_MAP record in AST file");
3283*0a6a1f1dSLionel Sambuc         return Failure;
3284f4a2713aSLionel Sambuc       }
3285f4a2713aSLionel Sambuc 
3286f4a2713aSLionel Sambuc       F.LocalNumRedeclarationsInMap = Record[0];
3287f4a2713aSLionel Sambuc       F.RedeclarationsMap = (const LocalRedeclarationsInfo *)Blob.data();
3288f4a2713aSLionel Sambuc       break;
3289f4a2713aSLionel Sambuc     }
3290f4a2713aSLionel Sambuc 
3291f4a2713aSLionel Sambuc     case MERGED_DECLARATIONS: {
3292f4a2713aSLionel Sambuc       for (unsigned Idx = 0; Idx < Record.size(); /* increment in loop */) {
3293f4a2713aSLionel Sambuc         GlobalDeclID CanonID = getGlobalDeclID(F, Record[Idx++]);
3294f4a2713aSLionel Sambuc         SmallVectorImpl<GlobalDeclID> &Decls = StoredMergedDecls[CanonID];
3295f4a2713aSLionel Sambuc         for (unsigned N = Record[Idx++]; N > 0; --N)
3296f4a2713aSLionel Sambuc           Decls.push_back(getGlobalDeclID(F, Record[Idx++]));
3297f4a2713aSLionel Sambuc       }
3298f4a2713aSLionel Sambuc       break;
3299f4a2713aSLionel Sambuc     }
3300f4a2713aSLionel Sambuc 
3301f4a2713aSLionel Sambuc     case MACRO_OFFSET: {
3302f4a2713aSLionel Sambuc       if (F.LocalNumMacros != 0) {
3303f4a2713aSLionel Sambuc         Error("duplicate MACRO_OFFSET record in AST file");
3304*0a6a1f1dSLionel Sambuc         return Failure;
3305f4a2713aSLionel Sambuc       }
3306f4a2713aSLionel Sambuc       F.MacroOffsets = (const uint32_t *)Blob.data();
3307f4a2713aSLionel Sambuc       F.LocalNumMacros = Record[0];
3308f4a2713aSLionel Sambuc       unsigned LocalBaseMacroID = Record[1];
3309f4a2713aSLionel Sambuc       F.BaseMacroID = getTotalNumMacros();
3310f4a2713aSLionel Sambuc 
3311f4a2713aSLionel Sambuc       if (F.LocalNumMacros > 0) {
3312f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for macros within this module.
3313f4a2713aSLionel Sambuc         GlobalMacroMap.insert(std::make_pair(getTotalNumMacros() + 1, &F));
3314f4a2713aSLionel Sambuc 
3315f4a2713aSLionel Sambuc         // Introduce the local -> global mapping for macros within this module.
3316f4a2713aSLionel Sambuc         F.MacroRemap.insertOrReplace(
3317f4a2713aSLionel Sambuc           std::make_pair(LocalBaseMacroID,
3318f4a2713aSLionel Sambuc                          F.BaseMacroID - LocalBaseMacroID));
3319f4a2713aSLionel Sambuc 
3320f4a2713aSLionel Sambuc         MacrosLoaded.resize(MacrosLoaded.size() + F.LocalNumMacros);
3321f4a2713aSLionel Sambuc       }
3322f4a2713aSLionel Sambuc       break;
3323f4a2713aSLionel Sambuc     }
3324f4a2713aSLionel Sambuc 
3325f4a2713aSLionel Sambuc     case MACRO_TABLE: {
3326f4a2713aSLionel Sambuc       // FIXME: Not used yet.
3327f4a2713aSLionel Sambuc       break;
3328f4a2713aSLionel Sambuc     }
3329f4a2713aSLionel Sambuc 
3330f4a2713aSLionel Sambuc     case LATE_PARSED_TEMPLATE: {
3331f4a2713aSLionel Sambuc       LateParsedTemplates.append(Record.begin(), Record.end());
3332f4a2713aSLionel Sambuc       break;
3333f4a2713aSLionel Sambuc     }
3334*0a6a1f1dSLionel Sambuc 
3335*0a6a1f1dSLionel Sambuc     case OPTIMIZE_PRAGMA_OPTIONS:
3336*0a6a1f1dSLionel Sambuc       if (Record.size() != 1) {
3337*0a6a1f1dSLionel Sambuc         Error("invalid pragma optimize record");
3338*0a6a1f1dSLionel Sambuc         return Failure;
3339*0a6a1f1dSLionel Sambuc       }
3340*0a6a1f1dSLionel Sambuc       OptimizeOffPragmaLocation = ReadSourceLocation(F, Record[0]);
3341*0a6a1f1dSLionel Sambuc       break;
3342*0a6a1f1dSLionel Sambuc 
3343*0a6a1f1dSLionel Sambuc     case UNUSED_LOCAL_TYPEDEF_NAME_CANDIDATES:
3344*0a6a1f1dSLionel Sambuc       for (unsigned I = 0, N = Record.size(); I != N; ++I)
3345*0a6a1f1dSLionel Sambuc         UnusedLocalTypedefNameCandidates.push_back(
3346*0a6a1f1dSLionel Sambuc             getGlobalDeclID(F, Record[I]));
3347*0a6a1f1dSLionel Sambuc       break;
3348f4a2713aSLionel Sambuc     }
3349f4a2713aSLionel Sambuc   }
3350f4a2713aSLionel Sambuc }
3351f4a2713aSLionel Sambuc 
3352*0a6a1f1dSLionel Sambuc ASTReader::ASTReadResult
ReadModuleMapFileBlock(RecordData & Record,ModuleFile & F,const ModuleFile * ImportedBy,unsigned ClientLoadCapabilities)3353*0a6a1f1dSLionel Sambuc ASTReader::ReadModuleMapFileBlock(RecordData &Record, ModuleFile &F,
3354*0a6a1f1dSLionel Sambuc                                   const ModuleFile *ImportedBy,
3355*0a6a1f1dSLionel Sambuc                                   unsigned ClientLoadCapabilities) {
3356*0a6a1f1dSLionel Sambuc   unsigned Idx = 0;
3357*0a6a1f1dSLionel Sambuc   F.ModuleMapPath = ReadPath(F, Record, Idx);
3358*0a6a1f1dSLionel Sambuc 
3359*0a6a1f1dSLionel Sambuc   if (F.Kind == MK_ExplicitModule) {
3360*0a6a1f1dSLionel Sambuc     // For an explicitly-loaded module, we don't care whether the original
3361*0a6a1f1dSLionel Sambuc     // module map file exists or matches.
3362*0a6a1f1dSLionel Sambuc     return Success;
3363*0a6a1f1dSLionel Sambuc   }
3364*0a6a1f1dSLionel Sambuc 
3365*0a6a1f1dSLionel Sambuc   // Try to resolve ModuleName in the current header search context and
3366*0a6a1f1dSLionel Sambuc   // verify that it is found in the same module map file as we saved. If the
3367*0a6a1f1dSLionel Sambuc   // top-level AST file is a main file, skip this check because there is no
3368*0a6a1f1dSLionel Sambuc   // usable header search context.
3369*0a6a1f1dSLionel Sambuc   assert(!F.ModuleName.empty() &&
3370*0a6a1f1dSLionel Sambuc          "MODULE_NAME should come before MODULE_MAP_FILE");
3371*0a6a1f1dSLionel Sambuc   if (F.Kind == MK_ImplicitModule &&
3372*0a6a1f1dSLionel Sambuc       (*ModuleMgr.begin())->Kind != MK_MainFile) {
3373*0a6a1f1dSLionel Sambuc     // An implicitly-loaded module file should have its module listed in some
3374*0a6a1f1dSLionel Sambuc     // module map file that we've already loaded.
3375*0a6a1f1dSLionel Sambuc     Module *M = PP.getHeaderSearchInfo().lookupModule(F.ModuleName);
3376*0a6a1f1dSLionel Sambuc     auto &Map = PP.getHeaderSearchInfo().getModuleMap();
3377*0a6a1f1dSLionel Sambuc     const FileEntry *ModMap = M ? Map.getModuleMapFileForUniquing(M) : nullptr;
3378*0a6a1f1dSLionel Sambuc     if (!ModMap) {
3379*0a6a1f1dSLionel Sambuc       assert(ImportedBy && "top-level import should be verified");
3380*0a6a1f1dSLionel Sambuc       if ((ClientLoadCapabilities & ARR_Missing) == 0)
3381*0a6a1f1dSLionel Sambuc         Diag(diag::err_imported_module_not_found) << F.ModuleName << F.FileName
3382*0a6a1f1dSLionel Sambuc                                                   << ImportedBy->FileName
3383*0a6a1f1dSLionel Sambuc                                                   << F.ModuleMapPath;
3384*0a6a1f1dSLionel Sambuc       return Missing;
3385*0a6a1f1dSLionel Sambuc     }
3386*0a6a1f1dSLionel Sambuc 
3387*0a6a1f1dSLionel Sambuc     assert(M->Name == F.ModuleName && "found module with different name");
3388*0a6a1f1dSLionel Sambuc 
3389*0a6a1f1dSLionel Sambuc     // Check the primary module map file.
3390*0a6a1f1dSLionel Sambuc     const FileEntry *StoredModMap = FileMgr.getFile(F.ModuleMapPath);
3391*0a6a1f1dSLionel Sambuc     if (StoredModMap == nullptr || StoredModMap != ModMap) {
3392*0a6a1f1dSLionel Sambuc       assert(ModMap && "found module is missing module map file");
3393*0a6a1f1dSLionel Sambuc       assert(ImportedBy && "top-level import should be verified");
3394*0a6a1f1dSLionel Sambuc       if ((ClientLoadCapabilities & ARR_OutOfDate) == 0)
3395*0a6a1f1dSLionel Sambuc         Diag(diag::err_imported_module_modmap_changed)
3396*0a6a1f1dSLionel Sambuc           << F.ModuleName << ImportedBy->FileName
3397*0a6a1f1dSLionel Sambuc           << ModMap->getName() << F.ModuleMapPath;
3398*0a6a1f1dSLionel Sambuc       return OutOfDate;
3399*0a6a1f1dSLionel Sambuc     }
3400*0a6a1f1dSLionel Sambuc 
3401*0a6a1f1dSLionel Sambuc     llvm::SmallPtrSet<const FileEntry *, 1> AdditionalStoredMaps;
3402*0a6a1f1dSLionel Sambuc     for (unsigned I = 0, N = Record[Idx++]; I < N; ++I) {
3403*0a6a1f1dSLionel Sambuc       // FIXME: we should use input files rather than storing names.
3404*0a6a1f1dSLionel Sambuc       std::string Filename = ReadPath(F, Record, Idx);
3405*0a6a1f1dSLionel Sambuc       const FileEntry *F =
3406*0a6a1f1dSLionel Sambuc           FileMgr.getFile(Filename, false, false);
3407*0a6a1f1dSLionel Sambuc       if (F == nullptr) {
3408*0a6a1f1dSLionel Sambuc         if ((ClientLoadCapabilities & ARR_OutOfDate) == 0)
3409*0a6a1f1dSLionel Sambuc           Error("could not find file '" + Filename +"' referenced by AST file");
3410*0a6a1f1dSLionel Sambuc         return OutOfDate;
3411*0a6a1f1dSLionel Sambuc       }
3412*0a6a1f1dSLionel Sambuc       AdditionalStoredMaps.insert(F);
3413*0a6a1f1dSLionel Sambuc     }
3414*0a6a1f1dSLionel Sambuc 
3415*0a6a1f1dSLionel Sambuc     // Check any additional module map files (e.g. module.private.modulemap)
3416*0a6a1f1dSLionel Sambuc     // that are not in the pcm.
3417*0a6a1f1dSLionel Sambuc     if (auto *AdditionalModuleMaps = Map.getAdditionalModuleMapFiles(M)) {
3418*0a6a1f1dSLionel Sambuc       for (const FileEntry *ModMap : *AdditionalModuleMaps) {
3419*0a6a1f1dSLionel Sambuc         // Remove files that match
3420*0a6a1f1dSLionel Sambuc         // Note: SmallPtrSet::erase is really remove
3421*0a6a1f1dSLionel Sambuc         if (!AdditionalStoredMaps.erase(ModMap)) {
3422*0a6a1f1dSLionel Sambuc           if ((ClientLoadCapabilities & ARR_OutOfDate) == 0)
3423*0a6a1f1dSLionel Sambuc             Diag(diag::err_module_different_modmap)
3424*0a6a1f1dSLionel Sambuc               << F.ModuleName << /*new*/0 << ModMap->getName();
3425*0a6a1f1dSLionel Sambuc           return OutOfDate;
3426*0a6a1f1dSLionel Sambuc         }
3427*0a6a1f1dSLionel Sambuc       }
3428*0a6a1f1dSLionel Sambuc     }
3429*0a6a1f1dSLionel Sambuc 
3430*0a6a1f1dSLionel Sambuc     // Check any additional module map files that are in the pcm, but not
3431*0a6a1f1dSLionel Sambuc     // found in header search. Cases that match are already removed.
3432*0a6a1f1dSLionel Sambuc     for (const FileEntry *ModMap : AdditionalStoredMaps) {
3433*0a6a1f1dSLionel Sambuc       if ((ClientLoadCapabilities & ARR_OutOfDate) == 0)
3434*0a6a1f1dSLionel Sambuc         Diag(diag::err_module_different_modmap)
3435*0a6a1f1dSLionel Sambuc           << F.ModuleName << /*not new*/1 << ModMap->getName();
3436*0a6a1f1dSLionel Sambuc       return OutOfDate;
3437*0a6a1f1dSLionel Sambuc     }
3438*0a6a1f1dSLionel Sambuc   }
3439*0a6a1f1dSLionel Sambuc 
3440*0a6a1f1dSLionel Sambuc   if (Listener)
3441*0a6a1f1dSLionel Sambuc     Listener->ReadModuleMapFile(F.ModuleMapPath);
3442*0a6a1f1dSLionel Sambuc   return Success;
3443*0a6a1f1dSLionel Sambuc }
3444*0a6a1f1dSLionel Sambuc 
3445*0a6a1f1dSLionel Sambuc 
3446f4a2713aSLionel Sambuc /// \brief Move the given method to the back of the global list of methods.
moveMethodToBackOfGlobalList(Sema & S,ObjCMethodDecl * Method)3447f4a2713aSLionel Sambuc static void moveMethodToBackOfGlobalList(Sema &S, ObjCMethodDecl *Method) {
3448f4a2713aSLionel Sambuc   // Find the entry for this selector in the method pool.
3449f4a2713aSLionel Sambuc   Sema::GlobalMethodPool::iterator Known
3450f4a2713aSLionel Sambuc     = S.MethodPool.find(Method->getSelector());
3451f4a2713aSLionel Sambuc   if (Known == S.MethodPool.end())
3452f4a2713aSLionel Sambuc     return;
3453f4a2713aSLionel Sambuc 
3454f4a2713aSLionel Sambuc   // Retrieve the appropriate method list.
3455f4a2713aSLionel Sambuc   ObjCMethodList &Start = Method->isInstanceMethod()? Known->second.first
3456f4a2713aSLionel Sambuc                                                     : Known->second.second;
3457f4a2713aSLionel Sambuc   bool Found = false;
3458f4a2713aSLionel Sambuc   for (ObjCMethodList *List = &Start; List; List = List->getNext()) {
3459f4a2713aSLionel Sambuc     if (!Found) {
3460*0a6a1f1dSLionel Sambuc       if (List->getMethod() == Method) {
3461f4a2713aSLionel Sambuc         Found = true;
3462f4a2713aSLionel Sambuc       } else {
3463f4a2713aSLionel Sambuc         // Keep searching.
3464f4a2713aSLionel Sambuc         continue;
3465f4a2713aSLionel Sambuc       }
3466f4a2713aSLionel Sambuc     }
3467f4a2713aSLionel Sambuc 
3468f4a2713aSLionel Sambuc     if (List->getNext())
3469*0a6a1f1dSLionel Sambuc       List->setMethod(List->getNext()->getMethod());
3470f4a2713aSLionel Sambuc     else
3471*0a6a1f1dSLionel Sambuc       List->setMethod(Method);
3472f4a2713aSLionel Sambuc   }
3473f4a2713aSLionel Sambuc }
3474f4a2713aSLionel Sambuc 
makeNamesVisible(const HiddenNames & Names,Module * Owner,bool FromFinalization)3475*0a6a1f1dSLionel Sambuc void ASTReader::makeNamesVisible(const HiddenNames &Names, Module *Owner,
3476*0a6a1f1dSLionel Sambuc                                  bool FromFinalization) {
3477*0a6a1f1dSLionel Sambuc   // FIXME: Only do this if Owner->NameVisibility == AllVisible.
3478*0a6a1f1dSLionel Sambuc   for (Decl *D : Names.HiddenDecls) {
3479f4a2713aSLionel Sambuc     bool wasHidden = D->Hidden;
3480f4a2713aSLionel Sambuc     D->Hidden = false;
3481f4a2713aSLionel Sambuc 
3482f4a2713aSLionel Sambuc     if (wasHidden && SemaObj) {
3483f4a2713aSLionel Sambuc       if (ObjCMethodDecl *Method = dyn_cast<ObjCMethodDecl>(D)) {
3484f4a2713aSLionel Sambuc         moveMethodToBackOfGlobalList(*SemaObj, Method);
3485f4a2713aSLionel Sambuc       }
3486f4a2713aSLionel Sambuc     }
3487f4a2713aSLionel Sambuc   }
3488*0a6a1f1dSLionel Sambuc 
3489*0a6a1f1dSLionel Sambuc   assert((FromFinalization || Owner->NameVisibility >= Module::MacrosVisible) &&
3490*0a6a1f1dSLionel Sambuc          "nothing to make visible?");
3491*0a6a1f1dSLionel Sambuc   for (const auto &Macro : Names.HiddenMacros) {
3492*0a6a1f1dSLionel Sambuc     if (FromFinalization)
3493*0a6a1f1dSLionel Sambuc       PP.appendMacroDirective(Macro.first,
3494*0a6a1f1dSLionel Sambuc                               Macro.second->import(PP, SourceLocation()));
3495*0a6a1f1dSLionel Sambuc     else
3496f4a2713aSLionel Sambuc       installImportedMacro(Macro.first, Macro.second, Owner);
3497f4a2713aSLionel Sambuc   }
3498f4a2713aSLionel Sambuc }
3499f4a2713aSLionel Sambuc 
makeModuleVisible(Module * Mod,Module::NameVisibilityKind NameVisibility,SourceLocation ImportLoc,bool Complain)3500f4a2713aSLionel Sambuc void ASTReader::makeModuleVisible(Module *Mod,
3501f4a2713aSLionel Sambuc                                   Module::NameVisibilityKind NameVisibility,
3502f4a2713aSLionel Sambuc                                   SourceLocation ImportLoc,
3503f4a2713aSLionel Sambuc                                   bool Complain) {
3504f4a2713aSLionel Sambuc   llvm::SmallPtrSet<Module *, 4> Visited;
3505f4a2713aSLionel Sambuc   SmallVector<Module *, 4> Stack;
3506f4a2713aSLionel Sambuc   Stack.push_back(Mod);
3507f4a2713aSLionel Sambuc   while (!Stack.empty()) {
3508f4a2713aSLionel Sambuc     Mod = Stack.pop_back_val();
3509f4a2713aSLionel Sambuc 
3510f4a2713aSLionel Sambuc     if (NameVisibility <= Mod->NameVisibility) {
3511f4a2713aSLionel Sambuc       // This module already has this level of visibility (or greater), so
3512f4a2713aSLionel Sambuc       // there is nothing more to do.
3513f4a2713aSLionel Sambuc       continue;
3514f4a2713aSLionel Sambuc     }
3515f4a2713aSLionel Sambuc 
3516f4a2713aSLionel Sambuc     if (!Mod->isAvailable()) {
3517f4a2713aSLionel Sambuc       // Modules that aren't available cannot be made visible.
3518f4a2713aSLionel Sambuc       continue;
3519f4a2713aSLionel Sambuc     }
3520f4a2713aSLionel Sambuc 
3521f4a2713aSLionel Sambuc     // Update the module's name visibility.
3522*0a6a1f1dSLionel Sambuc     if (NameVisibility >= Module::MacrosVisible &&
3523*0a6a1f1dSLionel Sambuc         Mod->NameVisibility < Module::MacrosVisible)
3524*0a6a1f1dSLionel Sambuc       Mod->MacroVisibilityLoc = ImportLoc;
3525f4a2713aSLionel Sambuc     Mod->NameVisibility = NameVisibility;
3526f4a2713aSLionel Sambuc 
3527f4a2713aSLionel Sambuc     // If we've already deserialized any names from this module,
3528f4a2713aSLionel Sambuc     // mark them as visible.
3529f4a2713aSLionel Sambuc     HiddenNamesMapType::iterator Hidden = HiddenNamesMap.find(Mod);
3530f4a2713aSLionel Sambuc     if (Hidden != HiddenNamesMap.end()) {
3531*0a6a1f1dSLionel Sambuc       auto HiddenNames = std::move(*Hidden);
3532f4a2713aSLionel Sambuc       HiddenNamesMap.erase(Hidden);
3533*0a6a1f1dSLionel Sambuc       makeNamesVisible(HiddenNames.second, HiddenNames.first,
3534*0a6a1f1dSLionel Sambuc                        /*FromFinalization*/false);
3535*0a6a1f1dSLionel Sambuc       assert(HiddenNamesMap.find(Mod) == HiddenNamesMap.end() &&
3536*0a6a1f1dSLionel Sambuc              "making names visible added hidden names");
3537f4a2713aSLionel Sambuc     }
3538f4a2713aSLionel Sambuc 
3539f4a2713aSLionel Sambuc     // Push any exported modules onto the stack to be marked as visible.
3540f4a2713aSLionel Sambuc     SmallVector<Module *, 16> Exports;
3541f4a2713aSLionel Sambuc     Mod->getExportedModules(Exports);
3542f4a2713aSLionel Sambuc     for (SmallVectorImpl<Module *>::iterator
3543f4a2713aSLionel Sambuc            I = Exports.begin(), E = Exports.end(); I != E; ++I) {
3544f4a2713aSLionel Sambuc       Module *Exported = *I;
3545*0a6a1f1dSLionel Sambuc       if (Visited.insert(Exported).second)
3546f4a2713aSLionel Sambuc         Stack.push_back(Exported);
3547f4a2713aSLionel Sambuc     }
3548f4a2713aSLionel Sambuc 
3549f4a2713aSLionel Sambuc     // Detect any conflicts.
3550f4a2713aSLionel Sambuc     if (Complain) {
3551f4a2713aSLionel Sambuc       assert(ImportLoc.isValid() && "Missing import location");
3552f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Mod->Conflicts.size(); I != N; ++I) {
3553f4a2713aSLionel Sambuc         if (Mod->Conflicts[I].Other->NameVisibility >= NameVisibility) {
3554f4a2713aSLionel Sambuc           Diag(ImportLoc, diag::warn_module_conflict)
3555f4a2713aSLionel Sambuc             << Mod->getFullModuleName()
3556f4a2713aSLionel Sambuc             << Mod->Conflicts[I].Other->getFullModuleName()
3557f4a2713aSLionel Sambuc             << Mod->Conflicts[I].Message;
3558f4a2713aSLionel Sambuc           // FIXME: Need note where the other module was imported.
3559f4a2713aSLionel Sambuc         }
3560f4a2713aSLionel Sambuc       }
3561f4a2713aSLionel Sambuc     }
3562f4a2713aSLionel Sambuc   }
3563f4a2713aSLionel Sambuc }
3564f4a2713aSLionel Sambuc 
loadGlobalIndex()3565f4a2713aSLionel Sambuc bool ASTReader::loadGlobalIndex() {
3566f4a2713aSLionel Sambuc   if (GlobalIndex)
3567f4a2713aSLionel Sambuc     return false;
3568f4a2713aSLionel Sambuc 
3569f4a2713aSLionel Sambuc   if (TriedLoadingGlobalIndex || !UseGlobalIndex ||
3570f4a2713aSLionel Sambuc       !Context.getLangOpts().Modules)
3571f4a2713aSLionel Sambuc     return true;
3572f4a2713aSLionel Sambuc 
3573f4a2713aSLionel Sambuc   // Try to load the global index.
3574f4a2713aSLionel Sambuc   TriedLoadingGlobalIndex = true;
3575f4a2713aSLionel Sambuc   StringRef ModuleCachePath
3576f4a2713aSLionel Sambuc     = getPreprocessor().getHeaderSearchInfo().getModuleCachePath();
3577f4a2713aSLionel Sambuc   std::pair<GlobalModuleIndex *, GlobalModuleIndex::ErrorCode> Result
3578f4a2713aSLionel Sambuc     = GlobalModuleIndex::readIndex(ModuleCachePath);
3579f4a2713aSLionel Sambuc   if (!Result.first)
3580f4a2713aSLionel Sambuc     return true;
3581f4a2713aSLionel Sambuc 
3582f4a2713aSLionel Sambuc   GlobalIndex.reset(Result.first);
3583f4a2713aSLionel Sambuc   ModuleMgr.setGlobalIndex(GlobalIndex.get());
3584f4a2713aSLionel Sambuc   return false;
3585f4a2713aSLionel Sambuc }
3586f4a2713aSLionel Sambuc 
isGlobalIndexUnavailable() const3587f4a2713aSLionel Sambuc bool ASTReader::isGlobalIndexUnavailable() const {
3588f4a2713aSLionel Sambuc   return Context.getLangOpts().Modules && UseGlobalIndex &&
3589f4a2713aSLionel Sambuc          !hasGlobalIndex() && TriedLoadingGlobalIndex;
3590f4a2713aSLionel Sambuc }
3591f4a2713aSLionel Sambuc 
updateModuleTimestamp(ModuleFile & MF)3592*0a6a1f1dSLionel Sambuc static void updateModuleTimestamp(ModuleFile &MF) {
3593*0a6a1f1dSLionel Sambuc   // Overwrite the timestamp file contents so that file's mtime changes.
3594*0a6a1f1dSLionel Sambuc   std::string TimestampFilename = MF.getTimestampFilename();
3595*0a6a1f1dSLionel Sambuc   std::error_code EC;
3596*0a6a1f1dSLionel Sambuc   llvm::raw_fd_ostream OS(TimestampFilename, EC, llvm::sys::fs::F_Text);
3597*0a6a1f1dSLionel Sambuc   if (EC)
3598*0a6a1f1dSLionel Sambuc     return;
3599*0a6a1f1dSLionel Sambuc   OS << "Timestamp file\n";
3600*0a6a1f1dSLionel Sambuc }
3601*0a6a1f1dSLionel Sambuc 
ReadAST(const std::string & FileName,ModuleKind Type,SourceLocation ImportLoc,unsigned ClientLoadCapabilities)3602f4a2713aSLionel Sambuc ASTReader::ASTReadResult ASTReader::ReadAST(const std::string &FileName,
3603f4a2713aSLionel Sambuc                                             ModuleKind Type,
3604f4a2713aSLionel Sambuc                                             SourceLocation ImportLoc,
3605f4a2713aSLionel Sambuc                                             unsigned ClientLoadCapabilities) {
3606f4a2713aSLionel Sambuc   llvm::SaveAndRestore<SourceLocation>
3607f4a2713aSLionel Sambuc     SetCurImportLocRAII(CurrentImportLoc, ImportLoc);
3608f4a2713aSLionel Sambuc 
3609*0a6a1f1dSLionel Sambuc   // Defer any pending actions until we get to the end of reading the AST file.
3610*0a6a1f1dSLionel Sambuc   Deserializing AnASTFile(this);
3611*0a6a1f1dSLionel Sambuc 
3612f4a2713aSLionel Sambuc   // Bump the generation number.
3613*0a6a1f1dSLionel Sambuc   unsigned PreviousGeneration = incrementGeneration(Context);
3614f4a2713aSLionel Sambuc 
3615f4a2713aSLionel Sambuc   unsigned NumModules = ModuleMgr.size();
3616f4a2713aSLionel Sambuc   SmallVector<ImportedModule, 4> Loaded;
3617f4a2713aSLionel Sambuc   switch(ASTReadResult ReadResult = ReadASTCore(FileName, Type, ImportLoc,
3618*0a6a1f1dSLionel Sambuc                                                 /*ImportedBy=*/nullptr, Loaded,
3619*0a6a1f1dSLionel Sambuc                                                 0, 0, 0,
3620f4a2713aSLionel Sambuc                                                 ClientLoadCapabilities)) {
3621f4a2713aSLionel Sambuc   case Failure:
3622f4a2713aSLionel Sambuc   case Missing:
3623f4a2713aSLionel Sambuc   case OutOfDate:
3624f4a2713aSLionel Sambuc   case VersionMismatch:
3625f4a2713aSLionel Sambuc   case ConfigurationMismatch:
3626*0a6a1f1dSLionel Sambuc   case HadErrors: {
3627*0a6a1f1dSLionel Sambuc     llvm::SmallPtrSet<ModuleFile *, 4> LoadedSet;
3628*0a6a1f1dSLionel Sambuc     for (const ImportedModule &IM : Loaded)
3629*0a6a1f1dSLionel Sambuc       LoadedSet.insert(IM.Mod);
3630*0a6a1f1dSLionel Sambuc 
3631f4a2713aSLionel Sambuc     ModuleMgr.removeModules(ModuleMgr.begin() + NumModules, ModuleMgr.end(),
3632*0a6a1f1dSLionel Sambuc                             LoadedSet,
3633f4a2713aSLionel Sambuc                             Context.getLangOpts().Modules
3634f4a2713aSLionel Sambuc                               ? &PP.getHeaderSearchInfo().getModuleMap()
3635*0a6a1f1dSLionel Sambuc                               : nullptr);
3636f4a2713aSLionel Sambuc 
3637f4a2713aSLionel Sambuc     // If we find that any modules are unusable, the global index is going
3638f4a2713aSLionel Sambuc     // to be out-of-date. Just remove it.
3639f4a2713aSLionel Sambuc     GlobalIndex.reset();
3640*0a6a1f1dSLionel Sambuc     ModuleMgr.setGlobalIndex(nullptr);
3641f4a2713aSLionel Sambuc     return ReadResult;
3642*0a6a1f1dSLionel Sambuc   }
3643f4a2713aSLionel Sambuc   case Success:
3644f4a2713aSLionel Sambuc     break;
3645f4a2713aSLionel Sambuc   }
3646f4a2713aSLionel Sambuc 
3647f4a2713aSLionel Sambuc   // Here comes stuff that we only do once the entire chain is loaded.
3648f4a2713aSLionel Sambuc 
3649f4a2713aSLionel Sambuc   // Load the AST blocks of all of the modules that we loaded.
3650f4a2713aSLionel Sambuc   for (SmallVectorImpl<ImportedModule>::iterator M = Loaded.begin(),
3651f4a2713aSLionel Sambuc                                               MEnd = Loaded.end();
3652f4a2713aSLionel Sambuc        M != MEnd; ++M) {
3653f4a2713aSLionel Sambuc     ModuleFile &F = *M->Mod;
3654f4a2713aSLionel Sambuc 
3655f4a2713aSLionel Sambuc     // Read the AST block.
3656*0a6a1f1dSLionel Sambuc     if (ASTReadResult Result = ReadASTBlock(F, ClientLoadCapabilities))
3657*0a6a1f1dSLionel Sambuc       return Result;
3658f4a2713aSLionel Sambuc 
3659f4a2713aSLionel Sambuc     // Once read, set the ModuleFile bit base offset and update the size in
3660f4a2713aSLionel Sambuc     // bits of all files we've seen.
3661f4a2713aSLionel Sambuc     F.GlobalBitOffset = TotalModulesSizeInBits;
3662f4a2713aSLionel Sambuc     TotalModulesSizeInBits += F.SizeInBits;
3663f4a2713aSLionel Sambuc     GlobalBitOffsetsMap.insert(std::make_pair(F.GlobalBitOffset, &F));
3664f4a2713aSLionel Sambuc 
3665f4a2713aSLionel Sambuc     // Preload SLocEntries.
3666f4a2713aSLionel Sambuc     for (unsigned I = 0, N = F.PreloadSLocEntries.size(); I != N; ++I) {
3667f4a2713aSLionel Sambuc       int Index = int(F.PreloadSLocEntries[I] - 1) + F.SLocEntryBaseID;
3668f4a2713aSLionel Sambuc       // Load it through the SourceManager and don't call ReadSLocEntry()
3669f4a2713aSLionel Sambuc       // directly because the entry may have already been loaded in which case
3670f4a2713aSLionel Sambuc       // calling ReadSLocEntry() directly would trigger an assertion in
3671f4a2713aSLionel Sambuc       // SourceManager.
3672f4a2713aSLionel Sambuc       SourceMgr.getLoadedSLocEntryByID(Index);
3673f4a2713aSLionel Sambuc     }
3674f4a2713aSLionel Sambuc   }
3675f4a2713aSLionel Sambuc 
3676f4a2713aSLionel Sambuc   // Setup the import locations and notify the module manager that we've
3677f4a2713aSLionel Sambuc   // committed to these module files.
3678f4a2713aSLionel Sambuc   for (SmallVectorImpl<ImportedModule>::iterator M = Loaded.begin(),
3679f4a2713aSLionel Sambuc                                               MEnd = Loaded.end();
3680f4a2713aSLionel Sambuc        M != MEnd; ++M) {
3681f4a2713aSLionel Sambuc     ModuleFile &F = *M->Mod;
3682f4a2713aSLionel Sambuc 
3683f4a2713aSLionel Sambuc     ModuleMgr.moduleFileAccepted(&F);
3684f4a2713aSLionel Sambuc 
3685f4a2713aSLionel Sambuc     // Set the import location.
3686f4a2713aSLionel Sambuc     F.DirectImportLoc = ImportLoc;
3687f4a2713aSLionel Sambuc     if (!M->ImportedBy)
3688f4a2713aSLionel Sambuc       F.ImportLoc = M->ImportLoc;
3689f4a2713aSLionel Sambuc     else
3690f4a2713aSLionel Sambuc       F.ImportLoc = ReadSourceLocation(*M->ImportedBy,
3691f4a2713aSLionel Sambuc                                        M->ImportLoc.getRawEncoding());
3692f4a2713aSLionel Sambuc   }
3693f4a2713aSLionel Sambuc 
3694f4a2713aSLionel Sambuc   // Mark all of the identifiers in the identifier table as being out of date,
3695f4a2713aSLionel Sambuc   // so that various accessors know to check the loaded modules when the
3696f4a2713aSLionel Sambuc   // identifier is used.
3697f4a2713aSLionel Sambuc   for (IdentifierTable::iterator Id = PP.getIdentifierTable().begin(),
3698f4a2713aSLionel Sambuc                               IdEnd = PP.getIdentifierTable().end();
3699f4a2713aSLionel Sambuc        Id != IdEnd; ++Id)
3700f4a2713aSLionel Sambuc     Id->second->setOutOfDate(true);
3701f4a2713aSLionel Sambuc 
3702f4a2713aSLionel Sambuc   // Resolve any unresolved module exports.
3703f4a2713aSLionel Sambuc   for (unsigned I = 0, N = UnresolvedModuleRefs.size(); I != N; ++I) {
3704f4a2713aSLionel Sambuc     UnresolvedModuleRef &Unresolved = UnresolvedModuleRefs[I];
3705f4a2713aSLionel Sambuc     SubmoduleID GlobalID = getGlobalSubmoduleID(*Unresolved.File,Unresolved.ID);
3706f4a2713aSLionel Sambuc     Module *ResolvedMod = getSubmodule(GlobalID);
3707f4a2713aSLionel Sambuc 
3708f4a2713aSLionel Sambuc     switch (Unresolved.Kind) {
3709f4a2713aSLionel Sambuc     case UnresolvedModuleRef::Conflict:
3710f4a2713aSLionel Sambuc       if (ResolvedMod) {
3711f4a2713aSLionel Sambuc         Module::Conflict Conflict;
3712f4a2713aSLionel Sambuc         Conflict.Other = ResolvedMod;
3713f4a2713aSLionel Sambuc         Conflict.Message = Unresolved.String.str();
3714f4a2713aSLionel Sambuc         Unresolved.Mod->Conflicts.push_back(Conflict);
3715f4a2713aSLionel Sambuc       }
3716f4a2713aSLionel Sambuc       continue;
3717f4a2713aSLionel Sambuc 
3718f4a2713aSLionel Sambuc     case UnresolvedModuleRef::Import:
3719f4a2713aSLionel Sambuc       if (ResolvedMod)
3720f4a2713aSLionel Sambuc         Unresolved.Mod->Imports.push_back(ResolvedMod);
3721f4a2713aSLionel Sambuc       continue;
3722f4a2713aSLionel Sambuc 
3723f4a2713aSLionel Sambuc     case UnresolvedModuleRef::Export:
3724f4a2713aSLionel Sambuc       if (ResolvedMod || Unresolved.IsWildcard)
3725f4a2713aSLionel Sambuc         Unresolved.Mod->Exports.push_back(
3726f4a2713aSLionel Sambuc           Module::ExportDecl(ResolvedMod, Unresolved.IsWildcard));
3727f4a2713aSLionel Sambuc       continue;
3728f4a2713aSLionel Sambuc     }
3729f4a2713aSLionel Sambuc   }
3730f4a2713aSLionel Sambuc   UnresolvedModuleRefs.clear();
3731f4a2713aSLionel Sambuc 
3732f4a2713aSLionel Sambuc   // FIXME: How do we load the 'use'd modules? They may not be submodules.
3733f4a2713aSLionel Sambuc   // Might be unnecessary as use declarations are only used to build the
3734f4a2713aSLionel Sambuc   // module itself.
3735f4a2713aSLionel Sambuc 
3736f4a2713aSLionel Sambuc   InitializeContext();
3737f4a2713aSLionel Sambuc 
3738f4a2713aSLionel Sambuc   if (SemaObj)
3739f4a2713aSLionel Sambuc     UpdateSema();
3740f4a2713aSLionel Sambuc 
3741f4a2713aSLionel Sambuc   if (DeserializationListener)
3742f4a2713aSLionel Sambuc     DeserializationListener->ReaderInitialized(this);
3743f4a2713aSLionel Sambuc 
3744f4a2713aSLionel Sambuc   ModuleFile &PrimaryModule = ModuleMgr.getPrimaryModule();
3745f4a2713aSLionel Sambuc   if (!PrimaryModule.OriginalSourceFileID.isInvalid()) {
3746f4a2713aSLionel Sambuc     PrimaryModule.OriginalSourceFileID
3747f4a2713aSLionel Sambuc       = FileID::get(PrimaryModule.SLocEntryBaseID
3748f4a2713aSLionel Sambuc                     + PrimaryModule.OriginalSourceFileID.getOpaqueValue() - 1);
3749f4a2713aSLionel Sambuc 
3750f4a2713aSLionel Sambuc     // If this AST file is a precompiled preamble, then set the
3751f4a2713aSLionel Sambuc     // preamble file ID of the source manager to the file source file
3752f4a2713aSLionel Sambuc     // from which the preamble was built.
3753f4a2713aSLionel Sambuc     if (Type == MK_Preamble) {
3754f4a2713aSLionel Sambuc       SourceMgr.setPreambleFileID(PrimaryModule.OriginalSourceFileID);
3755f4a2713aSLionel Sambuc     } else if (Type == MK_MainFile) {
3756f4a2713aSLionel Sambuc       SourceMgr.setMainFileID(PrimaryModule.OriginalSourceFileID);
3757f4a2713aSLionel Sambuc     }
3758f4a2713aSLionel Sambuc   }
3759f4a2713aSLionel Sambuc 
3760f4a2713aSLionel Sambuc   // For any Objective-C class definitions we have already loaded, make sure
3761f4a2713aSLionel Sambuc   // that we load any additional categories.
3762f4a2713aSLionel Sambuc   for (unsigned I = 0, N = ObjCClassesLoaded.size(); I != N; ++I) {
3763f4a2713aSLionel Sambuc     loadObjCCategories(ObjCClassesLoaded[I]->getGlobalID(),
3764f4a2713aSLionel Sambuc                        ObjCClassesLoaded[I],
3765f4a2713aSLionel Sambuc                        PreviousGeneration);
3766f4a2713aSLionel Sambuc   }
3767f4a2713aSLionel Sambuc 
3768*0a6a1f1dSLionel Sambuc   if (PP.getHeaderSearchInfo()
3769*0a6a1f1dSLionel Sambuc           .getHeaderSearchOpts()
3770*0a6a1f1dSLionel Sambuc           .ModulesValidateOncePerBuildSession) {
3771*0a6a1f1dSLionel Sambuc     // Now we are certain that the module and all modules it depends on are
3772*0a6a1f1dSLionel Sambuc     // up to date.  Create or update timestamp files for modules that are
3773*0a6a1f1dSLionel Sambuc     // located in the module cache (not for PCH files that could be anywhere
3774*0a6a1f1dSLionel Sambuc     // in the filesystem).
3775*0a6a1f1dSLionel Sambuc     for (unsigned I = 0, N = Loaded.size(); I != N; ++I) {
3776*0a6a1f1dSLionel Sambuc       ImportedModule &M = Loaded[I];
3777*0a6a1f1dSLionel Sambuc       if (M.Mod->Kind == MK_ImplicitModule) {
3778*0a6a1f1dSLionel Sambuc         updateModuleTimestamp(*M.Mod);
3779*0a6a1f1dSLionel Sambuc       }
3780*0a6a1f1dSLionel Sambuc     }
3781*0a6a1f1dSLionel Sambuc   }
3782*0a6a1f1dSLionel Sambuc 
3783f4a2713aSLionel Sambuc   return Success;
3784f4a2713aSLionel Sambuc }
3785f4a2713aSLionel Sambuc 
3786*0a6a1f1dSLionel Sambuc static ASTFileSignature readASTFileSignature(llvm::BitstreamReader &StreamFile);
3787*0a6a1f1dSLionel Sambuc 
3788f4a2713aSLionel Sambuc ASTReader::ASTReadResult
ReadASTCore(StringRef FileName,ModuleKind Type,SourceLocation ImportLoc,ModuleFile * ImportedBy,SmallVectorImpl<ImportedModule> & Loaded,off_t ExpectedSize,time_t ExpectedModTime,ASTFileSignature ExpectedSignature,unsigned ClientLoadCapabilities)3789f4a2713aSLionel Sambuc ASTReader::ReadASTCore(StringRef FileName,
3790f4a2713aSLionel Sambuc                        ModuleKind Type,
3791f4a2713aSLionel Sambuc                        SourceLocation ImportLoc,
3792f4a2713aSLionel Sambuc                        ModuleFile *ImportedBy,
3793f4a2713aSLionel Sambuc                        SmallVectorImpl<ImportedModule> &Loaded,
3794f4a2713aSLionel Sambuc                        off_t ExpectedSize, time_t ExpectedModTime,
3795*0a6a1f1dSLionel Sambuc                        ASTFileSignature ExpectedSignature,
3796f4a2713aSLionel Sambuc                        unsigned ClientLoadCapabilities) {
3797f4a2713aSLionel Sambuc   ModuleFile *M;
3798f4a2713aSLionel Sambuc   std::string ErrorStr;
3799f4a2713aSLionel Sambuc   ModuleManager::AddModuleResult AddResult
3800f4a2713aSLionel Sambuc     = ModuleMgr.addModule(FileName, Type, ImportLoc, ImportedBy,
3801*0a6a1f1dSLionel Sambuc                           getGeneration(), ExpectedSize, ExpectedModTime,
3802*0a6a1f1dSLionel Sambuc                           ExpectedSignature, readASTFileSignature,
3803f4a2713aSLionel Sambuc                           M, ErrorStr);
3804f4a2713aSLionel Sambuc 
3805f4a2713aSLionel Sambuc   switch (AddResult) {
3806f4a2713aSLionel Sambuc   case ModuleManager::AlreadyLoaded:
3807f4a2713aSLionel Sambuc     return Success;
3808f4a2713aSLionel Sambuc 
3809f4a2713aSLionel Sambuc   case ModuleManager::NewlyLoaded:
3810f4a2713aSLionel Sambuc     // Load module file below.
3811f4a2713aSLionel Sambuc     break;
3812f4a2713aSLionel Sambuc 
3813f4a2713aSLionel Sambuc   case ModuleManager::Missing:
3814*0a6a1f1dSLionel Sambuc     // The module file was missing; if the client can handle that, return
3815f4a2713aSLionel Sambuc     // it.
3816f4a2713aSLionel Sambuc     if (ClientLoadCapabilities & ARR_Missing)
3817f4a2713aSLionel Sambuc       return Missing;
3818f4a2713aSLionel Sambuc 
3819f4a2713aSLionel Sambuc     // Otherwise, return an error.
3820f4a2713aSLionel Sambuc     {
3821f4a2713aSLionel Sambuc       std::string Msg = "Unable to load module \"" + FileName.str() + "\": "
3822f4a2713aSLionel Sambuc                       + ErrorStr;
3823f4a2713aSLionel Sambuc       Error(Msg);
3824f4a2713aSLionel Sambuc     }
3825f4a2713aSLionel Sambuc     return Failure;
3826f4a2713aSLionel Sambuc 
3827f4a2713aSLionel Sambuc   case ModuleManager::OutOfDate:
3828f4a2713aSLionel Sambuc     // We couldn't load the module file because it is out-of-date. If the
3829f4a2713aSLionel Sambuc     // client can handle out-of-date, return it.
3830f4a2713aSLionel Sambuc     if (ClientLoadCapabilities & ARR_OutOfDate)
3831f4a2713aSLionel Sambuc       return OutOfDate;
3832f4a2713aSLionel Sambuc 
3833f4a2713aSLionel Sambuc     // Otherwise, return an error.
3834f4a2713aSLionel Sambuc     {
3835f4a2713aSLionel Sambuc       std::string Msg = "Unable to load module \"" + FileName.str() + "\": "
3836f4a2713aSLionel Sambuc                       + ErrorStr;
3837f4a2713aSLionel Sambuc       Error(Msg);
3838f4a2713aSLionel Sambuc     }
3839f4a2713aSLionel Sambuc     return Failure;
3840f4a2713aSLionel Sambuc   }
3841f4a2713aSLionel Sambuc 
3842f4a2713aSLionel Sambuc   assert(M && "Missing module file");
3843f4a2713aSLionel Sambuc 
3844f4a2713aSLionel Sambuc   // FIXME: This seems rather a hack. Should CurrentDir be part of the
3845f4a2713aSLionel Sambuc   // module?
3846f4a2713aSLionel Sambuc   if (FileName != "-") {
3847f4a2713aSLionel Sambuc     CurrentDir = llvm::sys::path::parent_path(FileName);
3848f4a2713aSLionel Sambuc     if (CurrentDir.empty()) CurrentDir = ".";
3849f4a2713aSLionel Sambuc   }
3850f4a2713aSLionel Sambuc 
3851f4a2713aSLionel Sambuc   ModuleFile &F = *M;
3852f4a2713aSLionel Sambuc   BitstreamCursor &Stream = F.Stream;
3853*0a6a1f1dSLionel Sambuc   Stream.init(&F.StreamFile);
3854f4a2713aSLionel Sambuc   F.SizeInBits = F.Buffer->getBufferSize() * 8;
3855f4a2713aSLionel Sambuc 
3856f4a2713aSLionel Sambuc   // Sniff for the signature.
3857f4a2713aSLionel Sambuc   if (Stream.Read(8) != 'C' ||
3858f4a2713aSLionel Sambuc       Stream.Read(8) != 'P' ||
3859f4a2713aSLionel Sambuc       Stream.Read(8) != 'C' ||
3860f4a2713aSLionel Sambuc       Stream.Read(8) != 'H') {
3861f4a2713aSLionel Sambuc     Diag(diag::err_not_a_pch_file) << FileName;
3862f4a2713aSLionel Sambuc     return Failure;
3863f4a2713aSLionel Sambuc   }
3864f4a2713aSLionel Sambuc 
3865f4a2713aSLionel Sambuc   // This is used for compatibility with older PCH formats.
3866f4a2713aSLionel Sambuc   bool HaveReadControlBlock = false;
3867f4a2713aSLionel Sambuc 
3868f4a2713aSLionel Sambuc   while (1) {
3869f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = Stream.advance();
3870f4a2713aSLionel Sambuc 
3871f4a2713aSLionel Sambuc     switch (Entry.Kind) {
3872f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Error:
3873f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::EndBlock:
3874f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Record:
3875f4a2713aSLionel Sambuc       Error("invalid record at top-level of AST file");
3876f4a2713aSLionel Sambuc       return Failure;
3877f4a2713aSLionel Sambuc 
3878f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::SubBlock:
3879f4a2713aSLionel Sambuc       break;
3880f4a2713aSLionel Sambuc     }
3881f4a2713aSLionel Sambuc 
3882f4a2713aSLionel Sambuc     // We only know the control subblock ID.
3883f4a2713aSLionel Sambuc     switch (Entry.ID) {
3884f4a2713aSLionel Sambuc     case llvm::bitc::BLOCKINFO_BLOCK_ID:
3885f4a2713aSLionel Sambuc       if (Stream.ReadBlockInfoBlock()) {
3886f4a2713aSLionel Sambuc         Error("malformed BlockInfoBlock in AST file");
3887f4a2713aSLionel Sambuc         return Failure;
3888f4a2713aSLionel Sambuc       }
3889f4a2713aSLionel Sambuc       break;
3890f4a2713aSLionel Sambuc     case CONTROL_BLOCK_ID:
3891f4a2713aSLionel Sambuc       HaveReadControlBlock = true;
3892*0a6a1f1dSLionel Sambuc       switch (ReadControlBlock(F, Loaded, ImportedBy, ClientLoadCapabilities)) {
3893f4a2713aSLionel Sambuc       case Success:
3894f4a2713aSLionel Sambuc         break;
3895f4a2713aSLionel Sambuc 
3896f4a2713aSLionel Sambuc       case Failure: return Failure;
3897f4a2713aSLionel Sambuc       case Missing: return Missing;
3898f4a2713aSLionel Sambuc       case OutOfDate: return OutOfDate;
3899f4a2713aSLionel Sambuc       case VersionMismatch: return VersionMismatch;
3900f4a2713aSLionel Sambuc       case ConfigurationMismatch: return ConfigurationMismatch;
3901f4a2713aSLionel Sambuc       case HadErrors: return HadErrors;
3902f4a2713aSLionel Sambuc       }
3903f4a2713aSLionel Sambuc       break;
3904f4a2713aSLionel Sambuc     case AST_BLOCK_ID:
3905f4a2713aSLionel Sambuc       if (!HaveReadControlBlock) {
3906f4a2713aSLionel Sambuc         if ((ClientLoadCapabilities & ARR_VersionMismatch) == 0)
3907*0a6a1f1dSLionel Sambuc           Diag(diag::err_pch_version_too_old);
3908f4a2713aSLionel Sambuc         return VersionMismatch;
3909f4a2713aSLionel Sambuc       }
3910f4a2713aSLionel Sambuc 
3911f4a2713aSLionel Sambuc       // Record that we've loaded this module.
3912f4a2713aSLionel Sambuc       Loaded.push_back(ImportedModule(M, ImportedBy, ImportLoc));
3913f4a2713aSLionel Sambuc       return Success;
3914f4a2713aSLionel Sambuc 
3915f4a2713aSLionel Sambuc     default:
3916f4a2713aSLionel Sambuc       if (Stream.SkipBlock()) {
3917f4a2713aSLionel Sambuc         Error("malformed block record in AST file");
3918f4a2713aSLionel Sambuc         return Failure;
3919f4a2713aSLionel Sambuc       }
3920f4a2713aSLionel Sambuc       break;
3921f4a2713aSLionel Sambuc     }
3922f4a2713aSLionel Sambuc   }
3923f4a2713aSLionel Sambuc 
3924f4a2713aSLionel Sambuc   return Success;
3925f4a2713aSLionel Sambuc }
3926f4a2713aSLionel Sambuc 
InitializeContext()3927f4a2713aSLionel Sambuc void ASTReader::InitializeContext() {
3928f4a2713aSLionel Sambuc   // If there's a listener, notify them that we "read" the translation unit.
3929f4a2713aSLionel Sambuc   if (DeserializationListener)
3930f4a2713aSLionel Sambuc     DeserializationListener->DeclRead(PREDEF_DECL_TRANSLATION_UNIT_ID,
3931f4a2713aSLionel Sambuc                                       Context.getTranslationUnitDecl());
3932f4a2713aSLionel Sambuc 
3933f4a2713aSLionel Sambuc   // FIXME: Find a better way to deal with collisions between these
3934f4a2713aSLionel Sambuc   // built-in types. Right now, we just ignore the problem.
3935f4a2713aSLionel Sambuc 
3936f4a2713aSLionel Sambuc   // Load the special types.
3937f4a2713aSLionel Sambuc   if (SpecialTypes.size() >= NumSpecialTypeIDs) {
3938f4a2713aSLionel Sambuc     if (unsigned String = SpecialTypes[SPECIAL_TYPE_CF_CONSTANT_STRING]) {
3939f4a2713aSLionel Sambuc       if (!Context.CFConstantStringTypeDecl)
3940f4a2713aSLionel Sambuc         Context.setCFConstantStringType(GetType(String));
3941f4a2713aSLionel Sambuc     }
3942f4a2713aSLionel Sambuc 
3943f4a2713aSLionel Sambuc     if (unsigned File = SpecialTypes[SPECIAL_TYPE_FILE]) {
3944f4a2713aSLionel Sambuc       QualType FileType = GetType(File);
3945f4a2713aSLionel Sambuc       if (FileType.isNull()) {
3946f4a2713aSLionel Sambuc         Error("FILE type is NULL");
3947f4a2713aSLionel Sambuc         return;
3948f4a2713aSLionel Sambuc       }
3949f4a2713aSLionel Sambuc 
3950f4a2713aSLionel Sambuc       if (!Context.FILEDecl) {
3951f4a2713aSLionel Sambuc         if (const TypedefType *Typedef = FileType->getAs<TypedefType>())
3952f4a2713aSLionel Sambuc           Context.setFILEDecl(Typedef->getDecl());
3953f4a2713aSLionel Sambuc         else {
3954f4a2713aSLionel Sambuc           const TagType *Tag = FileType->getAs<TagType>();
3955f4a2713aSLionel Sambuc           if (!Tag) {
3956f4a2713aSLionel Sambuc             Error("Invalid FILE type in AST file");
3957f4a2713aSLionel Sambuc             return;
3958f4a2713aSLionel Sambuc           }
3959f4a2713aSLionel Sambuc           Context.setFILEDecl(Tag->getDecl());
3960f4a2713aSLionel Sambuc         }
3961f4a2713aSLionel Sambuc       }
3962f4a2713aSLionel Sambuc     }
3963f4a2713aSLionel Sambuc 
3964f4a2713aSLionel Sambuc     if (unsigned Jmp_buf = SpecialTypes[SPECIAL_TYPE_JMP_BUF]) {
3965f4a2713aSLionel Sambuc       QualType Jmp_bufType = GetType(Jmp_buf);
3966f4a2713aSLionel Sambuc       if (Jmp_bufType.isNull()) {
3967f4a2713aSLionel Sambuc         Error("jmp_buf type is NULL");
3968f4a2713aSLionel Sambuc         return;
3969f4a2713aSLionel Sambuc       }
3970f4a2713aSLionel Sambuc 
3971f4a2713aSLionel Sambuc       if (!Context.jmp_bufDecl) {
3972f4a2713aSLionel Sambuc         if (const TypedefType *Typedef = Jmp_bufType->getAs<TypedefType>())
3973f4a2713aSLionel Sambuc           Context.setjmp_bufDecl(Typedef->getDecl());
3974f4a2713aSLionel Sambuc         else {
3975f4a2713aSLionel Sambuc           const TagType *Tag = Jmp_bufType->getAs<TagType>();
3976f4a2713aSLionel Sambuc           if (!Tag) {
3977f4a2713aSLionel Sambuc             Error("Invalid jmp_buf type in AST file");
3978f4a2713aSLionel Sambuc             return;
3979f4a2713aSLionel Sambuc           }
3980f4a2713aSLionel Sambuc           Context.setjmp_bufDecl(Tag->getDecl());
3981f4a2713aSLionel Sambuc         }
3982f4a2713aSLionel Sambuc       }
3983f4a2713aSLionel Sambuc     }
3984f4a2713aSLionel Sambuc 
3985f4a2713aSLionel Sambuc     if (unsigned Sigjmp_buf = SpecialTypes[SPECIAL_TYPE_SIGJMP_BUF]) {
3986f4a2713aSLionel Sambuc       QualType Sigjmp_bufType = GetType(Sigjmp_buf);
3987f4a2713aSLionel Sambuc       if (Sigjmp_bufType.isNull()) {
3988f4a2713aSLionel Sambuc         Error("sigjmp_buf type is NULL");
3989f4a2713aSLionel Sambuc         return;
3990f4a2713aSLionel Sambuc       }
3991f4a2713aSLionel Sambuc 
3992f4a2713aSLionel Sambuc       if (!Context.sigjmp_bufDecl) {
3993f4a2713aSLionel Sambuc         if (const TypedefType *Typedef = Sigjmp_bufType->getAs<TypedefType>())
3994f4a2713aSLionel Sambuc           Context.setsigjmp_bufDecl(Typedef->getDecl());
3995f4a2713aSLionel Sambuc         else {
3996f4a2713aSLionel Sambuc           const TagType *Tag = Sigjmp_bufType->getAs<TagType>();
3997f4a2713aSLionel Sambuc           assert(Tag && "Invalid sigjmp_buf type in AST file");
3998f4a2713aSLionel Sambuc           Context.setsigjmp_bufDecl(Tag->getDecl());
3999f4a2713aSLionel Sambuc         }
4000f4a2713aSLionel Sambuc       }
4001f4a2713aSLionel Sambuc     }
4002f4a2713aSLionel Sambuc 
4003f4a2713aSLionel Sambuc     if (unsigned ObjCIdRedef
4004f4a2713aSLionel Sambuc           = SpecialTypes[SPECIAL_TYPE_OBJC_ID_REDEFINITION]) {
4005f4a2713aSLionel Sambuc       if (Context.ObjCIdRedefinitionType.isNull())
4006f4a2713aSLionel Sambuc         Context.ObjCIdRedefinitionType = GetType(ObjCIdRedef);
4007f4a2713aSLionel Sambuc     }
4008f4a2713aSLionel Sambuc 
4009f4a2713aSLionel Sambuc     if (unsigned ObjCClassRedef
4010f4a2713aSLionel Sambuc           = SpecialTypes[SPECIAL_TYPE_OBJC_CLASS_REDEFINITION]) {
4011f4a2713aSLionel Sambuc       if (Context.ObjCClassRedefinitionType.isNull())
4012f4a2713aSLionel Sambuc         Context.ObjCClassRedefinitionType = GetType(ObjCClassRedef);
4013f4a2713aSLionel Sambuc     }
4014f4a2713aSLionel Sambuc 
4015f4a2713aSLionel Sambuc     if (unsigned ObjCSelRedef
4016f4a2713aSLionel Sambuc           = SpecialTypes[SPECIAL_TYPE_OBJC_SEL_REDEFINITION]) {
4017f4a2713aSLionel Sambuc       if (Context.ObjCSelRedefinitionType.isNull())
4018f4a2713aSLionel Sambuc         Context.ObjCSelRedefinitionType = GetType(ObjCSelRedef);
4019f4a2713aSLionel Sambuc     }
4020f4a2713aSLionel Sambuc 
4021f4a2713aSLionel Sambuc     if (unsigned Ucontext_t = SpecialTypes[SPECIAL_TYPE_UCONTEXT_T]) {
4022f4a2713aSLionel Sambuc       QualType Ucontext_tType = GetType(Ucontext_t);
4023f4a2713aSLionel Sambuc       if (Ucontext_tType.isNull()) {
4024f4a2713aSLionel Sambuc         Error("ucontext_t type is NULL");
4025f4a2713aSLionel Sambuc         return;
4026f4a2713aSLionel Sambuc       }
4027f4a2713aSLionel Sambuc 
4028f4a2713aSLionel Sambuc       if (!Context.ucontext_tDecl) {
4029f4a2713aSLionel Sambuc         if (const TypedefType *Typedef = Ucontext_tType->getAs<TypedefType>())
4030f4a2713aSLionel Sambuc           Context.setucontext_tDecl(Typedef->getDecl());
4031f4a2713aSLionel Sambuc         else {
4032f4a2713aSLionel Sambuc           const TagType *Tag = Ucontext_tType->getAs<TagType>();
4033f4a2713aSLionel Sambuc           assert(Tag && "Invalid ucontext_t type in AST file");
4034f4a2713aSLionel Sambuc           Context.setucontext_tDecl(Tag->getDecl());
4035f4a2713aSLionel Sambuc         }
4036f4a2713aSLionel Sambuc       }
4037f4a2713aSLionel Sambuc     }
4038f4a2713aSLionel Sambuc   }
4039f4a2713aSLionel Sambuc 
4040f4a2713aSLionel Sambuc   ReadPragmaDiagnosticMappings(Context.getDiagnostics());
4041f4a2713aSLionel Sambuc 
4042f4a2713aSLionel Sambuc   // If there were any CUDA special declarations, deserialize them.
4043f4a2713aSLionel Sambuc   if (!CUDASpecialDeclRefs.empty()) {
4044f4a2713aSLionel Sambuc     assert(CUDASpecialDeclRefs.size() == 1 && "More decl refs than expected!");
4045f4a2713aSLionel Sambuc     Context.setcudaConfigureCallDecl(
4046f4a2713aSLionel Sambuc                            cast<FunctionDecl>(GetDecl(CUDASpecialDeclRefs[0])));
4047f4a2713aSLionel Sambuc   }
4048f4a2713aSLionel Sambuc 
4049f4a2713aSLionel Sambuc   // Re-export any modules that were imported by a non-module AST file.
4050*0a6a1f1dSLionel Sambuc   // FIXME: This does not make macro-only imports visible again. It also doesn't
4051*0a6a1f1dSLionel Sambuc   // make #includes mapped to module imports visible.
4052*0a6a1f1dSLionel Sambuc   for (auto &Import : ImportedModules) {
4053*0a6a1f1dSLionel Sambuc     if (Module *Imported = getSubmodule(Import.ID))
4054f4a2713aSLionel Sambuc       makeModuleVisible(Imported, Module::AllVisible,
4055*0a6a1f1dSLionel Sambuc                         /*ImportLoc=*/Import.ImportLoc,
4056f4a2713aSLionel Sambuc                         /*Complain=*/false);
4057f4a2713aSLionel Sambuc   }
4058f4a2713aSLionel Sambuc   ImportedModules.clear();
4059f4a2713aSLionel Sambuc }
4060f4a2713aSLionel Sambuc 
finalizeForWriting()4061f4a2713aSLionel Sambuc void ASTReader::finalizeForWriting() {
4062*0a6a1f1dSLionel Sambuc   while (!HiddenNamesMap.empty()) {
4063*0a6a1f1dSLionel Sambuc     auto HiddenNames = std::move(*HiddenNamesMap.begin());
4064*0a6a1f1dSLionel Sambuc     HiddenNamesMap.erase(HiddenNamesMap.begin());
4065*0a6a1f1dSLionel Sambuc     makeNamesVisible(HiddenNames.second, HiddenNames.first,
4066*0a6a1f1dSLionel Sambuc                      /*FromFinalization*/true);
4067f4a2713aSLionel Sambuc   }
4068f4a2713aSLionel Sambuc }
4069f4a2713aSLionel Sambuc 
4070f4a2713aSLionel Sambuc /// \brief Given a cursor at the start of an AST file, scan ahead and drop the
4071f4a2713aSLionel Sambuc /// cursor into the start of the given block ID, returning false on success and
4072f4a2713aSLionel Sambuc /// true on failure.
SkipCursorToBlock(BitstreamCursor & Cursor,unsigned BlockID)4073f4a2713aSLionel Sambuc static bool SkipCursorToBlock(BitstreamCursor &Cursor, unsigned BlockID) {
4074f4a2713aSLionel Sambuc   while (1) {
4075f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = Cursor.advance();
4076f4a2713aSLionel Sambuc     switch (Entry.Kind) {
4077f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Error:
4078f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::EndBlock:
4079f4a2713aSLionel Sambuc       return true;
4080f4a2713aSLionel Sambuc 
4081f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Record:
4082f4a2713aSLionel Sambuc       // Ignore top-level records.
4083f4a2713aSLionel Sambuc       Cursor.skipRecord(Entry.ID);
4084f4a2713aSLionel Sambuc       break;
4085f4a2713aSLionel Sambuc 
4086f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::SubBlock:
4087f4a2713aSLionel Sambuc       if (Entry.ID == BlockID) {
4088f4a2713aSLionel Sambuc         if (Cursor.EnterSubBlock(BlockID))
4089f4a2713aSLionel Sambuc           return true;
4090f4a2713aSLionel Sambuc         // Found it!
4091f4a2713aSLionel Sambuc         return false;
4092f4a2713aSLionel Sambuc       }
4093f4a2713aSLionel Sambuc 
4094f4a2713aSLionel Sambuc       if (Cursor.SkipBlock())
4095f4a2713aSLionel Sambuc         return true;
4096f4a2713aSLionel Sambuc     }
4097f4a2713aSLionel Sambuc   }
4098f4a2713aSLionel Sambuc }
4099f4a2713aSLionel Sambuc 
readASTFileSignature(llvm::BitstreamReader & StreamFile)4100*0a6a1f1dSLionel Sambuc static ASTFileSignature readASTFileSignature(llvm::BitstreamReader &StreamFile){
4101*0a6a1f1dSLionel Sambuc   BitstreamCursor Stream(StreamFile);
4102*0a6a1f1dSLionel Sambuc   if (Stream.Read(8) != 'C' ||
4103*0a6a1f1dSLionel Sambuc       Stream.Read(8) != 'P' ||
4104*0a6a1f1dSLionel Sambuc       Stream.Read(8) != 'C' ||
4105*0a6a1f1dSLionel Sambuc       Stream.Read(8) != 'H') {
4106*0a6a1f1dSLionel Sambuc     return 0;
4107*0a6a1f1dSLionel Sambuc   }
4108*0a6a1f1dSLionel Sambuc 
4109*0a6a1f1dSLionel Sambuc   // Scan for the CONTROL_BLOCK_ID block.
4110*0a6a1f1dSLionel Sambuc   if (SkipCursorToBlock(Stream, CONTROL_BLOCK_ID))
4111*0a6a1f1dSLionel Sambuc     return 0;
4112*0a6a1f1dSLionel Sambuc 
4113*0a6a1f1dSLionel Sambuc   // Scan for SIGNATURE inside the control block.
4114*0a6a1f1dSLionel Sambuc   ASTReader::RecordData Record;
4115*0a6a1f1dSLionel Sambuc   while (1) {
4116*0a6a1f1dSLionel Sambuc     llvm::BitstreamEntry Entry = Stream.advanceSkippingSubblocks();
4117*0a6a1f1dSLionel Sambuc     if (Entry.Kind == llvm::BitstreamEntry::EndBlock ||
4118*0a6a1f1dSLionel Sambuc         Entry.Kind != llvm::BitstreamEntry::Record)
4119*0a6a1f1dSLionel Sambuc       return 0;
4120*0a6a1f1dSLionel Sambuc 
4121*0a6a1f1dSLionel Sambuc     Record.clear();
4122*0a6a1f1dSLionel Sambuc     StringRef Blob;
4123*0a6a1f1dSLionel Sambuc     if (SIGNATURE == Stream.readRecord(Entry.ID, Record, &Blob))
4124*0a6a1f1dSLionel Sambuc       return Record[0];
4125*0a6a1f1dSLionel Sambuc   }
4126*0a6a1f1dSLionel Sambuc }
4127*0a6a1f1dSLionel Sambuc 
4128f4a2713aSLionel Sambuc /// \brief Retrieve the name of the original source file name
4129f4a2713aSLionel Sambuc /// directly from the AST file, without actually loading the AST
4130f4a2713aSLionel Sambuc /// file.
getOriginalSourceFile(const std::string & ASTFileName,FileManager & FileMgr,DiagnosticsEngine & Diags)4131f4a2713aSLionel Sambuc std::string ASTReader::getOriginalSourceFile(const std::string &ASTFileName,
4132f4a2713aSLionel Sambuc                                              FileManager &FileMgr,
4133f4a2713aSLionel Sambuc                                              DiagnosticsEngine &Diags) {
4134f4a2713aSLionel Sambuc   // Open the AST file.
4135*0a6a1f1dSLionel Sambuc   auto Buffer = FileMgr.getBufferForFile(ASTFileName);
4136f4a2713aSLionel Sambuc   if (!Buffer) {
4137*0a6a1f1dSLionel Sambuc     Diags.Report(diag::err_fe_unable_to_read_pch_file)
4138*0a6a1f1dSLionel Sambuc         << ASTFileName << Buffer.getError().message();
4139f4a2713aSLionel Sambuc     return std::string();
4140f4a2713aSLionel Sambuc   }
4141f4a2713aSLionel Sambuc 
4142f4a2713aSLionel Sambuc   // Initialize the stream
4143f4a2713aSLionel Sambuc   llvm::BitstreamReader StreamFile;
4144*0a6a1f1dSLionel Sambuc   StreamFile.init((const unsigned char *)(*Buffer)->getBufferStart(),
4145*0a6a1f1dSLionel Sambuc                   (const unsigned char *)(*Buffer)->getBufferEnd());
4146*0a6a1f1dSLionel Sambuc   BitstreamCursor Stream(StreamFile);
4147f4a2713aSLionel Sambuc 
4148f4a2713aSLionel Sambuc   // Sniff for the signature.
4149f4a2713aSLionel Sambuc   if (Stream.Read(8) != 'C' ||
4150f4a2713aSLionel Sambuc       Stream.Read(8) != 'P' ||
4151f4a2713aSLionel Sambuc       Stream.Read(8) != 'C' ||
4152f4a2713aSLionel Sambuc       Stream.Read(8) != 'H') {
4153f4a2713aSLionel Sambuc     Diags.Report(diag::err_fe_not_a_pch_file) << ASTFileName;
4154f4a2713aSLionel Sambuc     return std::string();
4155f4a2713aSLionel Sambuc   }
4156f4a2713aSLionel Sambuc 
4157f4a2713aSLionel Sambuc   // Scan for the CONTROL_BLOCK_ID block.
4158f4a2713aSLionel Sambuc   if (SkipCursorToBlock(Stream, CONTROL_BLOCK_ID)) {
4159f4a2713aSLionel Sambuc     Diags.Report(diag::err_fe_pch_malformed_block) << ASTFileName;
4160f4a2713aSLionel Sambuc     return std::string();
4161f4a2713aSLionel Sambuc   }
4162f4a2713aSLionel Sambuc 
4163f4a2713aSLionel Sambuc   // Scan for ORIGINAL_FILE inside the control block.
4164f4a2713aSLionel Sambuc   RecordData Record;
4165f4a2713aSLionel Sambuc   while (1) {
4166f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = Stream.advanceSkippingSubblocks();
4167f4a2713aSLionel Sambuc     if (Entry.Kind == llvm::BitstreamEntry::EndBlock)
4168f4a2713aSLionel Sambuc       return std::string();
4169f4a2713aSLionel Sambuc 
4170f4a2713aSLionel Sambuc     if (Entry.Kind != llvm::BitstreamEntry::Record) {
4171f4a2713aSLionel Sambuc       Diags.Report(diag::err_fe_pch_malformed_block) << ASTFileName;
4172f4a2713aSLionel Sambuc       return std::string();
4173f4a2713aSLionel Sambuc     }
4174f4a2713aSLionel Sambuc 
4175f4a2713aSLionel Sambuc     Record.clear();
4176f4a2713aSLionel Sambuc     StringRef Blob;
4177f4a2713aSLionel Sambuc     if (Stream.readRecord(Entry.ID, Record, &Blob) == ORIGINAL_FILE)
4178f4a2713aSLionel Sambuc       return Blob.str();
4179f4a2713aSLionel Sambuc   }
4180f4a2713aSLionel Sambuc }
4181f4a2713aSLionel Sambuc 
4182f4a2713aSLionel Sambuc namespace {
4183f4a2713aSLionel Sambuc   class SimplePCHValidator : public ASTReaderListener {
4184f4a2713aSLionel Sambuc     const LangOptions &ExistingLangOpts;
4185f4a2713aSLionel Sambuc     const TargetOptions &ExistingTargetOpts;
4186f4a2713aSLionel Sambuc     const PreprocessorOptions &ExistingPPOpts;
4187f4a2713aSLionel Sambuc     FileManager &FileMgr;
4188f4a2713aSLionel Sambuc 
4189f4a2713aSLionel Sambuc   public:
SimplePCHValidator(const LangOptions & ExistingLangOpts,const TargetOptions & ExistingTargetOpts,const PreprocessorOptions & ExistingPPOpts,FileManager & FileMgr)4190f4a2713aSLionel Sambuc     SimplePCHValidator(const LangOptions &ExistingLangOpts,
4191f4a2713aSLionel Sambuc                        const TargetOptions &ExistingTargetOpts,
4192f4a2713aSLionel Sambuc                        const PreprocessorOptions &ExistingPPOpts,
4193f4a2713aSLionel Sambuc                        FileManager &FileMgr)
4194f4a2713aSLionel Sambuc       : ExistingLangOpts(ExistingLangOpts),
4195f4a2713aSLionel Sambuc         ExistingTargetOpts(ExistingTargetOpts),
4196f4a2713aSLionel Sambuc         ExistingPPOpts(ExistingPPOpts),
4197f4a2713aSLionel Sambuc         FileMgr(FileMgr)
4198f4a2713aSLionel Sambuc     {
4199f4a2713aSLionel Sambuc     }
4200f4a2713aSLionel Sambuc 
ReadLanguageOptions(const LangOptions & LangOpts,bool Complain,bool AllowCompatibleDifferences)4201*0a6a1f1dSLionel Sambuc     bool ReadLanguageOptions(const LangOptions &LangOpts, bool Complain,
4202*0a6a1f1dSLionel Sambuc                              bool AllowCompatibleDifferences) override {
4203*0a6a1f1dSLionel Sambuc       return checkLanguageOptions(ExistingLangOpts, LangOpts, nullptr,
4204*0a6a1f1dSLionel Sambuc                                   AllowCompatibleDifferences);
4205f4a2713aSLionel Sambuc     }
ReadTargetOptions(const TargetOptions & TargetOpts,bool Complain)4206*0a6a1f1dSLionel Sambuc     bool ReadTargetOptions(const TargetOptions &TargetOpts,
4207*0a6a1f1dSLionel Sambuc                            bool Complain) override {
4208*0a6a1f1dSLionel Sambuc       return checkTargetOptions(ExistingTargetOpts, TargetOpts, nullptr);
4209f4a2713aSLionel Sambuc     }
ReadPreprocessorOptions(const PreprocessorOptions & PPOpts,bool Complain,std::string & SuggestedPredefines)4210*0a6a1f1dSLionel Sambuc     bool ReadPreprocessorOptions(const PreprocessorOptions &PPOpts,
4211f4a2713aSLionel Sambuc                                  bool Complain,
4212*0a6a1f1dSLionel Sambuc                                  std::string &SuggestedPredefines) override {
4213*0a6a1f1dSLionel Sambuc       return checkPreprocessorOptions(ExistingPPOpts, PPOpts, nullptr, FileMgr,
4214f4a2713aSLionel Sambuc                                       SuggestedPredefines, ExistingLangOpts);
4215f4a2713aSLionel Sambuc     }
4216f4a2713aSLionel Sambuc   };
4217f4a2713aSLionel Sambuc }
4218f4a2713aSLionel Sambuc 
readASTFileControlBlock(StringRef Filename,FileManager & FileMgr,ASTReaderListener & Listener)4219f4a2713aSLionel Sambuc bool ASTReader::readASTFileControlBlock(StringRef Filename,
4220f4a2713aSLionel Sambuc                                         FileManager &FileMgr,
4221f4a2713aSLionel Sambuc                                         ASTReaderListener &Listener) {
4222f4a2713aSLionel Sambuc   // Open the AST file.
4223*0a6a1f1dSLionel Sambuc   auto Buffer = FileMgr.getBufferForFile(Filename);
4224f4a2713aSLionel Sambuc   if (!Buffer) {
4225f4a2713aSLionel Sambuc     return true;
4226f4a2713aSLionel Sambuc   }
4227f4a2713aSLionel Sambuc 
4228f4a2713aSLionel Sambuc   // Initialize the stream
4229f4a2713aSLionel Sambuc   llvm::BitstreamReader StreamFile;
4230*0a6a1f1dSLionel Sambuc   StreamFile.init((const unsigned char *)(*Buffer)->getBufferStart(),
4231*0a6a1f1dSLionel Sambuc                   (const unsigned char *)(*Buffer)->getBufferEnd());
4232*0a6a1f1dSLionel Sambuc   BitstreamCursor Stream(StreamFile);
4233f4a2713aSLionel Sambuc 
4234f4a2713aSLionel Sambuc   // Sniff for the signature.
4235f4a2713aSLionel Sambuc   if (Stream.Read(8) != 'C' ||
4236f4a2713aSLionel Sambuc       Stream.Read(8) != 'P' ||
4237f4a2713aSLionel Sambuc       Stream.Read(8) != 'C' ||
4238f4a2713aSLionel Sambuc       Stream.Read(8) != 'H') {
4239f4a2713aSLionel Sambuc     return true;
4240f4a2713aSLionel Sambuc   }
4241f4a2713aSLionel Sambuc 
4242f4a2713aSLionel Sambuc   // Scan for the CONTROL_BLOCK_ID block.
4243f4a2713aSLionel Sambuc   if (SkipCursorToBlock(Stream, CONTROL_BLOCK_ID))
4244f4a2713aSLionel Sambuc     return true;
4245f4a2713aSLionel Sambuc 
4246f4a2713aSLionel Sambuc   bool NeedsInputFiles = Listener.needsInputFileVisitation();
4247*0a6a1f1dSLionel Sambuc   bool NeedsSystemInputFiles = Listener.needsSystemInputFileVisitation();
4248*0a6a1f1dSLionel Sambuc   bool NeedsImports = Listener.needsImportVisitation();
4249f4a2713aSLionel Sambuc   BitstreamCursor InputFilesCursor;
4250f4a2713aSLionel Sambuc   if (NeedsInputFiles) {
4251f4a2713aSLionel Sambuc     InputFilesCursor = Stream;
4252f4a2713aSLionel Sambuc     if (SkipCursorToBlock(InputFilesCursor, INPUT_FILES_BLOCK_ID))
4253f4a2713aSLionel Sambuc       return true;
4254f4a2713aSLionel Sambuc 
4255f4a2713aSLionel Sambuc     // Read the abbreviations
4256f4a2713aSLionel Sambuc     while (true) {
4257f4a2713aSLionel Sambuc       uint64_t Offset = InputFilesCursor.GetCurrentBitNo();
4258f4a2713aSLionel Sambuc       unsigned Code = InputFilesCursor.ReadCode();
4259f4a2713aSLionel Sambuc 
4260f4a2713aSLionel Sambuc       // We expect all abbrevs to be at the start of the block.
4261f4a2713aSLionel Sambuc       if (Code != llvm::bitc::DEFINE_ABBREV) {
4262f4a2713aSLionel Sambuc         InputFilesCursor.JumpToBit(Offset);
4263f4a2713aSLionel Sambuc         break;
4264f4a2713aSLionel Sambuc       }
4265f4a2713aSLionel Sambuc       InputFilesCursor.ReadAbbrevRecord();
4266f4a2713aSLionel Sambuc     }
4267f4a2713aSLionel Sambuc   }
4268f4a2713aSLionel Sambuc 
4269f4a2713aSLionel Sambuc   // Scan for ORIGINAL_FILE inside the control block.
4270f4a2713aSLionel Sambuc   RecordData Record;
4271*0a6a1f1dSLionel Sambuc   std::string ModuleDir;
4272f4a2713aSLionel Sambuc   while (1) {
4273f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = Stream.advanceSkippingSubblocks();
4274f4a2713aSLionel Sambuc     if (Entry.Kind == llvm::BitstreamEntry::EndBlock)
4275f4a2713aSLionel Sambuc       return false;
4276f4a2713aSLionel Sambuc 
4277f4a2713aSLionel Sambuc     if (Entry.Kind != llvm::BitstreamEntry::Record)
4278f4a2713aSLionel Sambuc       return true;
4279f4a2713aSLionel Sambuc 
4280f4a2713aSLionel Sambuc     Record.clear();
4281f4a2713aSLionel Sambuc     StringRef Blob;
4282f4a2713aSLionel Sambuc     unsigned RecCode = Stream.readRecord(Entry.ID, Record, &Blob);
4283f4a2713aSLionel Sambuc     switch ((ControlRecordTypes)RecCode) {
4284f4a2713aSLionel Sambuc     case METADATA: {
4285f4a2713aSLionel Sambuc       if (Record[0] != VERSION_MAJOR)
4286f4a2713aSLionel Sambuc         return true;
4287f4a2713aSLionel Sambuc 
4288f4a2713aSLionel Sambuc       if (Listener.ReadFullVersionInformation(Blob))
4289f4a2713aSLionel Sambuc         return true;
4290f4a2713aSLionel Sambuc 
4291f4a2713aSLionel Sambuc       break;
4292f4a2713aSLionel Sambuc     }
4293*0a6a1f1dSLionel Sambuc     case MODULE_NAME:
4294*0a6a1f1dSLionel Sambuc       Listener.ReadModuleName(Blob);
4295*0a6a1f1dSLionel Sambuc       break;
4296*0a6a1f1dSLionel Sambuc     case MODULE_DIRECTORY:
4297*0a6a1f1dSLionel Sambuc       ModuleDir = Blob;
4298*0a6a1f1dSLionel Sambuc       break;
4299*0a6a1f1dSLionel Sambuc     case MODULE_MAP_FILE: {
4300*0a6a1f1dSLionel Sambuc       unsigned Idx = 0;
4301*0a6a1f1dSLionel Sambuc       auto Path = ReadString(Record, Idx);
4302*0a6a1f1dSLionel Sambuc       ResolveImportedPath(Path, ModuleDir);
4303*0a6a1f1dSLionel Sambuc       Listener.ReadModuleMapFile(Path);
4304*0a6a1f1dSLionel Sambuc       break;
4305*0a6a1f1dSLionel Sambuc     }
4306f4a2713aSLionel Sambuc     case LANGUAGE_OPTIONS:
4307*0a6a1f1dSLionel Sambuc       if (ParseLanguageOptions(Record, false, Listener,
4308*0a6a1f1dSLionel Sambuc                                /*AllowCompatibleConfigurationMismatch*/false))
4309f4a2713aSLionel Sambuc         return true;
4310f4a2713aSLionel Sambuc       break;
4311f4a2713aSLionel Sambuc 
4312f4a2713aSLionel Sambuc     case TARGET_OPTIONS:
4313f4a2713aSLionel Sambuc       if (ParseTargetOptions(Record, false, Listener))
4314f4a2713aSLionel Sambuc         return true;
4315f4a2713aSLionel Sambuc       break;
4316f4a2713aSLionel Sambuc 
4317f4a2713aSLionel Sambuc     case DIAGNOSTIC_OPTIONS:
4318f4a2713aSLionel Sambuc       if (ParseDiagnosticOptions(Record, false, Listener))
4319f4a2713aSLionel Sambuc         return true;
4320f4a2713aSLionel Sambuc       break;
4321f4a2713aSLionel Sambuc 
4322f4a2713aSLionel Sambuc     case FILE_SYSTEM_OPTIONS:
4323f4a2713aSLionel Sambuc       if (ParseFileSystemOptions(Record, false, Listener))
4324f4a2713aSLionel Sambuc         return true;
4325f4a2713aSLionel Sambuc       break;
4326f4a2713aSLionel Sambuc 
4327f4a2713aSLionel Sambuc     case HEADER_SEARCH_OPTIONS:
4328f4a2713aSLionel Sambuc       if (ParseHeaderSearchOptions(Record, false, Listener))
4329f4a2713aSLionel Sambuc         return true;
4330f4a2713aSLionel Sambuc       break;
4331f4a2713aSLionel Sambuc 
4332f4a2713aSLionel Sambuc     case PREPROCESSOR_OPTIONS: {
4333f4a2713aSLionel Sambuc       std::string IgnoredSuggestedPredefines;
4334f4a2713aSLionel Sambuc       if (ParsePreprocessorOptions(Record, false, Listener,
4335f4a2713aSLionel Sambuc                                    IgnoredSuggestedPredefines))
4336f4a2713aSLionel Sambuc         return true;
4337f4a2713aSLionel Sambuc       break;
4338f4a2713aSLionel Sambuc     }
4339f4a2713aSLionel Sambuc 
4340f4a2713aSLionel Sambuc     case INPUT_FILE_OFFSETS: {
4341f4a2713aSLionel Sambuc       if (!NeedsInputFiles)
4342f4a2713aSLionel Sambuc         break;
4343f4a2713aSLionel Sambuc 
4344f4a2713aSLionel Sambuc       unsigned NumInputFiles = Record[0];
4345f4a2713aSLionel Sambuc       unsigned NumUserFiles = Record[1];
4346f4a2713aSLionel Sambuc       const uint32_t *InputFileOffs = (const uint32_t *)Blob.data();
4347f4a2713aSLionel Sambuc       for (unsigned I = 0; I != NumInputFiles; ++I) {
4348f4a2713aSLionel Sambuc         // Go find this input file.
4349f4a2713aSLionel Sambuc         bool isSystemFile = I >= NumUserFiles;
4350*0a6a1f1dSLionel Sambuc 
4351*0a6a1f1dSLionel Sambuc         if (isSystemFile && !NeedsSystemInputFiles)
4352*0a6a1f1dSLionel Sambuc           break; // the rest are system input files
4353*0a6a1f1dSLionel Sambuc 
4354f4a2713aSLionel Sambuc         BitstreamCursor &Cursor = InputFilesCursor;
4355f4a2713aSLionel Sambuc         SavedStreamPosition SavedPosition(Cursor);
4356f4a2713aSLionel Sambuc         Cursor.JumpToBit(InputFileOffs[I]);
4357f4a2713aSLionel Sambuc 
4358f4a2713aSLionel Sambuc         unsigned Code = Cursor.ReadCode();
4359f4a2713aSLionel Sambuc         RecordData Record;
4360f4a2713aSLionel Sambuc         StringRef Blob;
4361f4a2713aSLionel Sambuc         bool shouldContinue = false;
4362f4a2713aSLionel Sambuc         switch ((InputFileRecordTypes)Cursor.readRecord(Code, Record, &Blob)) {
4363f4a2713aSLionel Sambuc         case INPUT_FILE:
4364*0a6a1f1dSLionel Sambuc           bool Overridden = static_cast<bool>(Record[3]);
4365*0a6a1f1dSLionel Sambuc           std::string Filename = Blob;
4366*0a6a1f1dSLionel Sambuc           ResolveImportedPath(Filename, ModuleDir);
4367*0a6a1f1dSLionel Sambuc           shouldContinue =
4368*0a6a1f1dSLionel Sambuc               Listener.visitInputFile(Filename, isSystemFile, Overridden);
4369f4a2713aSLionel Sambuc           break;
4370f4a2713aSLionel Sambuc         }
4371f4a2713aSLionel Sambuc         if (!shouldContinue)
4372f4a2713aSLionel Sambuc           break;
4373f4a2713aSLionel Sambuc       }
4374f4a2713aSLionel Sambuc       break;
4375f4a2713aSLionel Sambuc     }
4376f4a2713aSLionel Sambuc 
4377*0a6a1f1dSLionel Sambuc     case IMPORTS: {
4378*0a6a1f1dSLionel Sambuc       if (!NeedsImports)
4379*0a6a1f1dSLionel Sambuc         break;
4380*0a6a1f1dSLionel Sambuc 
4381*0a6a1f1dSLionel Sambuc       unsigned Idx = 0, N = Record.size();
4382*0a6a1f1dSLionel Sambuc       while (Idx < N) {
4383*0a6a1f1dSLionel Sambuc         // Read information about the AST file.
4384*0a6a1f1dSLionel Sambuc         Idx += 5; // ImportLoc, Size, ModTime, Signature
4385*0a6a1f1dSLionel Sambuc         std::string Filename = ReadString(Record, Idx);
4386*0a6a1f1dSLionel Sambuc         ResolveImportedPath(Filename, ModuleDir);
4387*0a6a1f1dSLionel Sambuc         Listener.visitImport(Filename);
4388*0a6a1f1dSLionel Sambuc       }
4389*0a6a1f1dSLionel Sambuc       break;
4390*0a6a1f1dSLionel Sambuc     }
4391*0a6a1f1dSLionel Sambuc 
4392f4a2713aSLionel Sambuc     default:
4393f4a2713aSLionel Sambuc       // No other validation to perform.
4394f4a2713aSLionel Sambuc       break;
4395f4a2713aSLionel Sambuc     }
4396f4a2713aSLionel Sambuc   }
4397f4a2713aSLionel Sambuc }
4398f4a2713aSLionel Sambuc 
4399f4a2713aSLionel Sambuc 
isAcceptableASTFile(StringRef Filename,FileManager & FileMgr,const LangOptions & LangOpts,const TargetOptions & TargetOpts,const PreprocessorOptions & PPOpts)4400f4a2713aSLionel Sambuc bool ASTReader::isAcceptableASTFile(StringRef Filename,
4401f4a2713aSLionel Sambuc                                     FileManager &FileMgr,
4402f4a2713aSLionel Sambuc                                     const LangOptions &LangOpts,
4403f4a2713aSLionel Sambuc                                     const TargetOptions &TargetOpts,
4404f4a2713aSLionel Sambuc                                     const PreprocessorOptions &PPOpts) {
4405f4a2713aSLionel Sambuc   SimplePCHValidator validator(LangOpts, TargetOpts, PPOpts, FileMgr);
4406f4a2713aSLionel Sambuc   return !readASTFileControlBlock(Filename, FileMgr, validator);
4407f4a2713aSLionel Sambuc }
4408f4a2713aSLionel Sambuc 
4409*0a6a1f1dSLionel Sambuc ASTReader::ASTReadResult
ReadSubmoduleBlock(ModuleFile & F,unsigned ClientLoadCapabilities)4410*0a6a1f1dSLionel Sambuc ASTReader::ReadSubmoduleBlock(ModuleFile &F, unsigned ClientLoadCapabilities) {
4411f4a2713aSLionel Sambuc   // Enter the submodule block.
4412f4a2713aSLionel Sambuc   if (F.Stream.EnterSubBlock(SUBMODULE_BLOCK_ID)) {
4413f4a2713aSLionel Sambuc     Error("malformed submodule block record in AST file");
4414*0a6a1f1dSLionel Sambuc     return Failure;
4415f4a2713aSLionel Sambuc   }
4416f4a2713aSLionel Sambuc 
4417f4a2713aSLionel Sambuc   ModuleMap &ModMap = PP.getHeaderSearchInfo().getModuleMap();
4418f4a2713aSLionel Sambuc   bool First = true;
4419*0a6a1f1dSLionel Sambuc   Module *CurrentModule = nullptr;
4420f4a2713aSLionel Sambuc   RecordData Record;
4421f4a2713aSLionel Sambuc   while (true) {
4422f4a2713aSLionel Sambuc     llvm::BitstreamEntry Entry = F.Stream.advanceSkippingSubblocks();
4423f4a2713aSLionel Sambuc 
4424f4a2713aSLionel Sambuc     switch (Entry.Kind) {
4425f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::SubBlock: // Handled for us already.
4426f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Error:
4427f4a2713aSLionel Sambuc       Error("malformed block record in AST file");
4428*0a6a1f1dSLionel Sambuc       return Failure;
4429f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::EndBlock:
4430*0a6a1f1dSLionel Sambuc       return Success;
4431f4a2713aSLionel Sambuc     case llvm::BitstreamEntry::Record:
4432f4a2713aSLionel Sambuc       // The interesting case.
4433f4a2713aSLionel Sambuc       break;
4434f4a2713aSLionel Sambuc     }
4435f4a2713aSLionel Sambuc 
4436f4a2713aSLionel Sambuc     // Read a record.
4437f4a2713aSLionel Sambuc     StringRef Blob;
4438f4a2713aSLionel Sambuc     Record.clear();
4439*0a6a1f1dSLionel Sambuc     auto Kind = F.Stream.readRecord(Entry.ID, Record, &Blob);
4440*0a6a1f1dSLionel Sambuc 
4441*0a6a1f1dSLionel Sambuc     if ((Kind == SUBMODULE_METADATA) != First) {
4442*0a6a1f1dSLionel Sambuc       Error("submodule metadata record should be at beginning of block");
4443*0a6a1f1dSLionel Sambuc       return Failure;
4444*0a6a1f1dSLionel Sambuc     }
4445*0a6a1f1dSLionel Sambuc     First = false;
4446*0a6a1f1dSLionel Sambuc 
4447*0a6a1f1dSLionel Sambuc     // Submodule information is only valid if we have a current module.
4448*0a6a1f1dSLionel Sambuc     // FIXME: Should we error on these cases?
4449*0a6a1f1dSLionel Sambuc     if (!CurrentModule && Kind != SUBMODULE_METADATA &&
4450*0a6a1f1dSLionel Sambuc         Kind != SUBMODULE_DEFINITION)
4451*0a6a1f1dSLionel Sambuc       continue;
4452*0a6a1f1dSLionel Sambuc 
4453*0a6a1f1dSLionel Sambuc     switch (Kind) {
4454f4a2713aSLionel Sambuc     default:  // Default behavior: ignore.
4455f4a2713aSLionel Sambuc       break;
4456f4a2713aSLionel Sambuc 
4457f4a2713aSLionel Sambuc     case SUBMODULE_DEFINITION: {
4458f4a2713aSLionel Sambuc       if (Record.size() < 8) {
4459f4a2713aSLionel Sambuc         Error("malformed module definition");
4460*0a6a1f1dSLionel Sambuc         return Failure;
4461f4a2713aSLionel Sambuc       }
4462f4a2713aSLionel Sambuc 
4463f4a2713aSLionel Sambuc       StringRef Name = Blob;
4464*0a6a1f1dSLionel Sambuc       unsigned Idx = 0;
4465*0a6a1f1dSLionel Sambuc       SubmoduleID GlobalID = getGlobalSubmoduleID(F, Record[Idx++]);
4466*0a6a1f1dSLionel Sambuc       SubmoduleID Parent = getGlobalSubmoduleID(F, Record[Idx++]);
4467*0a6a1f1dSLionel Sambuc       bool IsFramework = Record[Idx++];
4468*0a6a1f1dSLionel Sambuc       bool IsExplicit = Record[Idx++];
4469*0a6a1f1dSLionel Sambuc       bool IsSystem = Record[Idx++];
4470*0a6a1f1dSLionel Sambuc       bool IsExternC = Record[Idx++];
4471*0a6a1f1dSLionel Sambuc       bool InferSubmodules = Record[Idx++];
4472*0a6a1f1dSLionel Sambuc       bool InferExplicitSubmodules = Record[Idx++];
4473*0a6a1f1dSLionel Sambuc       bool InferExportWildcard = Record[Idx++];
4474*0a6a1f1dSLionel Sambuc       bool ConfigMacrosExhaustive = Record[Idx++];
4475f4a2713aSLionel Sambuc 
4476*0a6a1f1dSLionel Sambuc       Module *ParentModule = nullptr;
4477f4a2713aSLionel Sambuc       if (Parent)
4478f4a2713aSLionel Sambuc         ParentModule = getSubmodule(Parent);
4479f4a2713aSLionel Sambuc 
4480f4a2713aSLionel Sambuc       // Retrieve this (sub)module from the module map, creating it if
4481f4a2713aSLionel Sambuc       // necessary.
4482*0a6a1f1dSLionel Sambuc       CurrentModule = ModMap.findOrCreateModule(Name, ParentModule, IsFramework,
4483f4a2713aSLionel Sambuc                                                 IsExplicit).first;
4484*0a6a1f1dSLionel Sambuc 
4485*0a6a1f1dSLionel Sambuc       // FIXME: set the definition loc for CurrentModule, or call
4486*0a6a1f1dSLionel Sambuc       // ModMap.setInferredModuleAllowedBy()
4487*0a6a1f1dSLionel Sambuc 
4488f4a2713aSLionel Sambuc       SubmoduleID GlobalIndex = GlobalID - NUM_PREDEF_SUBMODULE_IDS;
4489f4a2713aSLionel Sambuc       if (GlobalIndex >= SubmodulesLoaded.size() ||
4490f4a2713aSLionel Sambuc           SubmodulesLoaded[GlobalIndex]) {
4491f4a2713aSLionel Sambuc         Error("too many submodules");
4492*0a6a1f1dSLionel Sambuc         return Failure;
4493f4a2713aSLionel Sambuc       }
4494f4a2713aSLionel Sambuc 
4495f4a2713aSLionel Sambuc       if (!ParentModule) {
4496f4a2713aSLionel Sambuc         if (const FileEntry *CurFile = CurrentModule->getASTFile()) {
4497f4a2713aSLionel Sambuc           if (CurFile != F.File) {
4498f4a2713aSLionel Sambuc             if (!Diags.isDiagnosticInFlight()) {
4499f4a2713aSLionel Sambuc               Diag(diag::err_module_file_conflict)
4500f4a2713aSLionel Sambuc                 << CurrentModule->getTopLevelModuleName()
4501f4a2713aSLionel Sambuc                 << CurFile->getName()
4502f4a2713aSLionel Sambuc                 << F.File->getName();
4503f4a2713aSLionel Sambuc             }
4504*0a6a1f1dSLionel Sambuc             return Failure;
4505f4a2713aSLionel Sambuc           }
4506f4a2713aSLionel Sambuc         }
4507f4a2713aSLionel Sambuc 
4508f4a2713aSLionel Sambuc         CurrentModule->setASTFile(F.File);
4509f4a2713aSLionel Sambuc       }
4510f4a2713aSLionel Sambuc 
4511f4a2713aSLionel Sambuc       CurrentModule->IsFromModuleFile = true;
4512f4a2713aSLionel Sambuc       CurrentModule->IsSystem = IsSystem || CurrentModule->IsSystem;
4513*0a6a1f1dSLionel Sambuc       CurrentModule->IsExternC = IsExternC;
4514f4a2713aSLionel Sambuc       CurrentModule->InferSubmodules = InferSubmodules;
4515f4a2713aSLionel Sambuc       CurrentModule->InferExplicitSubmodules = InferExplicitSubmodules;
4516f4a2713aSLionel Sambuc       CurrentModule->InferExportWildcard = InferExportWildcard;
4517f4a2713aSLionel Sambuc       CurrentModule->ConfigMacrosExhaustive = ConfigMacrosExhaustive;
4518f4a2713aSLionel Sambuc       if (DeserializationListener)
4519f4a2713aSLionel Sambuc         DeserializationListener->ModuleRead(GlobalID, CurrentModule);
4520f4a2713aSLionel Sambuc 
4521f4a2713aSLionel Sambuc       SubmodulesLoaded[GlobalIndex] = CurrentModule;
4522f4a2713aSLionel Sambuc 
4523f4a2713aSLionel Sambuc       // Clear out data that will be replaced by what is the module file.
4524f4a2713aSLionel Sambuc       CurrentModule->LinkLibraries.clear();
4525f4a2713aSLionel Sambuc       CurrentModule->ConfigMacros.clear();
4526f4a2713aSLionel Sambuc       CurrentModule->UnresolvedConflicts.clear();
4527f4a2713aSLionel Sambuc       CurrentModule->Conflicts.clear();
4528f4a2713aSLionel Sambuc       break;
4529f4a2713aSLionel Sambuc     }
4530f4a2713aSLionel Sambuc 
4531f4a2713aSLionel Sambuc     case SUBMODULE_UMBRELLA_HEADER: {
4532f4a2713aSLionel Sambuc       if (const FileEntry *Umbrella = PP.getFileManager().getFile(Blob)) {
4533f4a2713aSLionel Sambuc         if (!CurrentModule->getUmbrellaHeader())
4534f4a2713aSLionel Sambuc           ModMap.setUmbrellaHeader(CurrentModule, Umbrella);
4535f4a2713aSLionel Sambuc         else if (CurrentModule->getUmbrellaHeader() != Umbrella) {
4536*0a6a1f1dSLionel Sambuc           if ((ClientLoadCapabilities & ARR_OutOfDate) == 0)
4537f4a2713aSLionel Sambuc             Error("mismatched umbrella headers in submodule");
4538*0a6a1f1dSLionel Sambuc           return OutOfDate;
4539f4a2713aSLionel Sambuc         }
4540f4a2713aSLionel Sambuc       }
4541f4a2713aSLionel Sambuc       break;
4542f4a2713aSLionel Sambuc     }
4543f4a2713aSLionel Sambuc 
4544*0a6a1f1dSLionel Sambuc     case SUBMODULE_HEADER:
4545*0a6a1f1dSLionel Sambuc     case SUBMODULE_EXCLUDED_HEADER:
4546*0a6a1f1dSLionel Sambuc     case SUBMODULE_PRIVATE_HEADER:
4547*0a6a1f1dSLionel Sambuc       // We lazily associate headers with their modules via the HeaderInfo table.
4548f4a2713aSLionel Sambuc       // FIXME: Re-evaluate this section; maybe only store InputFile IDs instead
4549f4a2713aSLionel Sambuc       // of complete filenames or remove it entirely.
4550f4a2713aSLionel Sambuc       break;
4551f4a2713aSLionel Sambuc 
4552*0a6a1f1dSLionel Sambuc     case SUBMODULE_TEXTUAL_HEADER:
4553*0a6a1f1dSLionel Sambuc     case SUBMODULE_PRIVATE_TEXTUAL_HEADER:
4554*0a6a1f1dSLionel Sambuc       // FIXME: Textual headers are not marked in the HeaderInfo table. Load
4555*0a6a1f1dSLionel Sambuc       // them here.
4556f4a2713aSLionel Sambuc       break;
4557f4a2713aSLionel Sambuc 
4558f4a2713aSLionel Sambuc     case SUBMODULE_TOPHEADER: {
4559f4a2713aSLionel Sambuc       CurrentModule->addTopHeaderFilename(Blob);
4560f4a2713aSLionel Sambuc       break;
4561f4a2713aSLionel Sambuc     }
4562f4a2713aSLionel Sambuc 
4563f4a2713aSLionel Sambuc     case SUBMODULE_UMBRELLA_DIR: {
4564f4a2713aSLionel Sambuc       if (const DirectoryEntry *Umbrella
4565f4a2713aSLionel Sambuc                                   = PP.getFileManager().getDirectory(Blob)) {
4566f4a2713aSLionel Sambuc         if (!CurrentModule->getUmbrellaDir())
4567f4a2713aSLionel Sambuc           ModMap.setUmbrellaDir(CurrentModule, Umbrella);
4568f4a2713aSLionel Sambuc         else if (CurrentModule->getUmbrellaDir() != Umbrella) {
4569*0a6a1f1dSLionel Sambuc           if ((ClientLoadCapabilities & ARR_OutOfDate) == 0)
4570f4a2713aSLionel Sambuc             Error("mismatched umbrella directories in submodule");
4571*0a6a1f1dSLionel Sambuc           return OutOfDate;
4572f4a2713aSLionel Sambuc         }
4573f4a2713aSLionel Sambuc       }
4574f4a2713aSLionel Sambuc       break;
4575f4a2713aSLionel Sambuc     }
4576f4a2713aSLionel Sambuc 
4577f4a2713aSLionel Sambuc     case SUBMODULE_METADATA: {
4578f4a2713aSLionel Sambuc       F.BaseSubmoduleID = getTotalNumSubmodules();
4579f4a2713aSLionel Sambuc       F.LocalNumSubmodules = Record[0];
4580f4a2713aSLionel Sambuc       unsigned LocalBaseSubmoduleID = Record[1];
4581f4a2713aSLionel Sambuc       if (F.LocalNumSubmodules > 0) {
4582f4a2713aSLionel Sambuc         // Introduce the global -> local mapping for submodules within this
4583f4a2713aSLionel Sambuc         // module.
4584f4a2713aSLionel Sambuc         GlobalSubmoduleMap.insert(std::make_pair(getTotalNumSubmodules()+1,&F));
4585f4a2713aSLionel Sambuc 
4586f4a2713aSLionel Sambuc         // Introduce the local -> global mapping for submodules within this
4587f4a2713aSLionel Sambuc         // module.
4588f4a2713aSLionel Sambuc         F.SubmoduleRemap.insertOrReplace(
4589f4a2713aSLionel Sambuc           std::make_pair(LocalBaseSubmoduleID,
4590f4a2713aSLionel Sambuc                          F.BaseSubmoduleID - LocalBaseSubmoduleID));
4591f4a2713aSLionel Sambuc 
4592f4a2713aSLionel Sambuc         SubmodulesLoaded.resize(SubmodulesLoaded.size() + F.LocalNumSubmodules);
4593f4a2713aSLionel Sambuc       }
4594f4a2713aSLionel Sambuc       break;
4595f4a2713aSLionel Sambuc     }
4596f4a2713aSLionel Sambuc 
4597f4a2713aSLionel Sambuc     case SUBMODULE_IMPORTS: {
4598f4a2713aSLionel Sambuc       for (unsigned Idx = 0; Idx != Record.size(); ++Idx) {
4599f4a2713aSLionel Sambuc         UnresolvedModuleRef Unresolved;
4600f4a2713aSLionel Sambuc         Unresolved.File = &F;
4601f4a2713aSLionel Sambuc         Unresolved.Mod = CurrentModule;
4602f4a2713aSLionel Sambuc         Unresolved.ID = Record[Idx];
4603f4a2713aSLionel Sambuc         Unresolved.Kind = UnresolvedModuleRef::Import;
4604f4a2713aSLionel Sambuc         Unresolved.IsWildcard = false;
4605f4a2713aSLionel Sambuc         UnresolvedModuleRefs.push_back(Unresolved);
4606f4a2713aSLionel Sambuc       }
4607f4a2713aSLionel Sambuc       break;
4608f4a2713aSLionel Sambuc     }
4609f4a2713aSLionel Sambuc 
4610f4a2713aSLionel Sambuc     case SUBMODULE_EXPORTS: {
4611f4a2713aSLionel Sambuc       for (unsigned Idx = 0; Idx + 1 < Record.size(); Idx += 2) {
4612f4a2713aSLionel Sambuc         UnresolvedModuleRef Unresolved;
4613f4a2713aSLionel Sambuc         Unresolved.File = &F;
4614f4a2713aSLionel Sambuc         Unresolved.Mod = CurrentModule;
4615f4a2713aSLionel Sambuc         Unresolved.ID = Record[Idx];
4616f4a2713aSLionel Sambuc         Unresolved.Kind = UnresolvedModuleRef::Export;
4617f4a2713aSLionel Sambuc         Unresolved.IsWildcard = Record[Idx + 1];
4618f4a2713aSLionel Sambuc         UnresolvedModuleRefs.push_back(Unresolved);
4619f4a2713aSLionel Sambuc       }
4620f4a2713aSLionel Sambuc 
4621f4a2713aSLionel Sambuc       // Once we've loaded the set of exports, there's no reason to keep
4622f4a2713aSLionel Sambuc       // the parsed, unresolved exports around.
4623f4a2713aSLionel Sambuc       CurrentModule->UnresolvedExports.clear();
4624f4a2713aSLionel Sambuc       break;
4625f4a2713aSLionel Sambuc     }
4626f4a2713aSLionel Sambuc     case SUBMODULE_REQUIRES: {
4627f4a2713aSLionel Sambuc       CurrentModule->addRequirement(Blob, Record[0], Context.getLangOpts(),
4628f4a2713aSLionel Sambuc                                     Context.getTargetInfo());
4629f4a2713aSLionel Sambuc       break;
4630f4a2713aSLionel Sambuc     }
4631f4a2713aSLionel Sambuc 
4632f4a2713aSLionel Sambuc     case SUBMODULE_LINK_LIBRARY:
4633f4a2713aSLionel Sambuc       CurrentModule->LinkLibraries.push_back(
4634f4a2713aSLionel Sambuc                                          Module::LinkLibrary(Blob, Record[0]));
4635f4a2713aSLionel Sambuc       break;
4636f4a2713aSLionel Sambuc 
4637f4a2713aSLionel Sambuc     case SUBMODULE_CONFIG_MACRO:
4638f4a2713aSLionel Sambuc       CurrentModule->ConfigMacros.push_back(Blob.str());
4639f4a2713aSLionel Sambuc       break;
4640f4a2713aSLionel Sambuc 
4641f4a2713aSLionel Sambuc     case SUBMODULE_CONFLICT: {
4642f4a2713aSLionel Sambuc       UnresolvedModuleRef Unresolved;
4643f4a2713aSLionel Sambuc       Unresolved.File = &F;
4644f4a2713aSLionel Sambuc       Unresolved.Mod = CurrentModule;
4645f4a2713aSLionel Sambuc       Unresolved.ID = Record[0];
4646f4a2713aSLionel Sambuc       Unresolved.Kind = UnresolvedModuleRef::Conflict;
4647f4a2713aSLionel Sambuc       Unresolved.IsWildcard = false;
4648f4a2713aSLionel Sambuc       Unresolved.String = Blob;
4649f4a2713aSLionel Sambuc       UnresolvedModuleRefs.push_back(Unresolved);
4650f4a2713aSLionel Sambuc       break;
4651f4a2713aSLionel Sambuc     }
4652f4a2713aSLionel Sambuc     }
4653f4a2713aSLionel Sambuc   }
4654f4a2713aSLionel Sambuc }
4655f4a2713aSLionel Sambuc 
4656f4a2713aSLionel Sambuc /// \brief Parse the record that corresponds to a LangOptions data
4657f4a2713aSLionel Sambuc /// structure.
4658f4a2713aSLionel Sambuc ///
4659f4a2713aSLionel Sambuc /// This routine parses the language options from the AST file and then gives
4660f4a2713aSLionel Sambuc /// them to the AST listener if one is set.
4661f4a2713aSLionel Sambuc ///
4662f4a2713aSLionel Sambuc /// \returns true if the listener deems the file unacceptable, false otherwise.
ParseLanguageOptions(const RecordData & Record,bool Complain,ASTReaderListener & Listener,bool AllowCompatibleDifferences)4663f4a2713aSLionel Sambuc bool ASTReader::ParseLanguageOptions(const RecordData &Record,
4664f4a2713aSLionel Sambuc                                      bool Complain,
4665*0a6a1f1dSLionel Sambuc                                      ASTReaderListener &Listener,
4666*0a6a1f1dSLionel Sambuc                                      bool AllowCompatibleDifferences) {
4667f4a2713aSLionel Sambuc   LangOptions LangOpts;
4668f4a2713aSLionel Sambuc   unsigned Idx = 0;
4669f4a2713aSLionel Sambuc #define LANGOPT(Name, Bits, Default, Description) \
4670f4a2713aSLionel Sambuc   LangOpts.Name = Record[Idx++];
4671f4a2713aSLionel Sambuc #define ENUM_LANGOPT(Name, Type, Bits, Default, Description) \
4672f4a2713aSLionel Sambuc   LangOpts.set##Name(static_cast<LangOptions::Type>(Record[Idx++]));
4673f4a2713aSLionel Sambuc #include "clang/Basic/LangOptions.def"
4674*0a6a1f1dSLionel Sambuc #define SANITIZER(NAME, ID)                                                    \
4675*0a6a1f1dSLionel Sambuc   LangOpts.Sanitize.set(SanitizerKind::ID, Record[Idx++]);
4676f4a2713aSLionel Sambuc #include "clang/Basic/Sanitizers.def"
4677f4a2713aSLionel Sambuc 
4678f4a2713aSLionel Sambuc   ObjCRuntime::Kind runtimeKind = (ObjCRuntime::Kind) Record[Idx++];
4679f4a2713aSLionel Sambuc   VersionTuple runtimeVersion = ReadVersionTuple(Record, Idx);
4680f4a2713aSLionel Sambuc   LangOpts.ObjCRuntime = ObjCRuntime(runtimeKind, runtimeVersion);
4681f4a2713aSLionel Sambuc 
4682f4a2713aSLionel Sambuc   unsigned Length = Record[Idx++];
4683f4a2713aSLionel Sambuc   LangOpts.CurrentModule.assign(Record.begin() + Idx,
4684f4a2713aSLionel Sambuc                                 Record.begin() + Idx + Length);
4685f4a2713aSLionel Sambuc 
4686f4a2713aSLionel Sambuc   Idx += Length;
4687f4a2713aSLionel Sambuc 
4688f4a2713aSLionel Sambuc   // Comment options.
4689f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4690f4a2713aSLionel Sambuc     LangOpts.CommentOpts.BlockCommandNames.push_back(
4691f4a2713aSLionel Sambuc       ReadString(Record, Idx));
4692f4a2713aSLionel Sambuc   }
4693f4a2713aSLionel Sambuc   LangOpts.CommentOpts.ParseAllComments = Record[Idx++];
4694f4a2713aSLionel Sambuc 
4695*0a6a1f1dSLionel Sambuc   return Listener.ReadLanguageOptions(LangOpts, Complain,
4696*0a6a1f1dSLionel Sambuc                                       AllowCompatibleDifferences);
4697f4a2713aSLionel Sambuc }
4698f4a2713aSLionel Sambuc 
ParseTargetOptions(const RecordData & Record,bool Complain,ASTReaderListener & Listener)4699f4a2713aSLionel Sambuc bool ASTReader::ParseTargetOptions(const RecordData &Record,
4700f4a2713aSLionel Sambuc                                    bool Complain,
4701f4a2713aSLionel Sambuc                                    ASTReaderListener &Listener) {
4702f4a2713aSLionel Sambuc   unsigned Idx = 0;
4703f4a2713aSLionel Sambuc   TargetOptions TargetOpts;
4704f4a2713aSLionel Sambuc   TargetOpts.Triple = ReadString(Record, Idx);
4705f4a2713aSLionel Sambuc   TargetOpts.CPU = ReadString(Record, Idx);
4706f4a2713aSLionel Sambuc   TargetOpts.ABI = ReadString(Record, Idx);
4707f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4708f4a2713aSLionel Sambuc     TargetOpts.FeaturesAsWritten.push_back(ReadString(Record, Idx));
4709f4a2713aSLionel Sambuc   }
4710f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4711f4a2713aSLionel Sambuc     TargetOpts.Features.push_back(ReadString(Record, Idx));
4712f4a2713aSLionel Sambuc   }
4713f4a2713aSLionel Sambuc 
4714f4a2713aSLionel Sambuc   return Listener.ReadTargetOptions(TargetOpts, Complain);
4715f4a2713aSLionel Sambuc }
4716f4a2713aSLionel Sambuc 
ParseDiagnosticOptions(const RecordData & Record,bool Complain,ASTReaderListener & Listener)4717f4a2713aSLionel Sambuc bool ASTReader::ParseDiagnosticOptions(const RecordData &Record, bool Complain,
4718f4a2713aSLionel Sambuc                                        ASTReaderListener &Listener) {
4719*0a6a1f1dSLionel Sambuc   IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts(new DiagnosticOptions);
4720f4a2713aSLionel Sambuc   unsigned Idx = 0;
4721*0a6a1f1dSLionel Sambuc #define DIAGOPT(Name, Bits, Default) DiagOpts->Name = Record[Idx++];
4722f4a2713aSLionel Sambuc #define ENUM_DIAGOPT(Name, Type, Bits, Default) \
4723*0a6a1f1dSLionel Sambuc   DiagOpts->set##Name(static_cast<Type>(Record[Idx++]));
4724f4a2713aSLionel Sambuc #include "clang/Basic/DiagnosticOptions.def"
4725f4a2713aSLionel Sambuc 
4726*0a6a1f1dSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N)
4727*0a6a1f1dSLionel Sambuc     DiagOpts->Warnings.push_back(ReadString(Record, Idx));
4728*0a6a1f1dSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N)
4729*0a6a1f1dSLionel Sambuc     DiagOpts->Remarks.push_back(ReadString(Record, Idx));
4730f4a2713aSLionel Sambuc 
4731f4a2713aSLionel Sambuc   return Listener.ReadDiagnosticOptions(DiagOpts, Complain);
4732f4a2713aSLionel Sambuc }
4733f4a2713aSLionel Sambuc 
ParseFileSystemOptions(const RecordData & Record,bool Complain,ASTReaderListener & Listener)4734f4a2713aSLionel Sambuc bool ASTReader::ParseFileSystemOptions(const RecordData &Record, bool Complain,
4735f4a2713aSLionel Sambuc                                        ASTReaderListener &Listener) {
4736f4a2713aSLionel Sambuc   FileSystemOptions FSOpts;
4737f4a2713aSLionel Sambuc   unsigned Idx = 0;
4738f4a2713aSLionel Sambuc   FSOpts.WorkingDir = ReadString(Record, Idx);
4739f4a2713aSLionel Sambuc   return Listener.ReadFileSystemOptions(FSOpts, Complain);
4740f4a2713aSLionel Sambuc }
4741f4a2713aSLionel Sambuc 
ParseHeaderSearchOptions(const RecordData & Record,bool Complain,ASTReaderListener & Listener)4742f4a2713aSLionel Sambuc bool ASTReader::ParseHeaderSearchOptions(const RecordData &Record,
4743f4a2713aSLionel Sambuc                                          bool Complain,
4744f4a2713aSLionel Sambuc                                          ASTReaderListener &Listener) {
4745f4a2713aSLionel Sambuc   HeaderSearchOptions HSOpts;
4746f4a2713aSLionel Sambuc   unsigned Idx = 0;
4747f4a2713aSLionel Sambuc   HSOpts.Sysroot = ReadString(Record, Idx);
4748f4a2713aSLionel Sambuc 
4749f4a2713aSLionel Sambuc   // Include entries.
4750f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4751f4a2713aSLionel Sambuc     std::string Path = ReadString(Record, Idx);
4752f4a2713aSLionel Sambuc     frontend::IncludeDirGroup Group
4753f4a2713aSLionel Sambuc       = static_cast<frontend::IncludeDirGroup>(Record[Idx++]);
4754f4a2713aSLionel Sambuc     bool IsFramework = Record[Idx++];
4755f4a2713aSLionel Sambuc     bool IgnoreSysRoot = Record[Idx++];
4756f4a2713aSLionel Sambuc     HSOpts.UserEntries.push_back(
4757f4a2713aSLionel Sambuc       HeaderSearchOptions::Entry(Path, Group, IsFramework, IgnoreSysRoot));
4758f4a2713aSLionel Sambuc   }
4759f4a2713aSLionel Sambuc 
4760f4a2713aSLionel Sambuc   // System header prefixes.
4761f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4762f4a2713aSLionel Sambuc     std::string Prefix = ReadString(Record, Idx);
4763f4a2713aSLionel Sambuc     bool IsSystemHeader = Record[Idx++];
4764f4a2713aSLionel Sambuc     HSOpts.SystemHeaderPrefixes.push_back(
4765f4a2713aSLionel Sambuc       HeaderSearchOptions::SystemHeaderPrefix(Prefix, IsSystemHeader));
4766f4a2713aSLionel Sambuc   }
4767f4a2713aSLionel Sambuc 
4768f4a2713aSLionel Sambuc   HSOpts.ResourceDir = ReadString(Record, Idx);
4769f4a2713aSLionel Sambuc   HSOpts.ModuleCachePath = ReadString(Record, Idx);
4770*0a6a1f1dSLionel Sambuc   HSOpts.ModuleUserBuildPath = ReadString(Record, Idx);
4771f4a2713aSLionel Sambuc   HSOpts.DisableModuleHash = Record[Idx++];
4772f4a2713aSLionel Sambuc   HSOpts.UseBuiltinIncludes = Record[Idx++];
4773f4a2713aSLionel Sambuc   HSOpts.UseStandardSystemIncludes = Record[Idx++];
4774f4a2713aSLionel Sambuc   HSOpts.UseStandardCXXIncludes = Record[Idx++];
4775f4a2713aSLionel Sambuc   HSOpts.UseLibcxx = Record[Idx++];
4776f4a2713aSLionel Sambuc 
4777f4a2713aSLionel Sambuc   return Listener.ReadHeaderSearchOptions(HSOpts, Complain);
4778f4a2713aSLionel Sambuc }
4779f4a2713aSLionel Sambuc 
ParsePreprocessorOptions(const RecordData & Record,bool Complain,ASTReaderListener & Listener,std::string & SuggestedPredefines)4780f4a2713aSLionel Sambuc bool ASTReader::ParsePreprocessorOptions(const RecordData &Record,
4781f4a2713aSLionel Sambuc                                          bool Complain,
4782f4a2713aSLionel Sambuc                                          ASTReaderListener &Listener,
4783f4a2713aSLionel Sambuc                                          std::string &SuggestedPredefines) {
4784f4a2713aSLionel Sambuc   PreprocessorOptions PPOpts;
4785f4a2713aSLionel Sambuc   unsigned Idx = 0;
4786f4a2713aSLionel Sambuc 
4787f4a2713aSLionel Sambuc   // Macro definitions/undefs
4788f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4789f4a2713aSLionel Sambuc     std::string Macro = ReadString(Record, Idx);
4790f4a2713aSLionel Sambuc     bool IsUndef = Record[Idx++];
4791f4a2713aSLionel Sambuc     PPOpts.Macros.push_back(std::make_pair(Macro, IsUndef));
4792f4a2713aSLionel Sambuc   }
4793f4a2713aSLionel Sambuc 
4794f4a2713aSLionel Sambuc   // Includes
4795f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4796f4a2713aSLionel Sambuc     PPOpts.Includes.push_back(ReadString(Record, Idx));
4797f4a2713aSLionel Sambuc   }
4798f4a2713aSLionel Sambuc 
4799f4a2713aSLionel Sambuc   // Macro Includes
4800f4a2713aSLionel Sambuc   for (unsigned N = Record[Idx++]; N; --N) {
4801f4a2713aSLionel Sambuc     PPOpts.MacroIncludes.push_back(ReadString(Record, Idx));
4802f4a2713aSLionel Sambuc   }
4803f4a2713aSLionel Sambuc 
4804f4a2713aSLionel Sambuc   PPOpts.UsePredefines = Record[Idx++];
4805f4a2713aSLionel Sambuc   PPOpts.DetailedRecord = Record[Idx++];
4806f4a2713aSLionel Sambuc   PPOpts.ImplicitPCHInclude = ReadString(Record, Idx);
4807f4a2713aSLionel Sambuc   PPOpts.ImplicitPTHInclude = ReadString(Record, Idx);
4808f4a2713aSLionel Sambuc   PPOpts.ObjCXXARCStandardLibrary =
4809f4a2713aSLionel Sambuc     static_cast<ObjCXXARCStandardLibraryKind>(Record[Idx++]);
4810f4a2713aSLionel Sambuc   SuggestedPredefines.clear();
4811f4a2713aSLionel Sambuc   return Listener.ReadPreprocessorOptions(PPOpts, Complain,
4812f4a2713aSLionel Sambuc                                           SuggestedPredefines);
4813f4a2713aSLionel Sambuc }
4814f4a2713aSLionel Sambuc 
4815f4a2713aSLionel Sambuc std::pair<ModuleFile *, unsigned>
getModulePreprocessedEntity(unsigned GlobalIndex)4816f4a2713aSLionel Sambuc ASTReader::getModulePreprocessedEntity(unsigned GlobalIndex) {
4817f4a2713aSLionel Sambuc   GlobalPreprocessedEntityMapType::iterator
4818f4a2713aSLionel Sambuc   I = GlobalPreprocessedEntityMap.find(GlobalIndex);
4819f4a2713aSLionel Sambuc   assert(I != GlobalPreprocessedEntityMap.end() &&
4820f4a2713aSLionel Sambuc          "Corrupted global preprocessed entity map");
4821f4a2713aSLionel Sambuc   ModuleFile *M = I->second;
4822f4a2713aSLionel Sambuc   unsigned LocalIndex = GlobalIndex - M->BasePreprocessedEntityID;
4823f4a2713aSLionel Sambuc   return std::make_pair(M, LocalIndex);
4824f4a2713aSLionel Sambuc }
4825f4a2713aSLionel Sambuc 
4826f4a2713aSLionel Sambuc std::pair<PreprocessingRecord::iterator, PreprocessingRecord::iterator>
getModulePreprocessedEntities(ModuleFile & Mod) const4827f4a2713aSLionel Sambuc ASTReader::getModulePreprocessedEntities(ModuleFile &Mod) const {
4828f4a2713aSLionel Sambuc   if (PreprocessingRecord *PPRec = PP.getPreprocessingRecord())
4829f4a2713aSLionel Sambuc     return PPRec->getIteratorsForLoadedRange(Mod.BasePreprocessedEntityID,
4830f4a2713aSLionel Sambuc                                              Mod.NumPreprocessedEntities);
4831f4a2713aSLionel Sambuc 
4832f4a2713aSLionel Sambuc   return std::make_pair(PreprocessingRecord::iterator(),
4833f4a2713aSLionel Sambuc                         PreprocessingRecord::iterator());
4834f4a2713aSLionel Sambuc }
4835f4a2713aSLionel Sambuc 
4836f4a2713aSLionel Sambuc std::pair<ASTReader::ModuleDeclIterator, ASTReader::ModuleDeclIterator>
getModuleFileLevelDecls(ModuleFile & Mod)4837f4a2713aSLionel Sambuc ASTReader::getModuleFileLevelDecls(ModuleFile &Mod) {
4838f4a2713aSLionel Sambuc   return std::make_pair(ModuleDeclIterator(this, &Mod, Mod.FileSortedDecls),
4839f4a2713aSLionel Sambuc                         ModuleDeclIterator(this, &Mod,
4840f4a2713aSLionel Sambuc                                  Mod.FileSortedDecls + Mod.NumFileSortedDecls));
4841f4a2713aSLionel Sambuc }
4842f4a2713aSLionel Sambuc 
ReadPreprocessedEntity(unsigned Index)4843f4a2713aSLionel Sambuc PreprocessedEntity *ASTReader::ReadPreprocessedEntity(unsigned Index) {
4844f4a2713aSLionel Sambuc   PreprocessedEntityID PPID = Index+1;
4845f4a2713aSLionel Sambuc   std::pair<ModuleFile *, unsigned> PPInfo = getModulePreprocessedEntity(Index);
4846f4a2713aSLionel Sambuc   ModuleFile &M = *PPInfo.first;
4847f4a2713aSLionel Sambuc   unsigned LocalIndex = PPInfo.second;
4848f4a2713aSLionel Sambuc   const PPEntityOffset &PPOffs = M.PreprocessedEntityOffsets[LocalIndex];
4849f4a2713aSLionel Sambuc 
4850f4a2713aSLionel Sambuc   if (!PP.getPreprocessingRecord()) {
4851f4a2713aSLionel Sambuc     Error("no preprocessing record");
4852*0a6a1f1dSLionel Sambuc     return nullptr;
4853f4a2713aSLionel Sambuc   }
4854f4a2713aSLionel Sambuc 
4855f4a2713aSLionel Sambuc   SavedStreamPosition SavedPosition(M.PreprocessorDetailCursor);
4856f4a2713aSLionel Sambuc   M.PreprocessorDetailCursor.JumpToBit(PPOffs.BitOffset);
4857f4a2713aSLionel Sambuc 
4858f4a2713aSLionel Sambuc   llvm::BitstreamEntry Entry =
4859f4a2713aSLionel Sambuc     M.PreprocessorDetailCursor.advance(BitstreamCursor::AF_DontPopBlockAtEnd);
4860f4a2713aSLionel Sambuc   if (Entry.Kind != llvm::BitstreamEntry::Record)
4861*0a6a1f1dSLionel Sambuc     return nullptr;
4862f4a2713aSLionel Sambuc 
4863f4a2713aSLionel Sambuc   // Read the record.
4864f4a2713aSLionel Sambuc   SourceRange Range(ReadSourceLocation(M, PPOffs.Begin),
4865f4a2713aSLionel Sambuc                     ReadSourceLocation(M, PPOffs.End));
4866f4a2713aSLionel Sambuc   PreprocessingRecord &PPRec = *PP.getPreprocessingRecord();
4867f4a2713aSLionel Sambuc   StringRef Blob;
4868f4a2713aSLionel Sambuc   RecordData Record;
4869f4a2713aSLionel Sambuc   PreprocessorDetailRecordTypes RecType =
4870f4a2713aSLionel Sambuc     (PreprocessorDetailRecordTypes)M.PreprocessorDetailCursor.readRecord(
4871f4a2713aSLionel Sambuc                                           Entry.ID, Record, &Blob);
4872f4a2713aSLionel Sambuc   switch (RecType) {
4873f4a2713aSLionel Sambuc   case PPD_MACRO_EXPANSION: {
4874f4a2713aSLionel Sambuc     bool isBuiltin = Record[0];
4875*0a6a1f1dSLionel Sambuc     IdentifierInfo *Name = nullptr;
4876*0a6a1f1dSLionel Sambuc     MacroDefinition *Def = nullptr;
4877f4a2713aSLionel Sambuc     if (isBuiltin)
4878f4a2713aSLionel Sambuc       Name = getLocalIdentifier(M, Record[1]);
4879f4a2713aSLionel Sambuc     else {
4880f4a2713aSLionel Sambuc       PreprocessedEntityID
4881f4a2713aSLionel Sambuc           GlobalID = getGlobalPreprocessedEntityID(M, Record[1]);
4882f4a2713aSLionel Sambuc       Def =cast<MacroDefinition>(PPRec.getLoadedPreprocessedEntity(GlobalID-1));
4883f4a2713aSLionel Sambuc     }
4884f4a2713aSLionel Sambuc 
4885f4a2713aSLionel Sambuc     MacroExpansion *ME;
4886f4a2713aSLionel Sambuc     if (isBuiltin)
4887f4a2713aSLionel Sambuc       ME = new (PPRec) MacroExpansion(Name, Range);
4888f4a2713aSLionel Sambuc     else
4889f4a2713aSLionel Sambuc       ME = new (PPRec) MacroExpansion(Def, Range);
4890f4a2713aSLionel Sambuc 
4891f4a2713aSLionel Sambuc     return ME;
4892f4a2713aSLionel Sambuc   }
4893f4a2713aSLionel Sambuc 
4894f4a2713aSLionel Sambuc   case PPD_MACRO_DEFINITION: {
4895f4a2713aSLionel Sambuc     // Decode the identifier info and then check again; if the macro is
4896f4a2713aSLionel Sambuc     // still defined and associated with the identifier,
4897f4a2713aSLionel Sambuc     IdentifierInfo *II = getLocalIdentifier(M, Record[0]);
4898f4a2713aSLionel Sambuc     MacroDefinition *MD
4899f4a2713aSLionel Sambuc       = new (PPRec) MacroDefinition(II, Range);
4900f4a2713aSLionel Sambuc 
4901f4a2713aSLionel Sambuc     if (DeserializationListener)
4902f4a2713aSLionel Sambuc       DeserializationListener->MacroDefinitionRead(PPID, MD);
4903f4a2713aSLionel Sambuc 
4904f4a2713aSLionel Sambuc     return MD;
4905f4a2713aSLionel Sambuc   }
4906f4a2713aSLionel Sambuc 
4907f4a2713aSLionel Sambuc   case PPD_INCLUSION_DIRECTIVE: {
4908f4a2713aSLionel Sambuc     const char *FullFileNameStart = Blob.data() + Record[0];
4909f4a2713aSLionel Sambuc     StringRef FullFileName(FullFileNameStart, Blob.size() - Record[0]);
4910*0a6a1f1dSLionel Sambuc     const FileEntry *File = nullptr;
4911f4a2713aSLionel Sambuc     if (!FullFileName.empty())
4912f4a2713aSLionel Sambuc       File = PP.getFileManager().getFile(FullFileName);
4913f4a2713aSLionel Sambuc 
4914f4a2713aSLionel Sambuc     // FIXME: Stable encoding
4915f4a2713aSLionel Sambuc     InclusionDirective::InclusionKind Kind
4916f4a2713aSLionel Sambuc       = static_cast<InclusionDirective::InclusionKind>(Record[2]);
4917f4a2713aSLionel Sambuc     InclusionDirective *ID
4918f4a2713aSLionel Sambuc       = new (PPRec) InclusionDirective(PPRec, Kind,
4919f4a2713aSLionel Sambuc                                        StringRef(Blob.data(), Record[0]),
4920f4a2713aSLionel Sambuc                                        Record[1], Record[3],
4921f4a2713aSLionel Sambuc                                        File,
4922f4a2713aSLionel Sambuc                                        Range);
4923f4a2713aSLionel Sambuc     return ID;
4924f4a2713aSLionel Sambuc   }
4925f4a2713aSLionel Sambuc   }
4926f4a2713aSLionel Sambuc 
4927f4a2713aSLionel Sambuc   llvm_unreachable("Invalid PreprocessorDetailRecordTypes");
4928f4a2713aSLionel Sambuc }
4929f4a2713aSLionel Sambuc 
4930f4a2713aSLionel Sambuc /// \brief \arg SLocMapI points at a chunk of a module that contains no
4931f4a2713aSLionel Sambuc /// preprocessed entities or the entities it contains are not the ones we are
4932f4a2713aSLionel Sambuc /// looking for. Find the next module that contains entities and return the ID
4933f4a2713aSLionel Sambuc /// of the first entry.
findNextPreprocessedEntity(GlobalSLocOffsetMapType::const_iterator SLocMapI) const4934f4a2713aSLionel Sambuc PreprocessedEntityID ASTReader::findNextPreprocessedEntity(
4935f4a2713aSLionel Sambuc                        GlobalSLocOffsetMapType::const_iterator SLocMapI) const {
4936f4a2713aSLionel Sambuc   ++SLocMapI;
4937f4a2713aSLionel Sambuc   for (GlobalSLocOffsetMapType::const_iterator
4938f4a2713aSLionel Sambuc          EndI = GlobalSLocOffsetMap.end(); SLocMapI != EndI; ++SLocMapI) {
4939f4a2713aSLionel Sambuc     ModuleFile &M = *SLocMapI->second;
4940f4a2713aSLionel Sambuc     if (M.NumPreprocessedEntities)
4941f4a2713aSLionel Sambuc       return M.BasePreprocessedEntityID;
4942f4a2713aSLionel Sambuc   }
4943f4a2713aSLionel Sambuc 
4944f4a2713aSLionel Sambuc   return getTotalNumPreprocessedEntities();
4945f4a2713aSLionel Sambuc }
4946f4a2713aSLionel Sambuc 
4947f4a2713aSLionel Sambuc namespace {
4948f4a2713aSLionel Sambuc 
4949f4a2713aSLionel Sambuc template <unsigned PPEntityOffset::*PPLoc>
4950f4a2713aSLionel Sambuc struct PPEntityComp {
4951f4a2713aSLionel Sambuc   const ASTReader &Reader;
4952f4a2713aSLionel Sambuc   ModuleFile &M;
4953f4a2713aSLionel Sambuc 
PPEntityComp__anon18a49ed50711::PPEntityComp4954f4a2713aSLionel Sambuc   PPEntityComp(const ASTReader &Reader, ModuleFile &M) : Reader(Reader), M(M) { }
4955f4a2713aSLionel Sambuc 
operator ()__anon18a49ed50711::PPEntityComp4956f4a2713aSLionel Sambuc   bool operator()(const PPEntityOffset &L, const PPEntityOffset &R) const {
4957f4a2713aSLionel Sambuc     SourceLocation LHS = getLoc(L);
4958f4a2713aSLionel Sambuc     SourceLocation RHS = getLoc(R);
4959f4a2713aSLionel Sambuc     return Reader.getSourceManager().isBeforeInTranslationUnit(LHS, RHS);
4960f4a2713aSLionel Sambuc   }
4961f4a2713aSLionel Sambuc 
operator ()__anon18a49ed50711::PPEntityComp4962f4a2713aSLionel Sambuc   bool operator()(const PPEntityOffset &L, SourceLocation RHS) const {
4963f4a2713aSLionel Sambuc     SourceLocation LHS = getLoc(L);
4964f4a2713aSLionel Sambuc     return Reader.getSourceManager().isBeforeInTranslationUnit(LHS, RHS);
4965f4a2713aSLionel Sambuc   }
4966f4a2713aSLionel Sambuc 
operator ()__anon18a49ed50711::PPEntityComp4967f4a2713aSLionel Sambuc   bool operator()(SourceLocation LHS, const PPEntityOffset &R) const {
4968f4a2713aSLionel Sambuc     SourceLocation RHS = getLoc(R);
4969f4a2713aSLionel Sambuc     return Reader.getSourceManager().isBeforeInTranslationUnit(LHS, RHS);
4970f4a2713aSLionel Sambuc   }
4971f4a2713aSLionel Sambuc 
getLoc__anon18a49ed50711::PPEntityComp4972f4a2713aSLionel Sambuc   SourceLocation getLoc(const PPEntityOffset &PPE) const {
4973f4a2713aSLionel Sambuc     return Reader.ReadSourceLocation(M, PPE.*PPLoc);
4974f4a2713aSLionel Sambuc   }
4975f4a2713aSLionel Sambuc };
4976f4a2713aSLionel Sambuc 
4977f4a2713aSLionel Sambuc }
4978f4a2713aSLionel Sambuc 
findPreprocessedEntity(SourceLocation Loc,bool EndsAfter) const4979*0a6a1f1dSLionel Sambuc PreprocessedEntityID ASTReader::findPreprocessedEntity(SourceLocation Loc,
4980*0a6a1f1dSLionel Sambuc                                                        bool EndsAfter) const {
4981*0a6a1f1dSLionel Sambuc   if (SourceMgr.isLocalSourceLocation(Loc))
4982f4a2713aSLionel Sambuc     return getTotalNumPreprocessedEntities();
4983f4a2713aSLionel Sambuc 
4984*0a6a1f1dSLionel Sambuc   GlobalSLocOffsetMapType::const_iterator SLocMapI = GlobalSLocOffsetMap.find(
4985*0a6a1f1dSLionel Sambuc       SourceManager::MaxLoadedOffset - Loc.getOffset() - 1);
4986f4a2713aSLionel Sambuc   assert(SLocMapI != GlobalSLocOffsetMap.end() &&
4987f4a2713aSLionel Sambuc          "Corrupted global sloc offset map");
4988f4a2713aSLionel Sambuc 
4989f4a2713aSLionel Sambuc   if (SLocMapI->second->NumPreprocessedEntities == 0)
4990f4a2713aSLionel Sambuc     return findNextPreprocessedEntity(SLocMapI);
4991f4a2713aSLionel Sambuc 
4992f4a2713aSLionel Sambuc   ModuleFile &M = *SLocMapI->second;
4993f4a2713aSLionel Sambuc   typedef const PPEntityOffset *pp_iterator;
4994f4a2713aSLionel Sambuc   pp_iterator pp_begin = M.PreprocessedEntityOffsets;
4995f4a2713aSLionel Sambuc   pp_iterator pp_end = pp_begin + M.NumPreprocessedEntities;
4996f4a2713aSLionel Sambuc 
4997f4a2713aSLionel Sambuc   size_t Count = M.NumPreprocessedEntities;
4998f4a2713aSLionel Sambuc   size_t Half;
4999f4a2713aSLionel Sambuc   pp_iterator First = pp_begin;
5000f4a2713aSLionel Sambuc   pp_iterator PPI;
5001f4a2713aSLionel Sambuc 
5002*0a6a1f1dSLionel Sambuc   if (EndsAfter) {
5003*0a6a1f1dSLionel Sambuc     PPI = std::upper_bound(pp_begin, pp_end, Loc,
5004*0a6a1f1dSLionel Sambuc                            PPEntityComp<&PPEntityOffset::Begin>(*this, M));
5005*0a6a1f1dSLionel Sambuc   } else {
5006f4a2713aSLionel Sambuc     // Do a binary search manually instead of using std::lower_bound because
5007f4a2713aSLionel Sambuc     // The end locations of entities may be unordered (when a macro expansion
5008f4a2713aSLionel Sambuc     // is inside another macro argument), but for this case it is not important
5009f4a2713aSLionel Sambuc     // whether we get the first macro expansion or its containing macro.
5010f4a2713aSLionel Sambuc     while (Count > 0) {
5011f4a2713aSLionel Sambuc       Half = Count / 2;
5012f4a2713aSLionel Sambuc       PPI = First;
5013f4a2713aSLionel Sambuc       std::advance(PPI, Half);
5014f4a2713aSLionel Sambuc       if (SourceMgr.isBeforeInTranslationUnit(ReadSourceLocation(M, PPI->End),
5015*0a6a1f1dSLionel Sambuc                                               Loc)) {
5016f4a2713aSLionel Sambuc         First = PPI;
5017f4a2713aSLionel Sambuc         ++First;
5018f4a2713aSLionel Sambuc         Count = Count - Half - 1;
5019f4a2713aSLionel Sambuc       } else
5020f4a2713aSLionel Sambuc         Count = Half;
5021f4a2713aSLionel Sambuc     }
5022f4a2713aSLionel Sambuc   }
5023f4a2713aSLionel Sambuc 
5024f4a2713aSLionel Sambuc   if (PPI == pp_end)
5025f4a2713aSLionel Sambuc     return findNextPreprocessedEntity(SLocMapI);
5026f4a2713aSLionel Sambuc 
5027f4a2713aSLionel Sambuc   return M.BasePreprocessedEntityID + (PPI - pp_begin);
5028f4a2713aSLionel Sambuc }
5029f4a2713aSLionel Sambuc 
5030f4a2713aSLionel Sambuc /// \brief Returns a pair of [Begin, End) indices of preallocated
5031f4a2713aSLionel Sambuc /// preprocessed entities that \arg Range encompasses.
5032f4a2713aSLionel Sambuc std::pair<unsigned, unsigned>
findPreprocessedEntitiesInRange(SourceRange Range)5033f4a2713aSLionel Sambuc     ASTReader::findPreprocessedEntitiesInRange(SourceRange Range) {
5034f4a2713aSLionel Sambuc   if (Range.isInvalid())
5035f4a2713aSLionel Sambuc     return std::make_pair(0,0);
5036f4a2713aSLionel Sambuc   assert(!SourceMgr.isBeforeInTranslationUnit(Range.getEnd(),Range.getBegin()));
5037f4a2713aSLionel Sambuc 
5038*0a6a1f1dSLionel Sambuc   PreprocessedEntityID BeginID =
5039*0a6a1f1dSLionel Sambuc       findPreprocessedEntity(Range.getBegin(), false);
5040*0a6a1f1dSLionel Sambuc   PreprocessedEntityID EndID = findPreprocessedEntity(Range.getEnd(), true);
5041f4a2713aSLionel Sambuc   return std::make_pair(BeginID, EndID);
5042f4a2713aSLionel Sambuc }
5043f4a2713aSLionel Sambuc 
5044f4a2713aSLionel Sambuc /// \brief Optionally returns true or false if the preallocated preprocessed
5045f4a2713aSLionel Sambuc /// entity with index \arg Index came from file \arg FID.
isPreprocessedEntityInFileID(unsigned Index,FileID FID)5046f4a2713aSLionel Sambuc Optional<bool> ASTReader::isPreprocessedEntityInFileID(unsigned Index,
5047f4a2713aSLionel Sambuc                                                              FileID FID) {
5048f4a2713aSLionel Sambuc   if (FID.isInvalid())
5049f4a2713aSLionel Sambuc     return false;
5050f4a2713aSLionel Sambuc 
5051f4a2713aSLionel Sambuc   std::pair<ModuleFile *, unsigned> PPInfo = getModulePreprocessedEntity(Index);
5052f4a2713aSLionel Sambuc   ModuleFile &M = *PPInfo.first;
5053f4a2713aSLionel Sambuc   unsigned LocalIndex = PPInfo.second;
5054f4a2713aSLionel Sambuc   const PPEntityOffset &PPOffs = M.PreprocessedEntityOffsets[LocalIndex];
5055f4a2713aSLionel Sambuc 
5056f4a2713aSLionel Sambuc   SourceLocation Loc = ReadSourceLocation(M, PPOffs.Begin);
5057f4a2713aSLionel Sambuc   if (Loc.isInvalid())
5058f4a2713aSLionel Sambuc     return false;
5059f4a2713aSLionel Sambuc 
5060f4a2713aSLionel Sambuc   if (SourceMgr.isInFileID(SourceMgr.getFileLoc(Loc), FID))
5061f4a2713aSLionel Sambuc     return true;
5062f4a2713aSLionel Sambuc   else
5063f4a2713aSLionel Sambuc     return false;
5064f4a2713aSLionel Sambuc }
5065f4a2713aSLionel Sambuc 
5066f4a2713aSLionel Sambuc namespace {
5067f4a2713aSLionel Sambuc   /// \brief Visitor used to search for information about a header file.
5068f4a2713aSLionel Sambuc   class HeaderFileInfoVisitor {
5069f4a2713aSLionel Sambuc     const FileEntry *FE;
5070f4a2713aSLionel Sambuc 
5071f4a2713aSLionel Sambuc     Optional<HeaderFileInfo> HFI;
5072f4a2713aSLionel Sambuc 
5073f4a2713aSLionel Sambuc   public:
HeaderFileInfoVisitor(const FileEntry * FE)5074f4a2713aSLionel Sambuc     explicit HeaderFileInfoVisitor(const FileEntry *FE)
5075f4a2713aSLionel Sambuc       : FE(FE) { }
5076f4a2713aSLionel Sambuc 
visit(ModuleFile & M,void * UserData)5077f4a2713aSLionel Sambuc     static bool visit(ModuleFile &M, void *UserData) {
5078f4a2713aSLionel Sambuc       HeaderFileInfoVisitor *This
5079f4a2713aSLionel Sambuc         = static_cast<HeaderFileInfoVisitor *>(UserData);
5080f4a2713aSLionel Sambuc 
5081f4a2713aSLionel Sambuc       HeaderFileInfoLookupTable *Table
5082f4a2713aSLionel Sambuc         = static_cast<HeaderFileInfoLookupTable *>(M.HeaderFileInfoTable);
5083f4a2713aSLionel Sambuc       if (!Table)
5084f4a2713aSLionel Sambuc         return false;
5085f4a2713aSLionel Sambuc 
5086f4a2713aSLionel Sambuc       // Look in the on-disk hash table for an entry for this file name.
5087f4a2713aSLionel Sambuc       HeaderFileInfoLookupTable::iterator Pos = Table->find(This->FE);
5088f4a2713aSLionel Sambuc       if (Pos == Table->end())
5089f4a2713aSLionel Sambuc         return false;
5090f4a2713aSLionel Sambuc 
5091f4a2713aSLionel Sambuc       This->HFI = *Pos;
5092f4a2713aSLionel Sambuc       return true;
5093f4a2713aSLionel Sambuc     }
5094f4a2713aSLionel Sambuc 
getHeaderFileInfo() const5095f4a2713aSLionel Sambuc     Optional<HeaderFileInfo> getHeaderFileInfo() const { return HFI; }
5096f4a2713aSLionel Sambuc   };
5097f4a2713aSLionel Sambuc }
5098f4a2713aSLionel Sambuc 
GetHeaderFileInfo(const FileEntry * FE)5099f4a2713aSLionel Sambuc HeaderFileInfo ASTReader::GetHeaderFileInfo(const FileEntry *FE) {
5100f4a2713aSLionel Sambuc   HeaderFileInfoVisitor Visitor(FE);
5101f4a2713aSLionel Sambuc   ModuleMgr.visit(&HeaderFileInfoVisitor::visit, &Visitor);
5102f4a2713aSLionel Sambuc   if (Optional<HeaderFileInfo> HFI = Visitor.getHeaderFileInfo())
5103f4a2713aSLionel Sambuc     return *HFI;
5104f4a2713aSLionel Sambuc 
5105f4a2713aSLionel Sambuc   return HeaderFileInfo();
5106f4a2713aSLionel Sambuc }
5107f4a2713aSLionel Sambuc 
ReadPragmaDiagnosticMappings(DiagnosticsEngine & Diag)5108f4a2713aSLionel Sambuc void ASTReader::ReadPragmaDiagnosticMappings(DiagnosticsEngine &Diag) {
5109f4a2713aSLionel Sambuc   // FIXME: Make it work properly with modules.
5110f4a2713aSLionel Sambuc   SmallVector<DiagnosticsEngine::DiagState *, 32> DiagStates;
5111f4a2713aSLionel Sambuc   for (ModuleIterator I = ModuleMgr.begin(), E = ModuleMgr.end(); I != E; ++I) {
5112f4a2713aSLionel Sambuc     ModuleFile &F = *(*I);
5113f4a2713aSLionel Sambuc     unsigned Idx = 0;
5114f4a2713aSLionel Sambuc     DiagStates.clear();
5115f4a2713aSLionel Sambuc     assert(!Diag.DiagStates.empty());
5116f4a2713aSLionel Sambuc     DiagStates.push_back(&Diag.DiagStates.front()); // the command-line one.
5117f4a2713aSLionel Sambuc     while (Idx < F.PragmaDiagMappings.size()) {
5118f4a2713aSLionel Sambuc       SourceLocation Loc = ReadSourceLocation(F, F.PragmaDiagMappings[Idx++]);
5119f4a2713aSLionel Sambuc       unsigned DiagStateID = F.PragmaDiagMappings[Idx++];
5120f4a2713aSLionel Sambuc       if (DiagStateID != 0) {
5121f4a2713aSLionel Sambuc         Diag.DiagStatePoints.push_back(
5122f4a2713aSLionel Sambuc                     DiagnosticsEngine::DiagStatePoint(DiagStates[DiagStateID-1],
5123f4a2713aSLionel Sambuc                     FullSourceLoc(Loc, SourceMgr)));
5124f4a2713aSLionel Sambuc         continue;
5125f4a2713aSLionel Sambuc       }
5126f4a2713aSLionel Sambuc 
5127f4a2713aSLionel Sambuc       assert(DiagStateID == 0);
5128f4a2713aSLionel Sambuc       // A new DiagState was created here.
5129f4a2713aSLionel Sambuc       Diag.DiagStates.push_back(*Diag.GetCurDiagState());
5130f4a2713aSLionel Sambuc       DiagnosticsEngine::DiagState *NewState = &Diag.DiagStates.back();
5131f4a2713aSLionel Sambuc       DiagStates.push_back(NewState);
5132f4a2713aSLionel Sambuc       Diag.DiagStatePoints.push_back(
5133f4a2713aSLionel Sambuc           DiagnosticsEngine::DiagStatePoint(NewState,
5134f4a2713aSLionel Sambuc                                             FullSourceLoc(Loc, SourceMgr)));
5135f4a2713aSLionel Sambuc       while (1) {
5136f4a2713aSLionel Sambuc         assert(Idx < F.PragmaDiagMappings.size() &&
5137f4a2713aSLionel Sambuc                "Invalid data, didn't find '-1' marking end of diag/map pairs");
5138f4a2713aSLionel Sambuc         if (Idx >= F.PragmaDiagMappings.size()) {
5139f4a2713aSLionel Sambuc           break; // Something is messed up but at least avoid infinite loop in
5140f4a2713aSLionel Sambuc                  // release build.
5141f4a2713aSLionel Sambuc         }
5142f4a2713aSLionel Sambuc         unsigned DiagID = F.PragmaDiagMappings[Idx++];
5143f4a2713aSLionel Sambuc         if (DiagID == (unsigned)-1) {
5144f4a2713aSLionel Sambuc           break; // no more diag/map pairs for this location.
5145f4a2713aSLionel Sambuc         }
5146*0a6a1f1dSLionel Sambuc         diag::Severity Map = (diag::Severity)F.PragmaDiagMappings[Idx++];
5147*0a6a1f1dSLionel Sambuc         DiagnosticMapping Mapping = Diag.makeUserMapping(Map, Loc);
5148*0a6a1f1dSLionel Sambuc         Diag.GetCurDiagState()->setMapping(DiagID, Mapping);
5149f4a2713aSLionel Sambuc       }
5150f4a2713aSLionel Sambuc     }
5151f4a2713aSLionel Sambuc   }
5152f4a2713aSLionel Sambuc }
5153f4a2713aSLionel Sambuc 
5154f4a2713aSLionel Sambuc /// \brief Get the correct cursor and offset for loading a type.
TypeCursorForIndex(unsigned Index)5155f4a2713aSLionel Sambuc ASTReader::RecordLocation ASTReader::TypeCursorForIndex(unsigned Index) {
5156f4a2713aSLionel Sambuc   GlobalTypeMapType::iterator I = GlobalTypeMap.find(Index);
5157f4a2713aSLionel Sambuc   assert(I != GlobalTypeMap.end() && "Corrupted global type map");
5158f4a2713aSLionel Sambuc   ModuleFile *M = I->second;
5159f4a2713aSLionel Sambuc   return RecordLocation(M, M->TypeOffsets[Index - M->BaseTypeIndex]);
5160f4a2713aSLionel Sambuc }
5161f4a2713aSLionel Sambuc 
5162f4a2713aSLionel Sambuc /// \brief Read and return the type with the given index..
5163f4a2713aSLionel Sambuc ///
5164f4a2713aSLionel Sambuc /// The index is the type ID, shifted and minus the number of predefs. This
5165f4a2713aSLionel Sambuc /// routine actually reads the record corresponding to the type at the given
5166f4a2713aSLionel Sambuc /// location. It is a helper routine for GetType, which deals with reading type
5167f4a2713aSLionel Sambuc /// IDs.
readTypeRecord(unsigned Index)5168f4a2713aSLionel Sambuc QualType ASTReader::readTypeRecord(unsigned Index) {
5169f4a2713aSLionel Sambuc   RecordLocation Loc = TypeCursorForIndex(Index);
5170f4a2713aSLionel Sambuc   BitstreamCursor &DeclsCursor = Loc.F->DeclsCursor;
5171f4a2713aSLionel Sambuc 
5172f4a2713aSLionel Sambuc   // Keep track of where we are in the stream, then jump back there
5173f4a2713aSLionel Sambuc   // after reading this type.
5174f4a2713aSLionel Sambuc   SavedStreamPosition SavedPosition(DeclsCursor);
5175f4a2713aSLionel Sambuc 
5176f4a2713aSLionel Sambuc   ReadingKindTracker ReadingKind(Read_Type, *this);
5177f4a2713aSLionel Sambuc 
5178f4a2713aSLionel Sambuc   // Note that we are loading a type record.
5179f4a2713aSLionel Sambuc   Deserializing AType(this);
5180f4a2713aSLionel Sambuc 
5181f4a2713aSLionel Sambuc   unsigned Idx = 0;
5182f4a2713aSLionel Sambuc   DeclsCursor.JumpToBit(Loc.Offset);
5183f4a2713aSLionel Sambuc   RecordData Record;
5184f4a2713aSLionel Sambuc   unsigned Code = DeclsCursor.ReadCode();
5185f4a2713aSLionel Sambuc   switch ((TypeCode)DeclsCursor.readRecord(Code, Record)) {
5186f4a2713aSLionel Sambuc   case TYPE_EXT_QUAL: {
5187f4a2713aSLionel Sambuc     if (Record.size() != 2) {
5188f4a2713aSLionel Sambuc       Error("Incorrect encoding of extended qualifier type");
5189f4a2713aSLionel Sambuc       return QualType();
5190f4a2713aSLionel Sambuc     }
5191f4a2713aSLionel Sambuc     QualType Base = readType(*Loc.F, Record, Idx);
5192f4a2713aSLionel Sambuc     Qualifiers Quals = Qualifiers::fromOpaqueValue(Record[Idx++]);
5193f4a2713aSLionel Sambuc     return Context.getQualifiedType(Base, Quals);
5194f4a2713aSLionel Sambuc   }
5195f4a2713aSLionel Sambuc 
5196f4a2713aSLionel Sambuc   case TYPE_COMPLEX: {
5197f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5198f4a2713aSLionel Sambuc       Error("Incorrect encoding of complex type");
5199f4a2713aSLionel Sambuc       return QualType();
5200f4a2713aSLionel Sambuc     }
5201f4a2713aSLionel Sambuc     QualType ElemType = readType(*Loc.F, Record, Idx);
5202f4a2713aSLionel Sambuc     return Context.getComplexType(ElemType);
5203f4a2713aSLionel Sambuc   }
5204f4a2713aSLionel Sambuc 
5205f4a2713aSLionel Sambuc   case TYPE_POINTER: {
5206f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5207f4a2713aSLionel Sambuc       Error("Incorrect encoding of pointer type");
5208f4a2713aSLionel Sambuc       return QualType();
5209f4a2713aSLionel Sambuc     }
5210f4a2713aSLionel Sambuc     QualType PointeeType = readType(*Loc.F, Record, Idx);
5211f4a2713aSLionel Sambuc     return Context.getPointerType(PointeeType);
5212f4a2713aSLionel Sambuc   }
5213f4a2713aSLionel Sambuc 
5214f4a2713aSLionel Sambuc   case TYPE_DECAYED: {
5215f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5216f4a2713aSLionel Sambuc       Error("Incorrect encoding of decayed type");
5217f4a2713aSLionel Sambuc       return QualType();
5218f4a2713aSLionel Sambuc     }
5219f4a2713aSLionel Sambuc     QualType OriginalType = readType(*Loc.F, Record, Idx);
5220f4a2713aSLionel Sambuc     QualType DT = Context.getAdjustedParameterType(OriginalType);
5221f4a2713aSLionel Sambuc     if (!isa<DecayedType>(DT))
5222f4a2713aSLionel Sambuc       Error("Decayed type does not decay");
5223f4a2713aSLionel Sambuc     return DT;
5224f4a2713aSLionel Sambuc   }
5225f4a2713aSLionel Sambuc 
5226*0a6a1f1dSLionel Sambuc   case TYPE_ADJUSTED: {
5227*0a6a1f1dSLionel Sambuc     if (Record.size() != 2) {
5228*0a6a1f1dSLionel Sambuc       Error("Incorrect encoding of adjusted type");
5229*0a6a1f1dSLionel Sambuc       return QualType();
5230*0a6a1f1dSLionel Sambuc     }
5231*0a6a1f1dSLionel Sambuc     QualType OriginalTy = readType(*Loc.F, Record, Idx);
5232*0a6a1f1dSLionel Sambuc     QualType AdjustedTy = readType(*Loc.F, Record, Idx);
5233*0a6a1f1dSLionel Sambuc     return Context.getAdjustedType(OriginalTy, AdjustedTy);
5234*0a6a1f1dSLionel Sambuc   }
5235*0a6a1f1dSLionel Sambuc 
5236f4a2713aSLionel Sambuc   case TYPE_BLOCK_POINTER: {
5237f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5238f4a2713aSLionel Sambuc       Error("Incorrect encoding of block pointer type");
5239f4a2713aSLionel Sambuc       return QualType();
5240f4a2713aSLionel Sambuc     }
5241f4a2713aSLionel Sambuc     QualType PointeeType = readType(*Loc.F, Record, Idx);
5242f4a2713aSLionel Sambuc     return Context.getBlockPointerType(PointeeType);
5243f4a2713aSLionel Sambuc   }
5244f4a2713aSLionel Sambuc 
5245f4a2713aSLionel Sambuc   case TYPE_LVALUE_REFERENCE: {
5246f4a2713aSLionel Sambuc     if (Record.size() != 2) {
5247f4a2713aSLionel Sambuc       Error("Incorrect encoding of lvalue reference type");
5248f4a2713aSLionel Sambuc       return QualType();
5249f4a2713aSLionel Sambuc     }
5250f4a2713aSLionel Sambuc     QualType PointeeType = readType(*Loc.F, Record, Idx);
5251f4a2713aSLionel Sambuc     return Context.getLValueReferenceType(PointeeType, Record[1]);
5252f4a2713aSLionel Sambuc   }
5253f4a2713aSLionel Sambuc 
5254f4a2713aSLionel Sambuc   case TYPE_RVALUE_REFERENCE: {
5255f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5256f4a2713aSLionel Sambuc       Error("Incorrect encoding of rvalue reference type");
5257f4a2713aSLionel Sambuc       return QualType();
5258f4a2713aSLionel Sambuc     }
5259f4a2713aSLionel Sambuc     QualType PointeeType = readType(*Loc.F, Record, Idx);
5260f4a2713aSLionel Sambuc     return Context.getRValueReferenceType(PointeeType);
5261f4a2713aSLionel Sambuc   }
5262f4a2713aSLionel Sambuc 
5263f4a2713aSLionel Sambuc   case TYPE_MEMBER_POINTER: {
5264f4a2713aSLionel Sambuc     if (Record.size() != 2) {
5265f4a2713aSLionel Sambuc       Error("Incorrect encoding of member pointer type");
5266f4a2713aSLionel Sambuc       return QualType();
5267f4a2713aSLionel Sambuc     }
5268f4a2713aSLionel Sambuc     QualType PointeeType = readType(*Loc.F, Record, Idx);
5269f4a2713aSLionel Sambuc     QualType ClassType = readType(*Loc.F, Record, Idx);
5270f4a2713aSLionel Sambuc     if (PointeeType.isNull() || ClassType.isNull())
5271f4a2713aSLionel Sambuc       return QualType();
5272f4a2713aSLionel Sambuc 
5273f4a2713aSLionel Sambuc     return Context.getMemberPointerType(PointeeType, ClassType.getTypePtr());
5274f4a2713aSLionel Sambuc   }
5275f4a2713aSLionel Sambuc 
5276f4a2713aSLionel Sambuc   case TYPE_CONSTANT_ARRAY: {
5277f4a2713aSLionel Sambuc     QualType ElementType = readType(*Loc.F, Record, Idx);
5278f4a2713aSLionel Sambuc     ArrayType::ArraySizeModifier ASM = (ArrayType::ArraySizeModifier)Record[1];
5279f4a2713aSLionel Sambuc     unsigned IndexTypeQuals = Record[2];
5280f4a2713aSLionel Sambuc     unsigned Idx = 3;
5281f4a2713aSLionel Sambuc     llvm::APInt Size = ReadAPInt(Record, Idx);
5282f4a2713aSLionel Sambuc     return Context.getConstantArrayType(ElementType, Size,
5283f4a2713aSLionel Sambuc                                          ASM, IndexTypeQuals);
5284f4a2713aSLionel Sambuc   }
5285f4a2713aSLionel Sambuc 
5286f4a2713aSLionel Sambuc   case TYPE_INCOMPLETE_ARRAY: {
5287f4a2713aSLionel Sambuc     QualType ElementType = readType(*Loc.F, Record, Idx);
5288f4a2713aSLionel Sambuc     ArrayType::ArraySizeModifier ASM = (ArrayType::ArraySizeModifier)Record[1];
5289f4a2713aSLionel Sambuc     unsigned IndexTypeQuals = Record[2];
5290f4a2713aSLionel Sambuc     return Context.getIncompleteArrayType(ElementType, ASM, IndexTypeQuals);
5291f4a2713aSLionel Sambuc   }
5292f4a2713aSLionel Sambuc 
5293f4a2713aSLionel Sambuc   case TYPE_VARIABLE_ARRAY: {
5294f4a2713aSLionel Sambuc     QualType ElementType = readType(*Loc.F, Record, Idx);
5295f4a2713aSLionel Sambuc     ArrayType::ArraySizeModifier ASM = (ArrayType::ArraySizeModifier)Record[1];
5296f4a2713aSLionel Sambuc     unsigned IndexTypeQuals = Record[2];
5297f4a2713aSLionel Sambuc     SourceLocation LBLoc = ReadSourceLocation(*Loc.F, Record[3]);
5298f4a2713aSLionel Sambuc     SourceLocation RBLoc = ReadSourceLocation(*Loc.F, Record[4]);
5299f4a2713aSLionel Sambuc     return Context.getVariableArrayType(ElementType, ReadExpr(*Loc.F),
5300f4a2713aSLionel Sambuc                                          ASM, IndexTypeQuals,
5301f4a2713aSLionel Sambuc                                          SourceRange(LBLoc, RBLoc));
5302f4a2713aSLionel Sambuc   }
5303f4a2713aSLionel Sambuc 
5304f4a2713aSLionel Sambuc   case TYPE_VECTOR: {
5305f4a2713aSLionel Sambuc     if (Record.size() != 3) {
5306f4a2713aSLionel Sambuc       Error("incorrect encoding of vector type in AST file");
5307f4a2713aSLionel Sambuc       return QualType();
5308f4a2713aSLionel Sambuc     }
5309f4a2713aSLionel Sambuc 
5310f4a2713aSLionel Sambuc     QualType ElementType = readType(*Loc.F, Record, Idx);
5311f4a2713aSLionel Sambuc     unsigned NumElements = Record[1];
5312f4a2713aSLionel Sambuc     unsigned VecKind = Record[2];
5313f4a2713aSLionel Sambuc     return Context.getVectorType(ElementType, NumElements,
5314f4a2713aSLionel Sambuc                                   (VectorType::VectorKind)VecKind);
5315f4a2713aSLionel Sambuc   }
5316f4a2713aSLionel Sambuc 
5317f4a2713aSLionel Sambuc   case TYPE_EXT_VECTOR: {
5318f4a2713aSLionel Sambuc     if (Record.size() != 3) {
5319f4a2713aSLionel Sambuc       Error("incorrect encoding of extended vector type in AST file");
5320f4a2713aSLionel Sambuc       return QualType();
5321f4a2713aSLionel Sambuc     }
5322f4a2713aSLionel Sambuc 
5323f4a2713aSLionel Sambuc     QualType ElementType = readType(*Loc.F, Record, Idx);
5324f4a2713aSLionel Sambuc     unsigned NumElements = Record[1];
5325f4a2713aSLionel Sambuc     return Context.getExtVectorType(ElementType, NumElements);
5326f4a2713aSLionel Sambuc   }
5327f4a2713aSLionel Sambuc 
5328f4a2713aSLionel Sambuc   case TYPE_FUNCTION_NO_PROTO: {
5329f4a2713aSLionel Sambuc     if (Record.size() != 6) {
5330f4a2713aSLionel Sambuc       Error("incorrect encoding of no-proto function type");
5331f4a2713aSLionel Sambuc       return QualType();
5332f4a2713aSLionel Sambuc     }
5333f4a2713aSLionel Sambuc     QualType ResultType = readType(*Loc.F, Record, Idx);
5334f4a2713aSLionel Sambuc     FunctionType::ExtInfo Info(Record[1], Record[2], Record[3],
5335f4a2713aSLionel Sambuc                                (CallingConv)Record[4], Record[5]);
5336f4a2713aSLionel Sambuc     return Context.getFunctionNoProtoType(ResultType, Info);
5337f4a2713aSLionel Sambuc   }
5338f4a2713aSLionel Sambuc 
5339f4a2713aSLionel Sambuc   case TYPE_FUNCTION_PROTO: {
5340f4a2713aSLionel Sambuc     QualType ResultType = readType(*Loc.F, Record, Idx);
5341f4a2713aSLionel Sambuc 
5342f4a2713aSLionel Sambuc     FunctionProtoType::ExtProtoInfo EPI;
5343f4a2713aSLionel Sambuc     EPI.ExtInfo = FunctionType::ExtInfo(/*noreturn*/ Record[1],
5344f4a2713aSLionel Sambuc                                         /*hasregparm*/ Record[2],
5345f4a2713aSLionel Sambuc                                         /*regparm*/ Record[3],
5346f4a2713aSLionel Sambuc                                         static_cast<CallingConv>(Record[4]),
5347f4a2713aSLionel Sambuc                                         /*produces*/ Record[5]);
5348f4a2713aSLionel Sambuc 
5349f4a2713aSLionel Sambuc     unsigned Idx = 6;
5350f4a2713aSLionel Sambuc 
5351f4a2713aSLionel Sambuc     EPI.Variadic = Record[Idx++];
5352f4a2713aSLionel Sambuc     EPI.HasTrailingReturn = Record[Idx++];
5353f4a2713aSLionel Sambuc     EPI.TypeQuals = Record[Idx++];
5354f4a2713aSLionel Sambuc     EPI.RefQualifier = static_cast<RefQualifierKind>(Record[Idx++]);
5355*0a6a1f1dSLionel Sambuc     SmallVector<QualType, 8> ExceptionStorage;
5356*0a6a1f1dSLionel Sambuc     readExceptionSpec(*Loc.F, ExceptionStorage, EPI.ExceptionSpec, Record, Idx);
5357*0a6a1f1dSLionel Sambuc 
5358*0a6a1f1dSLionel Sambuc     unsigned NumParams = Record[Idx++];
5359*0a6a1f1dSLionel Sambuc     SmallVector<QualType, 16> ParamTypes;
5360*0a6a1f1dSLionel Sambuc     for (unsigned I = 0; I != NumParams; ++I)
5361*0a6a1f1dSLionel Sambuc       ParamTypes.push_back(readType(*Loc.F, Record, Idx));
5362*0a6a1f1dSLionel Sambuc 
5363f4a2713aSLionel Sambuc     return Context.getFunctionType(ResultType, ParamTypes, EPI);
5364f4a2713aSLionel Sambuc   }
5365f4a2713aSLionel Sambuc 
5366f4a2713aSLionel Sambuc   case TYPE_UNRESOLVED_USING: {
5367f4a2713aSLionel Sambuc     unsigned Idx = 0;
5368f4a2713aSLionel Sambuc     return Context.getTypeDeclType(
5369f4a2713aSLionel Sambuc                   ReadDeclAs<UnresolvedUsingTypenameDecl>(*Loc.F, Record, Idx));
5370f4a2713aSLionel Sambuc   }
5371f4a2713aSLionel Sambuc 
5372f4a2713aSLionel Sambuc   case TYPE_TYPEDEF: {
5373f4a2713aSLionel Sambuc     if (Record.size() != 2) {
5374f4a2713aSLionel Sambuc       Error("incorrect encoding of typedef type");
5375f4a2713aSLionel Sambuc       return QualType();
5376f4a2713aSLionel Sambuc     }
5377f4a2713aSLionel Sambuc     unsigned Idx = 0;
5378f4a2713aSLionel Sambuc     TypedefNameDecl *Decl = ReadDeclAs<TypedefNameDecl>(*Loc.F, Record, Idx);
5379f4a2713aSLionel Sambuc     QualType Canonical = readType(*Loc.F, Record, Idx);
5380f4a2713aSLionel Sambuc     if (!Canonical.isNull())
5381f4a2713aSLionel Sambuc       Canonical = Context.getCanonicalType(Canonical);
5382f4a2713aSLionel Sambuc     return Context.getTypedefType(Decl, Canonical);
5383f4a2713aSLionel Sambuc   }
5384f4a2713aSLionel Sambuc 
5385f4a2713aSLionel Sambuc   case TYPE_TYPEOF_EXPR:
5386f4a2713aSLionel Sambuc     return Context.getTypeOfExprType(ReadExpr(*Loc.F));
5387f4a2713aSLionel Sambuc 
5388f4a2713aSLionel Sambuc   case TYPE_TYPEOF: {
5389f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5390f4a2713aSLionel Sambuc       Error("incorrect encoding of typeof(type) in AST file");
5391f4a2713aSLionel Sambuc       return QualType();
5392f4a2713aSLionel Sambuc     }
5393f4a2713aSLionel Sambuc     QualType UnderlyingType = readType(*Loc.F, Record, Idx);
5394f4a2713aSLionel Sambuc     return Context.getTypeOfType(UnderlyingType);
5395f4a2713aSLionel Sambuc   }
5396f4a2713aSLionel Sambuc 
5397f4a2713aSLionel Sambuc   case TYPE_DECLTYPE: {
5398f4a2713aSLionel Sambuc     QualType UnderlyingType = readType(*Loc.F, Record, Idx);
5399f4a2713aSLionel Sambuc     return Context.getDecltypeType(ReadExpr(*Loc.F), UnderlyingType);
5400f4a2713aSLionel Sambuc   }
5401f4a2713aSLionel Sambuc 
5402f4a2713aSLionel Sambuc   case TYPE_UNARY_TRANSFORM: {
5403f4a2713aSLionel Sambuc     QualType BaseType = readType(*Loc.F, Record, Idx);
5404f4a2713aSLionel Sambuc     QualType UnderlyingType = readType(*Loc.F, Record, Idx);
5405f4a2713aSLionel Sambuc     UnaryTransformType::UTTKind UKind = (UnaryTransformType::UTTKind)Record[2];
5406f4a2713aSLionel Sambuc     return Context.getUnaryTransformType(BaseType, UnderlyingType, UKind);
5407f4a2713aSLionel Sambuc   }
5408f4a2713aSLionel Sambuc 
5409f4a2713aSLionel Sambuc   case TYPE_AUTO: {
5410f4a2713aSLionel Sambuc     QualType Deduced = readType(*Loc.F, Record, Idx);
5411f4a2713aSLionel Sambuc     bool IsDecltypeAuto = Record[Idx++];
5412f4a2713aSLionel Sambuc     bool IsDependent = Deduced.isNull() ? Record[Idx++] : false;
5413f4a2713aSLionel Sambuc     return Context.getAutoType(Deduced, IsDecltypeAuto, IsDependent);
5414f4a2713aSLionel Sambuc   }
5415f4a2713aSLionel Sambuc 
5416f4a2713aSLionel Sambuc   case TYPE_RECORD: {
5417f4a2713aSLionel Sambuc     if (Record.size() != 2) {
5418f4a2713aSLionel Sambuc       Error("incorrect encoding of record type");
5419f4a2713aSLionel Sambuc       return QualType();
5420f4a2713aSLionel Sambuc     }
5421f4a2713aSLionel Sambuc     unsigned Idx = 0;
5422f4a2713aSLionel Sambuc     bool IsDependent = Record[Idx++];
5423f4a2713aSLionel Sambuc     RecordDecl *RD = ReadDeclAs<RecordDecl>(*Loc.F, Record, Idx);
5424f4a2713aSLionel Sambuc     RD = cast_or_null<RecordDecl>(RD->getCanonicalDecl());
5425f4a2713aSLionel Sambuc     QualType T = Context.getRecordType(RD);
5426f4a2713aSLionel Sambuc     const_cast<Type*>(T.getTypePtr())->setDependent(IsDependent);
5427f4a2713aSLionel Sambuc     return T;
5428f4a2713aSLionel Sambuc   }
5429f4a2713aSLionel Sambuc 
5430f4a2713aSLionel Sambuc   case TYPE_ENUM: {
5431f4a2713aSLionel Sambuc     if (Record.size() != 2) {
5432f4a2713aSLionel Sambuc       Error("incorrect encoding of enum type");
5433f4a2713aSLionel Sambuc       return QualType();
5434f4a2713aSLionel Sambuc     }
5435f4a2713aSLionel Sambuc     unsigned Idx = 0;
5436f4a2713aSLionel Sambuc     bool IsDependent = Record[Idx++];
5437f4a2713aSLionel Sambuc     QualType T
5438f4a2713aSLionel Sambuc       = Context.getEnumType(ReadDeclAs<EnumDecl>(*Loc.F, Record, Idx));
5439f4a2713aSLionel Sambuc     const_cast<Type*>(T.getTypePtr())->setDependent(IsDependent);
5440f4a2713aSLionel Sambuc     return T;
5441f4a2713aSLionel Sambuc   }
5442f4a2713aSLionel Sambuc 
5443f4a2713aSLionel Sambuc   case TYPE_ATTRIBUTED: {
5444f4a2713aSLionel Sambuc     if (Record.size() != 3) {
5445f4a2713aSLionel Sambuc       Error("incorrect encoding of attributed type");
5446f4a2713aSLionel Sambuc       return QualType();
5447f4a2713aSLionel Sambuc     }
5448f4a2713aSLionel Sambuc     QualType modifiedType = readType(*Loc.F, Record, Idx);
5449f4a2713aSLionel Sambuc     QualType equivalentType = readType(*Loc.F, Record, Idx);
5450f4a2713aSLionel Sambuc     AttributedType::Kind kind = static_cast<AttributedType::Kind>(Record[2]);
5451f4a2713aSLionel Sambuc     return Context.getAttributedType(kind, modifiedType, equivalentType);
5452f4a2713aSLionel Sambuc   }
5453f4a2713aSLionel Sambuc 
5454f4a2713aSLionel Sambuc   case TYPE_PAREN: {
5455f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5456f4a2713aSLionel Sambuc       Error("incorrect encoding of paren type");
5457f4a2713aSLionel Sambuc       return QualType();
5458f4a2713aSLionel Sambuc     }
5459f4a2713aSLionel Sambuc     QualType InnerType = readType(*Loc.F, Record, Idx);
5460f4a2713aSLionel Sambuc     return Context.getParenType(InnerType);
5461f4a2713aSLionel Sambuc   }
5462f4a2713aSLionel Sambuc 
5463f4a2713aSLionel Sambuc   case TYPE_PACK_EXPANSION: {
5464f4a2713aSLionel Sambuc     if (Record.size() != 2) {
5465f4a2713aSLionel Sambuc       Error("incorrect encoding of pack expansion type");
5466f4a2713aSLionel Sambuc       return QualType();
5467f4a2713aSLionel Sambuc     }
5468f4a2713aSLionel Sambuc     QualType Pattern = readType(*Loc.F, Record, Idx);
5469f4a2713aSLionel Sambuc     if (Pattern.isNull())
5470f4a2713aSLionel Sambuc       return QualType();
5471f4a2713aSLionel Sambuc     Optional<unsigned> NumExpansions;
5472f4a2713aSLionel Sambuc     if (Record[1])
5473f4a2713aSLionel Sambuc       NumExpansions = Record[1] - 1;
5474f4a2713aSLionel Sambuc     return Context.getPackExpansionType(Pattern, NumExpansions);
5475f4a2713aSLionel Sambuc   }
5476f4a2713aSLionel Sambuc 
5477f4a2713aSLionel Sambuc   case TYPE_ELABORATED: {
5478f4a2713aSLionel Sambuc     unsigned Idx = 0;
5479f4a2713aSLionel Sambuc     ElaboratedTypeKeyword Keyword = (ElaboratedTypeKeyword)Record[Idx++];
5480f4a2713aSLionel Sambuc     NestedNameSpecifier *NNS = ReadNestedNameSpecifier(*Loc.F, Record, Idx);
5481f4a2713aSLionel Sambuc     QualType NamedType = readType(*Loc.F, Record, Idx);
5482f4a2713aSLionel Sambuc     return Context.getElaboratedType(Keyword, NNS, NamedType);
5483f4a2713aSLionel Sambuc   }
5484f4a2713aSLionel Sambuc 
5485f4a2713aSLionel Sambuc   case TYPE_OBJC_INTERFACE: {
5486f4a2713aSLionel Sambuc     unsigned Idx = 0;
5487f4a2713aSLionel Sambuc     ObjCInterfaceDecl *ItfD
5488f4a2713aSLionel Sambuc       = ReadDeclAs<ObjCInterfaceDecl>(*Loc.F, Record, Idx);
5489f4a2713aSLionel Sambuc     return Context.getObjCInterfaceType(ItfD->getCanonicalDecl());
5490f4a2713aSLionel Sambuc   }
5491f4a2713aSLionel Sambuc 
5492f4a2713aSLionel Sambuc   case TYPE_OBJC_OBJECT: {
5493f4a2713aSLionel Sambuc     unsigned Idx = 0;
5494f4a2713aSLionel Sambuc     QualType Base = readType(*Loc.F, Record, Idx);
5495f4a2713aSLionel Sambuc     unsigned NumProtos = Record[Idx++];
5496f4a2713aSLionel Sambuc     SmallVector<ObjCProtocolDecl*, 4> Protos;
5497f4a2713aSLionel Sambuc     for (unsigned I = 0; I != NumProtos; ++I)
5498f4a2713aSLionel Sambuc       Protos.push_back(ReadDeclAs<ObjCProtocolDecl>(*Loc.F, Record, Idx));
5499f4a2713aSLionel Sambuc     return Context.getObjCObjectType(Base, Protos.data(), NumProtos);
5500f4a2713aSLionel Sambuc   }
5501f4a2713aSLionel Sambuc 
5502f4a2713aSLionel Sambuc   case TYPE_OBJC_OBJECT_POINTER: {
5503f4a2713aSLionel Sambuc     unsigned Idx = 0;
5504f4a2713aSLionel Sambuc     QualType Pointee = readType(*Loc.F, Record, Idx);
5505f4a2713aSLionel Sambuc     return Context.getObjCObjectPointerType(Pointee);
5506f4a2713aSLionel Sambuc   }
5507f4a2713aSLionel Sambuc 
5508f4a2713aSLionel Sambuc   case TYPE_SUBST_TEMPLATE_TYPE_PARM: {
5509f4a2713aSLionel Sambuc     unsigned Idx = 0;
5510f4a2713aSLionel Sambuc     QualType Parm = readType(*Loc.F, Record, Idx);
5511f4a2713aSLionel Sambuc     QualType Replacement = readType(*Loc.F, Record, Idx);
5512*0a6a1f1dSLionel Sambuc     return Context.getSubstTemplateTypeParmType(
5513*0a6a1f1dSLionel Sambuc         cast<TemplateTypeParmType>(Parm),
5514*0a6a1f1dSLionel Sambuc         Context.getCanonicalType(Replacement));
5515f4a2713aSLionel Sambuc   }
5516f4a2713aSLionel Sambuc 
5517f4a2713aSLionel Sambuc   case TYPE_SUBST_TEMPLATE_TYPE_PARM_PACK: {
5518f4a2713aSLionel Sambuc     unsigned Idx = 0;
5519f4a2713aSLionel Sambuc     QualType Parm = readType(*Loc.F, Record, Idx);
5520f4a2713aSLionel Sambuc     TemplateArgument ArgPack = ReadTemplateArgument(*Loc.F, Record, Idx);
5521f4a2713aSLionel Sambuc     return Context.getSubstTemplateTypeParmPackType(
5522f4a2713aSLionel Sambuc                                                cast<TemplateTypeParmType>(Parm),
5523f4a2713aSLionel Sambuc                                                      ArgPack);
5524f4a2713aSLionel Sambuc   }
5525f4a2713aSLionel Sambuc 
5526f4a2713aSLionel Sambuc   case TYPE_INJECTED_CLASS_NAME: {
5527f4a2713aSLionel Sambuc     CXXRecordDecl *D = ReadDeclAs<CXXRecordDecl>(*Loc.F, Record, Idx);
5528f4a2713aSLionel Sambuc     QualType TST = readType(*Loc.F, Record, Idx); // probably derivable
5529f4a2713aSLionel Sambuc     // FIXME: ASTContext::getInjectedClassNameType is not currently suitable
5530f4a2713aSLionel Sambuc     // for AST reading, too much interdependencies.
5531*0a6a1f1dSLionel Sambuc     const Type *T = nullptr;
5532*0a6a1f1dSLionel Sambuc     for (auto *DI = D; DI; DI = DI->getPreviousDecl()) {
5533*0a6a1f1dSLionel Sambuc       if (const Type *Existing = DI->getTypeForDecl()) {
5534*0a6a1f1dSLionel Sambuc         T = Existing;
5535*0a6a1f1dSLionel Sambuc         break;
5536*0a6a1f1dSLionel Sambuc       }
5537*0a6a1f1dSLionel Sambuc     }
5538*0a6a1f1dSLionel Sambuc     if (!T) {
5539*0a6a1f1dSLionel Sambuc       T = new (Context, TypeAlignment) InjectedClassNameType(D, TST);
5540*0a6a1f1dSLionel Sambuc       for (auto *DI = D; DI; DI = DI->getPreviousDecl())
5541*0a6a1f1dSLionel Sambuc         DI->setTypeForDecl(T);
5542*0a6a1f1dSLionel Sambuc     }
5543*0a6a1f1dSLionel Sambuc     return QualType(T, 0);
5544f4a2713aSLionel Sambuc   }
5545f4a2713aSLionel Sambuc 
5546f4a2713aSLionel Sambuc   case TYPE_TEMPLATE_TYPE_PARM: {
5547f4a2713aSLionel Sambuc     unsigned Idx = 0;
5548f4a2713aSLionel Sambuc     unsigned Depth = Record[Idx++];
5549f4a2713aSLionel Sambuc     unsigned Index = Record[Idx++];
5550f4a2713aSLionel Sambuc     bool Pack = Record[Idx++];
5551f4a2713aSLionel Sambuc     TemplateTypeParmDecl *D
5552f4a2713aSLionel Sambuc       = ReadDeclAs<TemplateTypeParmDecl>(*Loc.F, Record, Idx);
5553f4a2713aSLionel Sambuc     return Context.getTemplateTypeParmType(Depth, Index, Pack, D);
5554f4a2713aSLionel Sambuc   }
5555f4a2713aSLionel Sambuc 
5556f4a2713aSLionel Sambuc   case TYPE_DEPENDENT_NAME: {
5557f4a2713aSLionel Sambuc     unsigned Idx = 0;
5558f4a2713aSLionel Sambuc     ElaboratedTypeKeyword Keyword = (ElaboratedTypeKeyword)Record[Idx++];
5559f4a2713aSLionel Sambuc     NestedNameSpecifier *NNS = ReadNestedNameSpecifier(*Loc.F, Record, Idx);
5560f4a2713aSLionel Sambuc     const IdentifierInfo *Name = this->GetIdentifierInfo(*Loc.F, Record, Idx);
5561f4a2713aSLionel Sambuc     QualType Canon = readType(*Loc.F, Record, Idx);
5562f4a2713aSLionel Sambuc     if (!Canon.isNull())
5563f4a2713aSLionel Sambuc       Canon = Context.getCanonicalType(Canon);
5564f4a2713aSLionel Sambuc     return Context.getDependentNameType(Keyword, NNS, Name, Canon);
5565f4a2713aSLionel Sambuc   }
5566f4a2713aSLionel Sambuc 
5567f4a2713aSLionel Sambuc   case TYPE_DEPENDENT_TEMPLATE_SPECIALIZATION: {
5568f4a2713aSLionel Sambuc     unsigned Idx = 0;
5569f4a2713aSLionel Sambuc     ElaboratedTypeKeyword Keyword = (ElaboratedTypeKeyword)Record[Idx++];
5570f4a2713aSLionel Sambuc     NestedNameSpecifier *NNS = ReadNestedNameSpecifier(*Loc.F, Record, Idx);
5571f4a2713aSLionel Sambuc     const IdentifierInfo *Name = this->GetIdentifierInfo(*Loc.F, Record, Idx);
5572f4a2713aSLionel Sambuc     unsigned NumArgs = Record[Idx++];
5573f4a2713aSLionel Sambuc     SmallVector<TemplateArgument, 8> Args;
5574f4a2713aSLionel Sambuc     Args.reserve(NumArgs);
5575f4a2713aSLionel Sambuc     while (NumArgs--)
5576f4a2713aSLionel Sambuc       Args.push_back(ReadTemplateArgument(*Loc.F, Record, Idx));
5577f4a2713aSLionel Sambuc     return Context.getDependentTemplateSpecializationType(Keyword, NNS, Name,
5578f4a2713aSLionel Sambuc                                                       Args.size(), Args.data());
5579f4a2713aSLionel Sambuc   }
5580f4a2713aSLionel Sambuc 
5581f4a2713aSLionel Sambuc   case TYPE_DEPENDENT_SIZED_ARRAY: {
5582f4a2713aSLionel Sambuc     unsigned Idx = 0;
5583f4a2713aSLionel Sambuc 
5584f4a2713aSLionel Sambuc     // ArrayType
5585f4a2713aSLionel Sambuc     QualType ElementType = readType(*Loc.F, Record, Idx);
5586f4a2713aSLionel Sambuc     ArrayType::ArraySizeModifier ASM
5587f4a2713aSLionel Sambuc       = (ArrayType::ArraySizeModifier)Record[Idx++];
5588f4a2713aSLionel Sambuc     unsigned IndexTypeQuals = Record[Idx++];
5589f4a2713aSLionel Sambuc 
5590f4a2713aSLionel Sambuc     // DependentSizedArrayType
5591f4a2713aSLionel Sambuc     Expr *NumElts = ReadExpr(*Loc.F);
5592f4a2713aSLionel Sambuc     SourceRange Brackets = ReadSourceRange(*Loc.F, Record, Idx);
5593f4a2713aSLionel Sambuc 
5594f4a2713aSLionel Sambuc     return Context.getDependentSizedArrayType(ElementType, NumElts, ASM,
5595f4a2713aSLionel Sambuc                                                IndexTypeQuals, Brackets);
5596f4a2713aSLionel Sambuc   }
5597f4a2713aSLionel Sambuc 
5598f4a2713aSLionel Sambuc   case TYPE_TEMPLATE_SPECIALIZATION: {
5599f4a2713aSLionel Sambuc     unsigned Idx = 0;
5600f4a2713aSLionel Sambuc     bool IsDependent = Record[Idx++];
5601f4a2713aSLionel Sambuc     TemplateName Name = ReadTemplateName(*Loc.F, Record, Idx);
5602f4a2713aSLionel Sambuc     SmallVector<TemplateArgument, 8> Args;
5603f4a2713aSLionel Sambuc     ReadTemplateArgumentList(Args, *Loc.F, Record, Idx);
5604f4a2713aSLionel Sambuc     QualType Underlying = readType(*Loc.F, Record, Idx);
5605f4a2713aSLionel Sambuc     QualType T;
5606f4a2713aSLionel Sambuc     if (Underlying.isNull())
5607f4a2713aSLionel Sambuc       T = Context.getCanonicalTemplateSpecializationType(Name, Args.data(),
5608f4a2713aSLionel Sambuc                                                           Args.size());
5609f4a2713aSLionel Sambuc     else
5610f4a2713aSLionel Sambuc       T = Context.getTemplateSpecializationType(Name, Args.data(),
5611f4a2713aSLionel Sambuc                                                  Args.size(), Underlying);
5612f4a2713aSLionel Sambuc     const_cast<Type*>(T.getTypePtr())->setDependent(IsDependent);
5613f4a2713aSLionel Sambuc     return T;
5614f4a2713aSLionel Sambuc   }
5615f4a2713aSLionel Sambuc 
5616f4a2713aSLionel Sambuc   case TYPE_ATOMIC: {
5617f4a2713aSLionel Sambuc     if (Record.size() != 1) {
5618f4a2713aSLionel Sambuc       Error("Incorrect encoding of atomic type");
5619f4a2713aSLionel Sambuc       return QualType();
5620f4a2713aSLionel Sambuc     }
5621f4a2713aSLionel Sambuc     QualType ValueType = readType(*Loc.F, Record, Idx);
5622f4a2713aSLionel Sambuc     return Context.getAtomicType(ValueType);
5623f4a2713aSLionel Sambuc   }
5624f4a2713aSLionel Sambuc   }
5625f4a2713aSLionel Sambuc   llvm_unreachable("Invalid TypeCode!");
5626f4a2713aSLionel Sambuc }
5627f4a2713aSLionel Sambuc 
readExceptionSpec(ModuleFile & ModuleFile,SmallVectorImpl<QualType> & Exceptions,FunctionProtoType::ExceptionSpecInfo & ESI,const RecordData & Record,unsigned & Idx)5628*0a6a1f1dSLionel Sambuc void ASTReader::readExceptionSpec(ModuleFile &ModuleFile,
5629*0a6a1f1dSLionel Sambuc                                   SmallVectorImpl<QualType> &Exceptions,
5630*0a6a1f1dSLionel Sambuc                                   FunctionProtoType::ExceptionSpecInfo &ESI,
5631*0a6a1f1dSLionel Sambuc                                   const RecordData &Record, unsigned &Idx) {
5632*0a6a1f1dSLionel Sambuc   ExceptionSpecificationType EST =
5633*0a6a1f1dSLionel Sambuc       static_cast<ExceptionSpecificationType>(Record[Idx++]);
5634*0a6a1f1dSLionel Sambuc   ESI.Type = EST;
5635*0a6a1f1dSLionel Sambuc   if (EST == EST_Dynamic) {
5636*0a6a1f1dSLionel Sambuc     for (unsigned I = 0, N = Record[Idx++]; I != N; ++I)
5637*0a6a1f1dSLionel Sambuc       Exceptions.push_back(readType(ModuleFile, Record, Idx));
5638*0a6a1f1dSLionel Sambuc     ESI.Exceptions = Exceptions;
5639*0a6a1f1dSLionel Sambuc   } else if (EST == EST_ComputedNoexcept) {
5640*0a6a1f1dSLionel Sambuc     ESI.NoexceptExpr = ReadExpr(ModuleFile);
5641*0a6a1f1dSLionel Sambuc   } else if (EST == EST_Uninstantiated) {
5642*0a6a1f1dSLionel Sambuc     ESI.SourceDecl = ReadDeclAs<FunctionDecl>(ModuleFile, Record, Idx);
5643*0a6a1f1dSLionel Sambuc     ESI.SourceTemplate = ReadDeclAs<FunctionDecl>(ModuleFile, Record, Idx);
5644*0a6a1f1dSLionel Sambuc   } else if (EST == EST_Unevaluated) {
5645*0a6a1f1dSLionel Sambuc     ESI.SourceDecl = ReadDeclAs<FunctionDecl>(ModuleFile, Record, Idx);
5646*0a6a1f1dSLionel Sambuc   }
5647*0a6a1f1dSLionel Sambuc }
5648*0a6a1f1dSLionel Sambuc 
5649f4a2713aSLionel Sambuc class clang::TypeLocReader : public TypeLocVisitor<TypeLocReader> {
5650f4a2713aSLionel Sambuc   ASTReader &Reader;
5651f4a2713aSLionel Sambuc   ModuleFile &F;
5652f4a2713aSLionel Sambuc   const ASTReader::RecordData &Record;
5653f4a2713aSLionel Sambuc   unsigned &Idx;
5654f4a2713aSLionel Sambuc 
ReadSourceLocation(const ASTReader::RecordData & R,unsigned & I)5655f4a2713aSLionel Sambuc   SourceLocation ReadSourceLocation(const ASTReader::RecordData &R,
5656f4a2713aSLionel Sambuc                                     unsigned &I) {
5657f4a2713aSLionel Sambuc     return Reader.ReadSourceLocation(F, R, I);
5658f4a2713aSLionel Sambuc   }
5659f4a2713aSLionel Sambuc 
5660f4a2713aSLionel Sambuc   template<typename T>
ReadDeclAs(const ASTReader::RecordData & Record,unsigned & Idx)5661f4a2713aSLionel Sambuc   T *ReadDeclAs(const ASTReader::RecordData &Record, unsigned &Idx) {
5662f4a2713aSLionel Sambuc     return Reader.ReadDeclAs<T>(F, Record, Idx);
5663f4a2713aSLionel Sambuc   }
5664f4a2713aSLionel Sambuc 
5665f4a2713aSLionel Sambuc public:
TypeLocReader(ASTReader & Reader,ModuleFile & F,const ASTReader::RecordData & Record,unsigned & Idx)5666f4a2713aSLionel Sambuc   TypeLocReader(ASTReader &Reader, ModuleFile &F,
5667f4a2713aSLionel Sambuc                 const ASTReader::RecordData &Record, unsigned &Idx)
5668f4a2713aSLionel Sambuc     : Reader(Reader), F(F), Record(Record), Idx(Idx)
5669f4a2713aSLionel Sambuc   { }
5670f4a2713aSLionel Sambuc 
5671f4a2713aSLionel Sambuc   // We want compile-time assurance that we've enumerated all of
5672f4a2713aSLionel Sambuc   // these, so unfortunately we have to declare them first, then
5673f4a2713aSLionel Sambuc   // define them out-of-line.
5674f4a2713aSLionel Sambuc #define ABSTRACT_TYPELOC(CLASS, PARENT)
5675f4a2713aSLionel Sambuc #define TYPELOC(CLASS, PARENT) \
5676f4a2713aSLionel Sambuc   void Visit##CLASS##TypeLoc(CLASS##TypeLoc TyLoc);
5677f4a2713aSLionel Sambuc #include "clang/AST/TypeLocNodes.def"
5678f4a2713aSLionel Sambuc 
5679f4a2713aSLionel Sambuc   void VisitFunctionTypeLoc(FunctionTypeLoc);
5680f4a2713aSLionel Sambuc   void VisitArrayTypeLoc(ArrayTypeLoc);
5681f4a2713aSLionel Sambuc };
5682f4a2713aSLionel Sambuc 
VisitQualifiedTypeLoc(QualifiedTypeLoc TL)5683f4a2713aSLionel Sambuc void TypeLocReader::VisitQualifiedTypeLoc(QualifiedTypeLoc TL) {
5684f4a2713aSLionel Sambuc   // nothing to do
5685f4a2713aSLionel Sambuc }
VisitBuiltinTypeLoc(BuiltinTypeLoc TL)5686f4a2713aSLionel Sambuc void TypeLocReader::VisitBuiltinTypeLoc(BuiltinTypeLoc TL) {
5687f4a2713aSLionel Sambuc   TL.setBuiltinLoc(ReadSourceLocation(Record, Idx));
5688f4a2713aSLionel Sambuc   if (TL.needsExtraLocalData()) {
5689f4a2713aSLionel Sambuc     TL.setWrittenTypeSpec(static_cast<DeclSpec::TST>(Record[Idx++]));
5690f4a2713aSLionel Sambuc     TL.setWrittenSignSpec(static_cast<DeclSpec::TSS>(Record[Idx++]));
5691f4a2713aSLionel Sambuc     TL.setWrittenWidthSpec(static_cast<DeclSpec::TSW>(Record[Idx++]));
5692f4a2713aSLionel Sambuc     TL.setModeAttr(Record[Idx++]);
5693f4a2713aSLionel Sambuc   }
5694f4a2713aSLionel Sambuc }
VisitComplexTypeLoc(ComplexTypeLoc TL)5695f4a2713aSLionel Sambuc void TypeLocReader::VisitComplexTypeLoc(ComplexTypeLoc TL) {
5696f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5697f4a2713aSLionel Sambuc }
VisitPointerTypeLoc(PointerTypeLoc TL)5698f4a2713aSLionel Sambuc void TypeLocReader::VisitPointerTypeLoc(PointerTypeLoc TL) {
5699f4a2713aSLionel Sambuc   TL.setStarLoc(ReadSourceLocation(Record, Idx));
5700f4a2713aSLionel Sambuc }
VisitDecayedTypeLoc(DecayedTypeLoc TL)5701f4a2713aSLionel Sambuc void TypeLocReader::VisitDecayedTypeLoc(DecayedTypeLoc TL) {
5702f4a2713aSLionel Sambuc   // nothing to do
5703f4a2713aSLionel Sambuc }
VisitAdjustedTypeLoc(AdjustedTypeLoc TL)5704*0a6a1f1dSLionel Sambuc void TypeLocReader::VisitAdjustedTypeLoc(AdjustedTypeLoc TL) {
5705*0a6a1f1dSLionel Sambuc   // nothing to do
5706*0a6a1f1dSLionel Sambuc }
VisitBlockPointerTypeLoc(BlockPointerTypeLoc TL)5707f4a2713aSLionel Sambuc void TypeLocReader::VisitBlockPointerTypeLoc(BlockPointerTypeLoc TL) {
5708f4a2713aSLionel Sambuc   TL.setCaretLoc(ReadSourceLocation(Record, Idx));
5709f4a2713aSLionel Sambuc }
VisitLValueReferenceTypeLoc(LValueReferenceTypeLoc TL)5710f4a2713aSLionel Sambuc void TypeLocReader::VisitLValueReferenceTypeLoc(LValueReferenceTypeLoc TL) {
5711f4a2713aSLionel Sambuc   TL.setAmpLoc(ReadSourceLocation(Record, Idx));
5712f4a2713aSLionel Sambuc }
VisitRValueReferenceTypeLoc(RValueReferenceTypeLoc TL)5713f4a2713aSLionel Sambuc void TypeLocReader::VisitRValueReferenceTypeLoc(RValueReferenceTypeLoc TL) {
5714f4a2713aSLionel Sambuc   TL.setAmpAmpLoc(ReadSourceLocation(Record, Idx));
5715f4a2713aSLionel Sambuc }
VisitMemberPointerTypeLoc(MemberPointerTypeLoc TL)5716f4a2713aSLionel Sambuc void TypeLocReader::VisitMemberPointerTypeLoc(MemberPointerTypeLoc TL) {
5717f4a2713aSLionel Sambuc   TL.setStarLoc(ReadSourceLocation(Record, Idx));
5718f4a2713aSLionel Sambuc   TL.setClassTInfo(Reader.GetTypeSourceInfo(F, Record, Idx));
5719f4a2713aSLionel Sambuc }
VisitArrayTypeLoc(ArrayTypeLoc TL)5720f4a2713aSLionel Sambuc void TypeLocReader::VisitArrayTypeLoc(ArrayTypeLoc TL) {
5721f4a2713aSLionel Sambuc   TL.setLBracketLoc(ReadSourceLocation(Record, Idx));
5722f4a2713aSLionel Sambuc   TL.setRBracketLoc(ReadSourceLocation(Record, Idx));
5723f4a2713aSLionel Sambuc   if (Record[Idx++])
5724f4a2713aSLionel Sambuc     TL.setSizeExpr(Reader.ReadExpr(F));
5725f4a2713aSLionel Sambuc   else
5726*0a6a1f1dSLionel Sambuc     TL.setSizeExpr(nullptr);
5727f4a2713aSLionel Sambuc }
VisitConstantArrayTypeLoc(ConstantArrayTypeLoc TL)5728f4a2713aSLionel Sambuc void TypeLocReader::VisitConstantArrayTypeLoc(ConstantArrayTypeLoc TL) {
5729f4a2713aSLionel Sambuc   VisitArrayTypeLoc(TL);
5730f4a2713aSLionel Sambuc }
VisitIncompleteArrayTypeLoc(IncompleteArrayTypeLoc TL)5731f4a2713aSLionel Sambuc void TypeLocReader::VisitIncompleteArrayTypeLoc(IncompleteArrayTypeLoc TL) {
5732f4a2713aSLionel Sambuc   VisitArrayTypeLoc(TL);
5733f4a2713aSLionel Sambuc }
VisitVariableArrayTypeLoc(VariableArrayTypeLoc TL)5734f4a2713aSLionel Sambuc void TypeLocReader::VisitVariableArrayTypeLoc(VariableArrayTypeLoc TL) {
5735f4a2713aSLionel Sambuc   VisitArrayTypeLoc(TL);
5736f4a2713aSLionel Sambuc }
VisitDependentSizedArrayTypeLoc(DependentSizedArrayTypeLoc TL)5737f4a2713aSLionel Sambuc void TypeLocReader::VisitDependentSizedArrayTypeLoc(
5738f4a2713aSLionel Sambuc                                             DependentSizedArrayTypeLoc TL) {
5739f4a2713aSLionel Sambuc   VisitArrayTypeLoc(TL);
5740f4a2713aSLionel Sambuc }
VisitDependentSizedExtVectorTypeLoc(DependentSizedExtVectorTypeLoc TL)5741f4a2713aSLionel Sambuc void TypeLocReader::VisitDependentSizedExtVectorTypeLoc(
5742f4a2713aSLionel Sambuc                                         DependentSizedExtVectorTypeLoc TL) {
5743f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5744f4a2713aSLionel Sambuc }
VisitVectorTypeLoc(VectorTypeLoc TL)5745f4a2713aSLionel Sambuc void TypeLocReader::VisitVectorTypeLoc(VectorTypeLoc TL) {
5746f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5747f4a2713aSLionel Sambuc }
VisitExtVectorTypeLoc(ExtVectorTypeLoc TL)5748f4a2713aSLionel Sambuc void TypeLocReader::VisitExtVectorTypeLoc(ExtVectorTypeLoc TL) {
5749f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5750f4a2713aSLionel Sambuc }
VisitFunctionTypeLoc(FunctionTypeLoc TL)5751f4a2713aSLionel Sambuc void TypeLocReader::VisitFunctionTypeLoc(FunctionTypeLoc TL) {
5752f4a2713aSLionel Sambuc   TL.setLocalRangeBegin(ReadSourceLocation(Record, Idx));
5753f4a2713aSLionel Sambuc   TL.setLParenLoc(ReadSourceLocation(Record, Idx));
5754f4a2713aSLionel Sambuc   TL.setRParenLoc(ReadSourceLocation(Record, Idx));
5755f4a2713aSLionel Sambuc   TL.setLocalRangeEnd(ReadSourceLocation(Record, Idx));
5756*0a6a1f1dSLionel Sambuc   for (unsigned i = 0, e = TL.getNumParams(); i != e; ++i) {
5757*0a6a1f1dSLionel Sambuc     TL.setParam(i, ReadDeclAs<ParmVarDecl>(Record, Idx));
5758f4a2713aSLionel Sambuc   }
5759f4a2713aSLionel Sambuc }
VisitFunctionProtoTypeLoc(FunctionProtoTypeLoc TL)5760f4a2713aSLionel Sambuc void TypeLocReader::VisitFunctionProtoTypeLoc(FunctionProtoTypeLoc TL) {
5761f4a2713aSLionel Sambuc   VisitFunctionTypeLoc(TL);
5762f4a2713aSLionel Sambuc }
VisitFunctionNoProtoTypeLoc(FunctionNoProtoTypeLoc TL)5763f4a2713aSLionel Sambuc void TypeLocReader::VisitFunctionNoProtoTypeLoc(FunctionNoProtoTypeLoc TL) {
5764f4a2713aSLionel Sambuc   VisitFunctionTypeLoc(TL);
5765f4a2713aSLionel Sambuc }
VisitUnresolvedUsingTypeLoc(UnresolvedUsingTypeLoc TL)5766f4a2713aSLionel Sambuc void TypeLocReader::VisitUnresolvedUsingTypeLoc(UnresolvedUsingTypeLoc TL) {
5767f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5768f4a2713aSLionel Sambuc }
VisitTypedefTypeLoc(TypedefTypeLoc TL)5769f4a2713aSLionel Sambuc void TypeLocReader::VisitTypedefTypeLoc(TypedefTypeLoc TL) {
5770f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5771f4a2713aSLionel Sambuc }
VisitTypeOfExprTypeLoc(TypeOfExprTypeLoc TL)5772f4a2713aSLionel Sambuc void TypeLocReader::VisitTypeOfExprTypeLoc(TypeOfExprTypeLoc TL) {
5773f4a2713aSLionel Sambuc   TL.setTypeofLoc(ReadSourceLocation(Record, Idx));
5774f4a2713aSLionel Sambuc   TL.setLParenLoc(ReadSourceLocation(Record, Idx));
5775f4a2713aSLionel Sambuc   TL.setRParenLoc(ReadSourceLocation(Record, Idx));
5776f4a2713aSLionel Sambuc }
VisitTypeOfTypeLoc(TypeOfTypeLoc TL)5777f4a2713aSLionel Sambuc void TypeLocReader::VisitTypeOfTypeLoc(TypeOfTypeLoc TL) {
5778f4a2713aSLionel Sambuc   TL.setTypeofLoc(ReadSourceLocation(Record, Idx));
5779f4a2713aSLionel Sambuc   TL.setLParenLoc(ReadSourceLocation(Record, Idx));
5780f4a2713aSLionel Sambuc   TL.setRParenLoc(ReadSourceLocation(Record, Idx));
5781f4a2713aSLionel Sambuc   TL.setUnderlyingTInfo(Reader.GetTypeSourceInfo(F, Record, Idx));
5782f4a2713aSLionel Sambuc }
VisitDecltypeTypeLoc(DecltypeTypeLoc TL)5783f4a2713aSLionel Sambuc void TypeLocReader::VisitDecltypeTypeLoc(DecltypeTypeLoc TL) {
5784f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5785f4a2713aSLionel Sambuc }
VisitUnaryTransformTypeLoc(UnaryTransformTypeLoc TL)5786f4a2713aSLionel Sambuc void TypeLocReader::VisitUnaryTransformTypeLoc(UnaryTransformTypeLoc TL) {
5787f4a2713aSLionel Sambuc   TL.setKWLoc(ReadSourceLocation(Record, Idx));
5788f4a2713aSLionel Sambuc   TL.setLParenLoc(ReadSourceLocation(Record, Idx));
5789f4a2713aSLionel Sambuc   TL.setRParenLoc(ReadSourceLocation(Record, Idx));
5790f4a2713aSLionel Sambuc   TL.setUnderlyingTInfo(Reader.GetTypeSourceInfo(F, Record, Idx));
5791f4a2713aSLionel Sambuc }
VisitAutoTypeLoc(AutoTypeLoc TL)5792f4a2713aSLionel Sambuc void TypeLocReader::VisitAutoTypeLoc(AutoTypeLoc TL) {
5793f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5794f4a2713aSLionel Sambuc }
VisitRecordTypeLoc(RecordTypeLoc TL)5795f4a2713aSLionel Sambuc void TypeLocReader::VisitRecordTypeLoc(RecordTypeLoc TL) {
5796f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5797f4a2713aSLionel Sambuc }
VisitEnumTypeLoc(EnumTypeLoc TL)5798f4a2713aSLionel Sambuc void TypeLocReader::VisitEnumTypeLoc(EnumTypeLoc TL) {
5799f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5800f4a2713aSLionel Sambuc }
VisitAttributedTypeLoc(AttributedTypeLoc TL)5801f4a2713aSLionel Sambuc void TypeLocReader::VisitAttributedTypeLoc(AttributedTypeLoc TL) {
5802f4a2713aSLionel Sambuc   TL.setAttrNameLoc(ReadSourceLocation(Record, Idx));
5803f4a2713aSLionel Sambuc   if (TL.hasAttrOperand()) {
5804f4a2713aSLionel Sambuc     SourceRange range;
5805f4a2713aSLionel Sambuc     range.setBegin(ReadSourceLocation(Record, Idx));
5806f4a2713aSLionel Sambuc     range.setEnd(ReadSourceLocation(Record, Idx));
5807f4a2713aSLionel Sambuc     TL.setAttrOperandParensRange(range);
5808f4a2713aSLionel Sambuc   }
5809f4a2713aSLionel Sambuc   if (TL.hasAttrExprOperand()) {
5810f4a2713aSLionel Sambuc     if (Record[Idx++])
5811f4a2713aSLionel Sambuc       TL.setAttrExprOperand(Reader.ReadExpr(F));
5812f4a2713aSLionel Sambuc     else
5813*0a6a1f1dSLionel Sambuc       TL.setAttrExprOperand(nullptr);
5814f4a2713aSLionel Sambuc   } else if (TL.hasAttrEnumOperand())
5815f4a2713aSLionel Sambuc     TL.setAttrEnumOperandLoc(ReadSourceLocation(Record, Idx));
5816f4a2713aSLionel Sambuc }
VisitTemplateTypeParmTypeLoc(TemplateTypeParmTypeLoc TL)5817f4a2713aSLionel Sambuc void TypeLocReader::VisitTemplateTypeParmTypeLoc(TemplateTypeParmTypeLoc TL) {
5818f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5819f4a2713aSLionel Sambuc }
VisitSubstTemplateTypeParmTypeLoc(SubstTemplateTypeParmTypeLoc TL)5820f4a2713aSLionel Sambuc void TypeLocReader::VisitSubstTemplateTypeParmTypeLoc(
5821f4a2713aSLionel Sambuc                                             SubstTemplateTypeParmTypeLoc TL) {
5822f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5823f4a2713aSLionel Sambuc }
VisitSubstTemplateTypeParmPackTypeLoc(SubstTemplateTypeParmPackTypeLoc TL)5824f4a2713aSLionel Sambuc void TypeLocReader::VisitSubstTemplateTypeParmPackTypeLoc(
5825f4a2713aSLionel Sambuc                                           SubstTemplateTypeParmPackTypeLoc TL) {
5826f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5827f4a2713aSLionel Sambuc }
VisitTemplateSpecializationTypeLoc(TemplateSpecializationTypeLoc TL)5828f4a2713aSLionel Sambuc void TypeLocReader::VisitTemplateSpecializationTypeLoc(
5829f4a2713aSLionel Sambuc                                            TemplateSpecializationTypeLoc TL) {
5830f4a2713aSLionel Sambuc   TL.setTemplateKeywordLoc(ReadSourceLocation(Record, Idx));
5831f4a2713aSLionel Sambuc   TL.setTemplateNameLoc(ReadSourceLocation(Record, Idx));
5832f4a2713aSLionel Sambuc   TL.setLAngleLoc(ReadSourceLocation(Record, Idx));
5833f4a2713aSLionel Sambuc   TL.setRAngleLoc(ReadSourceLocation(Record, Idx));
5834f4a2713aSLionel Sambuc   for (unsigned i = 0, e = TL.getNumArgs(); i != e; ++i)
5835f4a2713aSLionel Sambuc     TL.setArgLocInfo(i,
5836f4a2713aSLionel Sambuc         Reader.GetTemplateArgumentLocInfo(F,
5837f4a2713aSLionel Sambuc                                           TL.getTypePtr()->getArg(i).getKind(),
5838f4a2713aSLionel Sambuc                                           Record, Idx));
5839f4a2713aSLionel Sambuc }
VisitParenTypeLoc(ParenTypeLoc TL)5840f4a2713aSLionel Sambuc void TypeLocReader::VisitParenTypeLoc(ParenTypeLoc TL) {
5841f4a2713aSLionel Sambuc   TL.setLParenLoc(ReadSourceLocation(Record, Idx));
5842f4a2713aSLionel Sambuc   TL.setRParenLoc(ReadSourceLocation(Record, Idx));
5843f4a2713aSLionel Sambuc }
VisitElaboratedTypeLoc(ElaboratedTypeLoc TL)5844f4a2713aSLionel Sambuc void TypeLocReader::VisitElaboratedTypeLoc(ElaboratedTypeLoc TL) {
5845f4a2713aSLionel Sambuc   TL.setElaboratedKeywordLoc(ReadSourceLocation(Record, Idx));
5846f4a2713aSLionel Sambuc   TL.setQualifierLoc(Reader.ReadNestedNameSpecifierLoc(F, Record, Idx));
5847f4a2713aSLionel Sambuc }
VisitInjectedClassNameTypeLoc(InjectedClassNameTypeLoc TL)5848f4a2713aSLionel Sambuc void TypeLocReader::VisitInjectedClassNameTypeLoc(InjectedClassNameTypeLoc TL) {
5849f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5850f4a2713aSLionel Sambuc }
VisitDependentNameTypeLoc(DependentNameTypeLoc TL)5851f4a2713aSLionel Sambuc void TypeLocReader::VisitDependentNameTypeLoc(DependentNameTypeLoc TL) {
5852f4a2713aSLionel Sambuc   TL.setElaboratedKeywordLoc(ReadSourceLocation(Record, Idx));
5853f4a2713aSLionel Sambuc   TL.setQualifierLoc(Reader.ReadNestedNameSpecifierLoc(F, Record, Idx));
5854f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5855f4a2713aSLionel Sambuc }
VisitDependentTemplateSpecializationTypeLoc(DependentTemplateSpecializationTypeLoc TL)5856f4a2713aSLionel Sambuc void TypeLocReader::VisitDependentTemplateSpecializationTypeLoc(
5857f4a2713aSLionel Sambuc        DependentTemplateSpecializationTypeLoc TL) {
5858f4a2713aSLionel Sambuc   TL.setElaboratedKeywordLoc(ReadSourceLocation(Record, Idx));
5859f4a2713aSLionel Sambuc   TL.setQualifierLoc(Reader.ReadNestedNameSpecifierLoc(F, Record, Idx));
5860f4a2713aSLionel Sambuc   TL.setTemplateKeywordLoc(ReadSourceLocation(Record, Idx));
5861f4a2713aSLionel Sambuc   TL.setTemplateNameLoc(ReadSourceLocation(Record, Idx));
5862f4a2713aSLionel Sambuc   TL.setLAngleLoc(ReadSourceLocation(Record, Idx));
5863f4a2713aSLionel Sambuc   TL.setRAngleLoc(ReadSourceLocation(Record, Idx));
5864f4a2713aSLionel Sambuc   for (unsigned I = 0, E = TL.getNumArgs(); I != E; ++I)
5865f4a2713aSLionel Sambuc     TL.setArgLocInfo(I,
5866f4a2713aSLionel Sambuc         Reader.GetTemplateArgumentLocInfo(F,
5867f4a2713aSLionel Sambuc                                           TL.getTypePtr()->getArg(I).getKind(),
5868f4a2713aSLionel Sambuc                                           Record, Idx));
5869f4a2713aSLionel Sambuc }
VisitPackExpansionTypeLoc(PackExpansionTypeLoc TL)5870f4a2713aSLionel Sambuc void TypeLocReader::VisitPackExpansionTypeLoc(PackExpansionTypeLoc TL) {
5871f4a2713aSLionel Sambuc   TL.setEllipsisLoc(ReadSourceLocation(Record, Idx));
5872f4a2713aSLionel Sambuc }
VisitObjCInterfaceTypeLoc(ObjCInterfaceTypeLoc TL)5873f4a2713aSLionel Sambuc void TypeLocReader::VisitObjCInterfaceTypeLoc(ObjCInterfaceTypeLoc TL) {
5874f4a2713aSLionel Sambuc   TL.setNameLoc(ReadSourceLocation(Record, Idx));
5875f4a2713aSLionel Sambuc }
VisitObjCObjectTypeLoc(ObjCObjectTypeLoc TL)5876f4a2713aSLionel Sambuc void TypeLocReader::VisitObjCObjectTypeLoc(ObjCObjectTypeLoc TL) {
5877f4a2713aSLionel Sambuc   TL.setHasBaseTypeAsWritten(Record[Idx++]);
5878f4a2713aSLionel Sambuc   TL.setLAngleLoc(ReadSourceLocation(Record, Idx));
5879f4a2713aSLionel Sambuc   TL.setRAngleLoc(ReadSourceLocation(Record, Idx));
5880f4a2713aSLionel Sambuc   for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
5881f4a2713aSLionel Sambuc     TL.setProtocolLoc(i, ReadSourceLocation(Record, Idx));
5882f4a2713aSLionel Sambuc }
VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL)5883f4a2713aSLionel Sambuc void TypeLocReader::VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL) {
5884f4a2713aSLionel Sambuc   TL.setStarLoc(ReadSourceLocation(Record, Idx));
5885f4a2713aSLionel Sambuc }
VisitAtomicTypeLoc(AtomicTypeLoc TL)5886f4a2713aSLionel Sambuc void TypeLocReader::VisitAtomicTypeLoc(AtomicTypeLoc TL) {
5887f4a2713aSLionel Sambuc   TL.setKWLoc(ReadSourceLocation(Record, Idx));
5888f4a2713aSLionel Sambuc   TL.setLParenLoc(ReadSourceLocation(Record, Idx));
5889f4a2713aSLionel Sambuc   TL.setRParenLoc(ReadSourceLocation(Record, Idx));
5890f4a2713aSLionel Sambuc }
5891f4a2713aSLionel Sambuc 
GetTypeSourceInfo(ModuleFile & F,const RecordData & Record,unsigned & Idx)5892f4a2713aSLionel Sambuc TypeSourceInfo *ASTReader::GetTypeSourceInfo(ModuleFile &F,
5893f4a2713aSLionel Sambuc                                              const RecordData &Record,
5894f4a2713aSLionel Sambuc                                              unsigned &Idx) {
5895f4a2713aSLionel Sambuc   QualType InfoTy = readType(F, Record, Idx);
5896f4a2713aSLionel Sambuc   if (InfoTy.isNull())
5897*0a6a1f1dSLionel Sambuc     return nullptr;
5898f4a2713aSLionel Sambuc 
5899f4a2713aSLionel Sambuc   TypeSourceInfo *TInfo = getContext().CreateTypeSourceInfo(InfoTy);
5900f4a2713aSLionel Sambuc   TypeLocReader TLR(*this, F, Record, Idx);
5901f4a2713aSLionel Sambuc   for (TypeLoc TL = TInfo->getTypeLoc(); !TL.isNull(); TL = TL.getNextTypeLoc())
5902f4a2713aSLionel Sambuc     TLR.Visit(TL);
5903f4a2713aSLionel Sambuc   return TInfo;
5904f4a2713aSLionel Sambuc }
5905f4a2713aSLionel Sambuc 
GetType(TypeID ID)5906f4a2713aSLionel Sambuc QualType ASTReader::GetType(TypeID ID) {
5907f4a2713aSLionel Sambuc   unsigned FastQuals = ID & Qualifiers::FastMask;
5908f4a2713aSLionel Sambuc   unsigned Index = ID >> Qualifiers::FastWidth;
5909f4a2713aSLionel Sambuc 
5910f4a2713aSLionel Sambuc   if (Index < NUM_PREDEF_TYPE_IDS) {
5911f4a2713aSLionel Sambuc     QualType T;
5912f4a2713aSLionel Sambuc     switch ((PredefinedTypeIDs)Index) {
5913f4a2713aSLionel Sambuc     case PREDEF_TYPE_NULL_ID: return QualType();
5914f4a2713aSLionel Sambuc     case PREDEF_TYPE_VOID_ID: T = Context.VoidTy; break;
5915f4a2713aSLionel Sambuc     case PREDEF_TYPE_BOOL_ID: T = Context.BoolTy; break;
5916f4a2713aSLionel Sambuc 
5917f4a2713aSLionel Sambuc     case PREDEF_TYPE_CHAR_U_ID:
5918f4a2713aSLionel Sambuc     case PREDEF_TYPE_CHAR_S_ID:
5919f4a2713aSLionel Sambuc       // FIXME: Check that the signedness of CharTy is correct!
5920f4a2713aSLionel Sambuc       T = Context.CharTy;
5921f4a2713aSLionel Sambuc       break;
5922f4a2713aSLionel Sambuc 
5923f4a2713aSLionel Sambuc     case PREDEF_TYPE_UCHAR_ID:      T = Context.UnsignedCharTy;     break;
5924f4a2713aSLionel Sambuc     case PREDEF_TYPE_USHORT_ID:     T = Context.UnsignedShortTy;    break;
5925f4a2713aSLionel Sambuc     case PREDEF_TYPE_UINT_ID:       T = Context.UnsignedIntTy;      break;
5926f4a2713aSLionel Sambuc     case PREDEF_TYPE_ULONG_ID:      T = Context.UnsignedLongTy;     break;
5927f4a2713aSLionel Sambuc     case PREDEF_TYPE_ULONGLONG_ID:  T = Context.UnsignedLongLongTy; break;
5928f4a2713aSLionel Sambuc     case PREDEF_TYPE_UINT128_ID:    T = Context.UnsignedInt128Ty;   break;
5929f4a2713aSLionel Sambuc     case PREDEF_TYPE_SCHAR_ID:      T = Context.SignedCharTy;       break;
5930f4a2713aSLionel Sambuc     case PREDEF_TYPE_WCHAR_ID:      T = Context.WCharTy;            break;
5931f4a2713aSLionel Sambuc     case PREDEF_TYPE_SHORT_ID:      T = Context.ShortTy;            break;
5932f4a2713aSLionel Sambuc     case PREDEF_TYPE_INT_ID:        T = Context.IntTy;              break;
5933f4a2713aSLionel Sambuc     case PREDEF_TYPE_LONG_ID:       T = Context.LongTy;             break;
5934f4a2713aSLionel Sambuc     case PREDEF_TYPE_LONGLONG_ID:   T = Context.LongLongTy;         break;
5935f4a2713aSLionel Sambuc     case PREDEF_TYPE_INT128_ID:     T = Context.Int128Ty;           break;
5936f4a2713aSLionel Sambuc     case PREDEF_TYPE_HALF_ID:       T = Context.HalfTy;             break;
5937f4a2713aSLionel Sambuc     case PREDEF_TYPE_FLOAT_ID:      T = Context.FloatTy;            break;
5938f4a2713aSLionel Sambuc     case PREDEF_TYPE_DOUBLE_ID:     T = Context.DoubleTy;           break;
5939f4a2713aSLionel Sambuc     case PREDEF_TYPE_LONGDOUBLE_ID: T = Context.LongDoubleTy;       break;
5940f4a2713aSLionel Sambuc     case PREDEF_TYPE_OVERLOAD_ID:   T = Context.OverloadTy;         break;
5941f4a2713aSLionel Sambuc     case PREDEF_TYPE_BOUND_MEMBER:  T = Context.BoundMemberTy;      break;
5942f4a2713aSLionel Sambuc     case PREDEF_TYPE_PSEUDO_OBJECT: T = Context.PseudoObjectTy;     break;
5943f4a2713aSLionel Sambuc     case PREDEF_TYPE_DEPENDENT_ID:  T = Context.DependentTy;        break;
5944f4a2713aSLionel Sambuc     case PREDEF_TYPE_UNKNOWN_ANY:   T = Context.UnknownAnyTy;       break;
5945f4a2713aSLionel Sambuc     case PREDEF_TYPE_NULLPTR_ID:    T = Context.NullPtrTy;          break;
5946f4a2713aSLionel Sambuc     case PREDEF_TYPE_CHAR16_ID:     T = Context.Char16Ty;           break;
5947f4a2713aSLionel Sambuc     case PREDEF_TYPE_CHAR32_ID:     T = Context.Char32Ty;           break;
5948f4a2713aSLionel Sambuc     case PREDEF_TYPE_OBJC_ID:       T = Context.ObjCBuiltinIdTy;    break;
5949f4a2713aSLionel Sambuc     case PREDEF_TYPE_OBJC_CLASS:    T = Context.ObjCBuiltinClassTy; break;
5950f4a2713aSLionel Sambuc     case PREDEF_TYPE_OBJC_SEL:      T = Context.ObjCBuiltinSelTy;   break;
5951f4a2713aSLionel Sambuc     case PREDEF_TYPE_IMAGE1D_ID:    T = Context.OCLImage1dTy;       break;
5952f4a2713aSLionel Sambuc     case PREDEF_TYPE_IMAGE1D_ARR_ID: T = Context.OCLImage1dArrayTy; break;
5953f4a2713aSLionel Sambuc     case PREDEF_TYPE_IMAGE1D_BUFF_ID: T = Context.OCLImage1dBufferTy; break;
5954f4a2713aSLionel Sambuc     case PREDEF_TYPE_IMAGE2D_ID:    T = Context.OCLImage2dTy;       break;
5955f4a2713aSLionel Sambuc     case PREDEF_TYPE_IMAGE2D_ARR_ID: T = Context.OCLImage2dArrayTy; break;
5956f4a2713aSLionel Sambuc     case PREDEF_TYPE_IMAGE3D_ID:    T = Context.OCLImage3dTy;       break;
5957f4a2713aSLionel Sambuc     case PREDEF_TYPE_SAMPLER_ID:    T = Context.OCLSamplerTy;       break;
5958f4a2713aSLionel Sambuc     case PREDEF_TYPE_EVENT_ID:      T = Context.OCLEventTy;         break;
5959f4a2713aSLionel Sambuc     case PREDEF_TYPE_AUTO_DEDUCT:   T = Context.getAutoDeductType(); break;
5960f4a2713aSLionel Sambuc 
5961f4a2713aSLionel Sambuc     case PREDEF_TYPE_AUTO_RREF_DEDUCT:
5962f4a2713aSLionel Sambuc       T = Context.getAutoRRefDeductType();
5963f4a2713aSLionel Sambuc       break;
5964f4a2713aSLionel Sambuc 
5965f4a2713aSLionel Sambuc     case PREDEF_TYPE_ARC_UNBRIDGED_CAST:
5966f4a2713aSLionel Sambuc       T = Context.ARCUnbridgedCastTy;
5967f4a2713aSLionel Sambuc       break;
5968f4a2713aSLionel Sambuc 
5969f4a2713aSLionel Sambuc     case PREDEF_TYPE_VA_LIST_TAG:
5970f4a2713aSLionel Sambuc       T = Context.getVaListTagType();
5971f4a2713aSLionel Sambuc       break;
5972f4a2713aSLionel Sambuc 
5973f4a2713aSLionel Sambuc     case PREDEF_TYPE_BUILTIN_FN:
5974f4a2713aSLionel Sambuc       T = Context.BuiltinFnTy;
5975f4a2713aSLionel Sambuc       break;
5976f4a2713aSLionel Sambuc     }
5977f4a2713aSLionel Sambuc 
5978f4a2713aSLionel Sambuc     assert(!T.isNull() && "Unknown predefined type");
5979f4a2713aSLionel Sambuc     return T.withFastQualifiers(FastQuals);
5980f4a2713aSLionel Sambuc   }
5981f4a2713aSLionel Sambuc 
5982f4a2713aSLionel Sambuc   Index -= NUM_PREDEF_TYPE_IDS;
5983f4a2713aSLionel Sambuc   assert(Index < TypesLoaded.size() && "Type index out-of-range");
5984f4a2713aSLionel Sambuc   if (TypesLoaded[Index].isNull()) {
5985f4a2713aSLionel Sambuc     TypesLoaded[Index] = readTypeRecord(Index);
5986f4a2713aSLionel Sambuc     if (TypesLoaded[Index].isNull())
5987f4a2713aSLionel Sambuc       return QualType();
5988f4a2713aSLionel Sambuc 
5989f4a2713aSLionel Sambuc     TypesLoaded[Index]->setFromAST();
5990f4a2713aSLionel Sambuc     if (DeserializationListener)
5991f4a2713aSLionel Sambuc       DeserializationListener->TypeRead(TypeIdx::fromTypeID(ID),
5992f4a2713aSLionel Sambuc                                         TypesLoaded[Index]);
5993f4a2713aSLionel Sambuc   }
5994f4a2713aSLionel Sambuc 
5995f4a2713aSLionel Sambuc   return TypesLoaded[Index].withFastQualifiers(FastQuals);
5996f4a2713aSLionel Sambuc }
5997f4a2713aSLionel Sambuc 
getLocalType(ModuleFile & F,unsigned LocalID)5998f4a2713aSLionel Sambuc QualType ASTReader::getLocalType(ModuleFile &F, unsigned LocalID) {
5999f4a2713aSLionel Sambuc   return GetType(getGlobalTypeID(F, LocalID));
6000f4a2713aSLionel Sambuc }
6001f4a2713aSLionel Sambuc 
6002f4a2713aSLionel Sambuc serialization::TypeID
getGlobalTypeID(ModuleFile & F,unsigned LocalID) const6003f4a2713aSLionel Sambuc ASTReader::getGlobalTypeID(ModuleFile &F, unsigned LocalID) const {
6004f4a2713aSLionel Sambuc   unsigned FastQuals = LocalID & Qualifiers::FastMask;
6005f4a2713aSLionel Sambuc   unsigned LocalIndex = LocalID >> Qualifiers::FastWidth;
6006f4a2713aSLionel Sambuc 
6007f4a2713aSLionel Sambuc   if (LocalIndex < NUM_PREDEF_TYPE_IDS)
6008f4a2713aSLionel Sambuc     return LocalID;
6009f4a2713aSLionel Sambuc 
6010f4a2713aSLionel Sambuc   ContinuousRangeMap<uint32_t, int, 2>::iterator I
6011f4a2713aSLionel Sambuc     = F.TypeRemap.find(LocalIndex - NUM_PREDEF_TYPE_IDS);
6012f4a2713aSLionel Sambuc   assert(I != F.TypeRemap.end() && "Invalid index into type index remap");
6013f4a2713aSLionel Sambuc 
6014f4a2713aSLionel Sambuc   unsigned GlobalIndex = LocalIndex + I->second;
6015f4a2713aSLionel Sambuc   return (GlobalIndex << Qualifiers::FastWidth) | FastQuals;
6016f4a2713aSLionel Sambuc }
6017f4a2713aSLionel Sambuc 
6018f4a2713aSLionel Sambuc TemplateArgumentLocInfo
GetTemplateArgumentLocInfo(ModuleFile & F,TemplateArgument::ArgKind Kind,const RecordData & Record,unsigned & Index)6019f4a2713aSLionel Sambuc ASTReader::GetTemplateArgumentLocInfo(ModuleFile &F,
6020f4a2713aSLionel Sambuc                                       TemplateArgument::ArgKind Kind,
6021f4a2713aSLionel Sambuc                                       const RecordData &Record,
6022f4a2713aSLionel Sambuc                                       unsigned &Index) {
6023f4a2713aSLionel Sambuc   switch (Kind) {
6024f4a2713aSLionel Sambuc   case TemplateArgument::Expression:
6025f4a2713aSLionel Sambuc     return ReadExpr(F);
6026f4a2713aSLionel Sambuc   case TemplateArgument::Type:
6027f4a2713aSLionel Sambuc     return GetTypeSourceInfo(F, Record, Index);
6028f4a2713aSLionel Sambuc   case TemplateArgument::Template: {
6029f4a2713aSLionel Sambuc     NestedNameSpecifierLoc QualifierLoc = ReadNestedNameSpecifierLoc(F, Record,
6030f4a2713aSLionel Sambuc                                                                      Index);
6031f4a2713aSLionel Sambuc     SourceLocation TemplateNameLoc = ReadSourceLocation(F, Record, Index);
6032f4a2713aSLionel Sambuc     return TemplateArgumentLocInfo(QualifierLoc, TemplateNameLoc,
6033f4a2713aSLionel Sambuc                                    SourceLocation());
6034f4a2713aSLionel Sambuc   }
6035f4a2713aSLionel Sambuc   case TemplateArgument::TemplateExpansion: {
6036f4a2713aSLionel Sambuc     NestedNameSpecifierLoc QualifierLoc = ReadNestedNameSpecifierLoc(F, Record,
6037f4a2713aSLionel Sambuc                                                                      Index);
6038f4a2713aSLionel Sambuc     SourceLocation TemplateNameLoc = ReadSourceLocation(F, Record, Index);
6039f4a2713aSLionel Sambuc     SourceLocation EllipsisLoc = ReadSourceLocation(F, Record, Index);
6040f4a2713aSLionel Sambuc     return TemplateArgumentLocInfo(QualifierLoc, TemplateNameLoc,
6041f4a2713aSLionel Sambuc                                    EllipsisLoc);
6042f4a2713aSLionel Sambuc   }
6043f4a2713aSLionel Sambuc   case TemplateArgument::Null:
6044f4a2713aSLionel Sambuc   case TemplateArgument::Integral:
6045f4a2713aSLionel Sambuc   case TemplateArgument::Declaration:
6046f4a2713aSLionel Sambuc   case TemplateArgument::NullPtr:
6047f4a2713aSLionel Sambuc   case TemplateArgument::Pack:
6048f4a2713aSLionel Sambuc     // FIXME: Is this right?
6049f4a2713aSLionel Sambuc     return TemplateArgumentLocInfo();
6050f4a2713aSLionel Sambuc   }
6051f4a2713aSLionel Sambuc   llvm_unreachable("unexpected template argument loc");
6052f4a2713aSLionel Sambuc }
6053f4a2713aSLionel Sambuc 
6054f4a2713aSLionel Sambuc TemplateArgumentLoc
ReadTemplateArgumentLoc(ModuleFile & F,const RecordData & Record,unsigned & Index)6055f4a2713aSLionel Sambuc ASTReader::ReadTemplateArgumentLoc(ModuleFile &F,
6056f4a2713aSLionel Sambuc                                    const RecordData &Record, unsigned &Index) {
6057f4a2713aSLionel Sambuc   TemplateArgument Arg = ReadTemplateArgument(F, Record, Index);
6058f4a2713aSLionel Sambuc 
6059f4a2713aSLionel Sambuc   if (Arg.getKind() == TemplateArgument::Expression) {
6060f4a2713aSLionel Sambuc     if (Record[Index++]) // bool InfoHasSameExpr.
6061f4a2713aSLionel Sambuc       return TemplateArgumentLoc(Arg, TemplateArgumentLocInfo(Arg.getAsExpr()));
6062f4a2713aSLionel Sambuc   }
6063f4a2713aSLionel Sambuc   return TemplateArgumentLoc(Arg, GetTemplateArgumentLocInfo(F, Arg.getKind(),
6064f4a2713aSLionel Sambuc                                                              Record, Index));
6065f4a2713aSLionel Sambuc }
6066f4a2713aSLionel Sambuc 
6067f4a2713aSLionel Sambuc const ASTTemplateArgumentListInfo*
ReadASTTemplateArgumentListInfo(ModuleFile & F,const RecordData & Record,unsigned & Index)6068f4a2713aSLionel Sambuc ASTReader::ReadASTTemplateArgumentListInfo(ModuleFile &F,
6069f4a2713aSLionel Sambuc                                            const RecordData &Record,
6070f4a2713aSLionel Sambuc                                            unsigned &Index) {
6071f4a2713aSLionel Sambuc   SourceLocation LAngleLoc = ReadSourceLocation(F, Record, Index);
6072f4a2713aSLionel Sambuc   SourceLocation RAngleLoc = ReadSourceLocation(F, Record, Index);
6073f4a2713aSLionel Sambuc   unsigned NumArgsAsWritten = Record[Index++];
6074f4a2713aSLionel Sambuc   TemplateArgumentListInfo TemplArgsInfo(LAngleLoc, RAngleLoc);
6075f4a2713aSLionel Sambuc   for (unsigned i = 0; i != NumArgsAsWritten; ++i)
6076f4a2713aSLionel Sambuc     TemplArgsInfo.addArgument(ReadTemplateArgumentLoc(F, Record, Index));
6077f4a2713aSLionel Sambuc   return ASTTemplateArgumentListInfo::Create(getContext(), TemplArgsInfo);
6078f4a2713aSLionel Sambuc }
6079f4a2713aSLionel Sambuc 
GetExternalDecl(uint32_t ID)6080f4a2713aSLionel Sambuc Decl *ASTReader::GetExternalDecl(uint32_t ID) {
6081f4a2713aSLionel Sambuc   return GetDecl(ID);
6082f4a2713aSLionel Sambuc }
6083f4a2713aSLionel Sambuc 
CompleteRedeclChain(const Decl * D)6084*0a6a1f1dSLionel Sambuc void ASTReader::CompleteRedeclChain(const Decl *D) {
6085*0a6a1f1dSLionel Sambuc   if (NumCurrentElementsDeserializing) {
6086*0a6a1f1dSLionel Sambuc     // We arrange to not care about the complete redeclaration chain while we're
6087*0a6a1f1dSLionel Sambuc     // deserializing. Just remember that the AST has marked this one as complete
6088*0a6a1f1dSLionel Sambuc     // but that it's not actually complete yet, so we know we still need to
6089*0a6a1f1dSLionel Sambuc     // complete it later.
6090*0a6a1f1dSLionel Sambuc     PendingIncompleteDeclChains.push_back(const_cast<Decl*>(D));
6091*0a6a1f1dSLionel Sambuc     return;
6092*0a6a1f1dSLionel Sambuc   }
6093*0a6a1f1dSLionel Sambuc 
6094*0a6a1f1dSLionel Sambuc   const DeclContext *DC = D->getDeclContext()->getRedeclContext();
6095*0a6a1f1dSLionel Sambuc 
6096*0a6a1f1dSLionel Sambuc   // If this is a named declaration, complete it by looking it up
6097*0a6a1f1dSLionel Sambuc   // within its context.
6098*0a6a1f1dSLionel Sambuc   //
6099*0a6a1f1dSLionel Sambuc   // FIXME: Merging a function definition should merge
6100*0a6a1f1dSLionel Sambuc   // all mergeable entities within it.
6101*0a6a1f1dSLionel Sambuc   if (isa<TranslationUnitDecl>(DC) || isa<NamespaceDecl>(DC) ||
6102*0a6a1f1dSLionel Sambuc       isa<CXXRecordDecl>(DC) || isa<EnumDecl>(DC)) {
6103*0a6a1f1dSLionel Sambuc     if (DeclarationName Name = cast<NamedDecl>(D)->getDeclName()) {
6104*0a6a1f1dSLionel Sambuc       auto *II = Name.getAsIdentifierInfo();
6105*0a6a1f1dSLionel Sambuc       if (isa<TranslationUnitDecl>(DC) && II) {
6106*0a6a1f1dSLionel Sambuc         // Outside of C++, we don't have a lookup table for the TU, so update
6107*0a6a1f1dSLionel Sambuc         // the identifier instead. In C++, either way should work fine.
6108*0a6a1f1dSLionel Sambuc         if (II->isOutOfDate())
6109*0a6a1f1dSLionel Sambuc           updateOutOfDateIdentifier(*II);
6110*0a6a1f1dSLionel Sambuc       } else
6111*0a6a1f1dSLionel Sambuc         DC->lookup(Name);
6112*0a6a1f1dSLionel Sambuc     } else if (needsAnonymousDeclarationNumber(cast<NamedDecl>(D))) {
6113*0a6a1f1dSLionel Sambuc       // FIXME: It'd be nice to do something a bit more targeted here.
6114*0a6a1f1dSLionel Sambuc       D->getDeclContext()->decls_begin();
6115*0a6a1f1dSLionel Sambuc     }
6116*0a6a1f1dSLionel Sambuc   }
6117*0a6a1f1dSLionel Sambuc }
6118*0a6a1f1dSLionel Sambuc 
readCXXBaseSpecifiers(ModuleFile & M,const RecordData & Record,unsigned & Idx)6119*0a6a1f1dSLionel Sambuc uint64_t ASTReader::readCXXBaseSpecifiers(ModuleFile &M,
6120*0a6a1f1dSLionel Sambuc                                           const RecordData &Record,
6121f4a2713aSLionel Sambuc                                           unsigned &Idx) {
6122*0a6a1f1dSLionel Sambuc   if (Idx >= Record.size() || Record[Idx] > M.LocalNumCXXBaseSpecifiers) {
6123*0a6a1f1dSLionel Sambuc     Error("malformed AST file: missing C++ base specifier");
6124f4a2713aSLionel Sambuc     return 0;
6125*0a6a1f1dSLionel Sambuc   }
6126f4a2713aSLionel Sambuc 
6127f4a2713aSLionel Sambuc   unsigned LocalID = Record[Idx++];
6128f4a2713aSLionel Sambuc   return getGlobalBitOffset(M, M.CXXBaseSpecifiersOffsets[LocalID - 1]);
6129f4a2713aSLionel Sambuc }
6130f4a2713aSLionel Sambuc 
GetExternalCXXBaseSpecifiers(uint64_t Offset)6131f4a2713aSLionel Sambuc CXXBaseSpecifier *ASTReader::GetExternalCXXBaseSpecifiers(uint64_t Offset) {
6132f4a2713aSLionel Sambuc   RecordLocation Loc = getLocalBitOffset(Offset);
6133f4a2713aSLionel Sambuc   BitstreamCursor &Cursor = Loc.F->DeclsCursor;
6134f4a2713aSLionel Sambuc   SavedStreamPosition SavedPosition(Cursor);
6135f4a2713aSLionel Sambuc   Cursor.JumpToBit(Loc.Offset);
6136f4a2713aSLionel Sambuc   ReadingKindTracker ReadingKind(Read_Decl, *this);
6137f4a2713aSLionel Sambuc   RecordData Record;
6138f4a2713aSLionel Sambuc   unsigned Code = Cursor.ReadCode();
6139f4a2713aSLionel Sambuc   unsigned RecCode = Cursor.readRecord(Code, Record);
6140f4a2713aSLionel Sambuc   if (RecCode != DECL_CXX_BASE_SPECIFIERS) {
6141*0a6a1f1dSLionel Sambuc     Error("malformed AST file: missing C++ base specifiers");
6142*0a6a1f1dSLionel Sambuc     return nullptr;
6143f4a2713aSLionel Sambuc   }
6144f4a2713aSLionel Sambuc 
6145f4a2713aSLionel Sambuc   unsigned Idx = 0;
6146f4a2713aSLionel Sambuc   unsigned NumBases = Record[Idx++];
6147f4a2713aSLionel Sambuc   void *Mem = Context.Allocate(sizeof(CXXBaseSpecifier) * NumBases);
6148f4a2713aSLionel Sambuc   CXXBaseSpecifier *Bases = new (Mem) CXXBaseSpecifier [NumBases];
6149f4a2713aSLionel Sambuc   for (unsigned I = 0; I != NumBases; ++I)
6150f4a2713aSLionel Sambuc     Bases[I] = ReadCXXBaseSpecifier(*Loc.F, Record, Idx);
6151f4a2713aSLionel Sambuc   return Bases;
6152f4a2713aSLionel Sambuc }
6153f4a2713aSLionel Sambuc 
6154f4a2713aSLionel Sambuc serialization::DeclID
getGlobalDeclID(ModuleFile & F,LocalDeclID LocalID) const6155f4a2713aSLionel Sambuc ASTReader::getGlobalDeclID(ModuleFile &F, LocalDeclID LocalID) const {
6156f4a2713aSLionel Sambuc   if (LocalID < NUM_PREDEF_DECL_IDS)
6157f4a2713aSLionel Sambuc     return LocalID;
6158f4a2713aSLionel Sambuc 
6159f4a2713aSLionel Sambuc   ContinuousRangeMap<uint32_t, int, 2>::iterator I
6160f4a2713aSLionel Sambuc     = F.DeclRemap.find(LocalID - NUM_PREDEF_DECL_IDS);
6161f4a2713aSLionel Sambuc   assert(I != F.DeclRemap.end() && "Invalid index into decl index remap");
6162f4a2713aSLionel Sambuc 
6163f4a2713aSLionel Sambuc   return LocalID + I->second;
6164f4a2713aSLionel Sambuc }
6165f4a2713aSLionel Sambuc 
isDeclIDFromModule(serialization::GlobalDeclID ID,ModuleFile & M) const6166f4a2713aSLionel Sambuc bool ASTReader::isDeclIDFromModule(serialization::GlobalDeclID ID,
6167f4a2713aSLionel Sambuc                                    ModuleFile &M) const {
6168f4a2713aSLionel Sambuc   GlobalDeclMapType::const_iterator I = GlobalDeclMap.find(ID);
6169f4a2713aSLionel Sambuc   assert(I != GlobalDeclMap.end() && "Corrupted global declaration map");
6170f4a2713aSLionel Sambuc   return &M == I->second;
6171f4a2713aSLionel Sambuc }
6172f4a2713aSLionel Sambuc 
getOwningModuleFile(const Decl * D)6173f4a2713aSLionel Sambuc ModuleFile *ASTReader::getOwningModuleFile(const Decl *D) {
6174f4a2713aSLionel Sambuc   if (!D->isFromASTFile())
6175*0a6a1f1dSLionel Sambuc     return nullptr;
6176f4a2713aSLionel Sambuc   GlobalDeclMapType::const_iterator I = GlobalDeclMap.find(D->getGlobalID());
6177f4a2713aSLionel Sambuc   assert(I != GlobalDeclMap.end() && "Corrupted global declaration map");
6178f4a2713aSLionel Sambuc   return I->second;
6179f4a2713aSLionel Sambuc }
6180f4a2713aSLionel Sambuc 
getSourceLocationForDeclID(GlobalDeclID ID)6181f4a2713aSLionel Sambuc SourceLocation ASTReader::getSourceLocationForDeclID(GlobalDeclID ID) {
6182f4a2713aSLionel Sambuc   if (ID < NUM_PREDEF_DECL_IDS)
6183f4a2713aSLionel Sambuc     return SourceLocation();
6184f4a2713aSLionel Sambuc 
6185f4a2713aSLionel Sambuc   unsigned Index = ID - NUM_PREDEF_DECL_IDS;
6186f4a2713aSLionel Sambuc 
6187f4a2713aSLionel Sambuc   if (Index > DeclsLoaded.size()) {
6188f4a2713aSLionel Sambuc     Error("declaration ID out-of-range for AST file");
6189f4a2713aSLionel Sambuc     return SourceLocation();
6190f4a2713aSLionel Sambuc   }
6191f4a2713aSLionel Sambuc 
6192f4a2713aSLionel Sambuc   if (Decl *D = DeclsLoaded[Index])
6193f4a2713aSLionel Sambuc     return D->getLocation();
6194f4a2713aSLionel Sambuc 
6195f4a2713aSLionel Sambuc   unsigned RawLocation = 0;
6196f4a2713aSLionel Sambuc   RecordLocation Rec = DeclCursorForID(ID, RawLocation);
6197f4a2713aSLionel Sambuc   return ReadSourceLocation(*Rec.F, RawLocation);
6198f4a2713aSLionel Sambuc }
6199f4a2713aSLionel Sambuc 
GetExistingDecl(DeclID ID)6200*0a6a1f1dSLionel Sambuc Decl *ASTReader::GetExistingDecl(DeclID ID) {
6201f4a2713aSLionel Sambuc   if (ID < NUM_PREDEF_DECL_IDS) {
6202f4a2713aSLionel Sambuc     switch ((PredefinedDeclIDs)ID) {
6203f4a2713aSLionel Sambuc     case PREDEF_DECL_NULL_ID:
6204*0a6a1f1dSLionel Sambuc       return nullptr;
6205f4a2713aSLionel Sambuc 
6206f4a2713aSLionel Sambuc     case PREDEF_DECL_TRANSLATION_UNIT_ID:
6207f4a2713aSLionel Sambuc       return Context.getTranslationUnitDecl();
6208f4a2713aSLionel Sambuc 
6209f4a2713aSLionel Sambuc     case PREDEF_DECL_OBJC_ID_ID:
6210f4a2713aSLionel Sambuc       return Context.getObjCIdDecl();
6211f4a2713aSLionel Sambuc 
6212f4a2713aSLionel Sambuc     case PREDEF_DECL_OBJC_SEL_ID:
6213f4a2713aSLionel Sambuc       return Context.getObjCSelDecl();
6214f4a2713aSLionel Sambuc 
6215f4a2713aSLionel Sambuc     case PREDEF_DECL_OBJC_CLASS_ID:
6216f4a2713aSLionel Sambuc       return Context.getObjCClassDecl();
6217f4a2713aSLionel Sambuc 
6218f4a2713aSLionel Sambuc     case PREDEF_DECL_OBJC_PROTOCOL_ID:
6219f4a2713aSLionel Sambuc       return Context.getObjCProtocolDecl();
6220f4a2713aSLionel Sambuc 
6221f4a2713aSLionel Sambuc     case PREDEF_DECL_INT_128_ID:
6222f4a2713aSLionel Sambuc       return Context.getInt128Decl();
6223f4a2713aSLionel Sambuc 
6224f4a2713aSLionel Sambuc     case PREDEF_DECL_UNSIGNED_INT_128_ID:
6225f4a2713aSLionel Sambuc       return Context.getUInt128Decl();
6226f4a2713aSLionel Sambuc 
6227f4a2713aSLionel Sambuc     case PREDEF_DECL_OBJC_INSTANCETYPE_ID:
6228f4a2713aSLionel Sambuc       return Context.getObjCInstanceTypeDecl();
6229f4a2713aSLionel Sambuc 
6230f4a2713aSLionel Sambuc     case PREDEF_DECL_BUILTIN_VA_LIST_ID:
6231f4a2713aSLionel Sambuc       return Context.getBuiltinVaListDecl();
6232f4a2713aSLionel Sambuc     }
6233f4a2713aSLionel Sambuc   }
6234f4a2713aSLionel Sambuc 
6235f4a2713aSLionel Sambuc   unsigned Index = ID - NUM_PREDEF_DECL_IDS;
6236f4a2713aSLionel Sambuc 
6237f4a2713aSLionel Sambuc   if (Index >= DeclsLoaded.size()) {
6238f4a2713aSLionel Sambuc     assert(0 && "declaration ID out-of-range for AST file");
6239f4a2713aSLionel Sambuc     Error("declaration ID out-of-range for AST file");
6240*0a6a1f1dSLionel Sambuc     return nullptr;
6241*0a6a1f1dSLionel Sambuc   }
6242*0a6a1f1dSLionel Sambuc 
6243*0a6a1f1dSLionel Sambuc   return DeclsLoaded[Index];
6244*0a6a1f1dSLionel Sambuc }
6245*0a6a1f1dSLionel Sambuc 
GetDecl(DeclID ID)6246*0a6a1f1dSLionel Sambuc Decl *ASTReader::GetDecl(DeclID ID) {
6247*0a6a1f1dSLionel Sambuc   if (ID < NUM_PREDEF_DECL_IDS)
6248*0a6a1f1dSLionel Sambuc     return GetExistingDecl(ID);
6249*0a6a1f1dSLionel Sambuc 
6250*0a6a1f1dSLionel Sambuc   unsigned Index = ID - NUM_PREDEF_DECL_IDS;
6251*0a6a1f1dSLionel Sambuc 
6252*0a6a1f1dSLionel Sambuc   if (Index >= DeclsLoaded.size()) {
6253*0a6a1f1dSLionel Sambuc     assert(0 && "declaration ID out-of-range for AST file");
6254*0a6a1f1dSLionel Sambuc     Error("declaration ID out-of-range for AST file");
6255*0a6a1f1dSLionel Sambuc     return nullptr;
6256f4a2713aSLionel Sambuc   }
6257f4a2713aSLionel Sambuc 
6258f4a2713aSLionel Sambuc   if (!DeclsLoaded[Index]) {
6259f4a2713aSLionel Sambuc     ReadDeclRecord(ID);
6260f4a2713aSLionel Sambuc     if (DeserializationListener)
6261f4a2713aSLionel Sambuc       DeserializationListener->DeclRead(ID, DeclsLoaded[Index]);
6262f4a2713aSLionel Sambuc   }
6263f4a2713aSLionel Sambuc 
6264f4a2713aSLionel Sambuc   return DeclsLoaded[Index];
6265f4a2713aSLionel Sambuc }
6266f4a2713aSLionel Sambuc 
mapGlobalIDToModuleFileGlobalID(ModuleFile & M,DeclID GlobalID)6267f4a2713aSLionel Sambuc DeclID ASTReader::mapGlobalIDToModuleFileGlobalID(ModuleFile &M,
6268f4a2713aSLionel Sambuc                                                   DeclID GlobalID) {
6269f4a2713aSLionel Sambuc   if (GlobalID < NUM_PREDEF_DECL_IDS)
6270f4a2713aSLionel Sambuc     return GlobalID;
6271f4a2713aSLionel Sambuc 
6272f4a2713aSLionel Sambuc   GlobalDeclMapType::const_iterator I = GlobalDeclMap.find(GlobalID);
6273f4a2713aSLionel Sambuc   assert(I != GlobalDeclMap.end() && "Corrupted global declaration map");
6274f4a2713aSLionel Sambuc   ModuleFile *Owner = I->second;
6275f4a2713aSLionel Sambuc 
6276f4a2713aSLionel Sambuc   llvm::DenseMap<ModuleFile *, serialization::DeclID>::iterator Pos
6277f4a2713aSLionel Sambuc     = M.GlobalToLocalDeclIDs.find(Owner);
6278f4a2713aSLionel Sambuc   if (Pos == M.GlobalToLocalDeclIDs.end())
6279f4a2713aSLionel Sambuc     return 0;
6280f4a2713aSLionel Sambuc 
6281f4a2713aSLionel Sambuc   return GlobalID - Owner->BaseDeclID + Pos->second;
6282f4a2713aSLionel Sambuc }
6283f4a2713aSLionel Sambuc 
ReadDeclID(ModuleFile & F,const RecordData & Record,unsigned & Idx)6284f4a2713aSLionel Sambuc serialization::DeclID ASTReader::ReadDeclID(ModuleFile &F,
6285f4a2713aSLionel Sambuc                                             const RecordData &Record,
6286f4a2713aSLionel Sambuc                                             unsigned &Idx) {
6287f4a2713aSLionel Sambuc   if (Idx >= Record.size()) {
6288f4a2713aSLionel Sambuc     Error("Corrupted AST file");
6289f4a2713aSLionel Sambuc     return 0;
6290f4a2713aSLionel Sambuc   }
6291f4a2713aSLionel Sambuc 
6292f4a2713aSLionel Sambuc   return getGlobalDeclID(F, Record[Idx++]);
6293f4a2713aSLionel Sambuc }
6294f4a2713aSLionel Sambuc 
6295f4a2713aSLionel Sambuc /// \brief Resolve the offset of a statement into a statement.
6296f4a2713aSLionel Sambuc ///
6297f4a2713aSLionel Sambuc /// This operation will read a new statement from the external
6298f4a2713aSLionel Sambuc /// source each time it is called, and is meant to be used via a
6299f4a2713aSLionel Sambuc /// LazyOffsetPtr (which is used by Decls for the body of functions, etc).
GetExternalDeclStmt(uint64_t Offset)6300f4a2713aSLionel Sambuc Stmt *ASTReader::GetExternalDeclStmt(uint64_t Offset) {
6301f4a2713aSLionel Sambuc   // Switch case IDs are per Decl.
6302f4a2713aSLionel Sambuc   ClearSwitchCaseIDs();
6303f4a2713aSLionel Sambuc 
6304f4a2713aSLionel Sambuc   // Offset here is a global offset across the entire chain.
6305f4a2713aSLionel Sambuc   RecordLocation Loc = getLocalBitOffset(Offset);
6306f4a2713aSLionel Sambuc   Loc.F->DeclsCursor.JumpToBit(Loc.Offset);
6307f4a2713aSLionel Sambuc   return ReadStmtFromStream(*Loc.F);
6308f4a2713aSLionel Sambuc }
6309f4a2713aSLionel Sambuc 
6310f4a2713aSLionel Sambuc namespace {
6311f4a2713aSLionel Sambuc   class FindExternalLexicalDeclsVisitor {
6312f4a2713aSLionel Sambuc     ASTReader &Reader;
6313f4a2713aSLionel Sambuc     const DeclContext *DC;
6314f4a2713aSLionel Sambuc     bool (*isKindWeWant)(Decl::Kind);
6315f4a2713aSLionel Sambuc 
6316f4a2713aSLionel Sambuc     SmallVectorImpl<Decl*> &Decls;
6317f4a2713aSLionel Sambuc     bool PredefsVisited[NUM_PREDEF_DECL_IDS];
6318f4a2713aSLionel Sambuc 
6319f4a2713aSLionel Sambuc   public:
FindExternalLexicalDeclsVisitor(ASTReader & Reader,const DeclContext * DC,bool (* isKindWeWant)(Decl::Kind),SmallVectorImpl<Decl * > & Decls)6320f4a2713aSLionel Sambuc     FindExternalLexicalDeclsVisitor(ASTReader &Reader, const DeclContext *DC,
6321f4a2713aSLionel Sambuc                                     bool (*isKindWeWant)(Decl::Kind),
6322f4a2713aSLionel Sambuc                                     SmallVectorImpl<Decl*> &Decls)
6323f4a2713aSLionel Sambuc       : Reader(Reader), DC(DC), isKindWeWant(isKindWeWant), Decls(Decls)
6324f4a2713aSLionel Sambuc     {
6325f4a2713aSLionel Sambuc       for (unsigned I = 0; I != NUM_PREDEF_DECL_IDS; ++I)
6326f4a2713aSLionel Sambuc         PredefsVisited[I] = false;
6327f4a2713aSLionel Sambuc     }
6328f4a2713aSLionel Sambuc 
visit(ModuleFile & M,bool Preorder,void * UserData)6329f4a2713aSLionel Sambuc     static bool visit(ModuleFile &M, bool Preorder, void *UserData) {
6330f4a2713aSLionel Sambuc       if (Preorder)
6331f4a2713aSLionel Sambuc         return false;
6332f4a2713aSLionel Sambuc 
6333f4a2713aSLionel Sambuc       FindExternalLexicalDeclsVisitor *This
6334f4a2713aSLionel Sambuc         = static_cast<FindExternalLexicalDeclsVisitor *>(UserData);
6335f4a2713aSLionel Sambuc 
6336f4a2713aSLionel Sambuc       ModuleFile::DeclContextInfosMap::iterator Info
6337f4a2713aSLionel Sambuc         = M.DeclContextInfos.find(This->DC);
6338f4a2713aSLionel Sambuc       if (Info == M.DeclContextInfos.end() || !Info->second.LexicalDecls)
6339f4a2713aSLionel Sambuc         return false;
6340f4a2713aSLionel Sambuc 
6341f4a2713aSLionel Sambuc       // Load all of the declaration IDs
6342f4a2713aSLionel Sambuc       for (const KindDeclIDPair *ID = Info->second.LexicalDecls,
6343f4a2713aSLionel Sambuc                                *IDE = ID + Info->second.NumLexicalDecls;
6344f4a2713aSLionel Sambuc            ID != IDE; ++ID) {
6345f4a2713aSLionel Sambuc         if (This->isKindWeWant && !This->isKindWeWant((Decl::Kind)ID->first))
6346f4a2713aSLionel Sambuc           continue;
6347f4a2713aSLionel Sambuc 
6348f4a2713aSLionel Sambuc         // Don't add predefined declarations to the lexical context more
6349f4a2713aSLionel Sambuc         // than once.
6350f4a2713aSLionel Sambuc         if (ID->second < NUM_PREDEF_DECL_IDS) {
6351f4a2713aSLionel Sambuc           if (This->PredefsVisited[ID->second])
6352f4a2713aSLionel Sambuc             continue;
6353f4a2713aSLionel Sambuc 
6354f4a2713aSLionel Sambuc           This->PredefsVisited[ID->second] = true;
6355f4a2713aSLionel Sambuc         }
6356f4a2713aSLionel Sambuc 
6357f4a2713aSLionel Sambuc         if (Decl *D = This->Reader.GetLocalDecl(M, ID->second)) {
6358f4a2713aSLionel Sambuc           if (!This->DC->isDeclInLexicalTraversal(D))
6359f4a2713aSLionel Sambuc             This->Decls.push_back(D);
6360f4a2713aSLionel Sambuc         }
6361f4a2713aSLionel Sambuc       }
6362f4a2713aSLionel Sambuc 
6363f4a2713aSLionel Sambuc       return false;
6364f4a2713aSLionel Sambuc     }
6365f4a2713aSLionel Sambuc   };
6366f4a2713aSLionel Sambuc }
6367f4a2713aSLionel Sambuc 
FindExternalLexicalDecls(const DeclContext * DC,bool (* isKindWeWant)(Decl::Kind),SmallVectorImpl<Decl * > & Decls)6368f4a2713aSLionel Sambuc ExternalLoadResult ASTReader::FindExternalLexicalDecls(const DeclContext *DC,
6369f4a2713aSLionel Sambuc                                          bool (*isKindWeWant)(Decl::Kind),
6370f4a2713aSLionel Sambuc                                          SmallVectorImpl<Decl*> &Decls) {
6371f4a2713aSLionel Sambuc   // There might be lexical decls in multiple modules, for the TU at
6372f4a2713aSLionel Sambuc   // least. Walk all of the modules in the order they were loaded.
6373f4a2713aSLionel Sambuc   FindExternalLexicalDeclsVisitor Visitor(*this, DC, isKindWeWant, Decls);
6374f4a2713aSLionel Sambuc   ModuleMgr.visitDepthFirst(&FindExternalLexicalDeclsVisitor::visit, &Visitor);
6375f4a2713aSLionel Sambuc   ++NumLexicalDeclContextsRead;
6376f4a2713aSLionel Sambuc   return ELR_Success;
6377f4a2713aSLionel Sambuc }
6378f4a2713aSLionel Sambuc 
6379f4a2713aSLionel Sambuc namespace {
6380f4a2713aSLionel Sambuc 
6381f4a2713aSLionel Sambuc class DeclIDComp {
6382f4a2713aSLionel Sambuc   ASTReader &Reader;
6383f4a2713aSLionel Sambuc   ModuleFile &Mod;
6384f4a2713aSLionel Sambuc 
6385f4a2713aSLionel Sambuc public:
DeclIDComp(ASTReader & Reader,ModuleFile & M)6386f4a2713aSLionel Sambuc   DeclIDComp(ASTReader &Reader, ModuleFile &M) : Reader(Reader), Mod(M) {}
6387f4a2713aSLionel Sambuc 
operator ()(LocalDeclID L,LocalDeclID R) const6388f4a2713aSLionel Sambuc   bool operator()(LocalDeclID L, LocalDeclID R) const {
6389f4a2713aSLionel Sambuc     SourceLocation LHS = getLocation(L);
6390f4a2713aSLionel Sambuc     SourceLocation RHS = getLocation(R);
6391f4a2713aSLionel Sambuc     return Reader.getSourceManager().isBeforeInTranslationUnit(LHS, RHS);
6392f4a2713aSLionel Sambuc   }
6393f4a2713aSLionel Sambuc 
operator ()(SourceLocation LHS,LocalDeclID R) const6394f4a2713aSLionel Sambuc   bool operator()(SourceLocation LHS, LocalDeclID R) const {
6395f4a2713aSLionel Sambuc     SourceLocation RHS = getLocation(R);
6396f4a2713aSLionel Sambuc     return Reader.getSourceManager().isBeforeInTranslationUnit(LHS, RHS);
6397f4a2713aSLionel Sambuc   }
6398f4a2713aSLionel Sambuc 
operator ()(LocalDeclID L,SourceLocation RHS) const6399f4a2713aSLionel Sambuc   bool operator()(LocalDeclID L, SourceLocation RHS) const {
6400f4a2713aSLionel Sambuc     SourceLocation LHS = getLocation(L);
6401f4a2713aSLionel Sambuc     return Reader.getSourceManager().isBeforeInTranslationUnit(LHS, RHS);
6402f4a2713aSLionel Sambuc   }
6403f4a2713aSLionel Sambuc 
getLocation(LocalDeclID ID) const6404f4a2713aSLionel Sambuc   SourceLocation getLocation(LocalDeclID ID) const {
6405f4a2713aSLionel Sambuc     return Reader.getSourceManager().getFileLoc(
6406f4a2713aSLionel Sambuc             Reader.getSourceLocationForDeclID(Reader.getGlobalDeclID(Mod, ID)));
6407f4a2713aSLionel Sambuc   }
6408f4a2713aSLionel Sambuc };
6409f4a2713aSLionel Sambuc 
6410f4a2713aSLionel Sambuc }
6411f4a2713aSLionel Sambuc 
FindFileRegionDecls(FileID File,unsigned Offset,unsigned Length,SmallVectorImpl<Decl * > & Decls)6412f4a2713aSLionel Sambuc void ASTReader::FindFileRegionDecls(FileID File,
6413f4a2713aSLionel Sambuc                                     unsigned Offset, unsigned Length,
6414f4a2713aSLionel Sambuc                                     SmallVectorImpl<Decl *> &Decls) {
6415f4a2713aSLionel Sambuc   SourceManager &SM = getSourceManager();
6416f4a2713aSLionel Sambuc 
6417f4a2713aSLionel Sambuc   llvm::DenseMap<FileID, FileDeclsInfo>::iterator I = FileDeclIDs.find(File);
6418f4a2713aSLionel Sambuc   if (I == FileDeclIDs.end())
6419f4a2713aSLionel Sambuc     return;
6420f4a2713aSLionel Sambuc 
6421f4a2713aSLionel Sambuc   FileDeclsInfo &DInfo = I->second;
6422f4a2713aSLionel Sambuc   if (DInfo.Decls.empty())
6423f4a2713aSLionel Sambuc     return;
6424f4a2713aSLionel Sambuc 
6425f4a2713aSLionel Sambuc   SourceLocation
6426f4a2713aSLionel Sambuc     BeginLoc = SM.getLocForStartOfFile(File).getLocWithOffset(Offset);
6427f4a2713aSLionel Sambuc   SourceLocation EndLoc = BeginLoc.getLocWithOffset(Length);
6428f4a2713aSLionel Sambuc 
6429f4a2713aSLionel Sambuc   DeclIDComp DIDComp(*this, *DInfo.Mod);
6430f4a2713aSLionel Sambuc   ArrayRef<serialization::LocalDeclID>::iterator
6431f4a2713aSLionel Sambuc     BeginIt = std::lower_bound(DInfo.Decls.begin(), DInfo.Decls.end(),
6432f4a2713aSLionel Sambuc                                BeginLoc, DIDComp);
6433f4a2713aSLionel Sambuc   if (BeginIt != DInfo.Decls.begin())
6434f4a2713aSLionel Sambuc     --BeginIt;
6435f4a2713aSLionel Sambuc 
6436f4a2713aSLionel Sambuc   // If we are pointing at a top-level decl inside an objc container, we need
6437f4a2713aSLionel Sambuc   // to backtrack until we find it otherwise we will fail to report that the
6438f4a2713aSLionel Sambuc   // region overlaps with an objc container.
6439f4a2713aSLionel Sambuc   while (BeginIt != DInfo.Decls.begin() &&
6440f4a2713aSLionel Sambuc          GetDecl(getGlobalDeclID(*DInfo.Mod, *BeginIt))
6441f4a2713aSLionel Sambuc              ->isTopLevelDeclInObjCContainer())
6442f4a2713aSLionel Sambuc     --BeginIt;
6443f4a2713aSLionel Sambuc 
6444f4a2713aSLionel Sambuc   ArrayRef<serialization::LocalDeclID>::iterator
6445f4a2713aSLionel Sambuc     EndIt = std::upper_bound(DInfo.Decls.begin(), DInfo.Decls.end(),
6446f4a2713aSLionel Sambuc                              EndLoc, DIDComp);
6447f4a2713aSLionel Sambuc   if (EndIt != DInfo.Decls.end())
6448f4a2713aSLionel Sambuc     ++EndIt;
6449f4a2713aSLionel Sambuc 
6450f4a2713aSLionel Sambuc   for (ArrayRef<serialization::LocalDeclID>::iterator
6451f4a2713aSLionel Sambuc          DIt = BeginIt; DIt != EndIt; ++DIt)
6452f4a2713aSLionel Sambuc     Decls.push_back(GetDecl(getGlobalDeclID(*DInfo.Mod, *DIt)));
6453f4a2713aSLionel Sambuc }
6454f4a2713aSLionel Sambuc 
6455f4a2713aSLionel Sambuc namespace {
6456f4a2713aSLionel Sambuc   /// \brief ModuleFile visitor used to perform name lookup into a
6457f4a2713aSLionel Sambuc   /// declaration context.
6458f4a2713aSLionel Sambuc   class DeclContextNameLookupVisitor {
6459f4a2713aSLionel Sambuc     ASTReader &Reader;
6460*0a6a1f1dSLionel Sambuc     ArrayRef<const DeclContext *> Contexts;
6461f4a2713aSLionel Sambuc     DeclarationName Name;
6462f4a2713aSLionel Sambuc     SmallVectorImpl<NamedDecl *> &Decls;
6463f4a2713aSLionel Sambuc 
6464f4a2713aSLionel Sambuc   public:
DeclContextNameLookupVisitor(ASTReader & Reader,ArrayRef<const DeclContext * > Contexts,DeclarationName Name,SmallVectorImpl<NamedDecl * > & Decls)6465f4a2713aSLionel Sambuc     DeclContextNameLookupVisitor(ASTReader &Reader,
6466*0a6a1f1dSLionel Sambuc                                  ArrayRef<const DeclContext *> Contexts,
6467f4a2713aSLionel Sambuc                                  DeclarationName Name,
6468f4a2713aSLionel Sambuc                                  SmallVectorImpl<NamedDecl *> &Decls)
6469f4a2713aSLionel Sambuc       : Reader(Reader), Contexts(Contexts), Name(Name), Decls(Decls) { }
6470f4a2713aSLionel Sambuc 
visit(ModuleFile & M,void * UserData)6471f4a2713aSLionel Sambuc     static bool visit(ModuleFile &M, void *UserData) {
6472f4a2713aSLionel Sambuc       DeclContextNameLookupVisitor *This
6473f4a2713aSLionel Sambuc         = static_cast<DeclContextNameLookupVisitor *>(UserData);
6474f4a2713aSLionel Sambuc 
6475f4a2713aSLionel Sambuc       // Check whether we have any visible declaration information for
6476f4a2713aSLionel Sambuc       // this context in this module.
6477f4a2713aSLionel Sambuc       ModuleFile::DeclContextInfosMap::iterator Info;
6478f4a2713aSLionel Sambuc       bool FoundInfo = false;
6479*0a6a1f1dSLionel Sambuc       for (auto *DC : This->Contexts) {
6480*0a6a1f1dSLionel Sambuc         Info = M.DeclContextInfos.find(DC);
6481f4a2713aSLionel Sambuc         if (Info != M.DeclContextInfos.end() &&
6482f4a2713aSLionel Sambuc             Info->second.NameLookupTableData) {
6483f4a2713aSLionel Sambuc           FoundInfo = true;
6484f4a2713aSLionel Sambuc           break;
6485f4a2713aSLionel Sambuc         }
6486f4a2713aSLionel Sambuc       }
6487f4a2713aSLionel Sambuc 
6488f4a2713aSLionel Sambuc       if (!FoundInfo)
6489f4a2713aSLionel Sambuc         return false;
6490f4a2713aSLionel Sambuc 
6491f4a2713aSLionel Sambuc       // Look for this name within this module.
6492f4a2713aSLionel Sambuc       ASTDeclContextNameLookupTable *LookupTable =
6493f4a2713aSLionel Sambuc         Info->second.NameLookupTableData;
6494f4a2713aSLionel Sambuc       ASTDeclContextNameLookupTable::iterator Pos
6495f4a2713aSLionel Sambuc         = LookupTable->find(This->Name);
6496f4a2713aSLionel Sambuc       if (Pos == LookupTable->end())
6497f4a2713aSLionel Sambuc         return false;
6498f4a2713aSLionel Sambuc 
6499f4a2713aSLionel Sambuc       bool FoundAnything = false;
6500f4a2713aSLionel Sambuc       ASTDeclContextNameLookupTrait::data_type Data = *Pos;
6501f4a2713aSLionel Sambuc       for (; Data.first != Data.second; ++Data.first) {
6502f4a2713aSLionel Sambuc         NamedDecl *ND = This->Reader.GetLocalDeclAs<NamedDecl>(M, *Data.first);
6503f4a2713aSLionel Sambuc         if (!ND)
6504f4a2713aSLionel Sambuc           continue;
6505f4a2713aSLionel Sambuc 
6506f4a2713aSLionel Sambuc         if (ND->getDeclName() != This->Name) {
6507f4a2713aSLionel Sambuc           // A name might be null because the decl's redeclarable part is
6508f4a2713aSLionel Sambuc           // currently read before reading its name. The lookup is triggered by
6509f4a2713aSLionel Sambuc           // building that decl (likely indirectly), and so it is later in the
6510f4a2713aSLionel Sambuc           // sense of "already existing" and can be ignored here.
6511*0a6a1f1dSLionel Sambuc           // FIXME: This should not happen; deserializing declarations should
6512*0a6a1f1dSLionel Sambuc           // not perform lookups since that can lead to deserialization cycles.
6513f4a2713aSLionel Sambuc           continue;
6514f4a2713aSLionel Sambuc         }
6515f4a2713aSLionel Sambuc 
6516f4a2713aSLionel Sambuc         // Record this declaration.
6517f4a2713aSLionel Sambuc         FoundAnything = true;
6518f4a2713aSLionel Sambuc         This->Decls.push_back(ND);
6519f4a2713aSLionel Sambuc       }
6520f4a2713aSLionel Sambuc 
6521f4a2713aSLionel Sambuc       return FoundAnything;
6522f4a2713aSLionel Sambuc     }
6523f4a2713aSLionel Sambuc   };
6524f4a2713aSLionel Sambuc }
6525f4a2713aSLionel Sambuc 
6526f4a2713aSLionel Sambuc /// \brief Retrieve the "definitive" module file for the definition of the
6527f4a2713aSLionel Sambuc /// given declaration context, if there is one.
6528f4a2713aSLionel Sambuc ///
6529f4a2713aSLionel Sambuc /// The "definitive" module file is the only place where we need to look to
6530f4a2713aSLionel Sambuc /// find information about the declarations within the given declaration
6531f4a2713aSLionel Sambuc /// context. For example, C++ and Objective-C classes, C structs/unions, and
6532f4a2713aSLionel Sambuc /// Objective-C protocols, categories, and extensions are all defined in a
6533f4a2713aSLionel Sambuc /// single place in the source code, so they have definitive module files
6534f4a2713aSLionel Sambuc /// associated with them. C++ namespaces, on the other hand, can have
6535f4a2713aSLionel Sambuc /// definitions in multiple different module files.
6536f4a2713aSLionel Sambuc ///
6537f4a2713aSLionel Sambuc /// Note: this needs to be kept in sync with ASTWriter::AddedVisibleDecl's
6538f4a2713aSLionel Sambuc /// NDEBUG checking.
getDefinitiveModuleFileFor(const DeclContext * DC,ASTReader & Reader)6539f4a2713aSLionel Sambuc static ModuleFile *getDefinitiveModuleFileFor(const DeclContext *DC,
6540f4a2713aSLionel Sambuc                                               ASTReader &Reader) {
6541f4a2713aSLionel Sambuc   if (const DeclContext *DefDC = getDefinitiveDeclContext(DC))
6542f4a2713aSLionel Sambuc     return Reader.getOwningModuleFile(cast<Decl>(DefDC));
6543f4a2713aSLionel Sambuc 
6544*0a6a1f1dSLionel Sambuc   return nullptr;
6545f4a2713aSLionel Sambuc }
6546f4a2713aSLionel Sambuc 
6547f4a2713aSLionel Sambuc bool
FindExternalVisibleDeclsByName(const DeclContext * DC,DeclarationName Name)6548f4a2713aSLionel Sambuc ASTReader::FindExternalVisibleDeclsByName(const DeclContext *DC,
6549f4a2713aSLionel Sambuc                                           DeclarationName Name) {
6550f4a2713aSLionel Sambuc   assert(DC->hasExternalVisibleStorage() &&
6551f4a2713aSLionel Sambuc          "DeclContext has no visible decls in storage");
6552f4a2713aSLionel Sambuc   if (!Name)
6553f4a2713aSLionel Sambuc     return false;
6554f4a2713aSLionel Sambuc 
6555*0a6a1f1dSLionel Sambuc   Deserializing LookupResults(this);
6556*0a6a1f1dSLionel Sambuc 
6557f4a2713aSLionel Sambuc   SmallVector<NamedDecl *, 64> Decls;
6558f4a2713aSLionel Sambuc 
6559f4a2713aSLionel Sambuc   // Compute the declaration contexts we need to look into. Multiple such
6560f4a2713aSLionel Sambuc   // declaration contexts occur when two declaration contexts from disjoint
6561f4a2713aSLionel Sambuc   // modules get merged, e.g., when two namespaces with the same name are
6562f4a2713aSLionel Sambuc   // independently defined in separate modules.
6563f4a2713aSLionel Sambuc   SmallVector<const DeclContext *, 2> Contexts;
6564f4a2713aSLionel Sambuc   Contexts.push_back(DC);
6565f4a2713aSLionel Sambuc 
6566f4a2713aSLionel Sambuc   if (DC->isNamespace()) {
6567*0a6a1f1dSLionel Sambuc     auto Merged = MergedDecls.find(const_cast<Decl *>(cast<Decl>(DC)));
6568f4a2713aSLionel Sambuc     if (Merged != MergedDecls.end()) {
6569f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Merged->second.size(); I != N; ++I)
6570f4a2713aSLionel Sambuc         Contexts.push_back(cast<DeclContext>(GetDecl(Merged->second[I])));
6571f4a2713aSLionel Sambuc     }
6572f4a2713aSLionel Sambuc   }
6573f4a2713aSLionel Sambuc 
6574*0a6a1f1dSLionel Sambuc   auto LookUpInContexts = [&](ArrayRef<const DeclContext*> Contexts) {
6575f4a2713aSLionel Sambuc     DeclContextNameLookupVisitor Visitor(*this, Contexts, Name, Decls);
6576f4a2713aSLionel Sambuc 
6577f4a2713aSLionel Sambuc     // If we can definitively determine which module file to look into,
6578f4a2713aSLionel Sambuc     // only look there. Otherwise, look in all module files.
6579f4a2713aSLionel Sambuc     ModuleFile *Definitive;
6580f4a2713aSLionel Sambuc     if (Contexts.size() == 1 &&
6581*0a6a1f1dSLionel Sambuc         (Definitive = getDefinitiveModuleFileFor(Contexts[0], *this))) {
6582f4a2713aSLionel Sambuc       DeclContextNameLookupVisitor::visit(*Definitive, &Visitor);
6583f4a2713aSLionel Sambuc     } else {
6584f4a2713aSLionel Sambuc       ModuleMgr.visit(&DeclContextNameLookupVisitor::visit, &Visitor);
6585f4a2713aSLionel Sambuc     }
6586*0a6a1f1dSLionel Sambuc   };
6587*0a6a1f1dSLionel Sambuc 
6588*0a6a1f1dSLionel Sambuc   LookUpInContexts(Contexts);
6589*0a6a1f1dSLionel Sambuc 
6590*0a6a1f1dSLionel Sambuc   // If this might be an implicit special member function, then also search
6591*0a6a1f1dSLionel Sambuc   // all merged definitions of the surrounding class. We need to search them
6592*0a6a1f1dSLionel Sambuc   // individually, because finding an entity in one of them doesn't imply that
6593*0a6a1f1dSLionel Sambuc   // we can't find a different entity in another one.
6594*0a6a1f1dSLionel Sambuc   if (isa<CXXRecordDecl>(DC)) {
6595*0a6a1f1dSLionel Sambuc     auto Kind = Name.getNameKind();
6596*0a6a1f1dSLionel Sambuc     if (Kind == DeclarationName::CXXConstructorName ||
6597*0a6a1f1dSLionel Sambuc         Kind == DeclarationName::CXXDestructorName ||
6598*0a6a1f1dSLionel Sambuc         (Kind == DeclarationName::CXXOperatorName &&
6599*0a6a1f1dSLionel Sambuc          Name.getCXXOverloadedOperator() == OO_Equal)) {
6600*0a6a1f1dSLionel Sambuc       auto Merged = MergedLookups.find(DC);
6601*0a6a1f1dSLionel Sambuc       if (Merged != MergedLookups.end()) {
6602*0a6a1f1dSLionel Sambuc         for (unsigned I = 0; I != Merged->second.size(); ++I) {
6603*0a6a1f1dSLionel Sambuc           LookUpInContexts(Merged->second[I]);
6604*0a6a1f1dSLionel Sambuc           // We might have just added some more merged lookups. If so, our
6605*0a6a1f1dSLionel Sambuc           // iterator is now invalid, so grab a fresh one before continuing.
6606*0a6a1f1dSLionel Sambuc           Merged = MergedLookups.find(DC);
6607*0a6a1f1dSLionel Sambuc         }
6608*0a6a1f1dSLionel Sambuc       }
6609*0a6a1f1dSLionel Sambuc     }
6610*0a6a1f1dSLionel Sambuc   }
6611*0a6a1f1dSLionel Sambuc 
6612f4a2713aSLionel Sambuc   ++NumVisibleDeclContextsRead;
6613f4a2713aSLionel Sambuc   SetExternalVisibleDeclsForName(DC, Name, Decls);
6614f4a2713aSLionel Sambuc   return !Decls.empty();
6615f4a2713aSLionel Sambuc }
6616f4a2713aSLionel Sambuc 
6617f4a2713aSLionel Sambuc namespace {
6618f4a2713aSLionel Sambuc   /// \brief ModuleFile visitor used to retrieve all visible names in a
6619f4a2713aSLionel Sambuc   /// declaration context.
6620f4a2713aSLionel Sambuc   class DeclContextAllNamesVisitor {
6621f4a2713aSLionel Sambuc     ASTReader &Reader;
6622f4a2713aSLionel Sambuc     SmallVectorImpl<const DeclContext *> &Contexts;
6623f4a2713aSLionel Sambuc     DeclsMap &Decls;
6624f4a2713aSLionel Sambuc     bool VisitAll;
6625f4a2713aSLionel Sambuc 
6626f4a2713aSLionel Sambuc   public:
DeclContextAllNamesVisitor(ASTReader & Reader,SmallVectorImpl<const DeclContext * > & Contexts,DeclsMap & Decls,bool VisitAll)6627f4a2713aSLionel Sambuc     DeclContextAllNamesVisitor(ASTReader &Reader,
6628f4a2713aSLionel Sambuc                                SmallVectorImpl<const DeclContext *> &Contexts,
6629f4a2713aSLionel Sambuc                                DeclsMap &Decls, bool VisitAll)
6630f4a2713aSLionel Sambuc       : Reader(Reader), Contexts(Contexts), Decls(Decls), VisitAll(VisitAll) { }
6631f4a2713aSLionel Sambuc 
visit(ModuleFile & M,void * UserData)6632f4a2713aSLionel Sambuc     static bool visit(ModuleFile &M, void *UserData) {
6633f4a2713aSLionel Sambuc       DeclContextAllNamesVisitor *This
6634f4a2713aSLionel Sambuc         = static_cast<DeclContextAllNamesVisitor *>(UserData);
6635f4a2713aSLionel Sambuc 
6636f4a2713aSLionel Sambuc       // Check whether we have any visible declaration information for
6637f4a2713aSLionel Sambuc       // this context in this module.
6638f4a2713aSLionel Sambuc       ModuleFile::DeclContextInfosMap::iterator Info;
6639f4a2713aSLionel Sambuc       bool FoundInfo = false;
6640f4a2713aSLionel Sambuc       for (unsigned I = 0, N = This->Contexts.size(); I != N; ++I) {
6641f4a2713aSLionel Sambuc         Info = M.DeclContextInfos.find(This->Contexts[I]);
6642f4a2713aSLionel Sambuc         if (Info != M.DeclContextInfos.end() &&
6643f4a2713aSLionel Sambuc             Info->second.NameLookupTableData) {
6644f4a2713aSLionel Sambuc           FoundInfo = true;
6645f4a2713aSLionel Sambuc           break;
6646f4a2713aSLionel Sambuc         }
6647f4a2713aSLionel Sambuc       }
6648f4a2713aSLionel Sambuc 
6649f4a2713aSLionel Sambuc       if (!FoundInfo)
6650f4a2713aSLionel Sambuc         return false;
6651f4a2713aSLionel Sambuc 
6652f4a2713aSLionel Sambuc       ASTDeclContextNameLookupTable *LookupTable =
6653f4a2713aSLionel Sambuc         Info->second.NameLookupTableData;
6654f4a2713aSLionel Sambuc       bool FoundAnything = false;
6655f4a2713aSLionel Sambuc       for (ASTDeclContextNameLookupTable::data_iterator
6656f4a2713aSLionel Sambuc              I = LookupTable->data_begin(), E = LookupTable->data_end();
6657f4a2713aSLionel Sambuc            I != E;
6658f4a2713aSLionel Sambuc            ++I) {
6659f4a2713aSLionel Sambuc         ASTDeclContextNameLookupTrait::data_type Data = *I;
6660f4a2713aSLionel Sambuc         for (; Data.first != Data.second; ++Data.first) {
6661f4a2713aSLionel Sambuc           NamedDecl *ND = This->Reader.GetLocalDeclAs<NamedDecl>(M,
6662f4a2713aSLionel Sambuc                                                                  *Data.first);
6663f4a2713aSLionel Sambuc           if (!ND)
6664f4a2713aSLionel Sambuc             continue;
6665f4a2713aSLionel Sambuc 
6666f4a2713aSLionel Sambuc           // Record this declaration.
6667f4a2713aSLionel Sambuc           FoundAnything = true;
6668f4a2713aSLionel Sambuc           This->Decls[ND->getDeclName()].push_back(ND);
6669f4a2713aSLionel Sambuc         }
6670f4a2713aSLionel Sambuc       }
6671f4a2713aSLionel Sambuc 
6672f4a2713aSLionel Sambuc       return FoundAnything && !This->VisitAll;
6673f4a2713aSLionel Sambuc     }
6674f4a2713aSLionel Sambuc   };
6675f4a2713aSLionel Sambuc }
6676f4a2713aSLionel Sambuc 
completeVisibleDeclsMap(const DeclContext * DC)6677f4a2713aSLionel Sambuc void ASTReader::completeVisibleDeclsMap(const DeclContext *DC) {
6678f4a2713aSLionel Sambuc   if (!DC->hasExternalVisibleStorage())
6679f4a2713aSLionel Sambuc     return;
6680f4a2713aSLionel Sambuc   DeclsMap Decls;
6681f4a2713aSLionel Sambuc 
6682f4a2713aSLionel Sambuc   // Compute the declaration contexts we need to look into. Multiple such
6683f4a2713aSLionel Sambuc   // declaration contexts occur when two declaration contexts from disjoint
6684f4a2713aSLionel Sambuc   // modules get merged, e.g., when two namespaces with the same name are
6685f4a2713aSLionel Sambuc   // independently defined in separate modules.
6686f4a2713aSLionel Sambuc   SmallVector<const DeclContext *, 2> Contexts;
6687f4a2713aSLionel Sambuc   Contexts.push_back(DC);
6688f4a2713aSLionel Sambuc 
6689f4a2713aSLionel Sambuc   if (DC->isNamespace()) {
6690f4a2713aSLionel Sambuc     MergedDeclsMap::iterator Merged
6691f4a2713aSLionel Sambuc       = MergedDecls.find(const_cast<Decl *>(cast<Decl>(DC)));
6692f4a2713aSLionel Sambuc     if (Merged != MergedDecls.end()) {
6693f4a2713aSLionel Sambuc       for (unsigned I = 0, N = Merged->second.size(); I != N; ++I)
6694f4a2713aSLionel Sambuc         Contexts.push_back(cast<DeclContext>(GetDecl(Merged->second[I])));
6695f4a2713aSLionel Sambuc     }
6696f4a2713aSLionel Sambuc   }
6697f4a2713aSLionel Sambuc 
6698f4a2713aSLionel Sambuc   DeclContextAllNamesVisitor Visitor(*this, Contexts, Decls,
6699f4a2713aSLionel Sambuc                                      /*VisitAll=*/DC->isFileContext());
6700f4a2713aSLionel Sambuc   ModuleMgr.visit(&DeclContextAllNamesVisitor::visit, &Visitor);
6701f4a2713aSLionel Sambuc   ++NumVisibleDeclContextsRead;
6702f4a2713aSLionel Sambuc 
6703f4a2713aSLionel Sambuc   for (DeclsMap::iterator I = Decls.begin(), E = Decls.end(); I != E; ++I) {
6704f4a2713aSLionel Sambuc     SetExternalVisibleDeclsForName(DC, I->first, I->second);
6705f4a2713aSLionel Sambuc   }
6706f4a2713aSLionel Sambuc   const_cast<DeclContext *>(DC)->setHasExternalVisibleStorage(false);
6707f4a2713aSLionel Sambuc }
6708f4a2713aSLionel Sambuc 
6709f4a2713aSLionel Sambuc /// \brief Under non-PCH compilation the consumer receives the objc methods
6710f4a2713aSLionel Sambuc /// before receiving the implementation, and codegen depends on this.
6711f4a2713aSLionel Sambuc /// We simulate this by deserializing and passing to consumer the methods of the
6712f4a2713aSLionel Sambuc /// implementation before passing the deserialized implementation decl.
PassObjCImplDeclToConsumer(ObjCImplDecl * ImplD,ASTConsumer * Consumer)6713f4a2713aSLionel Sambuc static void PassObjCImplDeclToConsumer(ObjCImplDecl *ImplD,
6714f4a2713aSLionel Sambuc                                        ASTConsumer *Consumer) {
6715f4a2713aSLionel Sambuc   assert(ImplD && Consumer);
6716f4a2713aSLionel Sambuc 
6717*0a6a1f1dSLionel Sambuc   for (auto *I : ImplD->methods())
6718*0a6a1f1dSLionel Sambuc     Consumer->HandleInterestingDecl(DeclGroupRef(I));
6719f4a2713aSLionel Sambuc 
6720f4a2713aSLionel Sambuc   Consumer->HandleInterestingDecl(DeclGroupRef(ImplD));
6721f4a2713aSLionel Sambuc }
6722f4a2713aSLionel Sambuc 
PassInterestingDeclsToConsumer()6723f4a2713aSLionel Sambuc void ASTReader::PassInterestingDeclsToConsumer() {
6724f4a2713aSLionel Sambuc   assert(Consumer);
6725*0a6a1f1dSLionel Sambuc 
6726*0a6a1f1dSLionel Sambuc   if (PassingDeclsToConsumer)
6727*0a6a1f1dSLionel Sambuc     return;
6728*0a6a1f1dSLionel Sambuc 
6729*0a6a1f1dSLionel Sambuc   // Guard variable to avoid recursively redoing the process of passing
6730*0a6a1f1dSLionel Sambuc   // decls to consumer.
6731*0a6a1f1dSLionel Sambuc   SaveAndRestore<bool> GuardPassingDeclsToConsumer(PassingDeclsToConsumer,
6732*0a6a1f1dSLionel Sambuc                                                    true);
6733*0a6a1f1dSLionel Sambuc 
6734f4a2713aSLionel Sambuc   while (!InterestingDecls.empty()) {
6735f4a2713aSLionel Sambuc     Decl *D = InterestingDecls.front();
6736f4a2713aSLionel Sambuc     InterestingDecls.pop_front();
6737f4a2713aSLionel Sambuc 
6738f4a2713aSLionel Sambuc     PassInterestingDeclToConsumer(D);
6739f4a2713aSLionel Sambuc   }
6740f4a2713aSLionel Sambuc }
6741f4a2713aSLionel Sambuc 
PassInterestingDeclToConsumer(Decl * D)6742f4a2713aSLionel Sambuc void ASTReader::PassInterestingDeclToConsumer(Decl *D) {
6743f4a2713aSLionel Sambuc   if (ObjCImplDecl *ImplD = dyn_cast<ObjCImplDecl>(D))
6744f4a2713aSLionel Sambuc     PassObjCImplDeclToConsumer(ImplD, Consumer);
6745f4a2713aSLionel Sambuc   else
6746f4a2713aSLionel Sambuc     Consumer->HandleInterestingDecl(DeclGroupRef(D));
6747f4a2713aSLionel Sambuc }
6748f4a2713aSLionel Sambuc 
StartTranslationUnit(ASTConsumer * Consumer)6749f4a2713aSLionel Sambuc void ASTReader::StartTranslationUnit(ASTConsumer *Consumer) {
6750f4a2713aSLionel Sambuc   this->Consumer = Consumer;
6751f4a2713aSLionel Sambuc 
6752f4a2713aSLionel Sambuc   if (!Consumer)
6753f4a2713aSLionel Sambuc     return;
6754f4a2713aSLionel Sambuc 
6755*0a6a1f1dSLionel Sambuc   for (unsigned I = 0, N = EagerlyDeserializedDecls.size(); I != N; ++I) {
6756f4a2713aSLionel Sambuc     // Force deserialization of this decl, which will cause it to be queued for
6757f4a2713aSLionel Sambuc     // passing to the consumer.
6758*0a6a1f1dSLionel Sambuc     GetDecl(EagerlyDeserializedDecls[I]);
6759f4a2713aSLionel Sambuc   }
6760*0a6a1f1dSLionel Sambuc   EagerlyDeserializedDecls.clear();
6761f4a2713aSLionel Sambuc 
6762f4a2713aSLionel Sambuc   PassInterestingDeclsToConsumer();
6763f4a2713aSLionel Sambuc }
6764f4a2713aSLionel Sambuc 
PrintStats()6765f4a2713aSLionel Sambuc void ASTReader::PrintStats() {
6766f4a2713aSLionel Sambuc   std::fprintf(stderr, "*** AST File Statistics:\n");
6767f4a2713aSLionel Sambuc 
6768f4a2713aSLionel Sambuc   unsigned NumTypesLoaded
6769f4a2713aSLionel Sambuc     = TypesLoaded.size() - std::count(TypesLoaded.begin(), TypesLoaded.end(),
6770f4a2713aSLionel Sambuc                                       QualType());
6771f4a2713aSLionel Sambuc   unsigned NumDeclsLoaded
6772f4a2713aSLionel Sambuc     = DeclsLoaded.size() - std::count(DeclsLoaded.begin(), DeclsLoaded.end(),
6773*0a6a1f1dSLionel Sambuc                                       (Decl *)nullptr);
6774f4a2713aSLionel Sambuc   unsigned NumIdentifiersLoaded
6775f4a2713aSLionel Sambuc     = IdentifiersLoaded.size() - std::count(IdentifiersLoaded.begin(),
6776f4a2713aSLionel Sambuc                                             IdentifiersLoaded.end(),
6777*0a6a1f1dSLionel Sambuc                                             (IdentifierInfo *)nullptr);
6778f4a2713aSLionel Sambuc   unsigned NumMacrosLoaded
6779f4a2713aSLionel Sambuc     = MacrosLoaded.size() - std::count(MacrosLoaded.begin(),
6780f4a2713aSLionel Sambuc                                        MacrosLoaded.end(),
6781*0a6a1f1dSLionel Sambuc                                        (MacroInfo *)nullptr);
6782f4a2713aSLionel Sambuc   unsigned NumSelectorsLoaded
6783f4a2713aSLionel Sambuc     = SelectorsLoaded.size() - std::count(SelectorsLoaded.begin(),
6784f4a2713aSLionel Sambuc                                           SelectorsLoaded.end(),
6785f4a2713aSLionel Sambuc                                           Selector());
6786f4a2713aSLionel Sambuc 
6787f4a2713aSLionel Sambuc   if (unsigned TotalNumSLocEntries = getTotalNumSLocs())
6788f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u source location entries read (%f%%)\n",
6789f4a2713aSLionel Sambuc                  NumSLocEntriesRead, TotalNumSLocEntries,
6790f4a2713aSLionel Sambuc                  ((float)NumSLocEntriesRead/TotalNumSLocEntries * 100));
6791f4a2713aSLionel Sambuc   if (!TypesLoaded.empty())
6792f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u types read (%f%%)\n",
6793f4a2713aSLionel Sambuc                  NumTypesLoaded, (unsigned)TypesLoaded.size(),
6794f4a2713aSLionel Sambuc                  ((float)NumTypesLoaded/TypesLoaded.size() * 100));
6795f4a2713aSLionel Sambuc   if (!DeclsLoaded.empty())
6796f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u declarations read (%f%%)\n",
6797f4a2713aSLionel Sambuc                  NumDeclsLoaded, (unsigned)DeclsLoaded.size(),
6798f4a2713aSLionel Sambuc                  ((float)NumDeclsLoaded/DeclsLoaded.size() * 100));
6799f4a2713aSLionel Sambuc   if (!IdentifiersLoaded.empty())
6800f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u identifiers read (%f%%)\n",
6801f4a2713aSLionel Sambuc                  NumIdentifiersLoaded, (unsigned)IdentifiersLoaded.size(),
6802f4a2713aSLionel Sambuc                  ((float)NumIdentifiersLoaded/IdentifiersLoaded.size() * 100));
6803f4a2713aSLionel Sambuc   if (!MacrosLoaded.empty())
6804f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u macros read (%f%%)\n",
6805f4a2713aSLionel Sambuc                  NumMacrosLoaded, (unsigned)MacrosLoaded.size(),
6806f4a2713aSLionel Sambuc                  ((float)NumMacrosLoaded/MacrosLoaded.size() * 100));
6807f4a2713aSLionel Sambuc   if (!SelectorsLoaded.empty())
6808f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u selectors read (%f%%)\n",
6809f4a2713aSLionel Sambuc                  NumSelectorsLoaded, (unsigned)SelectorsLoaded.size(),
6810f4a2713aSLionel Sambuc                  ((float)NumSelectorsLoaded/SelectorsLoaded.size() * 100));
6811f4a2713aSLionel Sambuc   if (TotalNumStatements)
6812f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u statements read (%f%%)\n",
6813f4a2713aSLionel Sambuc                  NumStatementsRead, TotalNumStatements,
6814f4a2713aSLionel Sambuc                  ((float)NumStatementsRead/TotalNumStatements * 100));
6815f4a2713aSLionel Sambuc   if (TotalNumMacros)
6816f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u macros read (%f%%)\n",
6817f4a2713aSLionel Sambuc                  NumMacrosRead, TotalNumMacros,
6818f4a2713aSLionel Sambuc                  ((float)NumMacrosRead/TotalNumMacros * 100));
6819f4a2713aSLionel Sambuc   if (TotalLexicalDeclContexts)
6820f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u lexical declcontexts read (%f%%)\n",
6821f4a2713aSLionel Sambuc                  NumLexicalDeclContextsRead, TotalLexicalDeclContexts,
6822f4a2713aSLionel Sambuc                  ((float)NumLexicalDeclContextsRead/TotalLexicalDeclContexts
6823f4a2713aSLionel Sambuc                   * 100));
6824f4a2713aSLionel Sambuc   if (TotalVisibleDeclContexts)
6825f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u visible declcontexts read (%f%%)\n",
6826f4a2713aSLionel Sambuc                  NumVisibleDeclContextsRead, TotalVisibleDeclContexts,
6827f4a2713aSLionel Sambuc                  ((float)NumVisibleDeclContextsRead/TotalVisibleDeclContexts
6828f4a2713aSLionel Sambuc                   * 100));
6829f4a2713aSLionel Sambuc   if (TotalNumMethodPoolEntries) {
6830f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u method pool entries read (%f%%)\n",
6831f4a2713aSLionel Sambuc                  NumMethodPoolEntriesRead, TotalNumMethodPoolEntries,
6832f4a2713aSLionel Sambuc                  ((float)NumMethodPoolEntriesRead/TotalNumMethodPoolEntries
6833f4a2713aSLionel Sambuc                   * 100));
6834f4a2713aSLionel Sambuc   }
6835f4a2713aSLionel Sambuc   if (NumMethodPoolLookups) {
6836f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u method pool lookups succeeded (%f%%)\n",
6837f4a2713aSLionel Sambuc                  NumMethodPoolHits, NumMethodPoolLookups,
6838f4a2713aSLionel Sambuc                  ((float)NumMethodPoolHits/NumMethodPoolLookups * 100.0));
6839f4a2713aSLionel Sambuc   }
6840f4a2713aSLionel Sambuc   if (NumMethodPoolTableLookups) {
6841f4a2713aSLionel Sambuc     std::fprintf(stderr, "  %u/%u method pool table lookups succeeded (%f%%)\n",
6842f4a2713aSLionel Sambuc                  NumMethodPoolTableHits, NumMethodPoolTableLookups,
6843f4a2713aSLionel Sambuc                  ((float)NumMethodPoolTableHits/NumMethodPoolTableLookups
6844f4a2713aSLionel Sambuc                   * 100.0));
6845f4a2713aSLionel Sambuc   }
6846f4a2713aSLionel Sambuc 
6847f4a2713aSLionel Sambuc   if (NumIdentifierLookupHits) {
6848f4a2713aSLionel Sambuc     std::fprintf(stderr,
6849f4a2713aSLionel Sambuc                  "  %u / %u identifier table lookups succeeded (%f%%)\n",
6850f4a2713aSLionel Sambuc                  NumIdentifierLookupHits, NumIdentifierLookups,
6851f4a2713aSLionel Sambuc                  (double)NumIdentifierLookupHits*100.0/NumIdentifierLookups);
6852f4a2713aSLionel Sambuc   }
6853f4a2713aSLionel Sambuc 
6854f4a2713aSLionel Sambuc   if (GlobalIndex) {
6855f4a2713aSLionel Sambuc     std::fprintf(stderr, "\n");
6856f4a2713aSLionel Sambuc     GlobalIndex->printStats();
6857f4a2713aSLionel Sambuc   }
6858f4a2713aSLionel Sambuc 
6859f4a2713aSLionel Sambuc   std::fprintf(stderr, "\n");
6860f4a2713aSLionel Sambuc   dump();
6861f4a2713aSLionel Sambuc   std::fprintf(stderr, "\n");
6862f4a2713aSLionel Sambuc }
6863f4a2713aSLionel Sambuc 
6864f4a2713aSLionel Sambuc template<typename Key, typename ModuleFile, unsigned InitialCapacity>
6865f4a2713aSLionel Sambuc static void
dumpModuleIDMap(StringRef Name,const ContinuousRangeMap<Key,ModuleFile *,InitialCapacity> & Map)6866f4a2713aSLionel Sambuc dumpModuleIDMap(StringRef Name,
6867f4a2713aSLionel Sambuc                 const ContinuousRangeMap<Key, ModuleFile *,
6868f4a2713aSLionel Sambuc                                          InitialCapacity> &Map) {
6869f4a2713aSLionel Sambuc   if (Map.begin() == Map.end())
6870f4a2713aSLionel Sambuc     return;
6871f4a2713aSLionel Sambuc 
6872f4a2713aSLionel Sambuc   typedef ContinuousRangeMap<Key, ModuleFile *, InitialCapacity> MapType;
6873f4a2713aSLionel Sambuc   llvm::errs() << Name << ":\n";
6874f4a2713aSLionel Sambuc   for (typename MapType::const_iterator I = Map.begin(), IEnd = Map.end();
6875f4a2713aSLionel Sambuc        I != IEnd; ++I) {
6876f4a2713aSLionel Sambuc     llvm::errs() << "  " << I->first << " -> " << I->second->FileName
6877f4a2713aSLionel Sambuc       << "\n";
6878f4a2713aSLionel Sambuc   }
6879f4a2713aSLionel Sambuc }
6880f4a2713aSLionel Sambuc 
dump()6881f4a2713aSLionel Sambuc void ASTReader::dump() {
6882f4a2713aSLionel Sambuc   llvm::errs() << "*** PCH/ModuleFile Remappings:\n";
6883f4a2713aSLionel Sambuc   dumpModuleIDMap("Global bit offset map", GlobalBitOffsetsMap);
6884f4a2713aSLionel Sambuc   dumpModuleIDMap("Global source location entry map", GlobalSLocEntryMap);
6885f4a2713aSLionel Sambuc   dumpModuleIDMap("Global type map", GlobalTypeMap);
6886f4a2713aSLionel Sambuc   dumpModuleIDMap("Global declaration map", GlobalDeclMap);
6887f4a2713aSLionel Sambuc   dumpModuleIDMap("Global identifier map", GlobalIdentifierMap);
6888f4a2713aSLionel Sambuc   dumpModuleIDMap("Global macro map", GlobalMacroMap);
6889f4a2713aSLionel Sambuc   dumpModuleIDMap("Global submodule map", GlobalSubmoduleMap);
6890f4a2713aSLionel Sambuc   dumpModuleIDMap("Global selector map", GlobalSelectorMap);
6891f4a2713aSLionel Sambuc   dumpModuleIDMap("Global preprocessed entity map",
6892f4a2713aSLionel Sambuc                   GlobalPreprocessedEntityMap);
6893f4a2713aSLionel Sambuc 
6894f4a2713aSLionel Sambuc   llvm::errs() << "\n*** PCH/Modules Loaded:";
6895f4a2713aSLionel Sambuc   for (ModuleManager::ModuleConstIterator M = ModuleMgr.begin(),
6896f4a2713aSLionel Sambuc                                        MEnd = ModuleMgr.end();
6897f4a2713aSLionel Sambuc        M != MEnd; ++M)
6898f4a2713aSLionel Sambuc     (*M)->dump();
6899f4a2713aSLionel Sambuc }
6900f4a2713aSLionel Sambuc 
6901f4a2713aSLionel Sambuc /// Return the amount of memory used by memory buffers, breaking down
6902f4a2713aSLionel Sambuc /// by heap-backed versus mmap'ed memory.
getMemoryBufferSizes(MemoryBufferSizes & sizes) const6903f4a2713aSLionel Sambuc void ASTReader::getMemoryBufferSizes(MemoryBufferSizes &sizes) const {
6904f4a2713aSLionel Sambuc   for (ModuleConstIterator I = ModuleMgr.begin(),
6905f4a2713aSLionel Sambuc       E = ModuleMgr.end(); I != E; ++I) {
6906f4a2713aSLionel Sambuc     if (llvm::MemoryBuffer *buf = (*I)->Buffer.get()) {
6907f4a2713aSLionel Sambuc       size_t bytes = buf->getBufferSize();
6908f4a2713aSLionel Sambuc       switch (buf->getBufferKind()) {
6909f4a2713aSLionel Sambuc         case llvm::MemoryBuffer::MemoryBuffer_Malloc:
6910f4a2713aSLionel Sambuc           sizes.malloc_bytes += bytes;
6911f4a2713aSLionel Sambuc           break;
6912f4a2713aSLionel Sambuc         case llvm::MemoryBuffer::MemoryBuffer_MMap:
6913f4a2713aSLionel Sambuc           sizes.mmap_bytes += bytes;
6914f4a2713aSLionel Sambuc           break;
6915f4a2713aSLionel Sambuc       }
6916f4a2713aSLionel Sambuc     }
6917f4a2713aSLionel Sambuc   }
6918f4a2713aSLionel Sambuc }
6919f4a2713aSLionel Sambuc 
InitializeSema(Sema & S)6920f4a2713aSLionel Sambuc void ASTReader::InitializeSema(Sema &S) {
6921f4a2713aSLionel Sambuc   SemaObj = &S;
6922f4a2713aSLionel Sambuc   S.addExternalSource(this);
6923f4a2713aSLionel Sambuc 
6924f4a2713aSLionel Sambuc   // Makes sure any declarations that were deserialized "too early"
6925f4a2713aSLionel Sambuc   // still get added to the identifier's declaration chains.
6926*0a6a1f1dSLionel Sambuc   for (uint64_t ID : PreloadedDeclIDs) {
6927*0a6a1f1dSLionel Sambuc     NamedDecl *D = cast<NamedDecl>(GetDecl(ID));
6928*0a6a1f1dSLionel Sambuc     pushExternalDeclIntoScope(D, D->getDeclName());
6929f4a2713aSLionel Sambuc   }
6930*0a6a1f1dSLionel Sambuc   PreloadedDeclIDs.clear();
6931f4a2713aSLionel Sambuc 
6932f4a2713aSLionel Sambuc   // FIXME: What happens if these are changed by a module import?
6933f4a2713aSLionel Sambuc   if (!FPPragmaOptions.empty()) {
6934f4a2713aSLionel Sambuc     assert(FPPragmaOptions.size() == 1 && "Wrong number of FP_PRAGMA_OPTIONS");
6935f4a2713aSLionel Sambuc     SemaObj->FPFeatures.fp_contract = FPPragmaOptions[0];
6936f4a2713aSLionel Sambuc   }
6937f4a2713aSLionel Sambuc 
6938f4a2713aSLionel Sambuc   // FIXME: What happens if these are changed by a module import?
6939f4a2713aSLionel Sambuc   if (!OpenCLExtensions.empty()) {
6940f4a2713aSLionel Sambuc     unsigned I = 0;
6941f4a2713aSLionel Sambuc #define OPENCLEXT(nm)  SemaObj->OpenCLFeatures.nm = OpenCLExtensions[I++];
6942f4a2713aSLionel Sambuc #include "clang/Basic/OpenCLExtensions.def"
6943f4a2713aSLionel Sambuc 
6944f4a2713aSLionel Sambuc     assert(OpenCLExtensions.size() == I && "Wrong number of OPENCL_EXTENSIONS");
6945f4a2713aSLionel Sambuc   }
6946f4a2713aSLionel Sambuc 
6947f4a2713aSLionel Sambuc   UpdateSema();
6948f4a2713aSLionel Sambuc }
6949f4a2713aSLionel Sambuc 
UpdateSema()6950f4a2713aSLionel Sambuc void ASTReader::UpdateSema() {
6951f4a2713aSLionel Sambuc   assert(SemaObj && "no Sema to update");
6952f4a2713aSLionel Sambuc 
6953f4a2713aSLionel Sambuc   // Load the offsets of the declarations that Sema references.
6954f4a2713aSLionel Sambuc   // They will be lazily deserialized when needed.
6955f4a2713aSLionel Sambuc   if (!SemaDeclRefs.empty()) {
6956f4a2713aSLionel Sambuc     assert(SemaDeclRefs.size() % 2 == 0);
6957f4a2713aSLionel Sambuc     for (unsigned I = 0; I != SemaDeclRefs.size(); I += 2) {
6958f4a2713aSLionel Sambuc       if (!SemaObj->StdNamespace)
6959f4a2713aSLionel Sambuc         SemaObj->StdNamespace = SemaDeclRefs[I];
6960f4a2713aSLionel Sambuc       if (!SemaObj->StdBadAlloc)
6961f4a2713aSLionel Sambuc         SemaObj->StdBadAlloc = SemaDeclRefs[I+1];
6962f4a2713aSLionel Sambuc     }
6963f4a2713aSLionel Sambuc     SemaDeclRefs.clear();
6964f4a2713aSLionel Sambuc   }
6965*0a6a1f1dSLionel Sambuc 
6966*0a6a1f1dSLionel Sambuc   // Update the state of 'pragma clang optimize'. Use the same API as if we had
6967*0a6a1f1dSLionel Sambuc   // encountered the pragma in the source.
6968*0a6a1f1dSLionel Sambuc   if(OptimizeOffPragmaLocation.isValid())
6969*0a6a1f1dSLionel Sambuc     SemaObj->ActOnPragmaOptimize(/* IsOn = */ false, OptimizeOffPragmaLocation);
6970f4a2713aSLionel Sambuc }
6971f4a2713aSLionel Sambuc 
get(const char * NameStart,const char * NameEnd)6972f4a2713aSLionel Sambuc IdentifierInfo* ASTReader::get(const char *NameStart, const char *NameEnd) {
6973f4a2713aSLionel Sambuc   // Note that we are loading an identifier.
6974f4a2713aSLionel Sambuc   Deserializing AnIdentifier(this);
6975f4a2713aSLionel Sambuc   StringRef Name(NameStart, NameEnd - NameStart);
6976f4a2713aSLionel Sambuc 
6977f4a2713aSLionel Sambuc   // If there is a global index, look there first to determine which modules
6978f4a2713aSLionel Sambuc   // provably do not have any results for this identifier.
6979f4a2713aSLionel Sambuc   GlobalModuleIndex::HitSet Hits;
6980*0a6a1f1dSLionel Sambuc   GlobalModuleIndex::HitSet *HitsPtr = nullptr;
6981f4a2713aSLionel Sambuc   if (!loadGlobalIndex()) {
6982f4a2713aSLionel Sambuc     if (GlobalIndex->lookupIdentifier(Name, Hits)) {
6983f4a2713aSLionel Sambuc       HitsPtr = &Hits;
6984f4a2713aSLionel Sambuc     }
6985f4a2713aSLionel Sambuc   }
6986f4a2713aSLionel Sambuc   IdentifierLookupVisitor Visitor(Name, /*PriorGeneration=*/0,
6987f4a2713aSLionel Sambuc                                   NumIdentifierLookups,
6988f4a2713aSLionel Sambuc                                   NumIdentifierLookupHits);
6989f4a2713aSLionel Sambuc   ModuleMgr.visit(IdentifierLookupVisitor::visit, &Visitor, HitsPtr);
6990f4a2713aSLionel Sambuc   IdentifierInfo *II = Visitor.getIdentifierInfo();
6991f4a2713aSLionel Sambuc   markIdentifierUpToDate(II);
6992f4a2713aSLionel Sambuc   return II;
6993f4a2713aSLionel Sambuc }
6994f4a2713aSLionel Sambuc 
6995f4a2713aSLionel Sambuc namespace clang {
6996f4a2713aSLionel Sambuc   /// \brief An identifier-lookup iterator that enumerates all of the
6997f4a2713aSLionel Sambuc   /// identifiers stored within a set of AST files.
6998f4a2713aSLionel Sambuc   class ASTIdentifierIterator : public IdentifierIterator {
6999f4a2713aSLionel Sambuc     /// \brief The AST reader whose identifiers are being enumerated.
7000f4a2713aSLionel Sambuc     const ASTReader &Reader;
7001f4a2713aSLionel Sambuc 
7002f4a2713aSLionel Sambuc     /// \brief The current index into the chain of AST files stored in
7003f4a2713aSLionel Sambuc     /// the AST reader.
7004f4a2713aSLionel Sambuc     unsigned Index;
7005f4a2713aSLionel Sambuc 
7006f4a2713aSLionel Sambuc     /// \brief The current position within the identifier lookup table
7007f4a2713aSLionel Sambuc     /// of the current AST file.
7008f4a2713aSLionel Sambuc     ASTIdentifierLookupTable::key_iterator Current;
7009f4a2713aSLionel Sambuc 
7010f4a2713aSLionel Sambuc     /// \brief The end position within the identifier lookup table of
7011f4a2713aSLionel Sambuc     /// the current AST file.
7012f4a2713aSLionel Sambuc     ASTIdentifierLookupTable::key_iterator End;
7013f4a2713aSLionel Sambuc 
7014f4a2713aSLionel Sambuc   public:
7015f4a2713aSLionel Sambuc     explicit ASTIdentifierIterator(const ASTReader &Reader);
7016f4a2713aSLionel Sambuc 
7017*0a6a1f1dSLionel Sambuc     StringRef Next() override;
7018f4a2713aSLionel Sambuc   };
7019f4a2713aSLionel Sambuc }
7020f4a2713aSLionel Sambuc 
ASTIdentifierIterator(const ASTReader & Reader)7021f4a2713aSLionel Sambuc ASTIdentifierIterator::ASTIdentifierIterator(const ASTReader &Reader)
7022f4a2713aSLionel Sambuc   : Reader(Reader), Index(Reader.ModuleMgr.size() - 1) {
7023f4a2713aSLionel Sambuc   ASTIdentifierLookupTable *IdTable
7024f4a2713aSLionel Sambuc     = (ASTIdentifierLookupTable *)Reader.ModuleMgr[Index].IdentifierLookupTable;
7025f4a2713aSLionel Sambuc   Current = IdTable->key_begin();
7026f4a2713aSLionel Sambuc   End = IdTable->key_end();
7027f4a2713aSLionel Sambuc }
7028f4a2713aSLionel Sambuc 
Next()7029f4a2713aSLionel Sambuc StringRef ASTIdentifierIterator::Next() {
7030f4a2713aSLionel Sambuc   while (Current == End) {
7031f4a2713aSLionel Sambuc     // If we have exhausted all of our AST files, we're done.
7032f4a2713aSLionel Sambuc     if (Index == 0)
7033f4a2713aSLionel Sambuc       return StringRef();
7034f4a2713aSLionel Sambuc 
7035f4a2713aSLionel Sambuc     --Index;
7036f4a2713aSLionel Sambuc     ASTIdentifierLookupTable *IdTable
7037f4a2713aSLionel Sambuc       = (ASTIdentifierLookupTable *)Reader.ModuleMgr[Index].
7038f4a2713aSLionel Sambuc         IdentifierLookupTable;
7039f4a2713aSLionel Sambuc     Current = IdTable->key_begin();
7040f4a2713aSLionel Sambuc     End = IdTable->key_end();
7041f4a2713aSLionel Sambuc   }
7042f4a2713aSLionel Sambuc 
7043f4a2713aSLionel Sambuc   // We have any identifiers remaining in the current AST file; return
7044f4a2713aSLionel Sambuc   // the next one.
7045f4a2713aSLionel Sambuc   StringRef Result = *Current;
7046f4a2713aSLionel Sambuc   ++Current;
7047f4a2713aSLionel Sambuc   return Result;
7048f4a2713aSLionel Sambuc }
7049f4a2713aSLionel Sambuc 
getIdentifiers()7050f4a2713aSLionel Sambuc IdentifierIterator *ASTReader::getIdentifiers() {
7051f4a2713aSLionel Sambuc   if (!loadGlobalIndex())
7052f4a2713aSLionel Sambuc     return GlobalIndex->createIdentifierIterator();
7053f4a2713aSLionel Sambuc 
7054f4a2713aSLionel Sambuc   return new ASTIdentifierIterator(*this);
7055f4a2713aSLionel Sambuc }
7056f4a2713aSLionel Sambuc 
7057f4a2713aSLionel Sambuc namespace clang { namespace serialization {
7058f4a2713aSLionel Sambuc   class ReadMethodPoolVisitor {
7059f4a2713aSLionel Sambuc     ASTReader &Reader;
7060f4a2713aSLionel Sambuc     Selector Sel;
7061f4a2713aSLionel Sambuc     unsigned PriorGeneration;
7062f4a2713aSLionel Sambuc     unsigned InstanceBits;
7063f4a2713aSLionel Sambuc     unsigned FactoryBits;
7064*0a6a1f1dSLionel Sambuc     bool InstanceHasMoreThanOneDecl;
7065*0a6a1f1dSLionel Sambuc     bool FactoryHasMoreThanOneDecl;
7066f4a2713aSLionel Sambuc     SmallVector<ObjCMethodDecl *, 4> InstanceMethods;
7067f4a2713aSLionel Sambuc     SmallVector<ObjCMethodDecl *, 4> FactoryMethods;
7068f4a2713aSLionel Sambuc 
7069f4a2713aSLionel Sambuc   public:
ReadMethodPoolVisitor(ASTReader & Reader,Selector Sel,unsigned PriorGeneration)7070f4a2713aSLionel Sambuc     ReadMethodPoolVisitor(ASTReader &Reader, Selector Sel,
7071f4a2713aSLionel Sambuc                           unsigned PriorGeneration)
7072f4a2713aSLionel Sambuc         : Reader(Reader), Sel(Sel), PriorGeneration(PriorGeneration),
7073*0a6a1f1dSLionel Sambuc           InstanceBits(0), FactoryBits(0), InstanceHasMoreThanOneDecl(false),
7074*0a6a1f1dSLionel Sambuc           FactoryHasMoreThanOneDecl(false) {}
7075f4a2713aSLionel Sambuc 
visit(ModuleFile & M,void * UserData)7076f4a2713aSLionel Sambuc     static bool visit(ModuleFile &M, void *UserData) {
7077f4a2713aSLionel Sambuc       ReadMethodPoolVisitor *This
7078f4a2713aSLionel Sambuc         = static_cast<ReadMethodPoolVisitor *>(UserData);
7079f4a2713aSLionel Sambuc 
7080f4a2713aSLionel Sambuc       if (!M.SelectorLookupTable)
7081f4a2713aSLionel Sambuc         return false;
7082f4a2713aSLionel Sambuc 
7083f4a2713aSLionel Sambuc       // If we've already searched this module file, skip it now.
7084f4a2713aSLionel Sambuc       if (M.Generation <= This->PriorGeneration)
7085f4a2713aSLionel Sambuc         return true;
7086f4a2713aSLionel Sambuc 
7087f4a2713aSLionel Sambuc       ++This->Reader.NumMethodPoolTableLookups;
7088f4a2713aSLionel Sambuc       ASTSelectorLookupTable *PoolTable
7089f4a2713aSLionel Sambuc         = (ASTSelectorLookupTable*)M.SelectorLookupTable;
7090f4a2713aSLionel Sambuc       ASTSelectorLookupTable::iterator Pos = PoolTable->find(This->Sel);
7091f4a2713aSLionel Sambuc       if (Pos == PoolTable->end())
7092f4a2713aSLionel Sambuc         return false;
7093f4a2713aSLionel Sambuc 
7094f4a2713aSLionel Sambuc       ++This->Reader.NumMethodPoolTableHits;
7095f4a2713aSLionel Sambuc       ++This->Reader.NumSelectorsRead;
7096f4a2713aSLionel Sambuc       // FIXME: Not quite happy with the statistics here. We probably should
7097f4a2713aSLionel Sambuc       // disable this tracking when called via LoadSelector.
7098f4a2713aSLionel Sambuc       // Also, should entries without methods count as misses?
7099f4a2713aSLionel Sambuc       ++This->Reader.NumMethodPoolEntriesRead;
7100f4a2713aSLionel Sambuc       ASTSelectorLookupTrait::data_type Data = *Pos;
7101f4a2713aSLionel Sambuc       if (This->Reader.DeserializationListener)
7102f4a2713aSLionel Sambuc         This->Reader.DeserializationListener->SelectorRead(Data.ID,
7103f4a2713aSLionel Sambuc                                                            This->Sel);
7104f4a2713aSLionel Sambuc 
7105f4a2713aSLionel Sambuc       This->InstanceMethods.append(Data.Instance.begin(), Data.Instance.end());
7106f4a2713aSLionel Sambuc       This->FactoryMethods.append(Data.Factory.begin(), Data.Factory.end());
7107f4a2713aSLionel Sambuc       This->InstanceBits = Data.InstanceBits;
7108f4a2713aSLionel Sambuc       This->FactoryBits = Data.FactoryBits;
7109*0a6a1f1dSLionel Sambuc       This->InstanceHasMoreThanOneDecl = Data.InstanceHasMoreThanOneDecl;
7110*0a6a1f1dSLionel Sambuc       This->FactoryHasMoreThanOneDecl = Data.FactoryHasMoreThanOneDecl;
7111f4a2713aSLionel Sambuc       return true;
7112f4a2713aSLionel Sambuc     }
7113f4a2713aSLionel Sambuc 
7114f4a2713aSLionel Sambuc     /// \brief Retrieve the instance methods found by this visitor.
getInstanceMethods() const7115f4a2713aSLionel Sambuc     ArrayRef<ObjCMethodDecl *> getInstanceMethods() const {
7116f4a2713aSLionel Sambuc       return InstanceMethods;
7117f4a2713aSLionel Sambuc     }
7118f4a2713aSLionel Sambuc 
7119f4a2713aSLionel Sambuc     /// \brief Retrieve the instance methods found by this visitor.
getFactoryMethods() const7120f4a2713aSLionel Sambuc     ArrayRef<ObjCMethodDecl *> getFactoryMethods() const {
7121f4a2713aSLionel Sambuc       return FactoryMethods;
7122f4a2713aSLionel Sambuc     }
7123f4a2713aSLionel Sambuc 
getInstanceBits() const7124f4a2713aSLionel Sambuc     unsigned getInstanceBits() const { return InstanceBits; }
getFactoryBits() const7125f4a2713aSLionel Sambuc     unsigned getFactoryBits() const { return FactoryBits; }
instanceHasMoreThanOneDecl() const7126*0a6a1f1dSLionel Sambuc     bool instanceHasMoreThanOneDecl() const {
7127*0a6a1f1dSLionel Sambuc       return InstanceHasMoreThanOneDecl;
7128*0a6a1f1dSLionel Sambuc     }
factoryHasMoreThanOneDecl() const7129*0a6a1f1dSLionel Sambuc     bool factoryHasMoreThanOneDecl() const { return FactoryHasMoreThanOneDecl; }
7130f4a2713aSLionel Sambuc   };
7131f4a2713aSLionel Sambuc } } // end namespace clang::serialization
7132f4a2713aSLionel Sambuc 
7133f4a2713aSLionel Sambuc /// \brief Add the given set of methods to the method list.
addMethodsToPool(Sema & S,ArrayRef<ObjCMethodDecl * > Methods,ObjCMethodList & List)7134f4a2713aSLionel Sambuc static void addMethodsToPool(Sema &S, ArrayRef<ObjCMethodDecl *> Methods,
7135f4a2713aSLionel Sambuc                              ObjCMethodList &List) {
7136f4a2713aSLionel Sambuc   for (unsigned I = 0, N = Methods.size(); I != N; ++I) {
7137f4a2713aSLionel Sambuc     S.addMethodToGlobalList(&List, Methods[I]);
7138f4a2713aSLionel Sambuc   }
7139f4a2713aSLionel Sambuc }
7140f4a2713aSLionel Sambuc 
ReadMethodPool(Selector Sel)7141f4a2713aSLionel Sambuc void ASTReader::ReadMethodPool(Selector Sel) {
7142f4a2713aSLionel Sambuc   // Get the selector generation and update it to the current generation.
7143f4a2713aSLionel Sambuc   unsigned &Generation = SelectorGeneration[Sel];
7144f4a2713aSLionel Sambuc   unsigned PriorGeneration = Generation;
7145*0a6a1f1dSLionel Sambuc   Generation = getGeneration();
7146f4a2713aSLionel Sambuc 
7147f4a2713aSLionel Sambuc   // Search for methods defined with this selector.
7148f4a2713aSLionel Sambuc   ++NumMethodPoolLookups;
7149f4a2713aSLionel Sambuc   ReadMethodPoolVisitor Visitor(*this, Sel, PriorGeneration);
7150f4a2713aSLionel Sambuc   ModuleMgr.visit(&ReadMethodPoolVisitor::visit, &Visitor);
7151f4a2713aSLionel Sambuc 
7152f4a2713aSLionel Sambuc   if (Visitor.getInstanceMethods().empty() &&
7153f4a2713aSLionel Sambuc       Visitor.getFactoryMethods().empty())
7154f4a2713aSLionel Sambuc     return;
7155f4a2713aSLionel Sambuc 
7156f4a2713aSLionel Sambuc   ++NumMethodPoolHits;
7157f4a2713aSLionel Sambuc 
7158f4a2713aSLionel Sambuc   if (!getSema())
7159f4a2713aSLionel Sambuc     return;
7160f4a2713aSLionel Sambuc 
7161f4a2713aSLionel Sambuc   Sema &S = *getSema();
7162f4a2713aSLionel Sambuc   Sema::GlobalMethodPool::iterator Pos
7163f4a2713aSLionel Sambuc     = S.MethodPool.insert(std::make_pair(Sel, Sema::GlobalMethods())).first;
7164f4a2713aSLionel Sambuc 
7165*0a6a1f1dSLionel Sambuc   Pos->second.first.setBits(Visitor.getInstanceBits());
7166*0a6a1f1dSLionel Sambuc   Pos->second.first.setHasMoreThanOneDecl(Visitor.instanceHasMoreThanOneDecl());
7167*0a6a1f1dSLionel Sambuc   Pos->second.second.setBits(Visitor.getFactoryBits());
7168*0a6a1f1dSLionel Sambuc   Pos->second.second.setHasMoreThanOneDecl(Visitor.factoryHasMoreThanOneDecl());
7169*0a6a1f1dSLionel Sambuc 
7170*0a6a1f1dSLionel Sambuc   // Add methods to the global pool *after* setting hasMoreThanOneDecl, since
7171*0a6a1f1dSLionel Sambuc   // when building a module we keep every method individually and may need to
7172*0a6a1f1dSLionel Sambuc   // update hasMoreThanOneDecl as we add the methods.
7173f4a2713aSLionel Sambuc   addMethodsToPool(S, Visitor.getInstanceMethods(), Pos->second.first);
7174f4a2713aSLionel Sambuc   addMethodsToPool(S, Visitor.getFactoryMethods(), Pos->second.second);
7175f4a2713aSLionel Sambuc }
7176f4a2713aSLionel Sambuc 
ReadKnownNamespaces(SmallVectorImpl<NamespaceDecl * > & Namespaces)7177f4a2713aSLionel Sambuc void ASTReader::ReadKnownNamespaces(
7178f4a2713aSLionel Sambuc                           SmallVectorImpl<NamespaceDecl *> &Namespaces) {
7179f4a2713aSLionel Sambuc   Namespaces.clear();
7180f4a2713aSLionel Sambuc 
7181f4a2713aSLionel Sambuc   for (unsigned I = 0, N = KnownNamespaces.size(); I != N; ++I) {
7182f4a2713aSLionel Sambuc     if (NamespaceDecl *Namespace
7183f4a2713aSLionel Sambuc                 = dyn_cast_or_null<NamespaceDecl>(GetDecl(KnownNamespaces[I])))
7184f4a2713aSLionel Sambuc       Namespaces.push_back(Namespace);
7185f4a2713aSLionel Sambuc   }
7186f4a2713aSLionel Sambuc }
7187f4a2713aSLionel Sambuc 
ReadUndefinedButUsed(llvm::DenseMap<NamedDecl *,SourceLocation> & Undefined)7188f4a2713aSLionel Sambuc void ASTReader::ReadUndefinedButUsed(
7189f4a2713aSLionel Sambuc                         llvm::DenseMap<NamedDecl*, SourceLocation> &Undefined) {
7190f4a2713aSLionel Sambuc   for (unsigned Idx = 0, N = UndefinedButUsed.size(); Idx != N;) {
7191f4a2713aSLionel Sambuc     NamedDecl *D = cast<NamedDecl>(GetDecl(UndefinedButUsed[Idx++]));
7192f4a2713aSLionel Sambuc     SourceLocation Loc =
7193f4a2713aSLionel Sambuc         SourceLocation::getFromRawEncoding(UndefinedButUsed[Idx++]);
7194f4a2713aSLionel Sambuc     Undefined.insert(std::make_pair(D, Loc));
7195f4a2713aSLionel Sambuc   }
7196f4a2713aSLionel Sambuc }
7197f4a2713aSLionel Sambuc 
ReadTentativeDefinitions(SmallVectorImpl<VarDecl * > & TentativeDefs)7198f4a2713aSLionel Sambuc void ASTReader::ReadTentativeDefinitions(
7199f4a2713aSLionel Sambuc                   SmallVectorImpl<VarDecl *> &TentativeDefs) {
7200f4a2713aSLionel Sambuc   for (unsigned I = 0, N = TentativeDefinitions.size(); I != N; ++I) {
7201f4a2713aSLionel Sambuc     VarDecl *Var = dyn_cast_or_null<VarDecl>(GetDecl(TentativeDefinitions[I]));
7202f4a2713aSLionel Sambuc     if (Var)
7203f4a2713aSLionel Sambuc       TentativeDefs.push_back(Var);
7204f4a2713aSLionel Sambuc   }
7205f4a2713aSLionel Sambuc   TentativeDefinitions.clear();
7206f4a2713aSLionel Sambuc }
7207f4a2713aSLionel Sambuc 
ReadUnusedFileScopedDecls(SmallVectorImpl<const DeclaratorDecl * > & Decls)7208f4a2713aSLionel Sambuc void ASTReader::ReadUnusedFileScopedDecls(
7209f4a2713aSLionel Sambuc                                SmallVectorImpl<const DeclaratorDecl *> &Decls) {
7210f4a2713aSLionel Sambuc   for (unsigned I = 0, N = UnusedFileScopedDecls.size(); I != N; ++I) {
7211f4a2713aSLionel Sambuc     DeclaratorDecl *D
7212f4a2713aSLionel Sambuc       = dyn_cast_or_null<DeclaratorDecl>(GetDecl(UnusedFileScopedDecls[I]));
7213f4a2713aSLionel Sambuc     if (D)
7214f4a2713aSLionel Sambuc       Decls.push_back(D);
7215f4a2713aSLionel Sambuc   }
7216f4a2713aSLionel Sambuc   UnusedFileScopedDecls.clear();
7217f4a2713aSLionel Sambuc }
7218f4a2713aSLionel Sambuc 
ReadDelegatingConstructors(SmallVectorImpl<CXXConstructorDecl * > & Decls)7219f4a2713aSLionel Sambuc void ASTReader::ReadDelegatingConstructors(
7220f4a2713aSLionel Sambuc                                  SmallVectorImpl<CXXConstructorDecl *> &Decls) {
7221f4a2713aSLionel Sambuc   for (unsigned I = 0, N = DelegatingCtorDecls.size(); I != N; ++I) {
7222f4a2713aSLionel Sambuc     CXXConstructorDecl *D
7223f4a2713aSLionel Sambuc       = dyn_cast_or_null<CXXConstructorDecl>(GetDecl(DelegatingCtorDecls[I]));
7224f4a2713aSLionel Sambuc     if (D)
7225f4a2713aSLionel Sambuc       Decls.push_back(D);
7226f4a2713aSLionel Sambuc   }
7227f4a2713aSLionel Sambuc   DelegatingCtorDecls.clear();
7228f4a2713aSLionel Sambuc }
7229f4a2713aSLionel Sambuc 
ReadExtVectorDecls(SmallVectorImpl<TypedefNameDecl * > & Decls)7230f4a2713aSLionel Sambuc void ASTReader::ReadExtVectorDecls(SmallVectorImpl<TypedefNameDecl *> &Decls) {
7231f4a2713aSLionel Sambuc   for (unsigned I = 0, N = ExtVectorDecls.size(); I != N; ++I) {
7232f4a2713aSLionel Sambuc     TypedefNameDecl *D
7233f4a2713aSLionel Sambuc       = dyn_cast_or_null<TypedefNameDecl>(GetDecl(ExtVectorDecls[I]));
7234f4a2713aSLionel Sambuc     if (D)
7235f4a2713aSLionel Sambuc       Decls.push_back(D);
7236f4a2713aSLionel Sambuc   }
7237f4a2713aSLionel Sambuc   ExtVectorDecls.clear();
7238f4a2713aSLionel Sambuc }
7239f4a2713aSLionel Sambuc 
ReadDynamicClasses(SmallVectorImpl<CXXRecordDecl * > & Decls)7240f4a2713aSLionel Sambuc void ASTReader::ReadDynamicClasses(SmallVectorImpl<CXXRecordDecl *> &Decls) {
7241f4a2713aSLionel Sambuc   for (unsigned I = 0, N = DynamicClasses.size(); I != N; ++I) {
7242f4a2713aSLionel Sambuc     CXXRecordDecl *D
7243f4a2713aSLionel Sambuc       = dyn_cast_or_null<CXXRecordDecl>(GetDecl(DynamicClasses[I]));
7244f4a2713aSLionel Sambuc     if (D)
7245f4a2713aSLionel Sambuc       Decls.push_back(D);
7246f4a2713aSLionel Sambuc   }
7247f4a2713aSLionel Sambuc   DynamicClasses.clear();
7248f4a2713aSLionel Sambuc }
7249f4a2713aSLionel Sambuc 
ReadUnusedLocalTypedefNameCandidates(llvm::SmallSetVector<const TypedefNameDecl *,4> & Decls)7250*0a6a1f1dSLionel Sambuc void ASTReader::ReadUnusedLocalTypedefNameCandidates(
7251*0a6a1f1dSLionel Sambuc     llvm::SmallSetVector<const TypedefNameDecl *, 4> &Decls) {
7252*0a6a1f1dSLionel Sambuc   for (unsigned I = 0, N = UnusedLocalTypedefNameCandidates.size(); I != N;
7253*0a6a1f1dSLionel Sambuc        ++I) {
7254*0a6a1f1dSLionel Sambuc     TypedefNameDecl *D = dyn_cast_or_null<TypedefNameDecl>(
7255*0a6a1f1dSLionel Sambuc         GetDecl(UnusedLocalTypedefNameCandidates[I]));
7256*0a6a1f1dSLionel Sambuc     if (D)
7257*0a6a1f1dSLionel Sambuc       Decls.insert(D);
7258*0a6a1f1dSLionel Sambuc   }
7259*0a6a1f1dSLionel Sambuc   UnusedLocalTypedefNameCandidates.clear();
7260*0a6a1f1dSLionel Sambuc }
7261*0a6a1f1dSLionel Sambuc 
7262f4a2713aSLionel Sambuc void
ReadLocallyScopedExternCDecls(SmallVectorImpl<NamedDecl * > & Decls)7263f4a2713aSLionel Sambuc ASTReader::ReadLocallyScopedExternCDecls(SmallVectorImpl<NamedDecl *> &Decls) {
7264f4a2713aSLionel Sambuc   for (unsigned I = 0, N = LocallyScopedExternCDecls.size(); I != N; ++I) {
7265f4a2713aSLionel Sambuc     NamedDecl *D
7266f4a2713aSLionel Sambuc       = dyn_cast_or_null<NamedDecl>(GetDecl(LocallyScopedExternCDecls[I]));
7267f4a2713aSLionel Sambuc     if (D)
7268f4a2713aSLionel Sambuc       Decls.push_back(D);
7269f4a2713aSLionel Sambuc   }
7270f4a2713aSLionel Sambuc   LocallyScopedExternCDecls.clear();
7271f4a2713aSLionel Sambuc }
7272f4a2713aSLionel Sambuc 
ReadReferencedSelectors(SmallVectorImpl<std::pair<Selector,SourceLocation>> & Sels)7273f4a2713aSLionel Sambuc void ASTReader::ReadReferencedSelectors(
7274f4a2713aSLionel Sambuc        SmallVectorImpl<std::pair<Selector, SourceLocation> > &Sels) {
7275f4a2713aSLionel Sambuc   if (ReferencedSelectorsData.empty())
7276f4a2713aSLionel Sambuc     return;
7277f4a2713aSLionel Sambuc 
7278f4a2713aSLionel Sambuc   // If there are @selector references added them to its pool. This is for
7279f4a2713aSLionel Sambuc   // implementation of -Wselector.
7280f4a2713aSLionel Sambuc   unsigned int DataSize = ReferencedSelectorsData.size()-1;
7281f4a2713aSLionel Sambuc   unsigned I = 0;
7282f4a2713aSLionel Sambuc   while (I < DataSize) {
7283f4a2713aSLionel Sambuc     Selector Sel = DecodeSelector(ReferencedSelectorsData[I++]);
7284f4a2713aSLionel Sambuc     SourceLocation SelLoc
7285f4a2713aSLionel Sambuc       = SourceLocation::getFromRawEncoding(ReferencedSelectorsData[I++]);
7286f4a2713aSLionel Sambuc     Sels.push_back(std::make_pair(Sel, SelLoc));
7287f4a2713aSLionel Sambuc   }
7288f4a2713aSLionel Sambuc   ReferencedSelectorsData.clear();
7289f4a2713aSLionel Sambuc }
7290f4a2713aSLionel Sambuc 
ReadWeakUndeclaredIdentifiers(SmallVectorImpl<std::pair<IdentifierInfo *,WeakInfo>> & WeakIDs)7291f4a2713aSLionel Sambuc void ASTReader::ReadWeakUndeclaredIdentifiers(
7292f4a2713aSLionel Sambuc        SmallVectorImpl<std::pair<IdentifierInfo *, WeakInfo> > &WeakIDs) {
7293f4a2713aSLionel Sambuc   if (WeakUndeclaredIdentifiers.empty())
7294f4a2713aSLionel Sambuc     return;
7295f4a2713aSLionel Sambuc 
7296f4a2713aSLionel Sambuc   for (unsigned I = 0, N = WeakUndeclaredIdentifiers.size(); I < N; /*none*/) {
7297f4a2713aSLionel Sambuc     IdentifierInfo *WeakId
7298f4a2713aSLionel Sambuc       = DecodeIdentifierInfo(WeakUndeclaredIdentifiers[I++]);
7299f4a2713aSLionel Sambuc     IdentifierInfo *AliasId
7300f4a2713aSLionel Sambuc       = DecodeIdentifierInfo(WeakUndeclaredIdentifiers[I++]);
7301f4a2713aSLionel Sambuc     SourceLocation Loc
7302f4a2713aSLionel Sambuc       = SourceLocation::getFromRawEncoding(WeakUndeclaredIdentifiers[I++]);
7303f4a2713aSLionel Sambuc     bool Used = WeakUndeclaredIdentifiers[I++];
7304f4a2713aSLionel Sambuc     WeakInfo WI(AliasId, Loc);
7305f4a2713aSLionel Sambuc     WI.setUsed(Used);
7306f4a2713aSLionel Sambuc     WeakIDs.push_back(std::make_pair(WeakId, WI));
7307f4a2713aSLionel Sambuc   }
7308f4a2713aSLionel Sambuc   WeakUndeclaredIdentifiers.clear();
7309f4a2713aSLionel Sambuc }
7310f4a2713aSLionel Sambuc 
ReadUsedVTables(SmallVectorImpl<ExternalVTableUse> & VTables)7311f4a2713aSLionel Sambuc void ASTReader::ReadUsedVTables(SmallVectorImpl<ExternalVTableUse> &VTables) {
7312f4a2713aSLionel Sambuc   for (unsigned Idx = 0, N = VTableUses.size(); Idx < N; /* In loop */) {
7313f4a2713aSLionel Sambuc     ExternalVTableUse VT;
7314f4a2713aSLionel Sambuc     VT.Record = dyn_cast_or_null<CXXRecordDecl>(GetDecl(VTableUses[Idx++]));
7315f4a2713aSLionel Sambuc     VT.Location = SourceLocation::getFromRawEncoding(VTableUses[Idx++]);
7316f4a2713aSLionel Sambuc     VT.DefinitionRequired = VTableUses[Idx++];
7317f4a2713aSLionel Sambuc     VTables.push_back(VT);
7318f4a2713aSLionel Sambuc   }
7319f4a2713aSLionel Sambuc 
7320f4a2713aSLionel Sambuc   VTableUses.clear();
7321f4a2713aSLionel Sambuc }
7322f4a2713aSLionel Sambuc 
ReadPendingInstantiations(SmallVectorImpl<std::pair<ValueDecl *,SourceLocation>> & Pending)7323f4a2713aSLionel Sambuc void ASTReader::ReadPendingInstantiations(
7324f4a2713aSLionel Sambuc        SmallVectorImpl<std::pair<ValueDecl *, SourceLocation> > &Pending) {
7325f4a2713aSLionel Sambuc   for (unsigned Idx = 0, N = PendingInstantiations.size(); Idx < N;) {
7326f4a2713aSLionel Sambuc     ValueDecl *D = cast<ValueDecl>(GetDecl(PendingInstantiations[Idx++]));
7327f4a2713aSLionel Sambuc     SourceLocation Loc
7328f4a2713aSLionel Sambuc       = SourceLocation::getFromRawEncoding(PendingInstantiations[Idx++]);
7329f4a2713aSLionel Sambuc 
7330f4a2713aSLionel Sambuc     Pending.push_back(std::make_pair(D, Loc));
7331f4a2713aSLionel Sambuc   }
7332f4a2713aSLionel Sambuc   PendingInstantiations.clear();
7333f4a2713aSLionel Sambuc }
7334f4a2713aSLionel Sambuc 
ReadLateParsedTemplates(llvm::DenseMap<const FunctionDecl *,LateParsedTemplate * > & LPTMap)7335f4a2713aSLionel Sambuc void ASTReader::ReadLateParsedTemplates(
7336f4a2713aSLionel Sambuc     llvm::DenseMap<const FunctionDecl *, LateParsedTemplate *> &LPTMap) {
7337f4a2713aSLionel Sambuc   for (unsigned Idx = 0, N = LateParsedTemplates.size(); Idx < N;
7338f4a2713aSLionel Sambuc        /* In loop */) {
7339f4a2713aSLionel Sambuc     FunctionDecl *FD = cast<FunctionDecl>(GetDecl(LateParsedTemplates[Idx++]));
7340f4a2713aSLionel Sambuc 
7341f4a2713aSLionel Sambuc     LateParsedTemplate *LT = new LateParsedTemplate;
7342f4a2713aSLionel Sambuc     LT->D = GetDecl(LateParsedTemplates[Idx++]);
7343f4a2713aSLionel Sambuc 
7344f4a2713aSLionel Sambuc     ModuleFile *F = getOwningModuleFile(LT->D);
7345f4a2713aSLionel Sambuc     assert(F && "No module");
7346f4a2713aSLionel Sambuc 
7347f4a2713aSLionel Sambuc     unsigned TokN = LateParsedTemplates[Idx++];
7348f4a2713aSLionel Sambuc     LT->Toks.reserve(TokN);
7349f4a2713aSLionel Sambuc     for (unsigned T = 0; T < TokN; ++T)
7350f4a2713aSLionel Sambuc       LT->Toks.push_back(ReadToken(*F, LateParsedTemplates, Idx));
7351f4a2713aSLionel Sambuc 
7352f4a2713aSLionel Sambuc     LPTMap[FD] = LT;
7353f4a2713aSLionel Sambuc   }
7354f4a2713aSLionel Sambuc 
7355f4a2713aSLionel Sambuc   LateParsedTemplates.clear();
7356f4a2713aSLionel Sambuc }
7357f4a2713aSLionel Sambuc 
LoadSelector(Selector Sel)7358f4a2713aSLionel Sambuc void ASTReader::LoadSelector(Selector Sel) {
7359f4a2713aSLionel Sambuc   // It would be complicated to avoid reading the methods anyway. So don't.
7360f4a2713aSLionel Sambuc   ReadMethodPool(Sel);
7361f4a2713aSLionel Sambuc }
7362f4a2713aSLionel Sambuc 
SetIdentifierInfo(IdentifierID ID,IdentifierInfo * II)7363f4a2713aSLionel Sambuc void ASTReader::SetIdentifierInfo(IdentifierID ID, IdentifierInfo *II) {
7364f4a2713aSLionel Sambuc   assert(ID && "Non-zero identifier ID required");
7365f4a2713aSLionel Sambuc   assert(ID <= IdentifiersLoaded.size() && "identifier ID out of range");
7366f4a2713aSLionel Sambuc   IdentifiersLoaded[ID - 1] = II;
7367f4a2713aSLionel Sambuc   if (DeserializationListener)
7368f4a2713aSLionel Sambuc     DeserializationListener->IdentifierRead(ID, II);
7369f4a2713aSLionel Sambuc }
7370f4a2713aSLionel Sambuc 
7371f4a2713aSLionel Sambuc /// \brief Set the globally-visible declarations associated with the given
7372f4a2713aSLionel Sambuc /// identifier.
7373f4a2713aSLionel Sambuc ///
7374f4a2713aSLionel Sambuc /// If the AST reader is currently in a state where the given declaration IDs
7375f4a2713aSLionel Sambuc /// cannot safely be resolved, they are queued until it is safe to resolve
7376f4a2713aSLionel Sambuc /// them.
7377f4a2713aSLionel Sambuc ///
7378f4a2713aSLionel Sambuc /// \param II an IdentifierInfo that refers to one or more globally-visible
7379f4a2713aSLionel Sambuc /// declarations.
7380f4a2713aSLionel Sambuc ///
7381f4a2713aSLionel Sambuc /// \param DeclIDs the set of declaration IDs with the name @p II that are
7382f4a2713aSLionel Sambuc /// visible at global scope.
7383f4a2713aSLionel Sambuc ///
7384f4a2713aSLionel Sambuc /// \param Decls if non-null, this vector will be populated with the set of
7385f4a2713aSLionel Sambuc /// deserialized declarations. These declarations will not be pushed into
7386f4a2713aSLionel Sambuc /// scope.
7387f4a2713aSLionel Sambuc void
SetGloballyVisibleDecls(IdentifierInfo * II,const SmallVectorImpl<uint32_t> & DeclIDs,SmallVectorImpl<Decl * > * Decls)7388f4a2713aSLionel Sambuc ASTReader::SetGloballyVisibleDecls(IdentifierInfo *II,
7389f4a2713aSLionel Sambuc                               const SmallVectorImpl<uint32_t> &DeclIDs,
7390f4a2713aSLionel Sambuc                                    SmallVectorImpl<Decl *> *Decls) {
7391f4a2713aSLionel Sambuc   if (NumCurrentElementsDeserializing && !Decls) {
7392f4a2713aSLionel Sambuc     PendingIdentifierInfos[II].append(DeclIDs.begin(), DeclIDs.end());
7393f4a2713aSLionel Sambuc     return;
7394f4a2713aSLionel Sambuc   }
7395f4a2713aSLionel Sambuc 
7396f4a2713aSLionel Sambuc   for (unsigned I = 0, N = DeclIDs.size(); I != N; ++I) {
7397*0a6a1f1dSLionel Sambuc     if (!SemaObj) {
7398*0a6a1f1dSLionel Sambuc       // Queue this declaration so that it will be added to the
7399*0a6a1f1dSLionel Sambuc       // translation unit scope and identifier's declaration chain
7400*0a6a1f1dSLionel Sambuc       // once a Sema object is known.
7401*0a6a1f1dSLionel Sambuc       PreloadedDeclIDs.push_back(DeclIDs[I]);
7402*0a6a1f1dSLionel Sambuc       continue;
7403*0a6a1f1dSLionel Sambuc     }
7404*0a6a1f1dSLionel Sambuc 
7405f4a2713aSLionel Sambuc     NamedDecl *D = cast<NamedDecl>(GetDecl(DeclIDs[I]));
7406*0a6a1f1dSLionel Sambuc 
7407f4a2713aSLionel Sambuc     // If we're simply supposed to record the declarations, do so now.
7408f4a2713aSLionel Sambuc     if (Decls) {
7409f4a2713aSLionel Sambuc       Decls->push_back(D);
7410f4a2713aSLionel Sambuc       continue;
7411f4a2713aSLionel Sambuc     }
7412f4a2713aSLionel Sambuc 
7413f4a2713aSLionel Sambuc     // Introduce this declaration into the translation-unit scope
7414f4a2713aSLionel Sambuc     // and add it to the declaration chain for this identifier, so
7415f4a2713aSLionel Sambuc     // that (unqualified) name lookup will find it.
7416f4a2713aSLionel Sambuc     pushExternalDeclIntoScope(D, II);
7417f4a2713aSLionel Sambuc   }
7418f4a2713aSLionel Sambuc }
7419f4a2713aSLionel Sambuc 
DecodeIdentifierInfo(IdentifierID ID)7420f4a2713aSLionel Sambuc IdentifierInfo *ASTReader::DecodeIdentifierInfo(IdentifierID ID) {
7421f4a2713aSLionel Sambuc   if (ID == 0)
7422*0a6a1f1dSLionel Sambuc     return nullptr;
7423f4a2713aSLionel Sambuc 
7424f4a2713aSLionel Sambuc   if (IdentifiersLoaded.empty()) {
7425f4a2713aSLionel Sambuc     Error("no identifier table in AST file");
7426*0a6a1f1dSLionel Sambuc     return nullptr;
7427f4a2713aSLionel Sambuc   }
7428f4a2713aSLionel Sambuc 
7429f4a2713aSLionel Sambuc   ID -= 1;
7430f4a2713aSLionel Sambuc   if (!IdentifiersLoaded[ID]) {
7431f4a2713aSLionel Sambuc     GlobalIdentifierMapType::iterator I = GlobalIdentifierMap.find(ID + 1);
7432f4a2713aSLionel Sambuc     assert(I != GlobalIdentifierMap.end() && "Corrupted global identifier map");
7433f4a2713aSLionel Sambuc     ModuleFile *M = I->second;
7434f4a2713aSLionel Sambuc     unsigned Index = ID - M->BaseIdentifierID;
7435f4a2713aSLionel Sambuc     const char *Str = M->IdentifierTableData + M->IdentifierOffsets[Index];
7436f4a2713aSLionel Sambuc 
7437f4a2713aSLionel Sambuc     // All of the strings in the AST file are preceded by a 16-bit length.
7438f4a2713aSLionel Sambuc     // Extract that 16-bit length to avoid having to execute strlen().
7439f4a2713aSLionel Sambuc     // NOTE: 'StrLenPtr' is an 'unsigned char*' so that we load bytes as
7440f4a2713aSLionel Sambuc     //  unsigned integers.  This is important to avoid integer overflow when
7441f4a2713aSLionel Sambuc     //  we cast them to 'unsigned'.
7442f4a2713aSLionel Sambuc     const unsigned char *StrLenPtr = (const unsigned char*) Str - 2;
7443f4a2713aSLionel Sambuc     unsigned StrLen = (((unsigned) StrLenPtr[0])
7444f4a2713aSLionel Sambuc                        | (((unsigned) StrLenPtr[1]) << 8)) - 1;
7445f4a2713aSLionel Sambuc     IdentifiersLoaded[ID]
7446f4a2713aSLionel Sambuc       = &PP.getIdentifierTable().get(StringRef(Str, StrLen));
7447f4a2713aSLionel Sambuc     if (DeserializationListener)
7448f4a2713aSLionel Sambuc       DeserializationListener->IdentifierRead(ID + 1, IdentifiersLoaded[ID]);
7449f4a2713aSLionel Sambuc   }
7450f4a2713aSLionel Sambuc 
7451f4a2713aSLionel Sambuc   return IdentifiersLoaded[ID];
7452f4a2713aSLionel Sambuc }
7453f4a2713aSLionel Sambuc 
getLocalIdentifier(ModuleFile & M,unsigned LocalID)7454f4a2713aSLionel Sambuc IdentifierInfo *ASTReader::getLocalIdentifier(ModuleFile &M, unsigned LocalID) {
7455f4a2713aSLionel Sambuc   return DecodeIdentifierInfo(getGlobalIdentifierID(M, LocalID));
7456f4a2713aSLionel Sambuc }
7457f4a2713aSLionel Sambuc 
getGlobalIdentifierID(ModuleFile & M,unsigned LocalID)7458f4a2713aSLionel Sambuc IdentifierID ASTReader::getGlobalIdentifierID(ModuleFile &M, unsigned LocalID) {
7459f4a2713aSLionel Sambuc   if (LocalID < NUM_PREDEF_IDENT_IDS)
7460f4a2713aSLionel Sambuc     return LocalID;
7461f4a2713aSLionel Sambuc 
7462f4a2713aSLionel Sambuc   ContinuousRangeMap<uint32_t, int, 2>::iterator I
7463f4a2713aSLionel Sambuc     = M.IdentifierRemap.find(LocalID - NUM_PREDEF_IDENT_IDS);
7464f4a2713aSLionel Sambuc   assert(I != M.IdentifierRemap.end()
7465f4a2713aSLionel Sambuc          && "Invalid index into identifier index remap");
7466f4a2713aSLionel Sambuc 
7467f4a2713aSLionel Sambuc   return LocalID + I->second;
7468f4a2713aSLionel Sambuc }
7469f4a2713aSLionel Sambuc 
getMacro(MacroID ID)7470f4a2713aSLionel Sambuc MacroInfo *ASTReader::getMacro(MacroID ID) {
7471f4a2713aSLionel Sambuc   if (ID == 0)
7472*0a6a1f1dSLionel Sambuc     return nullptr;
7473f4a2713aSLionel Sambuc 
7474f4a2713aSLionel Sambuc   if (MacrosLoaded.empty()) {
7475f4a2713aSLionel Sambuc     Error("no macro table in AST file");
7476*0a6a1f1dSLionel Sambuc     return nullptr;
7477f4a2713aSLionel Sambuc   }
7478f4a2713aSLionel Sambuc 
7479f4a2713aSLionel Sambuc   ID -= NUM_PREDEF_MACRO_IDS;
7480f4a2713aSLionel Sambuc   if (!MacrosLoaded[ID]) {
7481f4a2713aSLionel Sambuc     GlobalMacroMapType::iterator I
7482f4a2713aSLionel Sambuc       = GlobalMacroMap.find(ID + NUM_PREDEF_MACRO_IDS);
7483f4a2713aSLionel Sambuc     assert(I != GlobalMacroMap.end() && "Corrupted global macro map");
7484f4a2713aSLionel Sambuc     ModuleFile *M = I->second;
7485f4a2713aSLionel Sambuc     unsigned Index = ID - M->BaseMacroID;
7486f4a2713aSLionel Sambuc     MacrosLoaded[ID] = ReadMacroRecord(*M, M->MacroOffsets[Index]);
7487f4a2713aSLionel Sambuc 
7488f4a2713aSLionel Sambuc     if (DeserializationListener)
7489f4a2713aSLionel Sambuc       DeserializationListener->MacroRead(ID + NUM_PREDEF_MACRO_IDS,
7490f4a2713aSLionel Sambuc                                          MacrosLoaded[ID]);
7491f4a2713aSLionel Sambuc   }
7492f4a2713aSLionel Sambuc 
7493f4a2713aSLionel Sambuc   return MacrosLoaded[ID];
7494f4a2713aSLionel Sambuc }
7495f4a2713aSLionel Sambuc 
getGlobalMacroID(ModuleFile & M,unsigned LocalID)7496f4a2713aSLionel Sambuc MacroID ASTReader::getGlobalMacroID(ModuleFile &M, unsigned LocalID) {
7497f4a2713aSLionel Sambuc   if (LocalID < NUM_PREDEF_MACRO_IDS)
7498f4a2713aSLionel Sambuc     return LocalID;
7499f4a2713aSLionel Sambuc 
7500f4a2713aSLionel Sambuc   ContinuousRangeMap<uint32_t, int, 2>::iterator I
7501f4a2713aSLionel Sambuc     = M.MacroRemap.find(LocalID - NUM_PREDEF_MACRO_IDS);
7502f4a2713aSLionel Sambuc   assert(I != M.MacroRemap.end() && "Invalid index into macro index remap");
7503f4a2713aSLionel Sambuc 
7504f4a2713aSLionel Sambuc   return LocalID + I->second;
7505f4a2713aSLionel Sambuc }
7506f4a2713aSLionel Sambuc 
7507f4a2713aSLionel Sambuc serialization::SubmoduleID
getGlobalSubmoduleID(ModuleFile & M,unsigned LocalID)7508f4a2713aSLionel Sambuc ASTReader::getGlobalSubmoduleID(ModuleFile &M, unsigned LocalID) {
7509f4a2713aSLionel Sambuc   if (LocalID < NUM_PREDEF_SUBMODULE_IDS)
7510f4a2713aSLionel Sambuc     return LocalID;
7511f4a2713aSLionel Sambuc 
7512f4a2713aSLionel Sambuc   ContinuousRangeMap<uint32_t, int, 2>::iterator I
7513f4a2713aSLionel Sambuc     = M.SubmoduleRemap.find(LocalID - NUM_PREDEF_SUBMODULE_IDS);
7514f4a2713aSLionel Sambuc   assert(I != M.SubmoduleRemap.end()
7515f4a2713aSLionel Sambuc          && "Invalid index into submodule index remap");
7516f4a2713aSLionel Sambuc 
7517f4a2713aSLionel Sambuc   return LocalID + I->second;
7518f4a2713aSLionel Sambuc }
7519f4a2713aSLionel Sambuc 
getSubmodule(SubmoduleID GlobalID)7520f4a2713aSLionel Sambuc Module *ASTReader::getSubmodule(SubmoduleID GlobalID) {
7521f4a2713aSLionel Sambuc   if (GlobalID < NUM_PREDEF_SUBMODULE_IDS) {
7522f4a2713aSLionel Sambuc     assert(GlobalID == 0 && "Unhandled global submodule ID");
7523*0a6a1f1dSLionel Sambuc     return nullptr;
7524f4a2713aSLionel Sambuc   }
7525f4a2713aSLionel Sambuc 
7526f4a2713aSLionel Sambuc   if (GlobalID > SubmodulesLoaded.size()) {
7527f4a2713aSLionel Sambuc     Error("submodule ID out of range in AST file");
7528*0a6a1f1dSLionel Sambuc     return nullptr;
7529f4a2713aSLionel Sambuc   }
7530f4a2713aSLionel Sambuc 
7531f4a2713aSLionel Sambuc   return SubmodulesLoaded[GlobalID - NUM_PREDEF_SUBMODULE_IDS];
7532f4a2713aSLionel Sambuc }
7533f4a2713aSLionel Sambuc 
getModule(unsigned ID)7534f4a2713aSLionel Sambuc Module *ASTReader::getModule(unsigned ID) {
7535f4a2713aSLionel Sambuc   return getSubmodule(ID);
7536f4a2713aSLionel Sambuc }
7537f4a2713aSLionel Sambuc 
getLocalSelector(ModuleFile & M,unsigned LocalID)7538f4a2713aSLionel Sambuc Selector ASTReader::getLocalSelector(ModuleFile &M, unsigned LocalID) {
7539f4a2713aSLionel Sambuc   return DecodeSelector(getGlobalSelectorID(M, LocalID));
7540f4a2713aSLionel Sambuc }
7541f4a2713aSLionel Sambuc 
DecodeSelector(serialization::SelectorID ID)7542f4a2713aSLionel Sambuc Selector ASTReader::DecodeSelector(serialization::SelectorID ID) {
7543f4a2713aSLionel Sambuc   if (ID == 0)
7544f4a2713aSLionel Sambuc     return Selector();
7545f4a2713aSLionel Sambuc 
7546f4a2713aSLionel Sambuc   if (ID > SelectorsLoaded.size()) {
7547f4a2713aSLionel Sambuc     Error("selector ID out of range in AST file");
7548f4a2713aSLionel Sambuc     return Selector();
7549f4a2713aSLionel Sambuc   }
7550f4a2713aSLionel Sambuc 
7551*0a6a1f1dSLionel Sambuc   if (SelectorsLoaded[ID - 1].getAsOpaquePtr() == nullptr) {
7552f4a2713aSLionel Sambuc     // Load this selector from the selector table.
7553f4a2713aSLionel Sambuc     GlobalSelectorMapType::iterator I = GlobalSelectorMap.find(ID);
7554f4a2713aSLionel Sambuc     assert(I != GlobalSelectorMap.end() && "Corrupted global selector map");
7555f4a2713aSLionel Sambuc     ModuleFile &M = *I->second;
7556f4a2713aSLionel Sambuc     ASTSelectorLookupTrait Trait(*this, M);
7557f4a2713aSLionel Sambuc     unsigned Idx = ID - M.BaseSelectorID - NUM_PREDEF_SELECTOR_IDS;
7558f4a2713aSLionel Sambuc     SelectorsLoaded[ID - 1] =
7559f4a2713aSLionel Sambuc       Trait.ReadKey(M.SelectorLookupTableData + M.SelectorOffsets[Idx], 0);
7560f4a2713aSLionel Sambuc     if (DeserializationListener)
7561f4a2713aSLionel Sambuc       DeserializationListener->SelectorRead(ID, SelectorsLoaded[ID - 1]);
7562f4a2713aSLionel Sambuc   }
7563f4a2713aSLionel Sambuc 
7564f4a2713aSLionel Sambuc   return SelectorsLoaded[ID - 1];
7565f4a2713aSLionel Sambuc }
7566f4a2713aSLionel Sambuc 
GetExternalSelector(serialization::SelectorID ID)7567f4a2713aSLionel Sambuc Selector ASTReader::GetExternalSelector(serialization::SelectorID ID) {
7568f4a2713aSLionel Sambuc   return DecodeSelector(ID);
7569f4a2713aSLionel Sambuc }
7570f4a2713aSLionel Sambuc 
GetNumExternalSelectors()7571f4a2713aSLionel Sambuc uint32_t ASTReader::GetNumExternalSelectors() {
7572f4a2713aSLionel Sambuc   // ID 0 (the null selector) is considered an external selector.
7573f4a2713aSLionel Sambuc   return getTotalNumSelectors() + 1;
7574f4a2713aSLionel Sambuc }
7575f4a2713aSLionel Sambuc 
7576f4a2713aSLionel Sambuc serialization::SelectorID
getGlobalSelectorID(ModuleFile & M,unsigned LocalID) const7577f4a2713aSLionel Sambuc ASTReader::getGlobalSelectorID(ModuleFile &M, unsigned LocalID) const {
7578f4a2713aSLionel Sambuc   if (LocalID < NUM_PREDEF_SELECTOR_IDS)
7579f4a2713aSLionel Sambuc     return LocalID;
7580f4a2713aSLionel Sambuc 
7581f4a2713aSLionel Sambuc   ContinuousRangeMap<uint32_t, int, 2>::iterator I
7582f4a2713aSLionel Sambuc     = M.SelectorRemap.find(LocalID - NUM_PREDEF_SELECTOR_IDS);
7583f4a2713aSLionel Sambuc   assert(I != M.SelectorRemap.end()
7584f4a2713aSLionel Sambuc          && "Invalid index into selector index remap");
7585f4a2713aSLionel Sambuc 
7586f4a2713aSLionel Sambuc   return LocalID + I->second;
7587f4a2713aSLionel Sambuc }
7588f4a2713aSLionel Sambuc 
7589f4a2713aSLionel Sambuc DeclarationName
ReadDeclarationName(ModuleFile & F,const RecordData & Record,unsigned & Idx)7590f4a2713aSLionel Sambuc ASTReader::ReadDeclarationName(ModuleFile &F,
7591f4a2713aSLionel Sambuc                                const RecordData &Record, unsigned &Idx) {
7592f4a2713aSLionel Sambuc   DeclarationName::NameKind Kind = (DeclarationName::NameKind)Record[Idx++];
7593f4a2713aSLionel Sambuc   switch (Kind) {
7594f4a2713aSLionel Sambuc   case DeclarationName::Identifier:
7595f4a2713aSLionel Sambuc     return DeclarationName(GetIdentifierInfo(F, Record, Idx));
7596f4a2713aSLionel Sambuc 
7597f4a2713aSLionel Sambuc   case DeclarationName::ObjCZeroArgSelector:
7598f4a2713aSLionel Sambuc   case DeclarationName::ObjCOneArgSelector:
7599f4a2713aSLionel Sambuc   case DeclarationName::ObjCMultiArgSelector:
7600f4a2713aSLionel Sambuc     return DeclarationName(ReadSelector(F, Record, Idx));
7601f4a2713aSLionel Sambuc 
7602f4a2713aSLionel Sambuc   case DeclarationName::CXXConstructorName:
7603f4a2713aSLionel Sambuc     return Context.DeclarationNames.getCXXConstructorName(
7604f4a2713aSLionel Sambuc                           Context.getCanonicalType(readType(F, Record, Idx)));
7605f4a2713aSLionel Sambuc 
7606f4a2713aSLionel Sambuc   case DeclarationName::CXXDestructorName:
7607f4a2713aSLionel Sambuc     return Context.DeclarationNames.getCXXDestructorName(
7608f4a2713aSLionel Sambuc                           Context.getCanonicalType(readType(F, Record, Idx)));
7609f4a2713aSLionel Sambuc 
7610f4a2713aSLionel Sambuc   case DeclarationName::CXXConversionFunctionName:
7611f4a2713aSLionel Sambuc     return Context.DeclarationNames.getCXXConversionFunctionName(
7612f4a2713aSLionel Sambuc                           Context.getCanonicalType(readType(F, Record, Idx)));
7613f4a2713aSLionel Sambuc 
7614f4a2713aSLionel Sambuc   case DeclarationName::CXXOperatorName:
7615f4a2713aSLionel Sambuc     return Context.DeclarationNames.getCXXOperatorName(
7616f4a2713aSLionel Sambuc                                        (OverloadedOperatorKind)Record[Idx++]);
7617f4a2713aSLionel Sambuc 
7618f4a2713aSLionel Sambuc   case DeclarationName::CXXLiteralOperatorName:
7619f4a2713aSLionel Sambuc     return Context.DeclarationNames.getCXXLiteralOperatorName(
7620f4a2713aSLionel Sambuc                                        GetIdentifierInfo(F, Record, Idx));
7621f4a2713aSLionel Sambuc 
7622f4a2713aSLionel Sambuc   case DeclarationName::CXXUsingDirective:
7623f4a2713aSLionel Sambuc     return DeclarationName::getUsingDirectiveName();
7624f4a2713aSLionel Sambuc   }
7625f4a2713aSLionel Sambuc 
7626f4a2713aSLionel Sambuc   llvm_unreachable("Invalid NameKind!");
7627f4a2713aSLionel Sambuc }
7628f4a2713aSLionel Sambuc 
ReadDeclarationNameLoc(ModuleFile & F,DeclarationNameLoc & DNLoc,DeclarationName Name,const RecordData & Record,unsigned & Idx)7629f4a2713aSLionel Sambuc void ASTReader::ReadDeclarationNameLoc(ModuleFile &F,
7630f4a2713aSLionel Sambuc                                        DeclarationNameLoc &DNLoc,
7631f4a2713aSLionel Sambuc                                        DeclarationName Name,
7632f4a2713aSLionel Sambuc                                       const RecordData &Record, unsigned &Idx) {
7633f4a2713aSLionel Sambuc   switch (Name.getNameKind()) {
7634f4a2713aSLionel Sambuc   case DeclarationName::CXXConstructorName:
7635f4a2713aSLionel Sambuc   case DeclarationName::CXXDestructorName:
7636f4a2713aSLionel Sambuc   case DeclarationName::CXXConversionFunctionName:
7637f4a2713aSLionel Sambuc     DNLoc.NamedType.TInfo = GetTypeSourceInfo(F, Record, Idx);
7638f4a2713aSLionel Sambuc     break;
7639f4a2713aSLionel Sambuc 
7640f4a2713aSLionel Sambuc   case DeclarationName::CXXOperatorName:
7641f4a2713aSLionel Sambuc     DNLoc.CXXOperatorName.BeginOpNameLoc
7642f4a2713aSLionel Sambuc         = ReadSourceLocation(F, Record, Idx).getRawEncoding();
7643f4a2713aSLionel Sambuc     DNLoc.CXXOperatorName.EndOpNameLoc
7644f4a2713aSLionel Sambuc         = ReadSourceLocation(F, Record, Idx).getRawEncoding();
7645f4a2713aSLionel Sambuc     break;
7646f4a2713aSLionel Sambuc 
7647f4a2713aSLionel Sambuc   case DeclarationName::CXXLiteralOperatorName:
7648f4a2713aSLionel Sambuc     DNLoc.CXXLiteralOperatorName.OpNameLoc
7649f4a2713aSLionel Sambuc         = ReadSourceLocation(F, Record, Idx).getRawEncoding();
7650f4a2713aSLionel Sambuc     break;
7651f4a2713aSLionel Sambuc 
7652f4a2713aSLionel Sambuc   case DeclarationName::Identifier:
7653f4a2713aSLionel Sambuc   case DeclarationName::ObjCZeroArgSelector:
7654f4a2713aSLionel Sambuc   case DeclarationName::ObjCOneArgSelector:
7655f4a2713aSLionel Sambuc   case DeclarationName::ObjCMultiArgSelector:
7656f4a2713aSLionel Sambuc   case DeclarationName::CXXUsingDirective:
7657f4a2713aSLionel Sambuc     break;
7658f4a2713aSLionel Sambuc   }
7659f4a2713aSLionel Sambuc }
7660f4a2713aSLionel Sambuc 
ReadDeclarationNameInfo(ModuleFile & F,DeclarationNameInfo & NameInfo,const RecordData & Record,unsigned & Idx)7661f4a2713aSLionel Sambuc void ASTReader::ReadDeclarationNameInfo(ModuleFile &F,
7662f4a2713aSLionel Sambuc                                         DeclarationNameInfo &NameInfo,
7663f4a2713aSLionel Sambuc                                       const RecordData &Record, unsigned &Idx) {
7664f4a2713aSLionel Sambuc   NameInfo.setName(ReadDeclarationName(F, Record, Idx));
7665f4a2713aSLionel Sambuc   NameInfo.setLoc(ReadSourceLocation(F, Record, Idx));
7666f4a2713aSLionel Sambuc   DeclarationNameLoc DNLoc;
7667f4a2713aSLionel Sambuc   ReadDeclarationNameLoc(F, DNLoc, NameInfo.getName(), Record, Idx);
7668f4a2713aSLionel Sambuc   NameInfo.setInfo(DNLoc);
7669f4a2713aSLionel Sambuc }
7670f4a2713aSLionel Sambuc 
ReadQualifierInfo(ModuleFile & F,QualifierInfo & Info,const RecordData & Record,unsigned & Idx)7671f4a2713aSLionel Sambuc void ASTReader::ReadQualifierInfo(ModuleFile &F, QualifierInfo &Info,
7672f4a2713aSLionel Sambuc                                   const RecordData &Record, unsigned &Idx) {
7673f4a2713aSLionel Sambuc   Info.QualifierLoc = ReadNestedNameSpecifierLoc(F, Record, Idx);
7674f4a2713aSLionel Sambuc   unsigned NumTPLists = Record[Idx++];
7675f4a2713aSLionel Sambuc   Info.NumTemplParamLists = NumTPLists;
7676f4a2713aSLionel Sambuc   if (NumTPLists) {
7677f4a2713aSLionel Sambuc     Info.TemplParamLists = new (Context) TemplateParameterList*[NumTPLists];
7678f4a2713aSLionel Sambuc     for (unsigned i=0; i != NumTPLists; ++i)
7679f4a2713aSLionel Sambuc       Info.TemplParamLists[i] = ReadTemplateParameterList(F, Record, Idx);
7680f4a2713aSLionel Sambuc   }
7681f4a2713aSLionel Sambuc }
7682f4a2713aSLionel Sambuc 
7683f4a2713aSLionel Sambuc TemplateName
ReadTemplateName(ModuleFile & F,const RecordData & Record,unsigned & Idx)7684f4a2713aSLionel Sambuc ASTReader::ReadTemplateName(ModuleFile &F, const RecordData &Record,
7685f4a2713aSLionel Sambuc                             unsigned &Idx) {
7686f4a2713aSLionel Sambuc   TemplateName::NameKind Kind = (TemplateName::NameKind)Record[Idx++];
7687f4a2713aSLionel Sambuc   switch (Kind) {
7688f4a2713aSLionel Sambuc   case TemplateName::Template:
7689f4a2713aSLionel Sambuc       return TemplateName(ReadDeclAs<TemplateDecl>(F, Record, Idx));
7690f4a2713aSLionel Sambuc 
7691f4a2713aSLionel Sambuc   case TemplateName::OverloadedTemplate: {
7692f4a2713aSLionel Sambuc     unsigned size = Record[Idx++];
7693f4a2713aSLionel Sambuc     UnresolvedSet<8> Decls;
7694f4a2713aSLionel Sambuc     while (size--)
7695f4a2713aSLionel Sambuc       Decls.addDecl(ReadDeclAs<NamedDecl>(F, Record, Idx));
7696f4a2713aSLionel Sambuc 
7697f4a2713aSLionel Sambuc     return Context.getOverloadedTemplateName(Decls.begin(), Decls.end());
7698f4a2713aSLionel Sambuc   }
7699f4a2713aSLionel Sambuc 
7700f4a2713aSLionel Sambuc   case TemplateName::QualifiedTemplate: {
7701f4a2713aSLionel Sambuc     NestedNameSpecifier *NNS = ReadNestedNameSpecifier(F, Record, Idx);
7702f4a2713aSLionel Sambuc     bool hasTemplKeyword = Record[Idx++];
7703f4a2713aSLionel Sambuc     TemplateDecl *Template = ReadDeclAs<TemplateDecl>(F, Record, Idx);
7704f4a2713aSLionel Sambuc     return Context.getQualifiedTemplateName(NNS, hasTemplKeyword, Template);
7705f4a2713aSLionel Sambuc   }
7706f4a2713aSLionel Sambuc 
7707f4a2713aSLionel Sambuc   case TemplateName::DependentTemplate: {
7708f4a2713aSLionel Sambuc     NestedNameSpecifier *NNS = ReadNestedNameSpecifier(F, Record, Idx);
7709f4a2713aSLionel Sambuc     if (Record[Idx++])  // isIdentifier
7710f4a2713aSLionel Sambuc       return Context.getDependentTemplateName(NNS,
7711f4a2713aSLionel Sambuc                                                GetIdentifierInfo(F, Record,
7712f4a2713aSLionel Sambuc                                                                  Idx));
7713f4a2713aSLionel Sambuc     return Context.getDependentTemplateName(NNS,
7714f4a2713aSLionel Sambuc                                          (OverloadedOperatorKind)Record[Idx++]);
7715f4a2713aSLionel Sambuc   }
7716f4a2713aSLionel Sambuc 
7717f4a2713aSLionel Sambuc   case TemplateName::SubstTemplateTemplateParm: {
7718f4a2713aSLionel Sambuc     TemplateTemplateParmDecl *param
7719f4a2713aSLionel Sambuc       = ReadDeclAs<TemplateTemplateParmDecl>(F, Record, Idx);
7720f4a2713aSLionel Sambuc     if (!param) return TemplateName();
7721f4a2713aSLionel Sambuc     TemplateName replacement = ReadTemplateName(F, Record, Idx);
7722f4a2713aSLionel Sambuc     return Context.getSubstTemplateTemplateParm(param, replacement);
7723f4a2713aSLionel Sambuc   }
7724f4a2713aSLionel Sambuc 
7725f4a2713aSLionel Sambuc   case TemplateName::SubstTemplateTemplateParmPack: {
7726f4a2713aSLionel Sambuc     TemplateTemplateParmDecl *Param
7727f4a2713aSLionel Sambuc       = ReadDeclAs<TemplateTemplateParmDecl>(F, Record, Idx);
7728f4a2713aSLionel Sambuc     if (!Param)
7729f4a2713aSLionel Sambuc       return TemplateName();
7730f4a2713aSLionel Sambuc 
7731f4a2713aSLionel Sambuc     TemplateArgument ArgPack = ReadTemplateArgument(F, Record, Idx);
7732f4a2713aSLionel Sambuc     if (ArgPack.getKind() != TemplateArgument::Pack)
7733f4a2713aSLionel Sambuc       return TemplateName();
7734f4a2713aSLionel Sambuc 
7735f4a2713aSLionel Sambuc     return Context.getSubstTemplateTemplateParmPack(Param, ArgPack);
7736f4a2713aSLionel Sambuc   }
7737f4a2713aSLionel Sambuc   }
7738f4a2713aSLionel Sambuc 
7739f4a2713aSLionel Sambuc   llvm_unreachable("Unhandled template name kind!");
7740f4a2713aSLionel Sambuc }
7741f4a2713aSLionel Sambuc 
7742f4a2713aSLionel Sambuc TemplateArgument
ReadTemplateArgument(ModuleFile & F,const RecordData & Record,unsigned & Idx)7743f4a2713aSLionel Sambuc ASTReader::ReadTemplateArgument(ModuleFile &F,
7744f4a2713aSLionel Sambuc                                 const RecordData &Record, unsigned &Idx) {
7745f4a2713aSLionel Sambuc   TemplateArgument::ArgKind Kind = (TemplateArgument::ArgKind)Record[Idx++];
7746f4a2713aSLionel Sambuc   switch (Kind) {
7747f4a2713aSLionel Sambuc   case TemplateArgument::Null:
7748f4a2713aSLionel Sambuc     return TemplateArgument();
7749f4a2713aSLionel Sambuc   case TemplateArgument::Type:
7750f4a2713aSLionel Sambuc     return TemplateArgument(readType(F, Record, Idx));
7751f4a2713aSLionel Sambuc   case TemplateArgument::Declaration: {
7752f4a2713aSLionel Sambuc     ValueDecl *D = ReadDeclAs<ValueDecl>(F, Record, Idx);
7753*0a6a1f1dSLionel Sambuc     return TemplateArgument(D, readType(F, Record, Idx));
7754f4a2713aSLionel Sambuc   }
7755f4a2713aSLionel Sambuc   case TemplateArgument::NullPtr:
7756f4a2713aSLionel Sambuc     return TemplateArgument(readType(F, Record, Idx), /*isNullPtr*/true);
7757f4a2713aSLionel Sambuc   case TemplateArgument::Integral: {
7758f4a2713aSLionel Sambuc     llvm::APSInt Value = ReadAPSInt(Record, Idx);
7759f4a2713aSLionel Sambuc     QualType T = readType(F, Record, Idx);
7760f4a2713aSLionel Sambuc     return TemplateArgument(Context, Value, T);
7761f4a2713aSLionel Sambuc   }
7762f4a2713aSLionel Sambuc   case TemplateArgument::Template:
7763f4a2713aSLionel Sambuc     return TemplateArgument(ReadTemplateName(F, Record, Idx));
7764f4a2713aSLionel Sambuc   case TemplateArgument::TemplateExpansion: {
7765f4a2713aSLionel Sambuc     TemplateName Name = ReadTemplateName(F, Record, Idx);
7766f4a2713aSLionel Sambuc     Optional<unsigned> NumTemplateExpansions;
7767f4a2713aSLionel Sambuc     if (unsigned NumExpansions = Record[Idx++])
7768f4a2713aSLionel Sambuc       NumTemplateExpansions = NumExpansions - 1;
7769f4a2713aSLionel Sambuc     return TemplateArgument(Name, NumTemplateExpansions);
7770f4a2713aSLionel Sambuc   }
7771f4a2713aSLionel Sambuc   case TemplateArgument::Expression:
7772f4a2713aSLionel Sambuc     return TemplateArgument(ReadExpr(F));
7773f4a2713aSLionel Sambuc   case TemplateArgument::Pack: {
7774f4a2713aSLionel Sambuc     unsigned NumArgs = Record[Idx++];
7775f4a2713aSLionel Sambuc     TemplateArgument *Args = new (Context) TemplateArgument[NumArgs];
7776f4a2713aSLionel Sambuc     for (unsigned I = 0; I != NumArgs; ++I)
7777f4a2713aSLionel Sambuc       Args[I] = ReadTemplateArgument(F, Record, Idx);
7778f4a2713aSLionel Sambuc     return TemplateArgument(Args, NumArgs);
7779f4a2713aSLionel Sambuc   }
7780f4a2713aSLionel Sambuc   }
7781f4a2713aSLionel Sambuc 
7782f4a2713aSLionel Sambuc   llvm_unreachable("Unhandled template argument kind!");
7783f4a2713aSLionel Sambuc }
7784f4a2713aSLionel Sambuc 
7785f4a2713aSLionel Sambuc TemplateParameterList *
ReadTemplateParameterList(ModuleFile & F,const RecordData & Record,unsigned & Idx)7786f4a2713aSLionel Sambuc ASTReader::ReadTemplateParameterList(ModuleFile &F,
7787f4a2713aSLionel Sambuc                                      const RecordData &Record, unsigned &Idx) {
7788f4a2713aSLionel Sambuc   SourceLocation TemplateLoc = ReadSourceLocation(F, Record, Idx);
7789f4a2713aSLionel Sambuc   SourceLocation LAngleLoc = ReadSourceLocation(F, Record, Idx);
7790f4a2713aSLionel Sambuc   SourceLocation RAngleLoc = ReadSourceLocation(F, Record, Idx);
7791f4a2713aSLionel Sambuc 
7792f4a2713aSLionel Sambuc   unsigned NumParams = Record[Idx++];
7793f4a2713aSLionel Sambuc   SmallVector<NamedDecl *, 16> Params;
7794f4a2713aSLionel Sambuc   Params.reserve(NumParams);
7795f4a2713aSLionel Sambuc   while (NumParams--)
7796f4a2713aSLionel Sambuc     Params.push_back(ReadDeclAs<NamedDecl>(F, Record, Idx));
7797f4a2713aSLionel Sambuc 
7798f4a2713aSLionel Sambuc   TemplateParameterList* TemplateParams =
7799f4a2713aSLionel Sambuc     TemplateParameterList::Create(Context, TemplateLoc, LAngleLoc,
7800f4a2713aSLionel Sambuc                                   Params.data(), Params.size(), RAngleLoc);
7801f4a2713aSLionel Sambuc   return TemplateParams;
7802f4a2713aSLionel Sambuc }
7803f4a2713aSLionel Sambuc 
7804f4a2713aSLionel Sambuc void
7805f4a2713aSLionel Sambuc ASTReader::
ReadTemplateArgumentList(SmallVectorImpl<TemplateArgument> & TemplArgs,ModuleFile & F,const RecordData & Record,unsigned & Idx)7806f4a2713aSLionel Sambuc ReadTemplateArgumentList(SmallVectorImpl<TemplateArgument> &TemplArgs,
7807f4a2713aSLionel Sambuc                          ModuleFile &F, const RecordData &Record,
7808f4a2713aSLionel Sambuc                          unsigned &Idx) {
7809f4a2713aSLionel Sambuc   unsigned NumTemplateArgs = Record[Idx++];
7810f4a2713aSLionel Sambuc   TemplArgs.reserve(NumTemplateArgs);
7811f4a2713aSLionel Sambuc   while (NumTemplateArgs--)
7812f4a2713aSLionel Sambuc     TemplArgs.push_back(ReadTemplateArgument(F, Record, Idx));
7813f4a2713aSLionel Sambuc }
7814f4a2713aSLionel Sambuc 
7815f4a2713aSLionel Sambuc /// \brief Read a UnresolvedSet structure.
ReadUnresolvedSet(ModuleFile & F,LazyASTUnresolvedSet & Set,const RecordData & Record,unsigned & Idx)7816f4a2713aSLionel Sambuc void ASTReader::ReadUnresolvedSet(ModuleFile &F, LazyASTUnresolvedSet &Set,
7817f4a2713aSLionel Sambuc                                   const RecordData &Record, unsigned &Idx) {
7818f4a2713aSLionel Sambuc   unsigned NumDecls = Record[Idx++];
7819f4a2713aSLionel Sambuc   Set.reserve(Context, NumDecls);
7820f4a2713aSLionel Sambuc   while (NumDecls--) {
7821f4a2713aSLionel Sambuc     DeclID ID = ReadDeclID(F, Record, Idx);
7822f4a2713aSLionel Sambuc     AccessSpecifier AS = (AccessSpecifier)Record[Idx++];
7823f4a2713aSLionel Sambuc     Set.addLazyDecl(Context, ID, AS);
7824f4a2713aSLionel Sambuc   }
7825f4a2713aSLionel Sambuc }
7826f4a2713aSLionel Sambuc 
7827f4a2713aSLionel Sambuc CXXBaseSpecifier
ReadCXXBaseSpecifier(ModuleFile & F,const RecordData & Record,unsigned & Idx)7828f4a2713aSLionel Sambuc ASTReader::ReadCXXBaseSpecifier(ModuleFile &F,
7829f4a2713aSLionel Sambuc                                 const RecordData &Record, unsigned &Idx) {
7830f4a2713aSLionel Sambuc   bool isVirtual = static_cast<bool>(Record[Idx++]);
7831f4a2713aSLionel Sambuc   bool isBaseOfClass = static_cast<bool>(Record[Idx++]);
7832f4a2713aSLionel Sambuc   AccessSpecifier AS = static_cast<AccessSpecifier>(Record[Idx++]);
7833f4a2713aSLionel Sambuc   bool inheritConstructors = static_cast<bool>(Record[Idx++]);
7834f4a2713aSLionel Sambuc   TypeSourceInfo *TInfo = GetTypeSourceInfo(F, Record, Idx);
7835f4a2713aSLionel Sambuc   SourceRange Range = ReadSourceRange(F, Record, Idx);
7836f4a2713aSLionel Sambuc   SourceLocation EllipsisLoc = ReadSourceLocation(F, Record, Idx);
7837f4a2713aSLionel Sambuc   CXXBaseSpecifier Result(Range, isVirtual, isBaseOfClass, AS, TInfo,
7838f4a2713aSLionel Sambuc                           EllipsisLoc);
7839f4a2713aSLionel Sambuc   Result.setInheritConstructors(inheritConstructors);
7840f4a2713aSLionel Sambuc   return Result;
7841f4a2713aSLionel Sambuc }
7842f4a2713aSLionel Sambuc 
7843f4a2713aSLionel Sambuc std::pair<CXXCtorInitializer **, unsigned>
ReadCXXCtorInitializers(ModuleFile & F,const RecordData & Record,unsigned & Idx)7844f4a2713aSLionel Sambuc ASTReader::ReadCXXCtorInitializers(ModuleFile &F, const RecordData &Record,
7845f4a2713aSLionel Sambuc                                    unsigned &Idx) {
7846*0a6a1f1dSLionel Sambuc   CXXCtorInitializer **CtorInitializers = nullptr;
7847f4a2713aSLionel Sambuc   unsigned NumInitializers = Record[Idx++];
7848f4a2713aSLionel Sambuc   if (NumInitializers) {
7849f4a2713aSLionel Sambuc     CtorInitializers
7850f4a2713aSLionel Sambuc         = new (Context) CXXCtorInitializer*[NumInitializers];
7851f4a2713aSLionel Sambuc     for (unsigned i=0; i != NumInitializers; ++i) {
7852*0a6a1f1dSLionel Sambuc       TypeSourceInfo *TInfo = nullptr;
7853f4a2713aSLionel Sambuc       bool IsBaseVirtual = false;
7854*0a6a1f1dSLionel Sambuc       FieldDecl *Member = nullptr;
7855*0a6a1f1dSLionel Sambuc       IndirectFieldDecl *IndirectMember = nullptr;
7856f4a2713aSLionel Sambuc 
7857f4a2713aSLionel Sambuc       CtorInitializerType Type = (CtorInitializerType)Record[Idx++];
7858f4a2713aSLionel Sambuc       switch (Type) {
7859f4a2713aSLionel Sambuc       case CTOR_INITIALIZER_BASE:
7860f4a2713aSLionel Sambuc         TInfo = GetTypeSourceInfo(F, Record, Idx);
7861f4a2713aSLionel Sambuc         IsBaseVirtual = Record[Idx++];
7862f4a2713aSLionel Sambuc         break;
7863f4a2713aSLionel Sambuc 
7864f4a2713aSLionel Sambuc       case CTOR_INITIALIZER_DELEGATING:
7865f4a2713aSLionel Sambuc         TInfo = GetTypeSourceInfo(F, Record, Idx);
7866f4a2713aSLionel Sambuc         break;
7867f4a2713aSLionel Sambuc 
7868f4a2713aSLionel Sambuc        case CTOR_INITIALIZER_MEMBER:
7869f4a2713aSLionel Sambuc         Member = ReadDeclAs<FieldDecl>(F, Record, Idx);
7870f4a2713aSLionel Sambuc         break;
7871f4a2713aSLionel Sambuc 
7872f4a2713aSLionel Sambuc        case CTOR_INITIALIZER_INDIRECT_MEMBER:
7873f4a2713aSLionel Sambuc         IndirectMember = ReadDeclAs<IndirectFieldDecl>(F, Record, Idx);
7874f4a2713aSLionel Sambuc         break;
7875f4a2713aSLionel Sambuc       }
7876f4a2713aSLionel Sambuc 
7877f4a2713aSLionel Sambuc       SourceLocation MemberOrEllipsisLoc = ReadSourceLocation(F, Record, Idx);
7878f4a2713aSLionel Sambuc       Expr *Init = ReadExpr(F);
7879f4a2713aSLionel Sambuc       SourceLocation LParenLoc = ReadSourceLocation(F, Record, Idx);
7880f4a2713aSLionel Sambuc       SourceLocation RParenLoc = ReadSourceLocation(F, Record, Idx);
7881f4a2713aSLionel Sambuc       bool IsWritten = Record[Idx++];
7882f4a2713aSLionel Sambuc       unsigned SourceOrderOrNumArrayIndices;
7883f4a2713aSLionel Sambuc       SmallVector<VarDecl *, 8> Indices;
7884f4a2713aSLionel Sambuc       if (IsWritten) {
7885f4a2713aSLionel Sambuc         SourceOrderOrNumArrayIndices = Record[Idx++];
7886f4a2713aSLionel Sambuc       } else {
7887f4a2713aSLionel Sambuc         SourceOrderOrNumArrayIndices = Record[Idx++];
7888f4a2713aSLionel Sambuc         Indices.reserve(SourceOrderOrNumArrayIndices);
7889f4a2713aSLionel Sambuc         for (unsigned i=0; i != SourceOrderOrNumArrayIndices; ++i)
7890f4a2713aSLionel Sambuc           Indices.push_back(ReadDeclAs<VarDecl>(F, Record, Idx));
7891f4a2713aSLionel Sambuc       }
7892f4a2713aSLionel Sambuc 
7893f4a2713aSLionel Sambuc       CXXCtorInitializer *BOMInit;
7894f4a2713aSLionel Sambuc       if (Type == CTOR_INITIALIZER_BASE) {
7895f4a2713aSLionel Sambuc         BOMInit = new (Context) CXXCtorInitializer(Context, TInfo, IsBaseVirtual,
7896f4a2713aSLionel Sambuc                                              LParenLoc, Init, RParenLoc,
7897f4a2713aSLionel Sambuc                                              MemberOrEllipsisLoc);
7898f4a2713aSLionel Sambuc       } else if (Type == CTOR_INITIALIZER_DELEGATING) {
7899f4a2713aSLionel Sambuc         BOMInit = new (Context) CXXCtorInitializer(Context, TInfo, LParenLoc,
7900f4a2713aSLionel Sambuc                                                    Init, RParenLoc);
7901f4a2713aSLionel Sambuc       } else if (IsWritten) {
7902f4a2713aSLionel Sambuc         if (Member)
7903f4a2713aSLionel Sambuc           BOMInit = new (Context) CXXCtorInitializer(Context, Member, MemberOrEllipsisLoc,
7904f4a2713aSLionel Sambuc                                                LParenLoc, Init, RParenLoc);
7905f4a2713aSLionel Sambuc         else
7906f4a2713aSLionel Sambuc           BOMInit = new (Context) CXXCtorInitializer(Context, IndirectMember,
7907f4a2713aSLionel Sambuc                                                MemberOrEllipsisLoc, LParenLoc,
7908f4a2713aSLionel Sambuc                                                Init, RParenLoc);
7909f4a2713aSLionel Sambuc       } else {
7910f4a2713aSLionel Sambuc         if (IndirectMember) {
7911f4a2713aSLionel Sambuc           assert(Indices.empty() && "Indirect field improperly initialized");
7912f4a2713aSLionel Sambuc           BOMInit = new (Context) CXXCtorInitializer(Context, IndirectMember,
7913f4a2713aSLionel Sambuc                                                      MemberOrEllipsisLoc, LParenLoc,
7914f4a2713aSLionel Sambuc                                                      Init, RParenLoc);
7915f4a2713aSLionel Sambuc         } else {
7916f4a2713aSLionel Sambuc           BOMInit = CXXCtorInitializer::Create(Context, Member, MemberOrEllipsisLoc,
7917f4a2713aSLionel Sambuc                                                LParenLoc, Init, RParenLoc,
7918f4a2713aSLionel Sambuc                                                Indices.data(), Indices.size());
7919f4a2713aSLionel Sambuc         }
7920f4a2713aSLionel Sambuc       }
7921f4a2713aSLionel Sambuc 
7922f4a2713aSLionel Sambuc       if (IsWritten)
7923f4a2713aSLionel Sambuc         BOMInit->setSourceOrder(SourceOrderOrNumArrayIndices);
7924f4a2713aSLionel Sambuc       CtorInitializers[i] = BOMInit;
7925f4a2713aSLionel Sambuc     }
7926f4a2713aSLionel Sambuc   }
7927f4a2713aSLionel Sambuc 
7928f4a2713aSLionel Sambuc   return std::make_pair(CtorInitializers, NumInitializers);
7929f4a2713aSLionel Sambuc }
7930f4a2713aSLionel Sambuc 
7931f4a2713aSLionel Sambuc NestedNameSpecifier *
ReadNestedNameSpecifier(ModuleFile & F,const RecordData & Record,unsigned & Idx)7932f4a2713aSLionel Sambuc ASTReader::ReadNestedNameSpecifier(ModuleFile &F,
7933f4a2713aSLionel Sambuc                                    const RecordData &Record, unsigned &Idx) {
7934f4a2713aSLionel Sambuc   unsigned N = Record[Idx++];
7935*0a6a1f1dSLionel Sambuc   NestedNameSpecifier *NNS = nullptr, *Prev = nullptr;
7936f4a2713aSLionel Sambuc   for (unsigned I = 0; I != N; ++I) {
7937f4a2713aSLionel Sambuc     NestedNameSpecifier::SpecifierKind Kind
7938f4a2713aSLionel Sambuc       = (NestedNameSpecifier::SpecifierKind)Record[Idx++];
7939f4a2713aSLionel Sambuc     switch (Kind) {
7940f4a2713aSLionel Sambuc     case NestedNameSpecifier::Identifier: {
7941f4a2713aSLionel Sambuc       IdentifierInfo *II = GetIdentifierInfo(F, Record, Idx);
7942f4a2713aSLionel Sambuc       NNS = NestedNameSpecifier::Create(Context, Prev, II);
7943f4a2713aSLionel Sambuc       break;
7944f4a2713aSLionel Sambuc     }
7945f4a2713aSLionel Sambuc 
7946f4a2713aSLionel Sambuc     case NestedNameSpecifier::Namespace: {
7947f4a2713aSLionel Sambuc       NamespaceDecl *NS = ReadDeclAs<NamespaceDecl>(F, Record, Idx);
7948f4a2713aSLionel Sambuc       NNS = NestedNameSpecifier::Create(Context, Prev, NS);
7949f4a2713aSLionel Sambuc       break;
7950f4a2713aSLionel Sambuc     }
7951f4a2713aSLionel Sambuc 
7952f4a2713aSLionel Sambuc     case NestedNameSpecifier::NamespaceAlias: {
7953f4a2713aSLionel Sambuc       NamespaceAliasDecl *Alias =ReadDeclAs<NamespaceAliasDecl>(F, Record, Idx);
7954f4a2713aSLionel Sambuc       NNS = NestedNameSpecifier::Create(Context, Prev, Alias);
7955f4a2713aSLionel Sambuc       break;
7956f4a2713aSLionel Sambuc     }
7957f4a2713aSLionel Sambuc 
7958f4a2713aSLionel Sambuc     case NestedNameSpecifier::TypeSpec:
7959f4a2713aSLionel Sambuc     case NestedNameSpecifier::TypeSpecWithTemplate: {
7960f4a2713aSLionel Sambuc       const Type *T = readType(F, Record, Idx).getTypePtrOrNull();
7961f4a2713aSLionel Sambuc       if (!T)
7962*0a6a1f1dSLionel Sambuc         return nullptr;
7963f4a2713aSLionel Sambuc 
7964f4a2713aSLionel Sambuc       bool Template = Record[Idx++];
7965f4a2713aSLionel Sambuc       NNS = NestedNameSpecifier::Create(Context, Prev, Template, T);
7966f4a2713aSLionel Sambuc       break;
7967f4a2713aSLionel Sambuc     }
7968f4a2713aSLionel Sambuc 
7969f4a2713aSLionel Sambuc     case NestedNameSpecifier::Global: {
7970f4a2713aSLionel Sambuc       NNS = NestedNameSpecifier::GlobalSpecifier(Context);
7971f4a2713aSLionel Sambuc       // No associated value, and there can't be a prefix.
7972f4a2713aSLionel Sambuc       break;
7973f4a2713aSLionel Sambuc     }
7974*0a6a1f1dSLionel Sambuc 
7975*0a6a1f1dSLionel Sambuc     case NestedNameSpecifier::Super: {
7976*0a6a1f1dSLionel Sambuc       CXXRecordDecl *RD = ReadDeclAs<CXXRecordDecl>(F, Record, Idx);
7977*0a6a1f1dSLionel Sambuc       NNS = NestedNameSpecifier::SuperSpecifier(Context, RD);
7978*0a6a1f1dSLionel Sambuc       break;
7979*0a6a1f1dSLionel Sambuc     }
7980f4a2713aSLionel Sambuc     }
7981f4a2713aSLionel Sambuc     Prev = NNS;
7982f4a2713aSLionel Sambuc   }
7983f4a2713aSLionel Sambuc   return NNS;
7984f4a2713aSLionel Sambuc }
7985f4a2713aSLionel Sambuc 
7986f4a2713aSLionel Sambuc NestedNameSpecifierLoc
ReadNestedNameSpecifierLoc(ModuleFile & F,const RecordData & Record,unsigned & Idx)7987f4a2713aSLionel Sambuc ASTReader::ReadNestedNameSpecifierLoc(ModuleFile &F, const RecordData &Record,
7988f4a2713aSLionel Sambuc                                       unsigned &Idx) {
7989f4a2713aSLionel Sambuc   unsigned N = Record[Idx++];
7990f4a2713aSLionel Sambuc   NestedNameSpecifierLocBuilder Builder;
7991f4a2713aSLionel Sambuc   for (unsigned I = 0; I != N; ++I) {
7992f4a2713aSLionel Sambuc     NestedNameSpecifier::SpecifierKind Kind
7993f4a2713aSLionel Sambuc       = (NestedNameSpecifier::SpecifierKind)Record[Idx++];
7994f4a2713aSLionel Sambuc     switch (Kind) {
7995f4a2713aSLionel Sambuc     case NestedNameSpecifier::Identifier: {
7996f4a2713aSLionel Sambuc       IdentifierInfo *II = GetIdentifierInfo(F, Record, Idx);
7997f4a2713aSLionel Sambuc       SourceRange Range = ReadSourceRange(F, Record, Idx);
7998f4a2713aSLionel Sambuc       Builder.Extend(Context, II, Range.getBegin(), Range.getEnd());
7999f4a2713aSLionel Sambuc       break;
8000f4a2713aSLionel Sambuc     }
8001f4a2713aSLionel Sambuc 
8002f4a2713aSLionel Sambuc     case NestedNameSpecifier::Namespace: {
8003f4a2713aSLionel Sambuc       NamespaceDecl *NS = ReadDeclAs<NamespaceDecl>(F, Record, Idx);
8004f4a2713aSLionel Sambuc       SourceRange Range = ReadSourceRange(F, Record, Idx);
8005f4a2713aSLionel Sambuc       Builder.Extend(Context, NS, Range.getBegin(), Range.getEnd());
8006f4a2713aSLionel Sambuc       break;
8007f4a2713aSLionel Sambuc     }
8008f4a2713aSLionel Sambuc 
8009f4a2713aSLionel Sambuc     case NestedNameSpecifier::NamespaceAlias: {
8010f4a2713aSLionel Sambuc       NamespaceAliasDecl *Alias =ReadDeclAs<NamespaceAliasDecl>(F, Record, Idx);
8011f4a2713aSLionel Sambuc       SourceRange Range = ReadSourceRange(F, Record, Idx);
8012f4a2713aSLionel Sambuc       Builder.Extend(Context, Alias, Range.getBegin(), Range.getEnd());
8013f4a2713aSLionel Sambuc       break;
8014f4a2713aSLionel Sambuc     }
8015f4a2713aSLionel Sambuc 
8016f4a2713aSLionel Sambuc     case NestedNameSpecifier::TypeSpec:
8017f4a2713aSLionel Sambuc     case NestedNameSpecifier::TypeSpecWithTemplate: {
8018f4a2713aSLionel Sambuc       bool Template = Record[Idx++];
8019f4a2713aSLionel Sambuc       TypeSourceInfo *T = GetTypeSourceInfo(F, Record, Idx);
8020f4a2713aSLionel Sambuc       if (!T)
8021f4a2713aSLionel Sambuc         return NestedNameSpecifierLoc();
8022f4a2713aSLionel Sambuc       SourceLocation ColonColonLoc = ReadSourceLocation(F, Record, Idx);
8023f4a2713aSLionel Sambuc 
8024f4a2713aSLionel Sambuc       // FIXME: 'template' keyword location not saved anywhere, so we fake it.
8025f4a2713aSLionel Sambuc       Builder.Extend(Context,
8026f4a2713aSLionel Sambuc                      Template? T->getTypeLoc().getBeginLoc() : SourceLocation(),
8027f4a2713aSLionel Sambuc                      T->getTypeLoc(), ColonColonLoc);
8028f4a2713aSLionel Sambuc       break;
8029f4a2713aSLionel Sambuc     }
8030f4a2713aSLionel Sambuc 
8031f4a2713aSLionel Sambuc     case NestedNameSpecifier::Global: {
8032f4a2713aSLionel Sambuc       SourceLocation ColonColonLoc = ReadSourceLocation(F, Record, Idx);
8033f4a2713aSLionel Sambuc       Builder.MakeGlobal(Context, ColonColonLoc);
8034f4a2713aSLionel Sambuc       break;
8035f4a2713aSLionel Sambuc     }
8036*0a6a1f1dSLionel Sambuc 
8037*0a6a1f1dSLionel Sambuc     case NestedNameSpecifier::Super: {
8038*0a6a1f1dSLionel Sambuc       CXXRecordDecl *RD = ReadDeclAs<CXXRecordDecl>(F, Record, Idx);
8039*0a6a1f1dSLionel Sambuc       SourceRange Range = ReadSourceRange(F, Record, Idx);
8040*0a6a1f1dSLionel Sambuc       Builder.MakeSuper(Context, RD, Range.getBegin(), Range.getEnd());
8041*0a6a1f1dSLionel Sambuc       break;
8042*0a6a1f1dSLionel Sambuc     }
8043f4a2713aSLionel Sambuc     }
8044f4a2713aSLionel Sambuc   }
8045f4a2713aSLionel Sambuc 
8046f4a2713aSLionel Sambuc   return Builder.getWithLocInContext(Context);
8047f4a2713aSLionel Sambuc }
8048f4a2713aSLionel Sambuc 
8049f4a2713aSLionel Sambuc SourceRange
ReadSourceRange(ModuleFile & F,const RecordData & Record,unsigned & Idx)8050f4a2713aSLionel Sambuc ASTReader::ReadSourceRange(ModuleFile &F, const RecordData &Record,
8051f4a2713aSLionel Sambuc                            unsigned &Idx) {
8052f4a2713aSLionel Sambuc   SourceLocation beg = ReadSourceLocation(F, Record, Idx);
8053f4a2713aSLionel Sambuc   SourceLocation end = ReadSourceLocation(F, Record, Idx);
8054f4a2713aSLionel Sambuc   return SourceRange(beg, end);
8055f4a2713aSLionel Sambuc }
8056f4a2713aSLionel Sambuc 
8057f4a2713aSLionel Sambuc /// \brief Read an integral value
ReadAPInt(const RecordData & Record,unsigned & Idx)8058f4a2713aSLionel Sambuc llvm::APInt ASTReader::ReadAPInt(const RecordData &Record, unsigned &Idx) {
8059f4a2713aSLionel Sambuc   unsigned BitWidth = Record[Idx++];
8060f4a2713aSLionel Sambuc   unsigned NumWords = llvm::APInt::getNumWords(BitWidth);
8061f4a2713aSLionel Sambuc   llvm::APInt Result(BitWidth, NumWords, &Record[Idx]);
8062f4a2713aSLionel Sambuc   Idx += NumWords;
8063f4a2713aSLionel Sambuc   return Result;
8064f4a2713aSLionel Sambuc }
8065f4a2713aSLionel Sambuc 
8066f4a2713aSLionel Sambuc /// \brief Read a signed integral value
ReadAPSInt(const RecordData & Record,unsigned & Idx)8067f4a2713aSLionel Sambuc llvm::APSInt ASTReader::ReadAPSInt(const RecordData &Record, unsigned &Idx) {
8068f4a2713aSLionel Sambuc   bool isUnsigned = Record[Idx++];
8069f4a2713aSLionel Sambuc   return llvm::APSInt(ReadAPInt(Record, Idx), isUnsigned);
8070f4a2713aSLionel Sambuc }
8071f4a2713aSLionel Sambuc 
8072f4a2713aSLionel Sambuc /// \brief Read a floating-point value
ReadAPFloat(const RecordData & Record,const llvm::fltSemantics & Sem,unsigned & Idx)8073f4a2713aSLionel Sambuc llvm::APFloat ASTReader::ReadAPFloat(const RecordData &Record,
8074f4a2713aSLionel Sambuc                                      const llvm::fltSemantics &Sem,
8075f4a2713aSLionel Sambuc                                      unsigned &Idx) {
8076f4a2713aSLionel Sambuc   return llvm::APFloat(Sem, ReadAPInt(Record, Idx));
8077f4a2713aSLionel Sambuc }
8078f4a2713aSLionel Sambuc 
8079f4a2713aSLionel Sambuc // \brief Read a string
ReadString(const RecordData & Record,unsigned & Idx)8080f4a2713aSLionel Sambuc std::string ASTReader::ReadString(const RecordData &Record, unsigned &Idx) {
8081f4a2713aSLionel Sambuc   unsigned Len = Record[Idx++];
8082f4a2713aSLionel Sambuc   std::string Result(Record.data() + Idx, Record.data() + Idx + Len);
8083f4a2713aSLionel Sambuc   Idx += Len;
8084f4a2713aSLionel Sambuc   return Result;
8085f4a2713aSLionel Sambuc }
8086f4a2713aSLionel Sambuc 
ReadPath(ModuleFile & F,const RecordData & Record,unsigned & Idx)8087*0a6a1f1dSLionel Sambuc std::string ASTReader::ReadPath(ModuleFile &F, const RecordData &Record,
8088*0a6a1f1dSLionel Sambuc                                 unsigned &Idx) {
8089*0a6a1f1dSLionel Sambuc   std::string Filename = ReadString(Record, Idx);
8090*0a6a1f1dSLionel Sambuc   ResolveImportedPath(F, Filename);
8091*0a6a1f1dSLionel Sambuc   return Filename;
8092*0a6a1f1dSLionel Sambuc }
8093*0a6a1f1dSLionel Sambuc 
ReadVersionTuple(const RecordData & Record,unsigned & Idx)8094f4a2713aSLionel Sambuc VersionTuple ASTReader::ReadVersionTuple(const RecordData &Record,
8095f4a2713aSLionel Sambuc                                          unsigned &Idx) {
8096f4a2713aSLionel Sambuc   unsigned Major = Record[Idx++];
8097f4a2713aSLionel Sambuc   unsigned Minor = Record[Idx++];
8098f4a2713aSLionel Sambuc   unsigned Subminor = Record[Idx++];
8099f4a2713aSLionel Sambuc   if (Minor == 0)
8100f4a2713aSLionel Sambuc     return VersionTuple(Major);
8101f4a2713aSLionel Sambuc   if (Subminor == 0)
8102f4a2713aSLionel Sambuc     return VersionTuple(Major, Minor - 1);
8103f4a2713aSLionel Sambuc   return VersionTuple(Major, Minor - 1, Subminor - 1);
8104f4a2713aSLionel Sambuc }
8105f4a2713aSLionel Sambuc 
ReadCXXTemporary(ModuleFile & F,const RecordData & Record,unsigned & Idx)8106f4a2713aSLionel Sambuc CXXTemporary *ASTReader::ReadCXXTemporary(ModuleFile &F,
8107f4a2713aSLionel Sambuc                                           const RecordData &Record,
8108f4a2713aSLionel Sambuc                                           unsigned &Idx) {
8109f4a2713aSLionel Sambuc   CXXDestructorDecl *Decl = ReadDeclAs<CXXDestructorDecl>(F, Record, Idx);
8110f4a2713aSLionel Sambuc   return CXXTemporary::Create(Context, Decl);
8111f4a2713aSLionel Sambuc }
8112f4a2713aSLionel Sambuc 
Diag(unsigned DiagID)8113f4a2713aSLionel Sambuc DiagnosticBuilder ASTReader::Diag(unsigned DiagID) {
8114f4a2713aSLionel Sambuc   return Diag(CurrentImportLoc, DiagID);
8115f4a2713aSLionel Sambuc }
8116f4a2713aSLionel Sambuc 
Diag(SourceLocation Loc,unsigned DiagID)8117f4a2713aSLionel Sambuc DiagnosticBuilder ASTReader::Diag(SourceLocation Loc, unsigned DiagID) {
8118f4a2713aSLionel Sambuc   return Diags.Report(Loc, DiagID);
8119f4a2713aSLionel Sambuc }
8120f4a2713aSLionel Sambuc 
8121f4a2713aSLionel Sambuc /// \brief Retrieve the identifier table associated with the
8122f4a2713aSLionel Sambuc /// preprocessor.
getIdentifierTable()8123f4a2713aSLionel Sambuc IdentifierTable &ASTReader::getIdentifierTable() {
8124f4a2713aSLionel Sambuc   return PP.getIdentifierTable();
8125f4a2713aSLionel Sambuc }
8126f4a2713aSLionel Sambuc 
8127f4a2713aSLionel Sambuc /// \brief Record that the given ID maps to the given switch-case
8128f4a2713aSLionel Sambuc /// statement.
RecordSwitchCaseID(SwitchCase * SC,unsigned ID)8129f4a2713aSLionel Sambuc void ASTReader::RecordSwitchCaseID(SwitchCase *SC, unsigned ID) {
8130*0a6a1f1dSLionel Sambuc   assert((*CurrSwitchCaseStmts)[ID] == nullptr &&
8131f4a2713aSLionel Sambuc          "Already have a SwitchCase with this ID");
8132f4a2713aSLionel Sambuc   (*CurrSwitchCaseStmts)[ID] = SC;
8133f4a2713aSLionel Sambuc }
8134f4a2713aSLionel Sambuc 
8135f4a2713aSLionel Sambuc /// \brief Retrieve the switch-case statement with the given ID.
getSwitchCaseWithID(unsigned ID)8136f4a2713aSLionel Sambuc SwitchCase *ASTReader::getSwitchCaseWithID(unsigned ID) {
8137*0a6a1f1dSLionel Sambuc   assert((*CurrSwitchCaseStmts)[ID] != nullptr && "No SwitchCase with this ID");
8138f4a2713aSLionel Sambuc   return (*CurrSwitchCaseStmts)[ID];
8139f4a2713aSLionel Sambuc }
8140f4a2713aSLionel Sambuc 
ClearSwitchCaseIDs()8141f4a2713aSLionel Sambuc void ASTReader::ClearSwitchCaseIDs() {
8142f4a2713aSLionel Sambuc   CurrSwitchCaseStmts->clear();
8143f4a2713aSLionel Sambuc }
8144f4a2713aSLionel Sambuc 
ReadComments()8145f4a2713aSLionel Sambuc void ASTReader::ReadComments() {
8146f4a2713aSLionel Sambuc   std::vector<RawComment *> Comments;
8147f4a2713aSLionel Sambuc   for (SmallVectorImpl<std::pair<BitstreamCursor,
8148f4a2713aSLionel Sambuc                                  serialization::ModuleFile *> >::iterator
8149f4a2713aSLionel Sambuc        I = CommentsCursors.begin(),
8150f4a2713aSLionel Sambuc        E = CommentsCursors.end();
8151f4a2713aSLionel Sambuc        I != E; ++I) {
8152*0a6a1f1dSLionel Sambuc     Comments.clear();
8153f4a2713aSLionel Sambuc     BitstreamCursor &Cursor = I->first;
8154f4a2713aSLionel Sambuc     serialization::ModuleFile &F = *I->second;
8155f4a2713aSLionel Sambuc     SavedStreamPosition SavedPosition(Cursor);
8156f4a2713aSLionel Sambuc 
8157f4a2713aSLionel Sambuc     RecordData Record;
8158f4a2713aSLionel Sambuc     while (true) {
8159f4a2713aSLionel Sambuc       llvm::BitstreamEntry Entry =
8160f4a2713aSLionel Sambuc         Cursor.advanceSkippingSubblocks(BitstreamCursor::AF_DontPopBlockAtEnd);
8161f4a2713aSLionel Sambuc 
8162f4a2713aSLionel Sambuc       switch (Entry.Kind) {
8163f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::SubBlock: // Handled for us already.
8164f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::Error:
8165f4a2713aSLionel Sambuc         Error("malformed block record in AST file");
8166f4a2713aSLionel Sambuc         return;
8167f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::EndBlock:
8168f4a2713aSLionel Sambuc         goto NextCursor;
8169f4a2713aSLionel Sambuc       case llvm::BitstreamEntry::Record:
8170f4a2713aSLionel Sambuc         // The interesting case.
8171f4a2713aSLionel Sambuc         break;
8172f4a2713aSLionel Sambuc       }
8173f4a2713aSLionel Sambuc 
8174f4a2713aSLionel Sambuc       // Read a record.
8175f4a2713aSLionel Sambuc       Record.clear();
8176f4a2713aSLionel Sambuc       switch ((CommentRecordTypes)Cursor.readRecord(Entry.ID, Record)) {
8177f4a2713aSLionel Sambuc       case COMMENTS_RAW_COMMENT: {
8178f4a2713aSLionel Sambuc         unsigned Idx = 0;
8179f4a2713aSLionel Sambuc         SourceRange SR = ReadSourceRange(F, Record, Idx);
8180f4a2713aSLionel Sambuc         RawComment::CommentKind Kind =
8181f4a2713aSLionel Sambuc             (RawComment::CommentKind) Record[Idx++];
8182f4a2713aSLionel Sambuc         bool IsTrailingComment = Record[Idx++];
8183f4a2713aSLionel Sambuc         bool IsAlmostTrailingComment = Record[Idx++];
8184f4a2713aSLionel Sambuc         Comments.push_back(new (Context) RawComment(
8185f4a2713aSLionel Sambuc             SR, Kind, IsTrailingComment, IsAlmostTrailingComment,
8186f4a2713aSLionel Sambuc             Context.getLangOpts().CommentOpts.ParseAllComments));
8187f4a2713aSLionel Sambuc         break;
8188f4a2713aSLionel Sambuc       }
8189f4a2713aSLionel Sambuc       }
8190f4a2713aSLionel Sambuc     }
8191*0a6a1f1dSLionel Sambuc   NextCursor:
8192*0a6a1f1dSLionel Sambuc     Context.Comments.addDeserializedComments(Comments);
8193f4a2713aSLionel Sambuc   }
8194*0a6a1f1dSLionel Sambuc }
8195*0a6a1f1dSLionel Sambuc 
getInputFiles(ModuleFile & F,SmallVectorImpl<serialization::InputFile> & Files)8196*0a6a1f1dSLionel Sambuc void ASTReader::getInputFiles(ModuleFile &F,
8197*0a6a1f1dSLionel Sambuc                              SmallVectorImpl<serialization::InputFile> &Files) {
8198*0a6a1f1dSLionel Sambuc   for (unsigned I = 0, E = F.InputFilesLoaded.size(); I != E; ++I) {
8199*0a6a1f1dSLionel Sambuc     unsigned ID = I+1;
8200*0a6a1f1dSLionel Sambuc     Files.push_back(getInputFile(F, ID));
8201*0a6a1f1dSLionel Sambuc   }
8202*0a6a1f1dSLionel Sambuc }
8203*0a6a1f1dSLionel Sambuc 
getOwningModuleNameForDiagnostic(const Decl * D)8204*0a6a1f1dSLionel Sambuc std::string ASTReader::getOwningModuleNameForDiagnostic(const Decl *D) {
8205*0a6a1f1dSLionel Sambuc   // If we know the owning module, use it.
8206*0a6a1f1dSLionel Sambuc   if (Module *M = D->getOwningModule())
8207*0a6a1f1dSLionel Sambuc     return M->getFullModuleName();
8208*0a6a1f1dSLionel Sambuc 
8209*0a6a1f1dSLionel Sambuc   // Otherwise, use the name of the top-level module the decl is within.
8210*0a6a1f1dSLionel Sambuc   if (ModuleFile *M = getOwningModuleFile(D))
8211*0a6a1f1dSLionel Sambuc     return M->ModuleName;
8212*0a6a1f1dSLionel Sambuc 
8213*0a6a1f1dSLionel Sambuc   // Not from a module.
8214*0a6a1f1dSLionel Sambuc   return "";
8215f4a2713aSLionel Sambuc }
8216f4a2713aSLionel Sambuc 
finishPendingActions()8217f4a2713aSLionel Sambuc void ASTReader::finishPendingActions() {
8218*0a6a1f1dSLionel Sambuc   while (!PendingIdentifierInfos.empty() ||
8219*0a6a1f1dSLionel Sambuc          !PendingIncompleteDeclChains.empty() || !PendingDeclChains.empty() ||
8220f4a2713aSLionel Sambuc          !PendingMacroIDs.empty() || !PendingDeclContextInfos.empty() ||
8221*0a6a1f1dSLionel Sambuc          !PendingUpdateRecords.empty()) {
8222f4a2713aSLionel Sambuc     // If any identifiers with corresponding top-level declarations have
8223f4a2713aSLionel Sambuc     // been loaded, load those declarations now.
8224f4a2713aSLionel Sambuc     typedef llvm::DenseMap<IdentifierInfo *, SmallVector<Decl *, 2> >
8225f4a2713aSLionel Sambuc       TopLevelDeclsMap;
8226f4a2713aSLionel Sambuc     TopLevelDeclsMap TopLevelDecls;
8227f4a2713aSLionel Sambuc 
8228f4a2713aSLionel Sambuc     while (!PendingIdentifierInfos.empty()) {
8229f4a2713aSLionel Sambuc       IdentifierInfo *II = PendingIdentifierInfos.back().first;
8230*0a6a1f1dSLionel Sambuc       SmallVector<uint32_t, 4> DeclIDs =
8231*0a6a1f1dSLionel Sambuc           std::move(PendingIdentifierInfos.back().second);
8232f4a2713aSLionel Sambuc       PendingIdentifierInfos.pop_back();
8233f4a2713aSLionel Sambuc 
8234f4a2713aSLionel Sambuc       SetGloballyVisibleDecls(II, DeclIDs, &TopLevelDecls[II]);
8235f4a2713aSLionel Sambuc     }
8236f4a2713aSLionel Sambuc 
8237*0a6a1f1dSLionel Sambuc     // For each decl chain that we wanted to complete while deserializing, mark
8238*0a6a1f1dSLionel Sambuc     // it as "still needs to be completed".
8239*0a6a1f1dSLionel Sambuc     for (unsigned I = 0; I != PendingIncompleteDeclChains.size(); ++I) {
8240*0a6a1f1dSLionel Sambuc       markIncompleteDeclChain(PendingIncompleteDeclChains[I]);
8241*0a6a1f1dSLionel Sambuc     }
8242*0a6a1f1dSLionel Sambuc     PendingIncompleteDeclChains.clear();
8243*0a6a1f1dSLionel Sambuc 
8244f4a2713aSLionel Sambuc     // Load pending declaration chains.
8245f4a2713aSLionel Sambuc     for (unsigned I = 0; I != PendingDeclChains.size(); ++I) {
8246f4a2713aSLionel Sambuc       loadPendingDeclChain(PendingDeclChains[I]);
8247f4a2713aSLionel Sambuc       PendingDeclChainsKnown.erase(PendingDeclChains[I]);
8248f4a2713aSLionel Sambuc     }
8249f4a2713aSLionel Sambuc     PendingDeclChains.clear();
8250f4a2713aSLionel Sambuc 
8251f4a2713aSLionel Sambuc     // Make the most recent of the top-level declarations visible.
8252f4a2713aSLionel Sambuc     for (TopLevelDeclsMap::iterator TLD = TopLevelDecls.begin(),
8253f4a2713aSLionel Sambuc            TLDEnd = TopLevelDecls.end(); TLD != TLDEnd; ++TLD) {
8254f4a2713aSLionel Sambuc       IdentifierInfo *II = TLD->first;
8255f4a2713aSLionel Sambuc       for (unsigned I = 0, N = TLD->second.size(); I != N; ++I) {
8256f4a2713aSLionel Sambuc         pushExternalDeclIntoScope(cast<NamedDecl>(TLD->second[I]), II);
8257f4a2713aSLionel Sambuc       }
8258f4a2713aSLionel Sambuc     }
8259f4a2713aSLionel Sambuc 
8260f4a2713aSLionel Sambuc     // Load any pending macro definitions.
8261f4a2713aSLionel Sambuc     for (unsigned I = 0; I != PendingMacroIDs.size(); ++I) {
8262f4a2713aSLionel Sambuc       IdentifierInfo *II = PendingMacroIDs.begin()[I].first;
8263f4a2713aSLionel Sambuc       SmallVector<PendingMacroInfo, 2> GlobalIDs;
8264f4a2713aSLionel Sambuc       GlobalIDs.swap(PendingMacroIDs.begin()[I].second);
8265f4a2713aSLionel Sambuc       // Initialize the macro history from chained-PCHs ahead of module imports.
8266f4a2713aSLionel Sambuc       for (unsigned IDIdx = 0, NumIDs = GlobalIDs.size(); IDIdx != NumIDs;
8267f4a2713aSLionel Sambuc            ++IDIdx) {
8268f4a2713aSLionel Sambuc         const PendingMacroInfo &Info = GlobalIDs[IDIdx];
8269*0a6a1f1dSLionel Sambuc         if (Info.M->Kind != MK_ImplicitModule &&
8270*0a6a1f1dSLionel Sambuc             Info.M->Kind != MK_ExplicitModule)
8271f4a2713aSLionel Sambuc           resolvePendingMacro(II, Info);
8272f4a2713aSLionel Sambuc       }
8273f4a2713aSLionel Sambuc       // Handle module imports.
8274f4a2713aSLionel Sambuc       for (unsigned IDIdx = 0, NumIDs = GlobalIDs.size(); IDIdx != NumIDs;
8275f4a2713aSLionel Sambuc            ++IDIdx) {
8276f4a2713aSLionel Sambuc         const PendingMacroInfo &Info = GlobalIDs[IDIdx];
8277*0a6a1f1dSLionel Sambuc         if (Info.M->Kind == MK_ImplicitModule ||
8278*0a6a1f1dSLionel Sambuc             Info.M->Kind == MK_ExplicitModule)
8279f4a2713aSLionel Sambuc           resolvePendingMacro(II, Info);
8280f4a2713aSLionel Sambuc       }
8281f4a2713aSLionel Sambuc     }
8282f4a2713aSLionel Sambuc     PendingMacroIDs.clear();
8283f4a2713aSLionel Sambuc 
8284f4a2713aSLionel Sambuc     // Wire up the DeclContexts for Decls that we delayed setting until
8285f4a2713aSLionel Sambuc     // recursive loading is completed.
8286f4a2713aSLionel Sambuc     while (!PendingDeclContextInfos.empty()) {
8287f4a2713aSLionel Sambuc       PendingDeclContextInfo Info = PendingDeclContextInfos.front();
8288f4a2713aSLionel Sambuc       PendingDeclContextInfos.pop_front();
8289f4a2713aSLionel Sambuc       DeclContext *SemaDC = cast<DeclContext>(GetDecl(Info.SemaDC));
8290f4a2713aSLionel Sambuc       DeclContext *LexicalDC = cast<DeclContext>(GetDecl(Info.LexicalDC));
8291f4a2713aSLionel Sambuc       Info.D->setDeclContextsImpl(SemaDC, LexicalDC, getContext());
8292f4a2713aSLionel Sambuc     }
8293f4a2713aSLionel Sambuc 
8294*0a6a1f1dSLionel Sambuc     // Perform any pending declaration updates.
8295*0a6a1f1dSLionel Sambuc     while (!PendingUpdateRecords.empty()) {
8296*0a6a1f1dSLionel Sambuc       auto Update = PendingUpdateRecords.pop_back_val();
8297*0a6a1f1dSLionel Sambuc       ReadingKindTracker ReadingKind(Read_Decl, *this);
8298*0a6a1f1dSLionel Sambuc       loadDeclUpdateRecords(Update.first, Update.second);
8299f4a2713aSLionel Sambuc     }
8300f4a2713aSLionel Sambuc   }
8301f4a2713aSLionel Sambuc 
8302f4a2713aSLionel Sambuc   // If we deserialized any C++ or Objective-C class definitions, any
8303f4a2713aSLionel Sambuc   // Objective-C protocol definitions, or any redeclarable templates, make sure
8304f4a2713aSLionel Sambuc   // that all redeclarations point to the definitions. Note that this can only
8305f4a2713aSLionel Sambuc   // happen now, after the redeclaration chains have been fully wired.
8306*0a6a1f1dSLionel Sambuc   for (Decl *D : PendingDefinitions) {
8307*0a6a1f1dSLionel Sambuc     if (TagDecl *TD = dyn_cast<TagDecl>(D)) {
8308*0a6a1f1dSLionel Sambuc       if (const TagType *TagT = dyn_cast<TagType>(TD->getTypeForDecl())) {
8309f4a2713aSLionel Sambuc         // Make sure that the TagType points at the definition.
8310f4a2713aSLionel Sambuc         const_cast<TagType*>(TagT)->decl = TD;
8311f4a2713aSLionel Sambuc       }
8312f4a2713aSLionel Sambuc 
8313*0a6a1f1dSLionel Sambuc       if (auto RD = dyn_cast<CXXRecordDecl>(D)) {
8314*0a6a1f1dSLionel Sambuc         for (auto R : RD->redecls()) {
8315*0a6a1f1dSLionel Sambuc           assert((R == D) == R->isThisDeclarationADefinition() &&
8316*0a6a1f1dSLionel Sambuc                  "declaration thinks it's the definition but it isn't");
8317*0a6a1f1dSLionel Sambuc           cast<CXXRecordDecl>(R)->DefinitionData = RD->DefinitionData;
8318*0a6a1f1dSLionel Sambuc         }
8319f4a2713aSLionel Sambuc       }
8320f4a2713aSLionel Sambuc 
8321f4a2713aSLionel Sambuc       continue;
8322f4a2713aSLionel Sambuc     }
8323f4a2713aSLionel Sambuc 
8324*0a6a1f1dSLionel Sambuc     if (auto ID = dyn_cast<ObjCInterfaceDecl>(D)) {
8325f4a2713aSLionel Sambuc       // Make sure that the ObjCInterfaceType points at the definition.
8326f4a2713aSLionel Sambuc       const_cast<ObjCInterfaceType *>(cast<ObjCInterfaceType>(ID->TypeForDecl))
8327f4a2713aSLionel Sambuc         ->Decl = ID;
8328f4a2713aSLionel Sambuc 
8329*0a6a1f1dSLionel Sambuc       for (auto R : ID->redecls())
8330f4a2713aSLionel Sambuc         R->Data = ID->Data;
8331f4a2713aSLionel Sambuc 
8332f4a2713aSLionel Sambuc       continue;
8333f4a2713aSLionel Sambuc     }
8334f4a2713aSLionel Sambuc 
8335*0a6a1f1dSLionel Sambuc     if (auto PD = dyn_cast<ObjCProtocolDecl>(D)) {
8336*0a6a1f1dSLionel Sambuc       for (auto R : PD->redecls())
8337f4a2713aSLionel Sambuc         R->Data = PD->Data;
8338f4a2713aSLionel Sambuc 
8339f4a2713aSLionel Sambuc       continue;
8340f4a2713aSLionel Sambuc     }
8341f4a2713aSLionel Sambuc 
8342*0a6a1f1dSLionel Sambuc     auto RTD = cast<RedeclarableTemplateDecl>(D)->getCanonicalDecl();
8343*0a6a1f1dSLionel Sambuc     for (auto R : RTD->redecls())
8344f4a2713aSLionel Sambuc       R->Common = RTD->Common;
8345f4a2713aSLionel Sambuc   }
8346f4a2713aSLionel Sambuc   PendingDefinitions.clear();
8347f4a2713aSLionel Sambuc 
8348f4a2713aSLionel Sambuc   // Load the bodies of any functions or methods we've encountered. We do
8349f4a2713aSLionel Sambuc   // this now (delayed) so that we can be sure that the declaration chains
8350f4a2713aSLionel Sambuc   // have been fully wired up.
8351f4a2713aSLionel Sambuc   for (PendingBodiesMap::iterator PB = PendingBodies.begin(),
8352f4a2713aSLionel Sambuc                                PBEnd = PendingBodies.end();
8353f4a2713aSLionel Sambuc        PB != PBEnd; ++PB) {
8354f4a2713aSLionel Sambuc     if (FunctionDecl *FD = dyn_cast<FunctionDecl>(PB->first)) {
8355f4a2713aSLionel Sambuc       // FIXME: Check for =delete/=default?
8356f4a2713aSLionel Sambuc       // FIXME: Complain about ODR violations here?
8357f4a2713aSLionel Sambuc       if (!getContext().getLangOpts().Modules || !FD->hasBody())
8358f4a2713aSLionel Sambuc         FD->setLazyBody(PB->second);
8359f4a2713aSLionel Sambuc       continue;
8360f4a2713aSLionel Sambuc     }
8361f4a2713aSLionel Sambuc 
8362f4a2713aSLionel Sambuc     ObjCMethodDecl *MD = cast<ObjCMethodDecl>(PB->first);
8363f4a2713aSLionel Sambuc     if (!getContext().getLangOpts().Modules || !MD->hasBody())
8364f4a2713aSLionel Sambuc       MD->setLazyBody(PB->second);
8365f4a2713aSLionel Sambuc   }
8366f4a2713aSLionel Sambuc   PendingBodies.clear();
8367f4a2713aSLionel Sambuc }
8368f4a2713aSLionel Sambuc 
diagnoseOdrViolations()8369*0a6a1f1dSLionel Sambuc void ASTReader::diagnoseOdrViolations() {
8370*0a6a1f1dSLionel Sambuc   if (PendingOdrMergeFailures.empty() && PendingOdrMergeChecks.empty())
8371*0a6a1f1dSLionel Sambuc     return;
8372*0a6a1f1dSLionel Sambuc 
8373*0a6a1f1dSLionel Sambuc   // Trigger the import of the full definition of each class that had any
8374*0a6a1f1dSLionel Sambuc   // odr-merging problems, so we can produce better diagnostics for them.
8375*0a6a1f1dSLionel Sambuc   // These updates may in turn find and diagnose some ODR failures, so take
8376*0a6a1f1dSLionel Sambuc   // ownership of the set first.
8377*0a6a1f1dSLionel Sambuc   auto OdrMergeFailures = std::move(PendingOdrMergeFailures);
8378*0a6a1f1dSLionel Sambuc   PendingOdrMergeFailures.clear();
8379*0a6a1f1dSLionel Sambuc   for (auto &Merge : OdrMergeFailures) {
8380*0a6a1f1dSLionel Sambuc     Merge.first->buildLookup();
8381*0a6a1f1dSLionel Sambuc     Merge.first->decls_begin();
8382*0a6a1f1dSLionel Sambuc     Merge.first->bases_begin();
8383*0a6a1f1dSLionel Sambuc     Merge.first->vbases_begin();
8384*0a6a1f1dSLionel Sambuc     for (auto *RD : Merge.second) {
8385*0a6a1f1dSLionel Sambuc       RD->decls_begin();
8386*0a6a1f1dSLionel Sambuc       RD->bases_begin();
8387*0a6a1f1dSLionel Sambuc       RD->vbases_begin();
8388*0a6a1f1dSLionel Sambuc     }
8389*0a6a1f1dSLionel Sambuc   }
8390*0a6a1f1dSLionel Sambuc 
8391*0a6a1f1dSLionel Sambuc   // For each declaration from a merged context, check that the canonical
8392*0a6a1f1dSLionel Sambuc   // definition of that context also contains a declaration of the same
8393*0a6a1f1dSLionel Sambuc   // entity.
8394*0a6a1f1dSLionel Sambuc   //
8395*0a6a1f1dSLionel Sambuc   // Caution: this loop does things that might invalidate iterators into
8396*0a6a1f1dSLionel Sambuc   // PendingOdrMergeChecks. Don't turn this into a range-based for loop!
8397*0a6a1f1dSLionel Sambuc   while (!PendingOdrMergeChecks.empty()) {
8398*0a6a1f1dSLionel Sambuc     NamedDecl *D = PendingOdrMergeChecks.pop_back_val();
8399*0a6a1f1dSLionel Sambuc 
8400*0a6a1f1dSLionel Sambuc     // FIXME: Skip over implicit declarations for now. This matters for things
8401*0a6a1f1dSLionel Sambuc     // like implicitly-declared special member functions. This isn't entirely
8402*0a6a1f1dSLionel Sambuc     // correct; we can end up with multiple unmerged declarations of the same
8403*0a6a1f1dSLionel Sambuc     // implicit entity.
8404*0a6a1f1dSLionel Sambuc     if (D->isImplicit())
8405*0a6a1f1dSLionel Sambuc       continue;
8406*0a6a1f1dSLionel Sambuc 
8407*0a6a1f1dSLionel Sambuc     DeclContext *CanonDef = D->getDeclContext();
8408*0a6a1f1dSLionel Sambuc 
8409*0a6a1f1dSLionel Sambuc     bool Found = false;
8410*0a6a1f1dSLionel Sambuc     const Decl *DCanon = D->getCanonicalDecl();
8411*0a6a1f1dSLionel Sambuc 
8412*0a6a1f1dSLionel Sambuc     for (auto RI : D->redecls()) {
8413*0a6a1f1dSLionel Sambuc       if (RI->getLexicalDeclContext() == CanonDef) {
8414*0a6a1f1dSLionel Sambuc         Found = true;
8415*0a6a1f1dSLionel Sambuc         break;
8416*0a6a1f1dSLionel Sambuc       }
8417*0a6a1f1dSLionel Sambuc     }
8418*0a6a1f1dSLionel Sambuc     if (Found)
8419*0a6a1f1dSLionel Sambuc       continue;
8420*0a6a1f1dSLionel Sambuc 
8421*0a6a1f1dSLionel Sambuc     llvm::SmallVector<const NamedDecl*, 4> Candidates;
8422*0a6a1f1dSLionel Sambuc     DeclContext::lookup_result R = CanonDef->lookup(D->getDeclName());
8423*0a6a1f1dSLionel Sambuc     for (DeclContext::lookup_iterator I = R.begin(), E = R.end();
8424*0a6a1f1dSLionel Sambuc          !Found && I != E; ++I) {
8425*0a6a1f1dSLionel Sambuc       for (auto RI : (*I)->redecls()) {
8426*0a6a1f1dSLionel Sambuc         if (RI->getLexicalDeclContext() == CanonDef) {
8427*0a6a1f1dSLionel Sambuc           // This declaration is present in the canonical definition. If it's
8428*0a6a1f1dSLionel Sambuc           // in the same redecl chain, it's the one we're looking for.
8429*0a6a1f1dSLionel Sambuc           if (RI->getCanonicalDecl() == DCanon)
8430*0a6a1f1dSLionel Sambuc             Found = true;
8431*0a6a1f1dSLionel Sambuc           else
8432*0a6a1f1dSLionel Sambuc             Candidates.push_back(cast<NamedDecl>(RI));
8433*0a6a1f1dSLionel Sambuc           break;
8434*0a6a1f1dSLionel Sambuc         }
8435*0a6a1f1dSLionel Sambuc       }
8436*0a6a1f1dSLionel Sambuc     }
8437*0a6a1f1dSLionel Sambuc 
8438*0a6a1f1dSLionel Sambuc     if (!Found) {
8439*0a6a1f1dSLionel Sambuc       // The AST doesn't like TagDecls becoming invalid after they've been
8440*0a6a1f1dSLionel Sambuc       // completed. We only really need to mark FieldDecls as invalid here.
8441*0a6a1f1dSLionel Sambuc       if (!isa<TagDecl>(D))
8442*0a6a1f1dSLionel Sambuc         D->setInvalidDecl();
8443*0a6a1f1dSLionel Sambuc 
8444*0a6a1f1dSLionel Sambuc       std::string CanonDefModule =
8445*0a6a1f1dSLionel Sambuc           getOwningModuleNameForDiagnostic(cast<Decl>(CanonDef));
8446*0a6a1f1dSLionel Sambuc       Diag(D->getLocation(), diag::err_module_odr_violation_missing_decl)
8447*0a6a1f1dSLionel Sambuc         << D << getOwningModuleNameForDiagnostic(D)
8448*0a6a1f1dSLionel Sambuc         << CanonDef << CanonDefModule.empty() << CanonDefModule;
8449*0a6a1f1dSLionel Sambuc 
8450*0a6a1f1dSLionel Sambuc       if (Candidates.empty())
8451*0a6a1f1dSLionel Sambuc         Diag(cast<Decl>(CanonDef)->getLocation(),
8452*0a6a1f1dSLionel Sambuc              diag::note_module_odr_violation_no_possible_decls) << D;
8453*0a6a1f1dSLionel Sambuc       else {
8454*0a6a1f1dSLionel Sambuc         for (unsigned I = 0, N = Candidates.size(); I != N; ++I)
8455*0a6a1f1dSLionel Sambuc           Diag(Candidates[I]->getLocation(),
8456*0a6a1f1dSLionel Sambuc                diag::note_module_odr_violation_possible_decl)
8457*0a6a1f1dSLionel Sambuc             << Candidates[I];
8458*0a6a1f1dSLionel Sambuc       }
8459*0a6a1f1dSLionel Sambuc 
8460*0a6a1f1dSLionel Sambuc       DiagnosedOdrMergeFailures.insert(CanonDef);
8461*0a6a1f1dSLionel Sambuc     }
8462*0a6a1f1dSLionel Sambuc   }
8463*0a6a1f1dSLionel Sambuc 
8464*0a6a1f1dSLionel Sambuc   // Issue any pending ODR-failure diagnostics.
8465*0a6a1f1dSLionel Sambuc   for (auto &Merge : OdrMergeFailures) {
8466*0a6a1f1dSLionel Sambuc     // If we've already pointed out a specific problem with this class, don't
8467*0a6a1f1dSLionel Sambuc     // bother issuing a general "something's different" diagnostic.
8468*0a6a1f1dSLionel Sambuc     if (!DiagnosedOdrMergeFailures.insert(Merge.first).second)
8469*0a6a1f1dSLionel Sambuc       continue;
8470*0a6a1f1dSLionel Sambuc 
8471*0a6a1f1dSLionel Sambuc     bool Diagnosed = false;
8472*0a6a1f1dSLionel Sambuc     for (auto *RD : Merge.second) {
8473*0a6a1f1dSLionel Sambuc       // Multiple different declarations got merged together; tell the user
8474*0a6a1f1dSLionel Sambuc       // where they came from.
8475*0a6a1f1dSLionel Sambuc       if (Merge.first != RD) {
8476*0a6a1f1dSLionel Sambuc         // FIXME: Walk the definition, figure out what's different,
8477*0a6a1f1dSLionel Sambuc         // and diagnose that.
8478*0a6a1f1dSLionel Sambuc         if (!Diagnosed) {
8479*0a6a1f1dSLionel Sambuc           std::string Module = getOwningModuleNameForDiagnostic(Merge.first);
8480*0a6a1f1dSLionel Sambuc           Diag(Merge.first->getLocation(),
8481*0a6a1f1dSLionel Sambuc                diag::err_module_odr_violation_different_definitions)
8482*0a6a1f1dSLionel Sambuc             << Merge.first << Module.empty() << Module;
8483*0a6a1f1dSLionel Sambuc           Diagnosed = true;
8484*0a6a1f1dSLionel Sambuc         }
8485*0a6a1f1dSLionel Sambuc 
8486*0a6a1f1dSLionel Sambuc         Diag(RD->getLocation(),
8487*0a6a1f1dSLionel Sambuc              diag::note_module_odr_violation_different_definitions)
8488*0a6a1f1dSLionel Sambuc           << getOwningModuleNameForDiagnostic(RD);
8489*0a6a1f1dSLionel Sambuc       }
8490*0a6a1f1dSLionel Sambuc     }
8491*0a6a1f1dSLionel Sambuc 
8492*0a6a1f1dSLionel Sambuc     if (!Diagnosed) {
8493*0a6a1f1dSLionel Sambuc       // All definitions are updates to the same declaration. This happens if a
8494*0a6a1f1dSLionel Sambuc       // module instantiates the declaration of a class template specialization
8495*0a6a1f1dSLionel Sambuc       // and two or more other modules instantiate its definition.
8496*0a6a1f1dSLionel Sambuc       //
8497*0a6a1f1dSLionel Sambuc       // FIXME: Indicate which modules had instantiations of this definition.
8498*0a6a1f1dSLionel Sambuc       // FIXME: How can this even happen?
8499*0a6a1f1dSLionel Sambuc       Diag(Merge.first->getLocation(),
8500*0a6a1f1dSLionel Sambuc            diag::err_module_odr_violation_different_instantiations)
8501*0a6a1f1dSLionel Sambuc         << Merge.first;
8502*0a6a1f1dSLionel Sambuc     }
8503*0a6a1f1dSLionel Sambuc   }
8504*0a6a1f1dSLionel Sambuc }
8505*0a6a1f1dSLionel Sambuc 
FinishedDeserializing()8506f4a2713aSLionel Sambuc void ASTReader::FinishedDeserializing() {
8507f4a2713aSLionel Sambuc   assert(NumCurrentElementsDeserializing &&
8508f4a2713aSLionel Sambuc          "FinishedDeserializing not paired with StartedDeserializing");
8509f4a2713aSLionel Sambuc   if (NumCurrentElementsDeserializing == 1) {
8510f4a2713aSLionel Sambuc     // We decrease NumCurrentElementsDeserializing only after pending actions
8511f4a2713aSLionel Sambuc     // are finished, to avoid recursively re-calling finishPendingActions().
8512f4a2713aSLionel Sambuc     finishPendingActions();
8513f4a2713aSLionel Sambuc   }
8514f4a2713aSLionel Sambuc   --NumCurrentElementsDeserializing;
8515f4a2713aSLionel Sambuc 
8516*0a6a1f1dSLionel Sambuc   if (NumCurrentElementsDeserializing == 0) {
8517*0a6a1f1dSLionel Sambuc     diagnoseOdrViolations();
8518f4a2713aSLionel Sambuc 
8519f4a2713aSLionel Sambuc     // We are not in recursive loading, so it's safe to pass the "interesting"
8520f4a2713aSLionel Sambuc     // decls to the consumer.
8521*0a6a1f1dSLionel Sambuc     if (Consumer)
8522*0a6a1f1dSLionel Sambuc       PassInterestingDeclsToConsumer();
8523f4a2713aSLionel Sambuc   }
8524f4a2713aSLionel Sambuc }
8525f4a2713aSLionel Sambuc 
pushExternalDeclIntoScope(NamedDecl * D,DeclarationName Name)8526f4a2713aSLionel Sambuc void ASTReader::pushExternalDeclIntoScope(NamedDecl *D, DeclarationName Name) {
8527f4a2713aSLionel Sambuc   D = D->getMostRecentDecl();
8528f4a2713aSLionel Sambuc 
8529f4a2713aSLionel Sambuc   if (SemaObj->IdResolver.tryAddTopLevelDecl(D, Name) && SemaObj->TUScope) {
8530f4a2713aSLionel Sambuc     SemaObj->TUScope->AddDecl(D);
8531f4a2713aSLionel Sambuc   } else if (SemaObj->TUScope) {
8532f4a2713aSLionel Sambuc     // Adding the decl to IdResolver may have failed because it was already in
8533f4a2713aSLionel Sambuc     // (even though it was not added in scope). If it is already in, make sure
8534f4a2713aSLionel Sambuc     // it gets in the scope as well.
8535f4a2713aSLionel Sambuc     if (std::find(SemaObj->IdResolver.begin(Name),
8536f4a2713aSLionel Sambuc                   SemaObj->IdResolver.end(), D) != SemaObj->IdResolver.end())
8537f4a2713aSLionel Sambuc       SemaObj->TUScope->AddDecl(D);
8538f4a2713aSLionel Sambuc   }
8539f4a2713aSLionel Sambuc }
8540f4a2713aSLionel Sambuc 
ASTReader(Preprocessor & PP,ASTContext & Context,StringRef isysroot,bool DisableValidation,bool AllowASTWithCompilerErrors,bool AllowConfigurationMismatch,bool ValidateSystemInputs,bool UseGlobalIndex)8541*0a6a1f1dSLionel Sambuc ASTReader::ASTReader(Preprocessor &PP, ASTContext &Context, StringRef isysroot,
8542*0a6a1f1dSLionel Sambuc                      bool DisableValidation, bool AllowASTWithCompilerErrors,
8543*0a6a1f1dSLionel Sambuc                      bool AllowConfigurationMismatch, bool ValidateSystemInputs,
8544*0a6a1f1dSLionel Sambuc                      bool UseGlobalIndex)
8545*0a6a1f1dSLionel Sambuc     : Listener(new PCHValidator(PP, *this)), DeserializationListener(nullptr),
8546*0a6a1f1dSLionel Sambuc       OwnsDeserializationListener(false), SourceMgr(PP.getSourceManager()),
8547*0a6a1f1dSLionel Sambuc       FileMgr(PP.getFileManager()), Diags(PP.getDiagnostics()),
8548*0a6a1f1dSLionel Sambuc       SemaObj(nullptr), PP(PP), Context(Context), Consumer(nullptr),
8549*0a6a1f1dSLionel Sambuc       ModuleMgr(PP.getFileManager()), isysroot(isysroot),
8550*0a6a1f1dSLionel Sambuc       DisableValidation(DisableValidation),
8551f4a2713aSLionel Sambuc       AllowASTWithCompilerErrors(AllowASTWithCompilerErrors),
8552*0a6a1f1dSLionel Sambuc       AllowConfigurationMismatch(AllowConfigurationMismatch),
8553*0a6a1f1dSLionel Sambuc       ValidateSystemInputs(ValidateSystemInputs),
8554f4a2713aSLionel Sambuc       UseGlobalIndex(UseGlobalIndex), TriedLoadingGlobalIndex(false),
8555*0a6a1f1dSLionel Sambuc       CurrSwitchCaseStmts(&SwitchCaseStmts),
8556*0a6a1f1dSLionel Sambuc       NumSLocEntriesRead(0), TotalNumSLocEntries(0), NumStatementsRead(0),
8557*0a6a1f1dSLionel Sambuc       TotalNumStatements(0), NumMacrosRead(0), TotalNumMacros(0),
8558*0a6a1f1dSLionel Sambuc       NumIdentifierLookups(0), NumIdentifierLookupHits(0), NumSelectorsRead(0),
8559*0a6a1f1dSLionel Sambuc       NumMethodPoolEntriesRead(0), NumMethodPoolLookups(0),
8560*0a6a1f1dSLionel Sambuc       NumMethodPoolHits(0), NumMethodPoolTableLookups(0),
8561*0a6a1f1dSLionel Sambuc       NumMethodPoolTableHits(0), TotalNumMethodPoolEntries(0),
8562f4a2713aSLionel Sambuc       NumLexicalDeclContextsRead(0), TotalLexicalDeclContexts(0),
8563f4a2713aSLionel Sambuc       NumVisibleDeclContextsRead(0), TotalVisibleDeclContexts(0),
8564f4a2713aSLionel Sambuc       TotalModulesSizeInBits(0), NumCurrentElementsDeserializing(0),
8565*0a6a1f1dSLionel Sambuc       PassingDeclsToConsumer(false), NumCXXBaseSpecifiersLoaded(0),
8566*0a6a1f1dSLionel Sambuc       ReadingKind(Read_None) {
8567f4a2713aSLionel Sambuc   SourceMgr.setExternalSLocEntrySource(this);
8568f4a2713aSLionel Sambuc }
8569f4a2713aSLionel Sambuc 
~ASTReader()8570f4a2713aSLionel Sambuc ASTReader::~ASTReader() {
8571*0a6a1f1dSLionel Sambuc   if (OwnsDeserializationListener)
8572*0a6a1f1dSLionel Sambuc     delete DeserializationListener;
8573*0a6a1f1dSLionel Sambuc 
8574f4a2713aSLionel Sambuc   for (DeclContextVisibleUpdatesPending::iterator
8575f4a2713aSLionel Sambuc            I = PendingVisibleUpdates.begin(),
8576f4a2713aSLionel Sambuc            E = PendingVisibleUpdates.end();
8577f4a2713aSLionel Sambuc        I != E; ++I) {
8578f4a2713aSLionel Sambuc     for (DeclContextVisibleUpdates::iterator J = I->second.begin(),
8579f4a2713aSLionel Sambuc                                              F = I->second.end();
8580f4a2713aSLionel Sambuc          J != F; ++J)
8581f4a2713aSLionel Sambuc       delete J->first;
8582f4a2713aSLionel Sambuc   }
8583f4a2713aSLionel Sambuc }
8584