//===-------- IncludeInserter.cpp - clang-tidy ----------------------------===// // // The LLVM Compiler Infrastructure // // This file is distributed under the University of Illinois Open Source // License. See LICENSE.TXT for details. // //===----------------------------------------------------------------------===// #include "IncludeInserter.h" #include "clang/Lex/Token.h" namespace clang { namespace tidy { namespace utils { class IncludeInserterCallback : public PPCallbacks { public: explicit IncludeInserterCallback(IncludeInserter *Inserter) : Inserter(Inserter) {} // Implements PPCallbacks::InclusionDerective(). Records the names and source // locations of the inclusions in the main source file being processed. void InclusionDirective(SourceLocation HashLocation, const Token &IncludeToken, StringRef FileNameRef, bool IsAngled, CharSourceRange FileNameRange, const FileEntry * /*IncludedFile*/, StringRef /*SearchPath*/, StringRef /*RelativePath*/, const Module * /*ImportedModule*/, SrcMgr::CharacteristicKind /*FileType*/) override { Inserter->AddInclude(FileNameRef, IsAngled, HashLocation, IncludeToken.getEndLoc()); } private: IncludeInserter *Inserter; }; IncludeInserter::IncludeInserter(const SourceManager &SourceMgr, const LangOptions &LangOpts, IncludeSorter::IncludeStyle Style) : SourceMgr(SourceMgr), LangOpts(LangOpts), Style(Style) {} IncludeInserter::~IncludeInserter() {} std::unique_ptr IncludeInserter::CreatePPCallbacks() { return llvm::make_unique(this); } llvm::Optional IncludeInserter::CreateIncludeInsertion(FileID FileID, StringRef Header, bool IsAngled) { // We assume the same Header will never be included both angled and not // angled. if (!InsertedHeaders[FileID].insert(Header).second) return llvm::None; if (IncludeSorterByFile.find(FileID) == IncludeSorterByFile.end()) { // This may happen if there have been no preprocessor directives in this // file. IncludeSorterByFile.insert(std::make_pair( FileID, llvm::make_unique( &SourceMgr, &LangOpts, FileID, SourceMgr.getFilename(SourceMgr.getLocForStartOfFile(FileID)), Style))); } return IncludeSorterByFile[FileID]->CreateIncludeInsertion(Header, IsAngled); } void IncludeInserter::AddInclude(StringRef FileName, bool IsAngled, SourceLocation HashLocation, SourceLocation EndLocation) { FileID FileID = SourceMgr.getFileID(HashLocation); if (IncludeSorterByFile.find(FileID) == IncludeSorterByFile.end()) { IncludeSorterByFile.insert(std::make_pair( FileID, llvm::make_unique( &SourceMgr, &LangOpts, FileID, SourceMgr.getFilename(HashLocation), Style))); } IncludeSorterByFile[FileID]->AddInclude(FileName, IsAngled, HashLocation, EndLocation); } } // namespace utils } // namespace tidy } // namespace clang