[cfe-commits] r143238 - in /cfe/trunk: include/clang/Serialization/ASTBitCodes.h include/clang/Serialization/ASTReader.h include/clang/Serialization/ASTWriter.h include/clang/Serialization/Module.h lib/Serialization/ASTReader.cpp lib/Serialization/ASTWriter.cpp lib/Serialization/ASTWriterDecl.cpp lib/Serialization/Module.cpp
Argyrios Kyrtzidis
akyrtzi at gmail.com
Fri Oct 28 15:54:21 PDT 2011
Author: akirtzidis
Date: Fri Oct 28 17:54:21 2011
New Revision: 143238
URL: http://llvm.org/viewvc/llvm-project?rev=143238&view=rev
Log:
[PCH] Keep track of file-level declarations that are contained by files.
Introduce a FILE_SORTED_DECLS [de]serialization record that contains
a file sorted array of file-level DeclIDs in a PCH/Module.
The rationale is to allow "targeted" deserialization of decls inside
a range of a source file.
Cocoa PCH increased by 0.8%
Difference of creation time for Cocoa PCH is below the noise level.
Modified:
cfe/trunk/include/clang/Serialization/ASTBitCodes.h
cfe/trunk/include/clang/Serialization/ASTReader.h
cfe/trunk/include/clang/Serialization/ASTWriter.h
cfe/trunk/include/clang/Serialization/Module.h
cfe/trunk/lib/Serialization/ASTReader.cpp
cfe/trunk/lib/Serialization/ASTWriter.cpp
cfe/trunk/lib/Serialization/ASTWriterDecl.cpp
cfe/trunk/lib/Serialization/Module.cpp
Modified: cfe/trunk/include/clang/Serialization/ASTBitCodes.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Serialization/ASTBitCodes.h?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/include/clang/Serialization/ASTBitCodes.h (original)
+++ cfe/trunk/include/clang/Serialization/ASTBitCodes.h Fri Oct 28 17:54:21 2011
@@ -436,7 +436,10 @@
/// \brief Record code for ObjC categories in a module that are chained to
/// an interface.
- OBJC_CHAINED_CATEGORIES
+ OBJC_CHAINED_CATEGORIES,
+
+ /// \brief Record code for a file sorted array of DeclIDs in a module.
+ FILE_SORTED_DECLS
};
/// \brief Record types used within a source manager block.
Modified: cfe/trunk/include/clang/Serialization/ASTReader.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Serialization/ASTReader.h?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/include/clang/Serialization/ASTReader.h (original)
+++ cfe/trunk/include/clang/Serialization/ASTReader.h Fri Oct 28 17:54:21 2011
@@ -296,6 +296,9 @@
/// \brief Declarations that have been replaced in a later file in the chain.
DeclReplacementMap ReplacedDecls;
+ /// \brief Map from a FileID to the file-level declarations that it contains.
+ llvm::DenseMap<FileID, ArrayRef<serialization::DeclID> > FileDeclIDs;
+
// Updates for visible decls can occur for other contexts than just the
// TU, and when we read those update records, the actual context will not
// be available yet (unless it's the TU), so have this pending map using the
Modified: cfe/trunk/include/clang/Serialization/ASTWriter.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Serialization/ASTWriter.h?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/include/clang/Serialization/ASTWriter.h (original)
+++ cfe/trunk/include/clang/Serialization/ASTWriter.h Fri Oct 28 17:54:21 2011
@@ -59,6 +59,8 @@
class TargetInfo;
class VersionTuple;
+namespace SrcMgr { class SLocEntry; }
+
/// \brief Writes an AST file containing the contents of a translation unit.
///
/// The ASTWriter class produces a bitstream containing the serialized
@@ -144,6 +146,25 @@
/// the declaration's ID.
std::vector<serialization::DeclOffset> DeclOffsets;
+ /// \brief Vector of pairs of raw location/DeclID.
+ typedef SmallVector<std::pair<unsigned, serialization::DeclID>, 64>
+ LocDeclIDsTy;
+ struct DeclIDInFileInfo {
+ LocDeclIDsTy DeclIDs;
+ /// \brief Set when the DeclIDs vectors from all files are joined, this
+ /// indicates the index that this particular vector has in the global one.
+ unsigned FirstDeclIndex;
+ };
+ typedef llvm::DenseMap<const SrcMgr::SLocEntry *,
+ DeclIDInFileInfo *> FileDeclIDsTy;
+
+ /// \brief Map from file SLocEntries to info about the file-level declarations
+ /// that it contains.
+ FileDeclIDsTy FileDeclIDs;
+
+ void associateDeclWithFile(const Decl *D, serialization::DeclID,
+ SourceLocation FileLoc);
+
/// \brief The first ID number we can use for our own types.
serialization::TypeID FirstTypeID;
@@ -354,6 +375,7 @@
uint64_t WriteDeclContextLexicalBlock(ASTContext &Context, DeclContext *DC);
uint64_t WriteDeclContextVisibleBlock(ASTContext &Context, DeclContext *DC);
void WriteTypeDeclOffsets();
+ void WriteFileDeclIDsMap();
void WriteSelectors(Sema &SemaRef);
void WriteReferencedSelectorsPool(Sema &SemaRef);
void WriteIdentifierTable(Preprocessor &PP, IdentifierResolver &IdResolver,
@@ -393,6 +415,7 @@
/// \brief Create a new precompiled header writer that outputs to
/// the given bitstream.
ASTWriter(llvm::BitstreamWriter &Stream);
+ ~ASTWriter();
/// \brief Write a precompiled header for the given semantic analysis.
///
Modified: cfe/trunk/include/clang/Serialization/Module.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Serialization/Module.h?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/include/clang/Serialization/Module.h (original)
+++ cfe/trunk/include/clang/Serialization/Module.h Fri Oct 28 17:54:21 2011
@@ -271,6 +271,9 @@
/// Key is the ID of the interface.
/// Value is a pair of linked category DeclIDs (head category, tail category).
ChainedObjCCategoriesMap ChainedObjCCategories;
+
+ /// \brief Array of file-level DeclIDs sorted by file.
+ const serialization::DeclID *FileSortedDecls;
// === Types ===
Modified: cfe/trunk/lib/Serialization/ASTReader.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTReader.cpp?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/lib/Serialization/ASTReader.cpp (original)
+++ cfe/trunk/lib/Serialization/ASTReader.cpp Fri Oct 28 17:54:21 2011
@@ -1134,6 +1134,13 @@
FileInfo.NumCreatedFIDs = Record[6];
if (Record[3])
FileInfo.setHasLineDirectives();
+
+ const DeclID *FirstDecl = F->FileSortedDecls + Record[7];
+ unsigned NumFileDecls = Record[8];
+ if (NumFileDecls) {
+ assert(F->FileSortedDecls && "FILE_SORTED_DECLS not encountered yet ?");
+ FileDeclIDs[FID] = llvm::makeArrayRef(FirstDecl, NumFileDecls);
+ }
break;
}
@@ -1960,6 +1967,10 @@
if (!Record.empty() && Listener)
Listener->ReadCounter(Record[0]);
break;
+
+ case FILE_SORTED_DECLS:
+ F.FileSortedDecls = (const DeclID *)BlobStart;
+ break;
case SOURCE_LOCATION_OFFSETS: {
F.SLocEntryOffsets = (const uint32_t *)BlobStart;
Modified: cfe/trunk/lib/Serialization/ASTWriter.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTWriter.cpp?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/lib/Serialization/ASTWriter.cpp (original)
+++ cfe/trunk/lib/Serialization/ASTWriter.cpp Fri Oct 28 17:54:21 2011
@@ -1172,6 +1172,8 @@
Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 12)); // Size
Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 32)); // Modification time
Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8)); // NumCreatedFIDs
+ Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 24)); // FirstDeclIndex
+ Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 8)); // NumDecls
Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob)); // File name
return Stream.EmitAbbrev(Abbrev);
}
@@ -1445,6 +1447,15 @@
Record.push_back(Content->OrigEntry->getModificationTime());
Record.push_back(File.NumCreatedFIDs);
+
+ FileDeclIDsTy::iterator FDI = FileDeclIDs.find(SLoc);
+ if (FDI != FileDeclIDs.end()) {
+ Record.push_back(FDI->second->FirstDeclIndex);
+ Record.push_back(FDI->second->DeclIDs.size());
+ } else {
+ Record.push_back(0);
+ Record.push_back(0);
+ }
// Turn the file name into an absolute path, if it isn't already.
const char *Filename = Content->OrigEntry->getName();
@@ -1972,6 +1983,29 @@
Stream.EmitRecordWithBlob(DeclOffsetAbbrev, Record, data(DeclOffsets));
}
+void ASTWriter::WriteFileDeclIDsMap() {
+ using namespace llvm;
+ RecordData Record;
+
+ // Join the vectors of DeclIDs from all files.
+ SmallVector<DeclID, 256> FileSortedIDs;
+ for (FileDeclIDsTy::iterator
+ FI = FileDeclIDs.begin(), FE = FileDeclIDs.end(); FI != FE; ++FI) {
+ DeclIDInFileInfo &Info = *FI->second;
+ Info.FirstDeclIndex = FileSortedIDs.size();
+ for (LocDeclIDsTy::iterator
+ DI = Info.DeclIDs.begin(), DE = Info.DeclIDs.end(); DI != DE; ++DI)
+ FileSortedIDs.push_back(DI->second);
+ }
+
+ BitCodeAbbrev *Abbrev = new BitCodeAbbrev();
+ Abbrev->Add(BitCodeAbbrevOp(FILE_SORTED_DECLS));
+ Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
+ unsigned AbbrevCode = Stream.EmitAbbrev(Abbrev);
+ Record.push_back(FILE_SORTED_DECLS);
+ Stream.EmitRecordWithBlob(AbbrevCode, Record, data(FileSortedIDs));
+}
+
//===----------------------------------------------------------------------===//
// Global Method Pool and Selector Serialization
//===----------------------------------------------------------------------===//
@@ -2732,6 +2766,12 @@
{
}
+ASTWriter::~ASTWriter() {
+ for (FileDeclIDsTy::iterator
+ I = FileDeclIDs.begin(), E = FileDeclIDs.end(); I != E; ++I)
+ delete I->second;
+}
+
void ASTWriter::WriteAST(Sema &SemaRef, MemorizeStatCalls *StatCalls,
const std::string &OutputFile,
bool IsModule, StringRef isysroot) {
@@ -2910,49 +2950,6 @@
WriteLanguageOptions(Context.getLangOptions());
if (StatCalls && isysroot.empty())
WriteStatCache(*StatCalls);
- WriteSourceManagerBlock(Context.getSourceManager(), PP, isysroot);
-
- if (Chain) {
- // Write the mapping information describing our module dependencies and how
- // each of those modules were mapped into our own offset/ID space, so that
- // the reader can build the appropriate mapping to its own offset/ID space.
- // The map consists solely of a blob with the following format:
- // *(module-name-len:i16 module-name:len*i8
- // source-location-offset:i32
- // identifier-id:i32
- // preprocessed-entity-id:i32
- // macro-definition-id:i32
- // selector-id:i32
- // declaration-id:i32
- // c++-base-specifiers-id:i32
- // type-id:i32)
- //
- llvm::BitCodeAbbrev *Abbrev = new BitCodeAbbrev();
- Abbrev->Add(BitCodeAbbrevOp(MODULE_OFFSET_MAP));
- Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
- unsigned ModuleOffsetMapAbbrev = Stream.EmitAbbrev(Abbrev);
- llvm::SmallString<2048> Buffer;
- {
- llvm::raw_svector_ostream Out(Buffer);
- for (ModuleManager::ModuleConstIterator M = Chain->ModuleMgr.begin(),
- MEnd = Chain->ModuleMgr.end();
- M != MEnd; ++M) {
- StringRef FileName = (*M)->FileName;
- io::Emit16(Out, FileName.size());
- Out.write(FileName.data(), FileName.size());
- io::Emit32(Out, (*M)->SLocEntryBaseOffset);
- io::Emit32(Out, (*M)->BaseIdentifierID);
- io::Emit32(Out, (*M)->BasePreprocessedEntityID);
- io::Emit32(Out, (*M)->BaseSelectorID);
- io::Emit32(Out, (*M)->BaseDeclID);
- io::Emit32(Out, (*M)->BaseTypeIndex);
- }
- }
- Record.clear();
- Record.push_back(MODULE_OFFSET_MAP);
- Stream.EmitRecordWithBlob(ModuleOffsetMapAbbrev, Record,
- Buffer.data(), Buffer.size());
- }
// Create a lexical update block containing all of the declarations in the
// translation unit that do not come from other AST files.
@@ -3030,6 +3027,51 @@
}
Stream.ExitBlock();
+ WriteFileDeclIDsMap();
+ WriteSourceManagerBlock(Context.getSourceManager(), PP, isysroot);
+
+ if (Chain) {
+ // Write the mapping information describing our module dependencies and how
+ // each of those modules were mapped into our own offset/ID space, so that
+ // the reader can build the appropriate mapping to its own offset/ID space.
+ // The map consists solely of a blob with the following format:
+ // *(module-name-len:i16 module-name:len*i8
+ // source-location-offset:i32
+ // identifier-id:i32
+ // preprocessed-entity-id:i32
+ // macro-definition-id:i32
+ // selector-id:i32
+ // declaration-id:i32
+ // c++-base-specifiers-id:i32
+ // type-id:i32)
+ //
+ llvm::BitCodeAbbrev *Abbrev = new BitCodeAbbrev();
+ Abbrev->Add(BitCodeAbbrevOp(MODULE_OFFSET_MAP));
+ Abbrev->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));
+ unsigned ModuleOffsetMapAbbrev = Stream.EmitAbbrev(Abbrev);
+ llvm::SmallString<2048> Buffer;
+ {
+ llvm::raw_svector_ostream Out(Buffer);
+ for (ModuleManager::ModuleConstIterator M = Chain->ModuleMgr.begin(),
+ MEnd = Chain->ModuleMgr.end();
+ M != MEnd; ++M) {
+ StringRef FileName = (*M)->FileName;
+ io::Emit16(Out, FileName.size());
+ Out.write(FileName.data(), FileName.size());
+ io::Emit32(Out, (*M)->SLocEntryBaseOffset);
+ io::Emit32(Out, (*M)->BaseIdentifierID);
+ io::Emit32(Out, (*M)->BasePreprocessedEntityID);
+ io::Emit32(Out, (*M)->BaseSelectorID);
+ io::Emit32(Out, (*M)->BaseDeclID);
+ io::Emit32(Out, (*M)->BaseTypeIndex);
+ }
+ }
+ Record.clear();
+ Record.push_back(MODULE_OFFSET_MAP);
+ Stream.EmitRecordWithBlob(ModuleOffsetMapAbbrev, Record,
+ Buffer.data(), Buffer.size());
+ }
+
WritePreprocessor(PP, IsModule);
WriteHeaderSearch(PP.getHeaderSearchInfo(), isysroot);
WriteSelectors(SemaRef);
@@ -3439,6 +3481,48 @@
return DeclIDs[D];
}
+static inline bool compLocDecl(std::pair<unsigned, serialization::DeclID> L,
+ std::pair<unsigned, serialization::DeclID> R) {
+ return L.first < R.first;
+}
+
+void ASTWriter::associateDeclWithFile(const Decl *D, DeclID ID,
+ SourceLocation FileLoc) {
+ assert(ID);
+ assert(FileLoc.isValid());
+ assert(FileLoc.isFileID());
+
+ // We only keep track of the file-level declarations of each file.
+ if (!D->getLexicalDeclContext()->isFileContext())
+ return;
+
+ SourceManager &SM = Context->getSourceManager();
+ assert(SM.isLocalSourceLocation(FileLoc));
+ FileID FID = SM.getFileID(FileLoc);
+ if (FID.isInvalid())
+ return;
+ const SrcMgr::SLocEntry *Entry = &SM.getSLocEntry(FID);
+ assert(Entry->isFile());
+
+ DeclIDInFileInfo *&Info = FileDeclIDs[Entry];
+ if (!Info)
+ Info = new DeclIDInFileInfo();
+
+ unsigned RawLoc = FileLoc.getRawEncoding();
+ std::pair<unsigned, serialization::DeclID> LocDecl(RawLoc, ID);
+ LocDeclIDsTy &Decls = Info->DeclIDs;
+
+ if (Decls.empty() || Decls.back().first <= RawLoc) {
+ Decls.push_back(LocDecl);
+ return;
+ }
+
+ LocDeclIDsTy::iterator
+ I = std::upper_bound(Decls.begin(), Decls.end(), LocDecl, compLocDecl);
+
+ Decls.insert(I, LocDecl);
+}
+
void ASTWriter::AddDeclarationName(DeclarationName Name, RecordDataImpl &Record) {
// FIXME: Emit a stable enum for NameKind. 0 = Identifier etc.
Record.push_back(Name.getNameKind());
Modified: cfe/trunk/lib/Serialization/ASTWriterDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTWriterDecl.cpp?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/lib/Serialization/ASTWriterDecl.cpp (original)
+++ cfe/trunk/lib/Serialization/ASTWriterDecl.cpp Fri Oct 28 17:54:21 2011
@@ -18,6 +18,7 @@
#include "clang/AST/DeclTemplate.h"
#include "clang/AST/Expr.h"
#include "clang/AST/DeclContextInternals.h"
+#include "clang/Basic/SourceManager.h"
#include "llvm/ADT/Twine.h"
#include "llvm/Bitcode/BitstreamWriter.h"
#include "llvm/Support/ErrorHandling.h"
@@ -1651,14 +1652,20 @@
unsigned Index = ID - FirstDeclID;
// Record the offset for this declaration
+ SourceLocation Loc = D->getLocation();
if (DeclOffsets.size() == Index)
- DeclOffsets.push_back(DeclOffset(D->getLocation(),
- Stream.GetCurrentBitNo()));
+ DeclOffsets.push_back(DeclOffset(Loc, Stream.GetCurrentBitNo()));
else if (DeclOffsets.size() < Index) {
DeclOffsets.resize(Index+1);
- DeclOffsets[Index].setLocation(D->getLocation());
+ DeclOffsets[Index].setLocation(Loc);
DeclOffsets[Index].BitOffset = Stream.GetCurrentBitNo();
}
+
+ SourceManager &SM = Context.getSourceManager();
+ if (Loc.isValid() && SM.isLocalSourceLocation(Loc)) {
+ SourceLocation FileLoc = SM.getFileLoc(Loc);
+ associateDeclWithFile(D, ID, FileLoc);
+ }
}
// Build and emit a record for this declaration
Modified: cfe/trunk/lib/Serialization/Module.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/Module.cpp?rev=143238&r1=143237&r2=143238&view=diff
==============================================================================
--- cfe/trunk/lib/Serialization/Module.cpp (original)
+++ cfe/trunk/lib/Serialization/Module.cpp Fri Oct 28 17:54:21 2011
@@ -35,6 +35,7 @@
SelectorLookupTableData(0), SelectorLookupTable(0), LocalNumDecls(0),
DeclOffsets(0), BaseDeclID(0),
LocalNumCXXBaseSpecifiers(0), CXXBaseSpecifiersOffsets(0),
+ FileSortedDecls(0),
LocalNumTypes(0), TypeOffsets(0), BaseTypeIndex(0), StatCache(0)
{}
More information about the cfe-commits
mailing list