[AMDGPU][AsmParser][NFC] Translate parsed MIMG instructions to MCInsts automatically.
[llvm-project.git] / clang-tools-extra / clang-tidy / utils / IncludeInserter.cpp
blobd0b7474992abd0853229a8186481dc92c5b0527f
1 //===-------- IncludeInserter.cpp - clang-tidy ----------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
9 #include "IncludeInserter.h"
10 #include "clang/Lex/PPCallbacks.h"
11 #include "clang/Lex/Preprocessor.h"
12 #include "clang/Lex/Token.h"
13 #include <optional>
15 namespace clang::tidy::utils {
17 class IncludeInserterCallback : public PPCallbacks {
18 public:
19 explicit IncludeInserterCallback(IncludeInserter *Inserter)
20 : Inserter(Inserter) {}
21 // Implements PPCallbacks::InclusionDirective(). Records the names and source
22 // locations of the inclusions in the main source file being processed.
23 void InclusionDirective(SourceLocation HashLocation,
24 const Token &IncludeToken, StringRef FileNameRef,
25 bool IsAngled, CharSourceRange FileNameRange,
26 OptionalFileEntryRef /*IncludedFile*/,
27 StringRef /*SearchPath*/, StringRef /*RelativePath*/,
28 const Module * /*ImportedModule*/,
29 SrcMgr::CharacteristicKind /*FileType*/) override {
30 Inserter->addInclude(FileNameRef, IsAngled, HashLocation,
31 IncludeToken.getEndLoc());
34 private:
35 IncludeInserter *Inserter;
38 IncludeInserter::IncludeInserter(IncludeSorter::IncludeStyle Style,
39 bool SelfContainedDiags)
40 : Style(Style), SelfContainedDiags(SelfContainedDiags) {}
42 void IncludeInserter::registerPreprocessor(Preprocessor *PP) {
43 assert(PP && "PP shouldn't be null");
44 SourceMgr = &PP->getSourceManager();
46 // If this gets registered multiple times, clear the maps
47 if (!IncludeSorterByFile.empty())
48 IncludeSorterByFile.clear();
49 if (!InsertedHeaders.empty())
50 InsertedHeaders.clear();
51 PP->addPPCallbacks(std::make_unique<IncludeInserterCallback>(this));
54 IncludeSorter &IncludeInserter::getOrCreate(FileID FileID) {
55 assert(SourceMgr && "SourceMgr shouldn't be null; did you remember to call "
56 "registerPreprocessor()?");
57 // std::unique_ptr is cheap to construct, so force a construction now to save
58 // the lookup needed if we were to insert into the map.
59 std::unique_ptr<IncludeSorter> &Entry = IncludeSorterByFile[FileID];
60 if (!Entry) {
61 // If it wasn't found, Entry will be default constructed to nullptr.
62 Entry = std::make_unique<IncludeSorter>(
63 SourceMgr, FileID,
64 SourceMgr->getFilename(SourceMgr->getLocForStartOfFile(FileID)), Style);
66 return *Entry;
69 std::optional<FixItHint>
70 IncludeInserter::createIncludeInsertion(FileID FileID, llvm::StringRef Header) {
71 bool IsAngled = Header.consume_front("<");
72 if (IsAngled != Header.consume_back(">"))
73 return std::nullopt;
74 // We assume the same Header will never be included both angled and not
75 // angled.
76 // In self contained diags mode we don't track what headers we have already
77 // inserted.
78 if (!SelfContainedDiags && !InsertedHeaders[FileID].insert(Header).second)
79 return std::nullopt;
81 return getOrCreate(FileID).createIncludeInsertion(Header, IsAngled);
84 std::optional<FixItHint>
85 IncludeInserter::createMainFileIncludeInsertion(StringRef Header) {
86 assert(SourceMgr && "SourceMgr shouldn't be null; did you remember to call "
87 "registerPreprocessor()?");
88 return createIncludeInsertion(SourceMgr->getMainFileID(), Header);
91 void IncludeInserter::addInclude(StringRef FileName, bool IsAngled,
92 SourceLocation HashLocation,
93 SourceLocation EndLocation) {
94 assert(SourceMgr && "SourceMgr shouldn't be null; did you remember to call "
95 "registerPreprocessor()?");
96 FileID FileID = SourceMgr->getFileID(HashLocation);
97 getOrCreate(FileID).addInclude(FileName, IsAngled, HashLocation, EndLocation);
100 } // namespace clang::tidy::utils