74#include "llvm/ADT/APFloat.h"
75#include "llvm/ADT/APInt.h"
76#include "llvm/ADT/APSInt.h"
77#include "llvm/ADT/ArrayRef.h"
78#include "llvm/ADT/DenseMap.h"
79#include "llvm/ADT/Hashing.h"
80#include "llvm/ADT/PointerIntPair.h"
81#include "llvm/ADT/STLExtras.h"
82#include "llvm/ADT/ScopeExit.h"
83#include "llvm/ADT/SmallPtrSet.h"
84#include "llvm/ADT/SmallString.h"
85#include "llvm/ADT/SmallVector.h"
86#include "llvm/ADT/StringMap.h"
87#include "llvm/ADT/StringRef.h"
88#include "llvm/Bitstream/BitCodes.h"
89#include "llvm/Bitstream/BitstreamWriter.h"
90#include "llvm/Support/Casting.h"
91#include "llvm/Support/Compression.h"
92#include "llvm/Support/DJB.h"
93#include "llvm/Support/Endian.h"
94#include "llvm/Support/EndianStream.h"
95#include "llvm/Support/Error.h"
96#include "llvm/Support/ErrorHandling.h"
97#include "llvm/Support/LEB128.h"
98#include "llvm/Support/MemoryBuffer.h"
99#include "llvm/Support/OnDiskHashTable.h"
100#include "llvm/Support/Path.h"
101#include "llvm/Support/SHA1.h"
102#include "llvm/Support/TimeProfiler.h"
103#include "llvm/Support/VersionTuple.h"
104#include "llvm/Support/raw_ostream.h"
119using namespace clang;
122template <
typename T,
typename Allocator>
123static StringRef
bytes(
const std::vector<T, Allocator> &
v) {
124 if (
v.empty())
return StringRef();
125 return StringRef(
reinterpret_cast<const char*
>(&
v[0]),
126 sizeof(T) *
v.size());
131 return StringRef(
reinterpret_cast<const char*
>(
v.data()),
132 sizeof(T) *
v.size());
135static std::string
bytes(
const std::vector<bool> &
V) {
137 Str.reserve(
V.size() / 8);
138 for (
unsigned I = 0, E =
V.size(); I < E;) {
140 for (
unsigned Bit = 0; Bit < 8 && I < E; ++Bit, ++I)
153#define TYPE_BIT_CODE(CLASS_ID, CODE_ID, CODE_VALUE) \
154 case Type::CLASS_ID: return TYPE_##CODE_ID;
155#include "clang/Serialization/TypeBitCodes.def"
157 llvm_unreachable(
"shouldn't be serializing a builtin type this way");
159 llvm_unreachable(
"bad type kind");
164std::set<const FileEntry *> GetAffectingModuleMaps(
const Preprocessor &PP,
166 std::set<const FileEntry *> ModuleMaps{};
167 std::set<const Module *> ProcessedModules;
178 for (
unsigned UID = 0, LastUID = FilesByUID.size(); UID != LastUID; ++UID) {
191 ModulesToProcess.push_back(KH.getModule());
210 auto ProcessModuleOnce = [&](
const Module *M) {
212 if (ProcessedModules.insert(Mod).second)
215 ModuleMaps.insert(F);
219 for (
const Module *CurrentModule : ModulesToProcess) {
220 ProcessModuleOnce(CurrentModule);
222 ProcessModuleOnce(ImportedModule);
224 ProcessModuleOnce(UndeclaredModule);
237 : Writer(Writer), BasicWriter(Writer,
Record) {}
262 Record.AddSourceLocation(Loc, Seq);
270#define ABSTRACT_TYPELOC(CLASS, PARENT)
271#define TYPELOC(CLASS, PARENT) \
272 void Visit##CLASS##TypeLoc(CLASS##TypeLoc TyLoc);
273#include "clang/AST/TypeLocNodes.def"
337 VisitArrayTypeLoc(TL);
341 VisitArrayTypeLoc(TL);
345 VisitArrayTypeLoc(TL);
348void TypeLocWriter::VisitDependentSizedArrayTypeLoc(
350 VisitArrayTypeLoc(TL);
353void TypeLocWriter::VisitDependentAddressSpaceTypeLoc(
357 addSourceLocation(
range.getBegin());
358 addSourceLocation(
range.getEnd());
362void TypeLocWriter::VisitDependentSizedExtVectorTypeLoc(
371void TypeLocWriter::VisitDependentVectorTypeLoc(
383 addSourceLocation(
range.getBegin());
384 addSourceLocation(
range.getEnd());
389void TypeLocWriter::VisitDependentSizedMatrixTypeLoc(
393 addSourceLocation(
range.getBegin());
394 addSourceLocation(
range.getEnd());
405 for (
unsigned i = 0, e = TL.
getNumParams(); i != e; ++i)
410 VisitFunctionTypeLoc(TL);
414 VisitFunctionTypeLoc(TL);
463void TypeLocWriter::VisitAutoTypeLoc(
AutoTypeLoc TL) {
473 for (
unsigned I = 0; I < TL.
getNumArgs(); ++I)
474 Record.AddTemplateArgumentLocInfo(
483void TypeLocWriter::VisitDeducedTemplateSpecializationTypeLoc(
492void TypeLocWriter::VisitEnumTypeLoc(
EnumTypeLoc TL) {
508void TypeLocWriter::VisitSubstTemplateTypeParmTypeLoc(
513void TypeLocWriter::VisitSubstTemplateTypeParmPackTypeLoc(
518void TypeLocWriter::VisitTemplateSpecializationTypeLoc(
524 for (
unsigned i = 0, e = TL.
getNumArgs(); i != e; ++i)
553void TypeLocWriter::VisitDependentTemplateSpecializationTypeLoc(
561 for (
unsigned I = 0, E = TL.
getNumArgs(); I != E; ++I)
597void TypeLocWriter::VisitPipeTypeLoc(
PipeTypeLoc TL) {
604void TypeLocWriter::VisitDependentBitIntTypeLoc(
609void ASTWriter::WriteTypeAbbrevs() {
610 using namespace llvm;
612 std::shared_ptr<BitCodeAbbrev> Abv;
615 Abv = std::make_shared<BitCodeAbbrev>();
617 Abv->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
618 Abv->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 3));
619 TypeExtQualAbbrev = Stream.EmitAbbrev(std::move(Abv));
627 llvm::BitstreamWriter &Stream,
630 Record.push_back(ID);
631 Stream.EmitRecord(llvm::bitc::BLOCKINFO_CODE_SETBID, Record);
634 if (!Name || Name[0] == 0)
638 Record.push_back(*Name++);
639 Stream.EmitRecord(llvm::bitc::BLOCKINFO_CODE_BLOCKNAME, Record);
643 llvm::BitstreamWriter &Stream,
646 Record.push_back(ID);
648 Record.push_back(*Name++);
649 Stream.EmitRecord(llvm::bitc::BLOCKINFO_CODE_SETRECORDNAME, Record);
654#define RECORD(X) EmitRecordID(X, #X, Stream, Record)
785void ASTWriter::WriteBlockInfoBlock() {
787 Stream.EnterBlockInfoBlock();
789#define BLOCK(X) EmitBlockID(X ## _ID, #X, Stream, Record)
790#define RECORD(X) EmitRecordID(X, #X, Stream, Record)
793 BLOCK(CONTROL_BLOCK);
803 BLOCK(OPTIONS_BLOCK);
810 BLOCK(INPUT_FILES_BLOCK);
873 BLOCK(SOURCE_MANAGER_BLOCK);
881 BLOCK(PREPROCESSOR_BLOCK);
889 BLOCK(SUBMODULE_BLOCK);
911 BLOCK(COMMENTS_BLOCK);
915 BLOCK(DECLTYPES_BLOCK);
919 RECORD(TYPE_BLOCK_POINTER);
920 RECORD(TYPE_LVALUE_REFERENCE);
921 RECORD(TYPE_RVALUE_REFERENCE);
922 RECORD(TYPE_MEMBER_POINTER);
923 RECORD(TYPE_CONSTANT_ARRAY);
924 RECORD(TYPE_INCOMPLETE_ARRAY);
925 RECORD(TYPE_VARIABLE_ARRAY);
928 RECORD(TYPE_FUNCTION_NO_PROTO);
929 RECORD(TYPE_FUNCTION_PROTO);
935 RECORD(TYPE_OBJC_INTERFACE);
936 RECORD(TYPE_OBJC_OBJECT_POINTER);
939 RECORD(TYPE_SUBST_TEMPLATE_TYPE_PARM);
940 RECORD(TYPE_UNRESOLVED_USING);
941 RECORD(TYPE_INJECTED_CLASS_NAME);
943 RECORD(TYPE_TEMPLATE_TYPE_PARM);
944 RECORD(TYPE_TEMPLATE_SPECIALIZATION);
945 RECORD(TYPE_DEPENDENT_NAME);
946 RECORD(TYPE_DEPENDENT_TEMPLATE_SPECIALIZATION);
947 RECORD(TYPE_DEPENDENT_SIZED_ARRAY);
949 RECORD(TYPE_MACRO_QUALIFIED);
950 RECORD(TYPE_PACK_EXPANSION);
952 RECORD(TYPE_SUBST_TEMPLATE_TYPE_PARM_PACK);
954 RECORD(TYPE_UNARY_TRANSFORM);
958 RECORD(TYPE_OBJC_TYPE_PARAM);
1036 BLOCK(PREPROCESSOR_DETAIL_BLOCK);
1042 BLOCK(EXTENSION_BLOCK);
1045 BLOCK(UNHASHED_CONTROL_BLOCK);
1064 return Changed | llvm::sys::path::remove_dots(Path);
1079 assert(
Filename &&
"No file name to adjust?");
1081 if (BaseDir.empty())
1086 for (;
Filename[Pos] && Pos < BaseDir.size(); ++Pos)
1096 if (!llvm::sys::path::is_separator(
Filename[Pos])) {
1097 if (!llvm::sys::path::is_separator(BaseDir.back()))
1114std::pair<ASTFileSignature, ASTFileSignature>
1115ASTWriter::createSignature(StringRef AllBytes, StringRef ASTBlockBytes) {
1117 Hasher.update(ASTBlockBytes);
1123 AllBytes.take_front(ASTBlockBytes.bytes_end() - AllBytes.bytes_begin()));
1125 AllBytes.take_back(AllBytes.bytes_end() - ASTBlockBytes.bytes_end()));
1128 return std::make_pair(ASTBlockHash, Signature);
1133 using namespace llvm;
1136 Stream.FlushToWord();
1137 auto StartOfUnhashedControl = Stream.GetCurrentBitNo() >> 3;
1145 if (WritingModule &&
1148 auto ASTBlockStartByte = ASTBlockRange.first >> 3;
1149 auto ASTBlockByteLength = (ASTBlockRange.second >> 3) - ASTBlockStartByte;
1150 std::tie(ASTBlockHash, Signature) = createSignature(
1151 StringRef(Buffer.begin(), StartOfUnhashedControl),
1152 StringRef(Buffer.begin() + ASTBlockStartByte, ASTBlockByteLength));
1154 Record.append(ASTBlockHash.begin(), ASTBlockHash.end());
1157 Record.append(Signature.begin(), Signature.end());
1165#define DIAGOPT(Name, Bits, Default) Record.push_back(DiagOpts.Name);
1166#define ENUM_DIAGOPT(Name, Type, Bits, Default) \
1167 Record.push_back(static_cast<unsigned>(DiagOpts.get##Name()));
1168#include "clang/Basic/DiagnosticOptions.def"
1170 for (
unsigned I = 0, N = DiagOpts.
Warnings.size(); I != N; ++I)
1173 for (
unsigned I = 0, N = DiagOpts.
Remarks.size(); I != N; ++I)
1187 for (
unsigned I = 0, N = HSOpts.
UserEntries.size(); I != N; ++I) {
1190 Record.push_back(
static_cast<unsigned>(Entry.
Group));
1210 WritePragmaDiagnosticMappings(Diags, WritingModule);
1214 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1216 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
1217 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1218 unsigned HSUsageAbbrevCode = Stream.EmitAbbrev(std::move(Abbrev));
1221 HSEntryUsage.size()};
1222 Stream.EmitRecordWithBlob(HSUsageAbbrevCode, Record,
bytes(HSEntryUsage));
1232 StringRef isysroot) {
1233 using namespace llvm;
1239 auto MetadataAbbrev = std::make_shared<BitCodeAbbrev>();
1240 MetadataAbbrev->Add(BitCodeAbbrevOp(
METADATA));
1241 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 16));
1242 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 16));
1243 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 16));
1244 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 16));
1245 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1246 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1247 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1248 MetadataAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1249 unsigned MetadataAbbrevCode = Stream.EmitAbbrev(std::move(MetadataAbbrev));
1250 assert((!WritingModule || isysroot.empty()) &&
1251 "writing module as a relocatable PCH?");
1253 RecordData::value_type
Record[] = {
1257 CLANG_VERSION_MAJOR,
1258 CLANG_VERSION_MINOR,
1261 ASTHasCompilerErrors};
1262 Stream.EmitRecordWithBlob(MetadataAbbrevCode, Record,
1266 if (WritingModule) {
1268 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1270 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1271 unsigned AbbrevCode = Stream.EmitAbbrev(std::move(Abbrev));
1273 Stream.EmitRecordWithBlob(AbbrevCode, Record, WritingModule->
Name);
1276 if (WritingModule && WritingModule->
Directory) {
1282 BaseDir.assign(CWD->getName());
1297 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1299 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1300 unsigned AbbrevCode = Stream.EmitAbbrev(std::move(Abbrev));
1303 Stream.EmitRecordWithBlob(AbbrevCode, Record, BaseDir);
1307 BaseDirectory.assign(BaseDir.begin(), BaseDir.end());
1308 }
else if (!isysroot.empty()) {
1310 BaseDirectory = std::string(isysroot);
1319 ? Map.getModuleMapFileForUniquing(WritingModule)->getName()
1324 if (
auto *AdditionalModMaps =
1325 Map.getAdditionalModuleMapFiles(WritingModule)) {
1326 Record.push_back(AdditionalModMaps->size());
1328 AdditionalModMaps->end());
1348 if (!M.isDirectlyImported())
1351 Record.push_back((
unsigned)M.Kind);
1356 Record.push_back(M.Signature ? 0 : M.File->getSize());
1359 llvm::append_range(Record, M.Signature);
1364 Stream.EmitRecord(
IMPORTS, Record);
1373#define LANGOPT(Name, Bits, Default, Description) \
1374 Record.push_back(LangOpts.Name);
1375#define ENUM_LANGOPT(Name, Type, Bits, Default, Description) \
1376 Record.push_back(static_cast<unsigned>(LangOpts.get##Name()));
1377#include "clang/Basic/LangOptions.def"
1378#define SANITIZER(NAME, ID) \
1379 Record.push_back(LangOpts.Sanitize.has(SanitizerKind::ID));
1380#include "clang/Basic/Sanitizers.def"
1420 for (
unsigned I = 0, N = TargetOpts.
Features.size(); I != N; ++I) {
1459 for (
unsigned I = 0, N = PPOpts.
Macros.size(); I != N; ++I) {
1466 for (
unsigned I = 0, N = PPOpts.
Includes.size(); I != N; ++I)
1471 for (
unsigned I = 0, N = PPOpts.
MacroIncludes.size(); I != N; ++I)
1486 if (
const FileEntry *MainFile =
SM.getFileEntryForID(
SM.getMainFileID())) {
1487 auto FileAbbrev = std::make_shared<BitCodeAbbrev>();
1489 FileAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1490 FileAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1491 unsigned FileAbbrevCode = Stream.EmitAbbrev(std::move(FileAbbrev));
1503 WriteInputFiles(Context.SourceMgr,
1511struct InputFileEntry {
1515 bool BufferOverridden;
1516 bool IsTopLevelModuleMap;
1517 uint32_t ContentHash[2];
1526 using namespace llvm;
1531 auto IFAbbrev = std::make_shared<BitCodeAbbrev>();
1533 IFAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1534 IFAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 12));
1535 IFAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 32));
1536 IFAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1537 IFAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1538 IFAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1539 IFAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1540 unsigned IFAbbrevCode = Stream.EmitAbbrev(std::move(IFAbbrev));
1543 auto IFHAbbrev = std::make_shared<BitCodeAbbrev>();
1545 IFHAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
1546 IFHAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
1547 unsigned IFHAbbrevCode = Stream.EmitAbbrev(std::move(IFHAbbrev));
1550 std::vector<InputFileEntry> UserFiles;
1551 std::vector<InputFileEntry> SystemFiles;
1555 assert(&SourceMgr.
getSLocEntry(FileID::get(I)) == SLoc);
1562 if (!
Cache->OrigEntry)
1566 if (!IsSLocAffecting[I])
1569 InputFileEntry Entry(*
Cache->OrigEntry);
1570 Entry.IsSystemFile =
isSystem(
File.getFileCharacteristic());
1571 Entry.IsTransient =
Cache->IsTransient;
1572 Entry.BufferOverridden =
Cache->BufferOverridden;
1573 Entry.IsTopLevelModuleMap =
isModuleMap(
File.getFileCharacteristic()) &&
1574 File.getIncludeLoc().isInvalid();
1576 auto ContentHash = hash_code(-1);
1580 auto MemBuff =
Cache->getBufferIfLoaded();
1582 ContentHash =
hash_value(MemBuff->getBuffer());
1585 << Entry.File.getName();
1587 auto CH = llvm::APInt(64, ContentHash);
1588 Entry.ContentHash[0] =
1589 static_cast<uint32_t
>(CH.getLoBits(32).getZExtValue());
1590 Entry.ContentHash[1] =
1591 static_cast<uint32_t
>(CH.getHiBits(32).getZExtValue());
1593 if (Entry.IsSystemFile)
1594 SystemFiles.push_back(Entry);
1596 UserFiles.push_back(Entry);
1600 auto SortedFiles = llvm::concat<InputFileEntry>(std::move(UserFiles),
1601 std::move(SystemFiles));
1603 unsigned UserFilesNum = 0;
1605 std::vector<uint64_t> InputFileOffsets;
1606 for (
const auto &Entry : SortedFiles) {
1607 uint32_t &InputFileID = InputFileIDs[Entry.File];
1608 if (InputFileID != 0)
1612 InputFileOffsets.push_back(Stream.GetCurrentBitNo());
1614 InputFileID = InputFileOffsets.size();
1616 if (!Entry.IsSystemFile)
1622 RecordData::value_type
Record[] = {
1624 InputFileOffsets.size(),
1627 Entry.BufferOverridden,
1629 Entry.IsTopLevelModuleMap};
1637 Entry.ContentHash[1]};
1638 Stream.EmitRecordWithAbbrev(IFHAbbrevCode, Record);
1645 auto OffsetsAbbrev = std::make_shared<BitCodeAbbrev>();
1647 OffsetsAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1648 OffsetsAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1650 OffsetsAbbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1651 unsigned OffsetsAbbrevCode = Stream.EmitAbbrev(std::move(OffsetsAbbrev));
1655 InputFileOffsets.size(), UserFilesNum};
1656 Stream.EmitRecordWithBlob(OffsetsAbbrevCode, Record,
bytes(InputFileOffsets));
1666 using namespace llvm;
1668 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1670 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1671 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1672 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 3));
1673 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1675 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1676 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1677 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 24));
1678 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1679 return Stream.EmitAbbrev(std::move(Abbrev));
1685 using namespace llvm;
1687 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1689 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1690 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1691 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 3));
1692 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1693 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1694 return Stream.EmitAbbrev(std::move(Abbrev));
1701 using namespace llvm;
1703 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1707 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1708 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1709 return Stream.EmitAbbrev(std::move(Abbrev));
1715 using namespace llvm;
1717 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1719 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1720 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8));
1721 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1722 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1723 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
1724 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
1725 return Stream.EmitAbbrev(std::move(Abbrev));
1730static std::pair<unsigned, unsigned>
1732 llvm::encodeULEB128(KeyLen, Out);
1733 llvm::encodeULEB128(DataLen, Out);
1734 return std::make_pair(KeyLen, DataLen);
1740 class HeaderFileInfoTrait {
1745 llvm::StringMap<unsigned> FrameworkNameOffset;
1748 HeaderFileInfoTrait(
ASTWriter &Writer) : Writer(Writer) {}
1755 using key_type_ref =
const key_type &;
1757 using UnresolvedModule =
1758 llvm::PointerIntPair<Module *, 2, ModuleMap::ModuleHeaderRole>;
1765 using data_type_ref =
const data_type &;
1774 return llvm::hash_combine(key.Size, key.ModTime);
1777 std::pair<unsigned, unsigned>
1778 EmitKeyDataLength(raw_ostream& Out, key_type_ref key, data_type_ref
Data) {
1779 unsigned KeyLen = key.Filename.size() + 1 + 8 + 8;
1780 unsigned DataLen = 1 + 4 + 4;
1781 for (
auto ModInfo :
Data.KnownHeaders)
1784 if (
Data.Unresolved.getPointer())
1789 void EmitKey(raw_ostream& Out, key_type_ref key,
unsigned KeyLen) {
1790 using namespace llvm::support;
1792 endian::Writer
LE(Out, little);
1797 Out.write(key.Filename.data(), KeyLen);
1800 void EmitData(raw_ostream &Out, key_type_ref key,
1801 data_type_ref
Data,
unsigned DataLen) {
1802 using namespace llvm::support;
1804 endian::Writer
LE(Out, little);
1805 uint64_t Start = Out.tell(); (void)Start;
1807 unsigned char Flags = (
Data.HFI.isImport << 5)
1808 | (
Data.HFI.isPragmaOnce << 4)
1809 | (
Data.HFI.DirInfo << 1)
1810 |
Data.HFI.IndexHeaderMapHeader;
1811 LE.write<uint8_t>(Flags);
1813 if (!
Data.HFI.ControllingMacro)
1814 LE.write<uint32_t>(
Data.HFI.ControllingMacroID);
1819 if (!
Data.HFI.Framework.empty()) {
1821 llvm::StringMap<unsigned>::iterator Pos
1822 = FrameworkNameOffset.find(
Data.HFI.Framework);
1823 if (Pos == FrameworkNameOffset.end()) {
1824 Offset = FrameworkStringData.size() + 1;
1825 FrameworkStringData.append(
Data.HFI.Framework);
1826 FrameworkStringData.push_back(0);
1828 FrameworkNameOffset[
Data.HFI.Framework] =
Offset;
1836 uint32_t
Value = (ModID << 3) | (
unsigned)Role;
1837 assert((
Value >> 3) == ModID &&
"overflow in header module info");
1842 for (
auto ModInfo :
Data.KnownHeaders)
1843 EmitModule(ModInfo.getModule(), ModInfo.getRole());
1844 if (
Data.Unresolved.getPointer())
1845 EmitModule(
Data.Unresolved.getPointer(),
Data.Unresolved.getInt());
1847 assert(Out.tell() - Start == DataLen &&
"Wrong data length");
1850 const char *strings_begin()
const {
return FrameworkStringData.begin(); }
1851 const char *strings_end()
const {
return FrameworkStringData.end(); }
1859void ASTWriter::WriteHeaderSearch(
const HeaderSearch &HS) {
1860 HeaderFileInfoTrait GeneratorTrait(*
this);
1861 llvm::OnDiskChainedHashTableGenerator<HeaderFileInfoTrait>
Generator;
1863 unsigned NumHeaderSearchEntries = 0;
1870 if (WritingModule) {
1872 while (!Worklist.empty()) {
1873 Module *M = Worklist.pop_back_val();
1890 if (!
U.Size || (!
U.ModTime && IncludeTimestamps)) {
1891 PP->
Diag(
U.FileNameLoc, diag::err_module_no_size_mtime_for_header)
1899 llvm::sys::path::append(
Filename,
U.FileName);
1902 StringRef FilenameDup = strdup(
Filename.c_str());
1903 SavedStrings.push_back(FilenameDup.data());
1905 HeaderFileInfoTrait::key_type Key = {
1906 FilenameDup, *
U.Size, IncludeTimestamps ? *
U.ModTime : 0
1908 HeaderFileInfoTrait::data_type
Data = {
1914 ++NumHeaderSearchEntries;
1927 for (
unsigned UID = 0, LastUID = FilesByUID.size(); UID != LastUID; ++UID) {
1949 Filename = StringRef(strdup(FilenameTmp.c_str()));
1950 SavedStrings.push_back(
Filename.data());
1953 HeaderFileInfoTrait::key_type Key = {
1956 HeaderFileInfoTrait::data_type
Data = {
1960 ++NumHeaderSearchEntries;
1965 uint32_t BucketOffset;
1967 using namespace llvm::support;
1969 llvm::raw_svector_ostream Out(TableData);
1971 endian::write<uint32_t>(Out, 0, little);
1972 BucketOffset =
Generator.Emit(Out, GeneratorTrait);
1976 using namespace llvm;
1978 auto Abbrev = std::make_shared<BitCodeAbbrev>();
1980 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
1981 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
1982 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
1983 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
1984 unsigned TableAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
1988 NumHeaderSearchEntries, TableData.size()};
1989 TableData.append(GeneratorTrait.strings_begin(),GeneratorTrait.strings_end());
1990 Stream.EmitRecordWithBlob(TableAbbrev, Record, TableData);
1993 for (
unsigned I = 0, N = SavedStrings.size(); I != N; ++I)
1994 free(
const_cast<char *
>(SavedStrings[I]));
1997static void emitBlob(llvm::BitstreamWriter &Stream, StringRef Blob,
1998 unsigned SLocBufferBlobCompressedAbbrv,
1999 unsigned SLocBufferBlobAbbrv) {
2000 using RecordDataType = ASTWriter::RecordData::value_type;
2005 if (llvm::compression::zstd::isAvailable()) {
2006 llvm::compression::zstd::compress(
2007 llvm::arrayRefFromStringRef(Blob.drop_back(1)), CompressedBuffer, 9);
2009 Stream.EmitRecordWithBlob(SLocBufferBlobCompressedAbbrv, Record,
2010 llvm::toStringRef(CompressedBuffer));
2013 if (llvm::compression::zlib::isAvailable()) {
2014 llvm::compression::zlib::compress(
2015 llvm::arrayRefFromStringRef(Blob.drop_back(1)), CompressedBuffer);
2017 Stream.EmitRecordWithBlob(SLocBufferBlobCompressedAbbrv, Record,
2018 llvm::toStringRef(CompressedBuffer));
2023 Stream.EmitRecordWithBlob(SLocBufferBlobAbbrv, Record, Blob);
2034void ASTWriter::WriteSourceManagerBlock(
SourceManager &SourceMgr,
2040 const uint64_t SourceManagerBlockOffset = Stream.GetCurrentBitNo();
2046 unsigned SLocBufferBlobCompressedAbbrv =
2052 std::vector<uint32_t> SLocEntryOffsets;
2053 uint64_t SLocEntryOffsetsBase = Stream.GetCurrentBitNo();
2060 FileID FID = FileID::get(I);
2064 uint64_t Offset = Stream.GetCurrentBitNo() - SLocEntryOffsetsBase;
2065 assert((
Offset >> 32) == 0 &&
"SLocEntry offset too large");
2071 if (
Cache->OrigEntry) {
2084 if (!IsSLocAffecting[I])
2086 SLocEntryOffsets.push_back(
Offset);
2090 Record.push_back(
File.getFileCharacteristic());
2093 bool EmitBlob =
false;
2096 "Writing to AST an overridden file is not supported");
2099 assert(InputFileIDs[Content->
OrigEntry] != 0 &&
"Missed file entry");
2102 Record.push_back(getAdjustedNumCreatedFIDs(FID));
2104 FileDeclIDsTy::iterator FDI = FileDeclIDs.find(FID);
2105 if (FDI != FileDeclIDs.end()) {
2106 Record.push_back(FDI->second->FirstDeclIndex);
2107 Record.push_back(FDI->second->DeclIDs.size());
2113 Stream.EmitRecordWithAbbrev(SLocFileAbbrv, Record);
2124 std::optional<llvm::MemoryBufferRef> Buffer =
2126 StringRef Name = Buffer ? Buffer->getBufferIdentifier() :
"";
2127 Stream.EmitRecordWithBlob(SLocBufferAbbrv, Record,
2128 StringRef(Name.data(), Name.size() + 1));
2131 if (Name ==
"<built-in>")
2132 PreloadSLocs.push_back(SLocEntryOffsets.size());
2138 std::optional<llvm::MemoryBufferRef> Buffer =
2141 Buffer = llvm::MemoryBufferRef(
"<<<INVALID BUFFER>>>",
"");
2142 StringRef Blob(Buffer->getBufferStart(), Buffer->getBufferSize() + 1);
2143 emitBlob(Stream, Blob, SLocBufferBlobCompressedAbbrv,
2144 SLocBufferBlobAbbrv);
2149 SLocEntryOffsets.push_back(
Offset);
2165 Record.push_back(getAdjustedOffset(NextOffset - SLoc->
getOffset()) - 1);
2166 Stream.EmitRecordWithAbbrev(SLocExpansionAbbrv, Record);
2172 if (SLocEntryOffsets.empty())
2177 using namespace llvm;
2179 auto Abbrev = std::make_shared<BitCodeAbbrev>();
2181 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 16));
2182 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 16));
2183 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 32));
2184 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2185 unsigned SLocOffsetsAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2187 RecordData::value_type
Record[] = {
2190 SLocEntryOffsetsBase - SourceManagerBlockOffset};
2191 Stream.EmitRecordWithBlob(SLocOffsetsAbbrev, Record,
2192 bytes(SLocEntryOffsets));
2206 llvm::DenseMap<int, int> FilenameMap;
2207 FilenameMap[-1] = -1;
2208 for (
const auto &L : LineTable) {
2211 for (
auto &LE : L.second) {
2212 if (FilenameMap.insert(std::make_pair(
LE.FilenameID,
2213 FilenameMap.size() - 1)).second)
2214 AddPath(LineTable.getFilename(
LE.FilenameID), Record);
2220 for (
const auto &L : LineTable) {
2228 Record.push_back(L.second.size());
2229 for (
const auto &LE : L.second) {
2232 Record.push_back(FilenameMap[
LE.FilenameID]);
2233 Record.push_back((
unsigned)
LE.FileKind);
2234 Record.push_back(
LE.IncludeOffset);
2249 if (MI->isBuiltinMacro())
2263void ASTWriter::writeIncludedFiles(raw_ostream &Out,
const Preprocessor &PP) {
2264 using namespace llvm::support;
2268 std::vector<uint32_t> IncludedInputFileIDs;
2269 IncludedInputFileIDs.reserve(IncludedFiles.size());
2272 auto InputFileIt = InputFileIDs.find(
File);
2273 if (InputFileIt == InputFileIDs.end())
2275 IncludedInputFileIDs.push_back(InputFileIt->second);
2278 llvm::sort(IncludedInputFileIDs);
2280 endian::Writer
LE(Out, little);
2281 LE.write<uint32_t>(IncludedInputFileIDs.size());
2282 for (uint32_t ID : IncludedInputFileIDs)
2283 LE.write<uint32_t>(
ID);
2288void ASTWriter::WritePreprocessor(
const Preprocessor &PP,
bool IsModule) {
2289 uint64_t MacroOffsetsBase = Stream.GetCurrentBitNo();
2293 WritePreprocessorDetail(*PPRec, MacroOffsetsBase);
2308 if (AssumeNonNullLoc.
isValid()) {
2322 Record.push_back(SkipInfo->FoundNonSkipPortion);
2323 Record.push_back(SkipInfo->FoundElse);
2330 Record.push_back(Cond.WasSkipping);
2331 Record.push_back(Cond.FoundNonSkip);
2332 Record.push_back(Cond.FoundElse);
2356 if (
Id.second->hadMacroDefinition() &&
2357 (!
Id.second->isFromAST() ||
2358 Id.second->hasChangedSinceDeserialization()))
2359 MacroIdentifiers.push_back(
Id.second);
2362 llvm::sort(MacroIdentifiers, llvm::deref<std::less<>>());
2368 uint64_t StartOffset = Stream.GetCurrentBitNo() - MacroOffsetsBase;
2369 assert((StartOffset >> 32) == 0 &&
"Macro identifiers offset too large");
2372 bool EmittedModuleMacros =
false;
2389 if (
auto *DefMD = dyn_cast<DefMacroDirective>(MD)) {
2391 }
else if (
auto *VisMD = dyn_cast<VisibilityMacroDirective>(MD)) {
2392 Record.push_back(VisMD->isPublic());
2394 ModuleMacroRecord.push_back(getSubmoduleID(WritingModule));
2397 ModuleMacroRecord.clear();
2398 EmittedModuleMacros =
true;
2408 if (
auto *DefMD = dyn_cast<DefMacroDirective>(MD)) {
2410 }
else if (
auto *VisMD = dyn_cast<VisibilityMacroDirective>(MD)) {
2411 Record.push_back(VisMD->isPublic());
2418 llvm::DenseMap<ModuleMacro *, unsigned> Visits;
2419 while (!Worklist.empty()) {
2420 auto *
Macro = Worklist.pop_back_val();
2423 ModuleMacroRecord.push_back(getSubmoduleID(
Macro->getOwningModule()));
2425 for (
auto *M :
Macro->overrides())
2426 ModuleMacroRecord.push_back(getSubmoduleID(M->getOwningModule()));
2429 ModuleMacroRecord.clear();
2432 for (
auto *M :
Macro->overrides())
2433 if (++Visits[M] == M->getNumOverridingMacros())
2434 Worklist.push_back(M);
2436 EmittedModuleMacros =
true;
2439 if (
Record.empty() && !EmittedModuleMacros)
2442 IdentMacroDirectivesOffsetMap[Name] = StartOffset;
2453 std::vector<uint32_t> MacroOffsets;
2455 for (
unsigned I = 0, N = MacroInfosToEmit.size(); I != N; ++I) {
2460 if (ID < FirstMacroID) {
2461 assert(0 &&
"Loaded MacroInfo entered MacroInfosToEmit ?");
2466 unsigned Index =
ID - FirstMacroID;
2467 if (Index >= MacroOffsets.size())
2468 MacroOffsets.resize(Index + 1);
2471 assert((
Offset >> 32) == 0 &&
"Macro offset too large");
2472 MacroOffsets[Index] =
Offset;
2499 Stream.EmitRecord(Code, Record);
2503 for (
unsigned TokNo = 0, e = MI->
getNumTokens(); TokNo != e; ++TokNo) {
2509 Stream.EmitRecord(
PP_TOKEN, Record);
2518 using namespace llvm;
2520 auto Abbrev = std::make_shared<BitCodeAbbrev>();
2522 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
2523 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
2524 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 32));
2525 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2527 unsigned MacroOffsetAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2531 MacroOffsetsBase - ASTBlockStartOffset};
2532 Stream.EmitRecordWithBlob(MacroOffsetAbbrev, Record,
bytes(MacroOffsets));
2536 auto Abbrev = std::make_shared<BitCodeAbbrev>();
2538 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2539 unsigned IncludedFilesAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2542 raw_svector_ostream Out(Buffer);
2543 writeIncludedFiles(Out, PP);
2545 Stream.EmitRecordWithBlob(IncludedFilesAbbrev, Record, Buffer.data(),
2551 uint64_t MacroOffsetsBase) {
2561 unsigned NumPreprocessingRecords = 0;
2562 using namespace llvm;
2565 unsigned InclusionAbbrev = 0;
2567 auto Abbrev = std::make_shared<BitCodeAbbrev>();
2569 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
2570 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2571 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 2));
2572 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2573 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2574 InclusionAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2577 unsigned FirstPreprocessorEntityID
2578 = (Chain ? PPRec.getNumLoadedPreprocessedEntities() : 0)
2580 unsigned NextPreprocessorEntityID = FirstPreprocessorEntityID;
2585 (void)++E, ++NumPreprocessingRecords, ++NextPreprocessorEntityID) {
2589 assert((
Offset >> 32) == 0 &&
"Preprocessed entity offset too large");
2590 PreprocessedEntityOffsets.push_back(
2593 if (
auto *MD = dyn_cast<MacroDefinitionRecord>(*E)) {
2595 MacroDefinitions[MD] = NextPreprocessorEntityID;
2602 if (
auto *ME = dyn_cast<MacroExpansion>(*E)) {
2603 Record.push_back(ME->isBuiltinMacro());
2604 if (ME->isBuiltinMacro())
2607 Record.push_back(MacroDefinitions[ME->getDefinition()]);
2612 if (
auto *ID = dyn_cast<InclusionDirective>(*E)) {
2614 Record.push_back(
ID->getFileName().size());
2615 Record.push_back(
ID->wasInQuotes());
2616 Record.push_back(
static_cast<unsigned>(
ID->getKind()));
2617 Record.push_back(
ID->importedModule());
2619 Buffer +=
ID->getFileName();
2623 Buffer +=
ID->getFile()->getName();
2624 Stream.EmitRecordWithBlob(InclusionAbbrev, Record, Buffer);
2628 llvm_unreachable(
"Unhandled PreprocessedEntity in ASTWriter");
2633 if (NumPreprocessingRecords > 0) {
2634 assert(PreprocessedEntityOffsets.size() == NumPreprocessingRecords);
2637 using namespace llvm;
2639 auto Abbrev = std::make_shared<BitCodeAbbrev>();
2641 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
2642 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2643 unsigned PPEOffsetAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2646 FirstPreprocessorEntityID -
2648 Stream.EmitRecordWithBlob(PPEOffsetAbbrev, Record,
2649 bytes(PreprocessedEntityOffsets));
2654 if (SkippedRanges.size() > 0) {
2655 std::vector<PPSkippedRange> SerializedSkippedRanges;
2656 SerializedSkippedRanges.reserve(SkippedRanges.size());
2657 for (
auto const& Range : SkippedRanges)
2658 SerializedSkippedRanges.emplace_back(Range);
2660 using namespace llvm;
2661 auto Abbrev = std::make_shared<BitCodeAbbrev>();
2663 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2664 unsigned PPESkippedRangeAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2668 Stream.EmitRecordWithBlob(PPESkippedRangeAbbrev, Record,
2669 bytes(SerializedSkippedRanges));
2677 auto Known = SubmoduleIDs.find(Mod);
2678 if (Known != SubmoduleIDs.end())
2679 return Known->second;
2682 if (Top != WritingModule &&
2684 !Top->fullModuleNameIs(StringRef(
getLangOpts().CurrentModule))))
2687 return SubmoduleIDs[Mod] = NextSubmoduleID++;
2690unsigned ASTWriter::getSubmoduleID(
Module *Mod) {
2703 unsigned ChildModules = 0;
2705 Sub != SubEnd; ++Sub)
2708 return ChildModules + 1;
2711void ASTWriter::WriteSubmodules(
Module *WritingModule) {
2716 using namespace llvm;
2718 auto Abbrev = std::make_shared<BitCodeAbbrev>();
2720 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
2721 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
2722 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 4));
2723 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2724 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2725 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2726 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2727 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2728 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2729 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2730 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2731 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2732 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2733 unsigned DefinitionAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2735 Abbrev = std::make_shared<BitCodeAbbrev>();
2737 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2738 unsigned UmbrellaAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2740 Abbrev = std::make_shared<BitCodeAbbrev>();
2742 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2743 unsigned HeaderAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2745 Abbrev = std::make_shared<BitCodeAbbrev>();
2747 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2748 unsigned TopHeaderAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2750 Abbrev = std::make_shared<BitCodeAbbrev>();
2752 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2753 unsigned UmbrellaDirAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2755 Abbrev = std::make_shared<BitCodeAbbrev>();
2757 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2758 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2759 unsigned RequiresAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2761 Abbrev = std::make_shared<BitCodeAbbrev>();
2763 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2764 unsigned ExcludedHeaderAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2766 Abbrev = std::make_shared<BitCodeAbbrev>();
2768 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2769 unsigned TextualHeaderAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2771 Abbrev = std::make_shared<BitCodeAbbrev>();
2773 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2774 unsigned PrivateHeaderAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2776 Abbrev = std::make_shared<BitCodeAbbrev>();
2778 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2779 unsigned PrivateTextualHeaderAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2781 Abbrev = std::make_shared<BitCodeAbbrev>();
2783 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 1));
2784 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2785 unsigned LinkLibraryAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2787 Abbrev = std::make_shared<BitCodeAbbrev>();
2789 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2790 unsigned ConfigMacroAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2792 Abbrev = std::make_shared<BitCodeAbbrev>();
2794 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
2795 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2796 unsigned ConflictAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2798 Abbrev = std::make_shared<BitCodeAbbrev>();
2800 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
2801 unsigned ExportAsAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
2804 RecordData::value_type
Record[] = {
2810 std::queue<Module *> Q;
2811 Q.push(WritingModule);
2812 while (!Q.empty()) {
2815 unsigned ID = getSubmoduleID(Mod);
2819 assert(SubmoduleIDs[Mod->
Parent] &&
"Submodule parent not written?");
2820 ParentID = SubmoduleIDs[Mod->
Parent];
2828 (RecordData::value_type)Mod->
Kind,
2838 Stream.EmitRecordWithBlob(DefinitionAbbrev, Record, Mod->
Name);
2844 Stream.EmitRecordWithBlob(RequiresAbbrev, Record, R.first);
2850 Stream.EmitRecordWithBlob(UmbrellaAbbrev, Record,
2851 UmbrellaHeader.NameAsWritten);
2854 Stream.EmitRecordWithBlob(UmbrellaDirAbbrev, Record,
2855 UmbrellaDir.NameAsWritten);
2860 unsigned RecordKind;
2871 for (
auto &HL : HeaderLists) {
2872 RecordData::value_type
Record[] = {HL.RecordKind};
2873 for (
auto &H : Mod->
Headers[HL.HeaderKind])
2874 Stream.EmitRecordWithBlob(HL.Abbrev, Record, H.NameAsWritten);
2881 for (
auto *H : TopHeaders) {
2884 Stream.EmitRecordWithBlob(TopHeaderAbbrev, Record, HeaderName);
2892 Record.push_back(getSubmoduleID(I));
2900 Record.push_back(getSubmoduleID(I));
2907 for (
const auto &E : Mod->
Exports) {
2910 Record.push_back(getSubmoduleID(E.getPointer()));
2911 Record.push_back(E.getInt());
2926 Stream.EmitRecordWithBlob(LinkLibraryAbbrev, Record, LL.Library);
2934 getSubmoduleID(
C.Other)};
2935 Stream.EmitRecordWithBlob(ConflictAbbrev, Record,
C.Message);
2941 Stream.EmitRecordWithBlob(ConfigMacroAbbrev, Record, CM);
2954 Stream.EmitRecordWithBlob(ExportAsAbbrev, Record, Mod->
ExportAsModule);
2964 assert((NextSubmoduleID - FirstSubmoduleID ==
2966 "Wrong # of submodules; found a reference to a non-local, "
2967 "non-imported submodule?");
2972 llvm::SmallDenseMap<const DiagnosticsEngine::DiagState *, unsigned, 64>
2974 unsigned CurrID = 0;
2977 auto EncodeDiagStateFlags =
2978 [](
const DiagnosticsEngine::DiagState *DS) ->
unsigned {
2981 {(
unsigned)DS->IgnoreAllWarnings, (
unsigned)DS->EnableAllWarnings,
2982 (
unsigned)DS->WarningsAsErrors, (
unsigned)DS->ErrorsAsFatal,
2983 (
unsigned)DS->SuppressSystemWarnings})
2988 unsigned Flags = EncodeDiagStateFlags(
Diag.DiagStatesByLoc.FirstDiagState);
2991 auto AddDiagState = [&](
const DiagnosticsEngine::DiagState *State,
2992 bool IncludeNonPragmaStates) {
2995 assert(Flags == EncodeDiagStateFlags(State) &&
2996 "diag state flags vary in single AST file");
2998 unsigned &DiagStateID = DiagStateIDMap[State];
2999 Record.push_back(DiagStateID);
3001 if (DiagStateID == 0) {
3002 DiagStateID = ++CurrID;
3005 auto SizeIdx =
Record.size();
3007 for (
const auto &I : *State) {
3008 if (I.second.isPragma() || IncludeNonPragmaStates) {
3009 Record.push_back(I.first);
3010 Record.push_back(I.second.serialize());
3018 AddDiagState(
Diag.DiagStatesByLoc.FirstDiagState, isModule);
3021 auto NumLocationsIdx =
Record.size();
3025 unsigned NumLocations = 0;
3026 for (
auto &FileIDAndFile :
Diag.DiagStatesByLoc.Files) {
3027 if (!FileIDAndFile.first.isValid() ||
3028 !FileIDAndFile.second.HasLocalTransitions)
3033 assert(!Loc.
isInvalid() &&
"start loc for valid FileID is invalid");
3036 Record.push_back(FileIDAndFile.second.StateTransitions.size());
3037 for (
auto &StatePoint : FileIDAndFile.second.StateTransitions) {
3038 Record.push_back(getAdjustedOffset(StatePoint.Offset));
3039 AddDiagState(StatePoint.State,
false);
3044 Record[NumLocationsIdx] = NumLocations;
3053 AddDiagState(
Diag.DiagStatesByLoc.CurDiagState,
false);
3063void ASTWriter::WriteType(
QualType T) {
3064 TypeIdx &IdxRef = TypeIdxs[T];
3066 IdxRef =
TypeIdx(NextTypeID++);
3069 assert(Idx.
getIndex() >= FirstTypeID &&
"Re-writing a type from a prior AST");
3072 uint64_t Offset = ASTTypeWriter(*this).write(T) - DeclTypesBlockStartOffset;
3075 unsigned Index = Idx.
getIndex() - FirstTypeID;
3076 if (TypeOffsets.size() == Index)
3077 TypeOffsets.emplace_back(
Offset);
3078 else if (TypeOffsets.size() < Index) {
3079 TypeOffsets.resize(Index + 1);
3080 TypeOffsets[Index].setBitOffset(
Offset);
3082 llvm_unreachable(
"Types emitted in wrong order");
3102 for (
const auto *D : DC->
decls()) {
3103 KindDeclPairs.push_back(D->getKind());
3107 ++NumLexicalDeclContexts;
3109 Stream.EmitRecordWithBlob(DeclContextLexicalAbbrev, Record,
3110 bytes(KindDeclPairs));
3114void ASTWriter::WriteTypeDeclOffsets() {
3115 using namespace llvm;
3118 auto Abbrev = std::make_shared<BitCodeAbbrev>();
3120 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3121 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3122 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
3123 unsigned TypeOffsetAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
3127 Stream.EmitRecordWithBlob(TypeOffsetAbbrev, Record,
bytes(TypeOffsets));
3131 Abbrev = std::make_shared<BitCodeAbbrev>();
3133 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3134 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3135 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
3136 unsigned DeclOffsetAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
3140 Stream.EmitRecordWithBlob(DeclOffsetAbbrev, Record,
bytes(DeclOffsets));
3144void ASTWriter::WriteFileDeclIDsMap() {
3145 using namespace llvm;
3148 SortedFileDeclIDs.reserve(FileDeclIDs.size());
3149 for (
const auto &
P : FileDeclIDs)
3150 SortedFileDeclIDs.push_back(std::make_pair(
P.first,
P.second.get()));
3151 llvm::sort(SortedFileDeclIDs, llvm::less_first());
3155 for (
auto &FileDeclEntry : SortedFileDeclIDs) {
3156 DeclIDInFileInfo &Info = *FileDeclEntry.second;
3157 Info.FirstDeclIndex = FileGroupedDeclIDs.size();
3158 llvm::stable_sort(Info.DeclIDs);
3159 for (
auto &LocDeclEntry : Info.DeclIDs)
3160 FileGroupedDeclIDs.push_back(LocDeclEntry.second);
3163 auto Abbrev = std::make_shared<BitCodeAbbrev>();
3165 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3166 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
3167 unsigned AbbrevCode = Stream.EmitAbbrev(std::move(Abbrev));
3169 FileGroupedDeclIDs.size()};
3170 Stream.EmitRecordWithBlob(AbbrevCode, Record,
bytes(FileGroupedDeclIDs));
3173void ASTWriter::WriteComments() {
3175 auto _ = llvm::make_scope_exit([
this] { Stream.ExitBlock(); });
3179 for (
const auto &FO : Context->
Comments.OrderedComments) {
3180 for (
const auto &OC : FO.second) {
3199class ASTMethodPoolTrait {
3204 using key_type_ref = key_type;
3210 using data_type_ref =
const data_type &;
3215 explicit ASTMethodPoolTrait(
ASTWriter &Writer) : Writer(Writer) {}
3221 std::pair<unsigned, unsigned>
3222 EmitKeyDataLength(raw_ostream& Out,
Selector Sel,
3223 data_type_ref Methods) {
3225 unsigned DataLen = 4 + 2 + 2;
3228 if (ShouldWriteMethodListNode(Method))
3232 if (ShouldWriteMethodListNode(Method))
3237 void EmitKey(raw_ostream& Out,
Selector Sel,
unsigned) {
3238 using namespace llvm::support;
3240 endian::Writer
LE(Out, little);
3242 assert((Start >> 32) == 0 &&
"Selector key offset too large");
3245 LE.write<uint16_t>(N);
3248 for (
unsigned I = 0; I != N; ++I)
3253 void EmitData(raw_ostream& Out, key_type_ref,
3254 data_type_ref Methods,
unsigned DataLen) {
3255 using namespace llvm::support;
3257 endian::Writer
LE(Out, little);
3258 uint64_t Start = Out.tell(); (void)Start;
3259 LE.write<uint32_t>(Methods.ID);
3260 unsigned NumInstanceMethods = 0;
3263 if (ShouldWriteMethodListNode(Method))
3264 ++NumInstanceMethods;
3266 unsigned NumFactoryMethods = 0;
3269 if (ShouldWriteMethodListNode(Method))
3270 ++NumFactoryMethods;
3272 unsigned InstanceBits = Methods.Instance.getBits();
3273 assert(InstanceBits < 4);
3274 unsigned InstanceHasMoreThanOneDeclBit =
3275 Methods.Instance.hasMoreThanOneDecl();
3276 unsigned FullInstanceBits = (NumInstanceMethods << 3) |
3277 (InstanceHasMoreThanOneDeclBit << 2) |
3279 unsigned FactoryBits = Methods.Factory.getBits();
3280 assert(FactoryBits < 4);
3281 unsigned FactoryHasMoreThanOneDeclBit =
3282 Methods.Factory.hasMoreThanOneDecl();
3283 unsigned FullFactoryBits = (NumFactoryMethods << 3) |
3284 (FactoryHasMoreThanOneDeclBit << 2) |
3286 LE.write<uint16_t>(FullInstanceBits);
3287 LE.write<uint16_t>(FullFactoryBits);
3290 if (ShouldWriteMethodListNode(Method))
3291 LE.write<uint32_t>(Writer.
getDeclID(Method->getMethod()));
3294 if (ShouldWriteMethodListNode(Method))
3295 LE.write<uint32_t>(Writer.
getDeclID(Method->getMethod()));
3297 assert(Out.tell() - Start == DataLen &&
"Data length is wrong");
3302 return (
Node->getMethod() && !
Node->getMethod()->isFromASTFile());
3313void ASTWriter::WriteSelectors(
Sema &SemaRef) {
3314 using namespace llvm;
3319 unsigned NumTableEntries = 0;
3322 llvm::OnDiskChainedHashTableGenerator<ASTMethodPoolTrait>
Generator;
3323 ASTMethodPoolTrait Trait(*
this);
3327 SelectorOffsets.resize(NextSelectorID - FirstSelectorID);
3328 for (
auto &SelectorAndID : SelectorIDs) {
3332 ASTMethodPoolTrait::data_type
Data = {
3338 Data.Instance = F->second.first;
3339 Data.Factory = F->second.second;
3343 if (Chain && ID < FirstSelectorID) {
3345 bool changed =
false;
3348 if (!M->getMethod()->isFromASTFile()) {
3356 if (!M->getMethod()->isFromASTFile()) {
3364 }
else if (
Data.Instance.getMethod() ||
Data.Factory.getMethod()) {
3373 uint32_t BucketOffset;
3375 using namespace llvm::support;
3377 ASTMethodPoolTrait Trait(*
this);
3378 llvm::raw_svector_ostream Out(MethodPool);
3380 endian::write<uint32_t>(Out, 0, little);
3381 BucketOffset =
Generator.Emit(Out, Trait);
3385 auto Abbrev = std::make_shared<BitCodeAbbrev>();
3387 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3388 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3389 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
3390 unsigned MethodPoolAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
3396 Stream.EmitRecordWithBlob(MethodPoolAbbrev, Record, MethodPool);
3400 Abbrev = std::make_shared<BitCodeAbbrev>();
3402 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3403 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3404 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
3405 unsigned SelectorOffsetAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
3409 RecordData::value_type
Record[] = {
3412 Stream.EmitRecordWithBlob(SelectorOffsetAbbrev, Record,
3413 bytes(SelectorOffsets));
3419void ASTWriter::WriteReferencedSelectorsPool(
Sema &SemaRef) {
3420 using namespace llvm;
3432 Selector Sel = SelectorAndLocation.first;
3434 Writer.AddSelectorRef(Sel);
3456 for (; Redecl; Redecl = Redecl->getPreviousDecl()) {
3458 if (!Redecl->isFromASTFile()) {
3462 if (!Redecl->getDeclContext()->getRedeclContext()->Equals(
3465 return cast<NamedDecl>(Redecl);
3470 if (Redecl->getOwningModuleID() == 0)
3475 if (!
First->isFromASTFile())
3476 return cast<NamedDecl>(
First);
3486class ASTIdentifierTableTrait {
3510 using key_type_ref = key_type;
3513 using data_type_ref = data_type;
3521 : Writer(Writer), PP(PP), IdResolver(IdResolver), IsModule(IsModule),
3522 NeedDecls(!IsModule || !Writer.getLangOpts().
CPlusPlus),
3523 InterestingIdentifierOffsets(InterestingIdentifierOffsets) {}
3525 bool needDecls()
const {
return NeedDecls; }
3528 return llvm::djbHash(II->
getName());
3540 std::pair<unsigned, unsigned>
3549 InterestingIdentifierOffsets->push_back(Out.tell());
3552 unsigned DataLen = 4;
3562 DEnd = IdResolver.
end();
3577 using namespace llvm::support;
3579 endian::Writer
LE(Out, little);
3583 LE.write<uint32_t>(
ID << 1);
3587 LE.write<uint32_t>((
ID << 1) | 0x01);
3589 assert((Bits & 0xffff) == Bits &&
"ObjCOrBuiltinID too big for ASTReader.");
3590 LE.write<uint16_t>(Bits);
3592 bool HadMacroDefinition = MacroOffset != 0;
3593 Bits = (Bits << 1) |
unsigned(HadMacroDefinition);
3595 Bits = (Bits << 1) |
unsigned(II->
isPoisoned());
3598 LE.write<uint16_t>(Bits);
3600 if (HadMacroDefinition)
3601 LE.write<uint32_t>(MacroOffset);
3612 for (
NamedDecl *D : llvm::reverse(Decls))
3629 using namespace llvm;
3636 llvm::OnDiskChainedHashTableGenerator<ASTIdentifierTableTrait>
Generator;
3637 ASTIdentifierTableTrait Trait(
3638 *
this, PP, IdResolver, IsModule,
3648 IIs.push_back(
ID.second);
3651 llvm::sort(IIs, llvm::deref<std::less<>>());
3653 if (Trait.isInterestingNonMacroIdentifier(II))
3658 IdentifierOffsets.resize(NextIdentID - FirstIdentID);
3659 for (
auto IdentIDPair : IdentifierIDs) {
3662 assert(II &&
"NULL identifier in identifier table");
3665 if (ID >= FirstIdentID || !Chain || !II->
isFromAST()
3667 (Trait.needDecls() &&
3674 uint32_t BucketOffset;
3676 using namespace llvm::support;
3680 endian::write<uint32_t>(Out, 0, little);
3681 BucketOffset =
Generator.Emit(Out, Trait);
3685 auto Abbrev = std::make_shared<BitCodeAbbrev>();
3687 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3688 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
3689 unsigned IDTableAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
3697 auto Abbrev = std::make_shared<BitCodeAbbrev>();
3699 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3700 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed, 32));
3701 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
3702 unsigned IdentifierOffsetAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
3705 for (
unsigned I = 0, N = IdentifierOffsets.size(); I != N; ++I)
3706 assert(IdentifierOffsets[I] &&
"Missing identifier offset?");
3710 IdentifierOffsets.size(),
3712 Stream.EmitRecordWithBlob(IdentifierOffsetAbbrev, Record,
3713 bytes(IdentifierOffsets));
3717 if (!InterestingIdents.empty())
3728class ASTDeclContextNameLookupTrait {
3734 using key_type_ref = key_type;
3737 using data_type = std::pair<unsigned, unsigned>;
3738 using data_type_ref =
const data_type &;
3743 explicit ASTDeclContextNameLookupTrait(
ASTWriter &Writer) : Writer(Writer) {}
3745 template<
typename Coll>
3746 data_type getData(
const Coll &Decls) {
3747 unsigned Start = DeclIDs.size();
3752 return std::make_pair(Start, DeclIDs.size());
3756 unsigned Start = DeclIDs.size();
3757 llvm::append_range(DeclIDs, FromReader);
3758 return std::make_pair(Start, DeclIDs.size());
3761 static bool EqualKey(key_type_ref a, key_type_ref
b) {
3766 return Name.getHash();
3769 void EmitFileRef(raw_ostream &Out,
ModuleFile *F)
const {
3771 "have reference to loaded module file but no chain?");
3773 using namespace llvm::support;
3778 std::pair<unsigned, unsigned> EmitKeyDataLength(raw_ostream &Out,
3780 data_type_ref Lookup) {
3781 unsigned KeyLen = 1;
3782 switch (Name.getKind()) {
3802 unsigned DataLen = 4 * (Lookup.second - Lookup.first);
3808 using namespace llvm::support;
3810 endian::Writer
LE(Out, little);
3811 LE.write<uint8_t>(Name.getKind());
3812 switch (Name.getKind()) {
3825 "Invalid operator?");
3826 LE.write<uint8_t>(Name.getOperatorKind());
3835 llvm_unreachable(
"Invalid name kind?");
3838 void EmitData(raw_ostream &Out, key_type_ref, data_type Lookup,
3840 using namespace llvm::support;
3842 endian::Writer
LE(Out, little);
3843 uint64_t Start = Out.tell(); (void)Start;
3844 for (
unsigned I = Lookup.first, N = Lookup.second; I != N; ++I)
3845 LE.write<uint32_t>(DeclIDs[I]);
3846 assert(Out.tell() - Start == DataLen &&
"Data length is wrong");
3854 return Result.hasExternalDecls() &&
3855 DC->hasNeedToReconcileExternalVisibleStorage();
3860 for (
auto *D :
Result.getLookupResult())
3868ASTWriter::GenerateNameLookupTable(
const DeclContext *ConstDC,
3870 assert(!ConstDC->hasLazyLocalLexicalLookups() &&
3871 !ConstDC->hasLazyExternalLexicalLookups() &&
3872 "must call buildLookups first");
3880 ASTDeclContextNameLookupTrait>
Generator;
3881 ASTDeclContextNameLookupTrait Trait(*
this);
3893 auto &Name = Lookup.first;
3894 auto &
Result = Lookup.second;
3900 if (isLookupResultExternal(
Result, DC) &&
3901 isLookupResultEntirelyExternal(
Result, DC))
3918 if (Lookup.second.getLookupResult().empty())
3921 switch (Lookup.first.getNameKind()) {
3923 Names.push_back(Lookup.first);
3927 assert(isa<CXXRecordDecl>(DC) &&
3928 "Cannot have a constructor name outside of a class!");
3929 ConstructorNameSet.insert(Name);
3933 assert(isa<CXXRecordDecl>(DC) &&
3934 "Cannot have a conversion function name outside of a class!");
3935 ConversionNameSet.insert(Name);
3943 if (
auto *D = dyn_cast<CXXRecordDecl>(DC)) {
3957 if (ConstructorNameSet.erase(ImplicitCtorName))
3958 Names.push_back(ImplicitCtorName);
3963 if (!ConstructorNameSet.empty() || !ConversionNameSet.empty())
3964 for (
Decl *ChildD : cast<CXXRecordDecl>(DC)->decls())
3965 if (
auto *ChildND = dyn_cast<NamedDecl>(ChildD)) {
3966 auto Name = ChildND->getDeclName();
3967 switch (Name.getNameKind()) {
3972 if (ConstructorNameSet.erase(Name))
3973 Names.push_back(Name);
3977 if (ConversionNameSet.erase(Name))
3978 Names.push_back(Name);
3982 if (ConstructorNameSet.empty() && ConversionNameSet.empty())
3986 assert(ConstructorNameSet.empty() &&
"Failed to find all of the visible "
3987 "constructors by walking all the "
3988 "lexical members of the context.");
3989 assert(ConversionNameSet.empty() &&
"Failed to find all of the visible "
3990 "conversion functions by walking all "
3991 "the lexical members of the context.");
3998 for (
auto &Name : Names)
4010 for (
auto &Name : Names) {
4013 switch (Name.getNameKind()) {
4031 if (!ConstructorDecls.empty())
4032 Generator.insert(ConstructorDecls.front()->getDeclName(),
4033 Trait.getData(ConstructorDecls), Trait);
4034 if (!ConversionDecls.empty())
4035 Generator.insert(ConversionDecls.front()->getDeclName(),
4036 Trait.getData(ConversionDecls), Trait);
4041 Generator.emit(LookupTable, Trait, Lookups ? &Lookups->Table :
nullptr);
4054 if (isa<NamespaceDecl>(DC) && Chain &&
4057 for (
auto *Prev = cast<NamespaceDecl>(DC)->getPreviousDecl(); Prev;
4058 Prev = Prev->getPreviousDecl())
4059 if (!Prev->isFromASTFile())
4072 LookupResults.reserve(Map->size());
4073 for (
auto &Entry : *Map)
4074 LookupResults.push_back(
4075 std::make_pair(Entry.first, Entry.second.getLookupResult()));
4078 llvm::sort(LookupResults, llvm::less_first());
4079 for (
auto &NameAndResult : LookupResults) {
4087 assert(
Result.empty() &&
"Cannot have a constructor or conversion "
4088 "function name in a namespace!");
4093 if (!ND->isFromASTFile())
4119 if (!Map || Map->empty())
4124 GenerateNameLookupTable(DC, LookupTable);
4128 Stream.EmitRecordWithBlob(DeclContextVisibleLookupAbbrev, Record,
4130 ++NumVisibleDeclContexts;
4140void ASTWriter::WriteDeclContextVisibleUpdate(
const DeclContext *DC) {
4142 if (!Map || Map->empty())
4147 GenerateNameLookupTable(DC, LookupTable);
4151 if (isa<NamespaceDecl>(DC))
4156 Stream.EmitRecordWithBlob(UpdateVisibleAbbrev, Record, LookupTable);
4166void ASTWriter::WriteOpenCLExtensions(
Sema &SemaRef) {
4172 for (
const auto &I:Opts.OptMap) {
4174 auto V = I.getValue();
4175 Record.push_back(
V.Supported ? 1 : 0);
4176 Record.push_back(
V.Enabled ? 1 : 0);
4177 Record.push_back(
V.WithPragma ? 1 : 0);
4184void ASTWriter::WriteCUDAPragmas(
Sema &SemaRef) {
4185 if (SemaRef.ForceCUDAHostDeviceDepth > 0) {
4186 RecordData::value_type
Record[] = {SemaRef.ForceCUDAHostDeviceDepth};
4191void ASTWriter::WriteObjCCategories() {
4195 for (
unsigned I = 0, N = ObjCClassesWithCategories.size(); I != N; ++I) {
4197 unsigned StartIndex = Categories.size();
4202 Categories.push_back(0);
4206 Cat =
Class->known_categories_begin(),
4207 CatEnd =
Class->known_categories_end();
4208 Cat != CatEnd; ++Cat, ++Size) {
4209 assert(
getDeclID(*Cat) != 0 &&
"Bogus category");
4214 Categories[StartIndex] =
Size;
4218 CategoriesMap.push_back(CatInfo);
4223 llvm::array_pod_sort(CategoriesMap.begin(), CategoriesMap.end());
4226 using namespace llvm;
4228 auto Abbrev = std::make_shared<BitCodeAbbrev>();
4230 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6));
4231 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
4232 unsigned AbbrevID = Stream.EmitAbbrev(std::move(Abbrev));
4235 Stream.EmitRecordWithBlob(AbbrevID, Record,
4236 reinterpret_cast<char *
>(CategoriesMap.data()),
4243void ASTWriter::WriteLateParsedTemplates(
Sema &SemaRef) {
4250 for (
auto &LPTMapEntry : LPTMap) {
4257 for (
const auto &Tok : LPT.
Toks) {
4265void ASTWriter::WriteOptimizePragmaOptions(
Sema &SemaRef) {
4273void ASTWriter::WriteMSStructPragmaOptions(
Sema &SemaRef) {
4281void ASTWriter::WriteMSPointersToMembersPragmaOptions(
Sema &SemaRef) {
4289void ASTWriter::WritePackPragmaOptions(
Sema &SemaRef) {
4303 AddString(StackEntry.StackSlotLabel, Record);
4309void ASTWriter::WriteFloatControlPragmaOptions(
Sema &SemaRef) {
4319 for (
const auto &StackEntry : SemaRef.
FpPragmaStack.Stack) {
4320 Record.push_back(StackEntry.Value.getAsOpaqueInt());
4323 AddString(StackEntry.StackSlotLabel, Record);
4328void ASTWriter::WriteModuleFileExtension(
Sema &SemaRef,
4334 auto Abv = std::make_shared<llvm::BitCodeAbbrev>();
4336 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::VBR, 6));
4337 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::VBR, 6));
4338 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::VBR, 6));
4339 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::VBR, 6));
4340 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::Blob));
4341 unsigned Abbrev = Stream.EmitAbbrev(std::move(Abv));
4347 Record.push_back(Metadata.MajorVersion);
4348 Record.push_back(Metadata.MinorVersion);
4349 Record.push_back(Metadata.BlockName.size());
4350 Record.push_back(Metadata.UserInfo.size());
4352 Buffer += Metadata.BlockName;
4353 Buffer += Metadata.UserInfo;
4354 Stream.EmitRecordWithBlob(Abbrev, Record, Buffer);
4368 auto &Record = *
this;
4372 if (!A || (isa<PreferredNameAttr>(A) &&
4373 Writer->isWritingStdCXXNamedModules()))
4374 return Record.push_back(0);
4376 Record.push_back(A->
getKind() + 1);
4380 Record.AddSourceRange(A->
getRange());
4384 Record.push_back(A->getAttributeSpellingListIndexRaw());
4386#include "clang/Serialization/AttrPCHWrite.inc"
4392 for (
const auto *A : Attrs)
4399 Record.push_back(Tok.
getKind());
4406 case tok::annot_pragma_loop_hint: {
4408 AddToken(Info->PragmaName, Record);
4410 Record.push_back(Info->Toks.size());
4411 for (
const auto &T : Info->Toks)
4415 case tok::annot_pragma_pack: {
4418 Record.push_back(
static_cast<unsigned>(Info->Action));
4424 case tok::annot_pragma_openmp:
4425 case tok::annot_pragma_openmp_end:
4426 case tok::annot_pragma_unused:
4429 llvm_unreachable(
"missing serialization code for annotation token");
4440 Record.push_back(Str.size());
4441 Record.insert(Record.end(), Str.begin(), Str.end());
4445 assert(Context &&
"should have context when outputting path");
4451 const char *PathBegin = Path.data();
4452 const char *PathPtr =
4454 if (PathPtr != PathBegin) {
4455 Path.erase(Path.begin(), Path.begin() + (PathPtr - PathBegin));
4472 Stream.EmitRecordWithBlob(Abbrev, Record, FilePath);
4477 Record.push_back(Version.getMajor());
4478 if (std::optional<unsigned> Minor = Version.getMinor())
4479 Record.push_back(*Minor + 1);
4481 Record.push_back(0);
4482 if (std::optional<unsigned> Subminor = Version.getSubminor())
4483 Record.push_back(*Subminor + 1);
4485 Record.push_back(0);
4491 IdentID ID = IdentifierIDs[II];
4494 if (ID >= FirstIdentID)
4495 IdentifierOffsets[ID - FirstIdentID] =
Offset;
4501 unsigned ID = SelectorIDs[Sel];
4502 assert(ID &&
"Unknown selector");
4505 if (ID < FirstSelectorID)
4507 SelectorOffsets[ID - FirstSelectorID] =
Offset;
4513 ArrayRef<std::shared_ptr<ModuleFileExtension>> Extensions,
4514 bool IncludeTimestamps)
4515 : Stream(Stream), Buffer(Buffer), ModuleCache(ModuleCache),
4516 IncludeTimestamps(IncludeTimestamps) {
4517 for (
const auto &Ext : Extensions) {
4518 if (
auto Writer = Ext->createExtensionWriter(*
this))
4519 ModuleFileExtensionWriters.push_back(std::move(Writer));
4526 assert(WritingAST &&
"can't determine lang opts when not writing AST");
4535 Module *WritingModule, StringRef isysroot,
4537 bool ShouldCacheASTInMemory) {
4538 llvm::TimeTraceScope scope(
"WriteAST", OutputFile);
4541 ASTHasCompilerErrors = hasErrors;
4544 Stream.Emit((
unsigned)
'C', 8);
4545 Stream.Emit((
unsigned)
'P', 8);
4546 Stream.Emit((
unsigned)
'C', 8);
4547 Stream.Emit((
unsigned)
'H', 8);
4549 WriteBlockInfoBlock();
4553 this->WritingModule = WritingModule;
4554 ASTFileSignature Signature = WriteASTCore(SemaRef, isysroot, WritingModule);
4557 this->WritingModule =
nullptr;
4558 this->BaseDirectory.clear();
4561 if (ShouldCacheASTInMemory) {
4564 llvm::MemoryBuffer::getMemBufferCopy(
4565 StringRef(Buffer.begin(), Buffer.size())));
4570template<
typename Vector>
4573 for (
typename Vector::iterator I = Vec.begin(
nullptr,
true), E = Vec.end();
4579void ASTWriter::collectNonAffectingInputFiles() {
4583 IsSLocAffecting.resize(N,
true);
4588 auto AffectingModuleMaps = GetAffectingModuleMaps(*PP, WritingModule);
4590 unsigned FileIDAdjustment = 0;
4591 unsigned OffsetAdjustment = 0;
4593 NonAffectingFileIDAdjustments.reserve(N);
4594 NonAffectingOffsetAdjustments.reserve(N);
4596 NonAffectingFileIDAdjustments.push_back(FileIDAdjustment);
4597 NonAffectingOffsetAdjustments.push_back(OffsetAdjustment);
4599 for (
unsigned I = 1; I != N; ++I) {
4601 FileID FID = FileID::get(I);
4608 if (!
Cache->OrigEntry)
4612 AffectingModuleMaps.empty() ||
4613 AffectingModuleMaps.find(
Cache->OrigEntry) != AffectingModuleMaps.end())
4616 IsSLocAffecting[I] =
false;
4618 FileIDAdjustment += 1;
4624 if (!NonAffectingFileIDs.empty() &&
4625 NonAffectingFileIDs.back().ID == FID.ID - 1) {
4626 NonAffectingFileIDs.back() = FID;
4628 NonAffectingFileIDAdjustments.back() = FileIDAdjustment;
4629 NonAffectingOffsetAdjustments.back() = OffsetAdjustment;
4633 NonAffectingFileIDs.push_back(FID);
4636 NonAffectingFileIDAdjustments.push_back(FileIDAdjustment);
4637 NonAffectingOffsetAdjustments.push_back(OffsetAdjustment);
4643 using namespace llvm;
4645 bool isModule = WritingModule !=
nullptr;
4654 collectNonAffectingInputFiles();
4668 RegisterPredefDecl(Context.ObjCProtocolClassDecl,
4672 RegisterPredefDecl(Context.ObjCInstanceTypeDecl,
4676 RegisterPredefDecl(Context.BuiltinMSVaListDecl,
4681 RegisterPredefDecl(Context.MakeIntegerSeqDecl,
4683 RegisterPredefDecl(Context.CFConstantStringTypeDecl,
4685 RegisterPredefDecl(Context.CFConstantStringTagDecl,
4687 RegisterPredefDecl(Context.TypePackElementDecl,
4700 UnusedFileScopedDecls);
4712 for (
const auto &WeakUndeclaredIdentifierList :
4714 const IdentifierInfo *
const II = WeakUndeclaredIdentifierList.first;
4715 for (
const auto &WI : WeakUndeclaredIdentifierList.second) {
4729 for (
unsigned I = 0, N = SemaRef.
VTableUses.size(); I != N; ++I) {
4739 AddDeclRef(TD, UnusedLocalTypedefNameCandidates);
4748 "There are local ones at end of translation unit!");
4765 for (
const auto &I : SemaRef.KnownNamespaces) {
4775 for (
const auto &I : Undefined) {
4785 for (
const auto &DeleteExprsInfo :
4787 AddDeclRef(DeleteExprsInfo.first, DeleteExprsToAnalyze);
4788 DeleteExprsToAnalyze.push_back(DeleteExprsInfo.second.size());
4789 for (
const auto &DeleteLoc : DeleteExprsInfo.second) {
4791 DeleteExprsToAnalyze.push_back(DeleteLoc.second);
4797 WriteControlBlock(PP, Context, isysroot);
4800 Stream.FlushToWord();
4801 ASTBlockRange.first = Stream.GetCurrentBitNo();
4803 ASTBlockStartOffset = Stream.GetCurrentBitNo();
4818 NewGlobalKindDeclPairs.push_back(D->
getKind());
4819 NewGlobalKindDeclPairs.push_back(
GetDeclRef(D));
4823 auto Abv = std::make_shared<BitCodeAbbrev>();
4825 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::Blob));
4826 unsigned TuUpdateLexicalAbbrev = Stream.EmitAbbrev(std::move(Abv));
4829 Stream.EmitRecordWithBlob(TuUpdateLexicalAbbrev, Record,
4830 bytes(NewGlobalKindDeclPairs));
4834 Abv = std::make_shared<BitCodeAbbrev>();
4836 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::VBR, 6));
4837 Abv->Add(llvm::BitCodeAbbrevOp(llvm::BitCodeAbbrevOp::Blob));
4838 UpdateVisibleAbbrev = Stream.EmitAbbrev(std::move(Abv));
4839 WriteDeclContextVisibleUpdate(TU);
4842 if (Context.ExternCContext)
4843 WriteDeclContextVisibleUpdate(Context.ExternCContext);
4857 for (
const auto &Number : Context.MangleNumbers)
4858 if (!Number.first->isFromASTFile())
4861 for (
const auto &Number : Context.StaticLocalNumbers)
4862 if (!Number.first->isFromASTFile())
4869 for (
const auto *I : DeclsToEmitEvenIfUnreferenced) {
4883 llvm::sort(IIs, llvm::deref<std::less<>>());
4901 for (
auto &SelectorAndID : SelectorIDs)
4902 AllSelectors.push_back(SelectorAndID.first);
4903 for (
auto &
Selector : AllSelectors)
4912 AddTypeRef(Context.ObjCIdRedefinitionType, SpecialTypes);
4913 AddTypeRef(Context.ObjCClassRedefinitionType, SpecialTypes);
4914 AddTypeRef(Context.ObjCSelRedefinitionType, SpecialTypes);
4937 auto Abbrev = std::make_shared<BitCodeAbbrev>();
4939 Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
4940 unsigned ModuleOffsetMapAbbrev = Stream.EmitAbbrev(std::move(Abbrev));
4943 llvm::raw_svector_ostream Out(Buffer);
4945 using namespace llvm::support;
4947 endian::Writer
LE(Out, little);
4948 LE.write<uint8_t>(
static_cast<uint8_t
>(M.
Kind));
4950 LE.write<uint16_t>(Name.size());
4951 Out.write(Name.data(), Name.size());
4955 uint32_t
None = std::numeric_limits<uint32_t>::max();
4957 auto writeBaseIDOrNone = [&](
auto BaseID,
bool ShouldWrite) {
4958 assert(BaseID < std::numeric_limits<uint32_t>::max() &&
"base id too high");
4960 LE.write<uint32_t>(BaseID);
4962 LE.write<uint32_t>(
None);
4979 Stream.EmitRecordWithBlob(ModuleOffsetMapAbbrev, Record,
4980 Buffer.data(), Buffer.size());
4985 for (
auto *D : SemaRef.DeclsToCheckForDeferredDiags)
4986 DeclsToCheckForDeferredDiags.push_back(
GetDeclRef(D));
4993 DeclTypesBlockStartOffset = Stream.GetCurrentBitNo();
4997 WriteDeclUpdatesBlocks(DeclUpdatesOffsetsRecord);
4998 while (!DeclTypesToEmit.empty()) {
4999 DeclOrType DOT = DeclTypesToEmit.front();
5000 DeclTypesToEmit.pop();
5002 WriteType(DOT.getType());
5004 WriteDecl(Context, DOT.getDecl());
5006 }
while (!DeclUpdates.empty());
5009 DoneWritingDeclsAndTypes =
true;
5012 WriteTypeDeclOffsets();
5013 if (!DeclUpdatesOffsetsRecord.empty())
5015 WriteFileDeclIDsMap();
5018 WritePreprocessor(PP, isModule);
5020 WriteSelectors(SemaRef);
5021 WriteReferencedSelectorsPool(SemaRef);
5022 WriteLateParsedTemplates(SemaRef);
5023 WriteIdentifierTable(PP, SemaRef.
IdResolver, isModule);
5025 WriteOpenCLExtensions(SemaRef);
5026 WriteCUDAPragmas(SemaRef);
5030 WriteSubmodules(WritingModule);
5035 if (!EagerlyDeserializedDecls.empty())
5038 if (!ModularCodegenDecls.empty())
5042 if (!TentativeDefinitions.empty())
5046 if (!UnusedFileScopedDecls.empty())
5050 if (!WeakUndeclaredIdentifiers.empty())
5052 WeakUndeclaredIdentifiers);
5055 if (!ExtVectorDecls.empty())
5059 if (!VTableUses.empty())
5063 if (!UnusedLocalTypedefNameCandidates.empty())
5065 UnusedLocalTypedefNameCandidates);
5068 if (!PendingInstantiations.empty())
5072 if (!SemaDeclRefs.empty())
5076 if (!DeclsToCheckForDeferredDiags.empty())
5078 DeclsToCheckForDeferredDiags);