Showing
1000 changed files
with
611 additions
and
1737 deletions
Too many changes to show.
To preserve performance only 1000 of 1000+ files are displayed.
llvm-project/.vscode/settings.json
0 → 100644
1 | +{ | ||
2 | + "files.associations": { | ||
3 | + "algorithm": "cpp", | ||
4 | + "typeinfo": "cpp", | ||
5 | + "cmath": "cpp", | ||
6 | + "cstdlib": "cpp", | ||
7 | + "limits": "cpp", | ||
8 | + "vector": "cpp", | ||
9 | + "__bit_reference": "cpp", | ||
10 | + "__config": "cpp", | ||
11 | + "__debug": "cpp", | ||
12 | + "__functional_base": "cpp", | ||
13 | + "__hash_table": "cpp", | ||
14 | + "__locale": "cpp", | ||
15 | + "__node_handle": "cpp", | ||
16 | + "__nullptr": "cpp", | ||
17 | + "__split_buffer": "cpp", | ||
18 | + "__threading_support": "cpp", | ||
19 | + "__tuple": "cpp", | ||
20 | + "array": "cpp", | ||
21 | + "atomic": "cpp", | ||
22 | + "bit": "cpp", | ||
23 | + "bitset": "cpp", | ||
24 | + "cctype": "cpp", | ||
25 | + "chrono": "cpp", | ||
26 | + "cstdarg": "cpp", | ||
27 | + "cstddef": "cpp", | ||
28 | + "cstdint": "cpp", | ||
29 | + "cstdio": "cpp", | ||
30 | + "cstring": "cpp", | ||
31 | + "ctime": "cpp", | ||
32 | + "cwchar": "cpp", | ||
33 | + "exception": "cpp", | ||
34 | + "functional": "cpp", | ||
35 | + "initializer_list": "cpp", | ||
36 | + "ios": "cpp", | ||
37 | + "iosfwd": "cpp", | ||
38 | + "iostream": "cpp", | ||
39 | + "istream": "cpp", | ||
40 | + "iterator": "cpp", | ||
41 | + "locale": "cpp", | ||
42 | + "memory": "cpp", | ||
43 | + "mutex": "cpp", | ||
44 | + "new": "cpp", | ||
45 | + "numeric": "cpp", | ||
46 | + "optional": "cpp", | ||
47 | + "ostream": "cpp", | ||
48 | + "random": "cpp", | ||
49 | + "ratio": "cpp", | ||
50 | + "set": "cpp", | ||
51 | + "sstream": "cpp", | ||
52 | + "stdexcept": "cpp", | ||
53 | + "streambuf": "cpp", | ||
54 | + "string": "cpp", | ||
55 | + "string_view": "cpp", | ||
56 | + "system_error": "cpp", | ||
57 | + "tuple": "cpp", | ||
58 | + "type_traits": "cpp", | ||
59 | + "unordered_map": "cpp", | ||
60 | + "utility": "cpp", | ||
61 | + "*.tcc": "cpp", | ||
62 | + "memory_resource": "cpp", | ||
63 | + "clocale": "cpp", | ||
64 | + "condition_variable": "cpp", | ||
65 | + "cwctype": "cpp", | ||
66 | + "deque": "cpp", | ||
67 | + "list": "cpp", | ||
68 | + "fstream": "cpp", | ||
69 | + "shared_mutex": "cpp", | ||
70 | + "thread": "cpp", | ||
71 | + "mock_vector": "cpp", | ||
72 | + "*.inc": "cpp", | ||
73 | + "filesystem": "cpp", | ||
74 | + "*.def": "cpp", | ||
75 | + "queue": "cpp", | ||
76 | + "stack": "cpp" | ||
77 | + } | ||
78 | +} | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
1 | include(CMakeDependentOption) | 1 | include(CMakeDependentOption) |
2 | 2 | ||
3 | -option(CLANG_TIDY_ENABLE_STATIC_ANALYZER | ||
4 | - "Include static analyzer checks in clang-tidy" ON) | ||
5 | - | ||
6 | add_subdirectory(clang-apply-replacements) | 3 | add_subdirectory(clang-apply-replacements) |
7 | add_subdirectory(clang-reorder-fields) | 4 | add_subdirectory(clang-reorder-fields) |
8 | add_subdirectory(modularize) | 5 | add_subdirectory(modularize) | ... | ... |
... | @@ -99,7 +99,7 @@ CreateSymbolInfo(const NamedDecl *ND, const SourceManager &SM, | ... | @@ -99,7 +99,7 @@ CreateSymbolInfo(const NamedDecl *ND, const SourceManager &SM, |
99 | 99 | ||
100 | SourceLocation Loc = SM.getExpansionLoc(ND->getLocation()); | 100 | SourceLocation Loc = SM.getExpansionLoc(ND->getLocation()); |
101 | if (!Loc.isValid()) { | 101 | if (!Loc.isValid()) { |
102 | - llvm::errs() << "Declaration " << ND->getDeclName() << "(" | 102 | + llvm::errs() << "Declaration " << ND->getNameAsString() << "(" |
103 | << ND->getDeclKindName() | 103 | << ND->getDeclKindName() |
104 | << ") has invalid declaration location."; | 104 | << ") has invalid declaration location."; |
105 | return llvm::None; | 105 | return llvm::None; | ... | ... |
... | @@ -116,7 +116,7 @@ void HelperDeclRGBuilder::run( | ... | @@ -116,7 +116,7 @@ void HelperDeclRGBuilder::run( |
116 | const auto *DC = Result.Nodes.getNodeAs<Decl>("dc"); | 116 | const auto *DC = Result.Nodes.getNodeAs<Decl>("dc"); |
117 | assert(DC); | 117 | assert(DC); |
118 | LLVM_DEBUG(llvm::dbgs() << "Find helper function usage: " | 118 | LLVM_DEBUG(llvm::dbgs() << "Find helper function usage: " |
119 | - << FuncRef->getDecl()->getDeclName() << " (" | 119 | + << FuncRef->getDecl()->getNameAsString() << " (" |
120 | << FuncRef->getDecl() << ")\n"); | 120 | << FuncRef->getDecl() << ")\n"); |
121 | RG->addEdge( | 121 | RG->addEdge( |
122 | getOutmostClassOrFunDecl(DC->getCanonicalDecl()), | 122 | getOutmostClassOrFunDecl(DC->getCanonicalDecl()), |
... | @@ -126,7 +126,7 @@ void HelperDeclRGBuilder::run( | ... | @@ -126,7 +126,7 @@ void HelperDeclRGBuilder::run( |
126 | const auto *DC = Result.Nodes.getNodeAs<Decl>("dc"); | 126 | const auto *DC = Result.Nodes.getNodeAs<Decl>("dc"); |
127 | assert(DC); | 127 | assert(DC); |
128 | LLVM_DEBUG(llvm::dbgs() | 128 | LLVM_DEBUG(llvm::dbgs() |
129 | - << "Find helper class usage: " << UsedClass->getDeclName() | 129 | + << "Find helper class usage: " << UsedClass->getNameAsString() |
130 | << " (" << UsedClass << ")\n"); | 130 | << " (" << UsedClass << ")\n"); |
131 | RG->addEdge(getOutmostClassOrFunDecl(DC->getCanonicalDecl()), UsedClass); | 131 | RG->addEdge(getOutmostClassOrFunDecl(DC->getCanonicalDecl()), UsedClass); |
132 | } | 132 | } | ... | ... |
... | @@ -675,8 +675,8 @@ void ClangMoveTool::run(const ast_matchers::MatchFinder::MatchResult &Result) { | ... | @@ -675,8 +675,8 @@ void ClangMoveTool::run(const ast_matchers::MatchFinder::MatchResult &Result) { |
675 | Result.Nodes.getNodeAs<NamedDecl>("helper_decls")) { | 675 | Result.Nodes.getNodeAs<NamedDecl>("helper_decls")) { |
676 | MovedDecls.push_back(ND); | 676 | MovedDecls.push_back(ND); |
677 | HelperDeclarations.push_back(ND); | 677 | HelperDeclarations.push_back(ND); |
678 | - LLVM_DEBUG(llvm::dbgs() | 678 | + LLVM_DEBUG(llvm::dbgs() << "Add helper : " << ND->getNameAsString() << " (" |
679 | - << "Add helper : " << ND->getDeclName() << " (" << ND << ")\n"); | 679 | + << ND << ")\n"); |
680 | } else if (const auto *UD = Result.Nodes.getNodeAs<NamedDecl>("using_decl")) { | 680 | } else if (const auto *UD = Result.Nodes.getNodeAs<NamedDecl>("using_decl")) { |
681 | MovedDecls.push_back(UD); | 681 | MovedDecls.push_back(UD); |
682 | } | 682 | } |
... | @@ -735,12 +735,12 @@ void ClangMoveTool::removeDeclsInOldFiles() { | ... | @@ -735,12 +735,12 @@ void ClangMoveTool::removeDeclsInOldFiles() { |
735 | // We remove the helper declarations which are not used in the old.cc after | 735 | // We remove the helper declarations which are not used in the old.cc after |
736 | // moving the given declarations. | 736 | // moving the given declarations. |
737 | for (const auto *D : HelperDeclarations) { | 737 | for (const auto *D : HelperDeclarations) { |
738 | - LLVM_DEBUG(llvm::dbgs() << "Check helper is used: " << D->getDeclName() | 738 | + LLVM_DEBUG(llvm::dbgs() << "Check helper is used: " |
739 | - << " (" << D << ")\n"); | 739 | + << D->getNameAsString() << " (" << D << ")\n"); |
740 | if (!UsedDecls.count(HelperDeclRGBuilder::getOutmostClassOrFunDecl( | 740 | if (!UsedDecls.count(HelperDeclRGBuilder::getOutmostClassOrFunDecl( |
741 | D->getCanonicalDecl()))) { | 741 | D->getCanonicalDecl()))) { |
742 | LLVM_DEBUG(llvm::dbgs() << "Helper removed in old.cc: " | 742 | LLVM_DEBUG(llvm::dbgs() << "Helper removed in old.cc: " |
743 | - << D->getDeclName() << " (" << D << ")\n"); | 743 | + << D->getNameAsString() << " (" << D << ")\n"); |
744 | RemovedDecls.push_back(D); | 744 | RemovedDecls.push_back(D); |
745 | } | 745 | } |
746 | } | 746 | } |
... | @@ -820,7 +820,7 @@ void ClangMoveTool::moveDeclsToNewFiles() { | ... | @@ -820,7 +820,7 @@ void ClangMoveTool::moveDeclsToNewFiles() { |
820 | D->getCanonicalDecl()))) | 820 | D->getCanonicalDecl()))) |
821 | continue; | 821 | continue; |
822 | 822 | ||
823 | - LLVM_DEBUG(llvm::dbgs() << "Helper used in new.cc: " << D->getDeclName() | 823 | + LLVM_DEBUG(llvm::dbgs() << "Helper used in new.cc: " << D->getNameAsString() |
824 | << " " << D << "\n"); | 824 | << " " << D << "\n"); |
825 | ActualNewCCDecls.push_back(D); | 825 | ActualNewCCDecls.push_back(D); |
826 | } | 826 | } | ... | ... |
... | @@ -110,33 +110,31 @@ int main(int argc, const char **argv) { | ... | @@ -110,33 +110,31 @@ int main(int argc, const char **argv) { |
110 | ClangTool Tool(OptionsParser->getCompilations(), | 110 | ClangTool Tool(OptionsParser->getCompilations(), |
111 | OptionsParser->getSourcePathList()); | 111 | OptionsParser->getSourcePathList()); |
112 | std::vector<std::unique_ptr<ASTUnit>> ASTs; | 112 | std::vector<std::unique_ptr<ASTUnit>> ASTs; |
113 | + int Status = Tool.buildASTs(ASTs); | ||
113 | int ASTStatus = 0; | 114 | int ASTStatus = 0; |
114 | - switch (Tool.buildASTs(ASTs)) { | 115 | + if (Status == 1) { |
115 | - case 0: | 116 | + // Building ASTs failed. |
116 | - break; | ||
117 | - case 1: // Building ASTs failed. | ||
118 | return 1; | 117 | return 1; |
119 | - case 2: | 118 | + } else if (Status == 2) { |
120 | ASTStatus |= 1; | 119 | ASTStatus |= 1; |
121 | llvm::errs() << "Failed to build AST for some of the files, " | 120 | llvm::errs() << "Failed to build AST for some of the files, " |
122 | << "results may be incomplete." | 121 | << "results may be incomplete." |
123 | << "\n"; | 122 | << "\n"; |
124 | - break; | 123 | + } else { |
125 | - default: | 124 | + assert(Status == 0 && "Unexpected status returned"); |
126 | - llvm_unreachable("Unexpected status returned"); | ||
127 | } | 125 | } |
128 | 126 | ||
129 | QuerySession QS(ASTs); | 127 | QuerySession QS(ASTs); |
130 | 128 | ||
131 | if (!Commands.empty()) { | 129 | if (!Commands.empty()) { |
132 | - for (auto &Command : Commands) { | 130 | + for (auto I = Commands.begin(), E = Commands.end(); I != E; ++I) { |
133 | - QueryRef Q = QueryParser::parse(Command, QS); | 131 | + QueryRef Q = QueryParser::parse(*I, QS); |
134 | if (!Q->run(llvm::outs(), QS)) | 132 | if (!Q->run(llvm::outs(), QS)) |
135 | return 1; | 133 | return 1; |
136 | } | 134 | } |
137 | } else if (!CommandFiles.empty()) { | 135 | } else if (!CommandFiles.empty()) { |
138 | - for (auto &CommandFile : CommandFiles) { | 136 | + for (auto I = CommandFiles.begin(), E = CommandFiles.end(); I != E; ++I) { |
139 | - if (runCommandsInFile(argv[0], CommandFile, QS)) | 137 | + if (runCommandsInFile(argv[0], *I, QS)) |
140 | return 1; | 138 | return 1; |
141 | } | 139 | } |
142 | } else { | 140 | } else { | ... | ... |
... | @@ -3,11 +3,6 @@ set(LLVM_LINK_COMPONENTS | ... | @@ -3,11 +3,6 @@ set(LLVM_LINK_COMPONENTS |
3 | Support | 3 | Support |
4 | ) | 4 | ) |
5 | 5 | ||
6 | -configure_file( | ||
7 | - ${CMAKE_CURRENT_SOURCE_DIR}/clang-tidy-config.h.cmake | ||
8 | - ${CMAKE_CURRENT_BINARY_DIR}/clang-tidy-config.h) | ||
9 | -include_directories(BEFORE ${CMAKE_CURRENT_BINARY_DIR}) | ||
10 | - | ||
11 | add_clang_library(clangTidy | 6 | add_clang_library(clangTidy |
12 | ClangTidy.cpp | 7 | ClangTidy.cpp |
13 | ClangTidyCheck.cpp | 8 | ClangTidyCheck.cpp |
... | @@ -39,7 +34,7 @@ clang_target_link_libraries(clangTidy | ... | @@ -39,7 +34,7 @@ clang_target_link_libraries(clangTidy |
39 | clangToolingCore | 34 | clangToolingCore |
40 | ) | 35 | ) |
41 | 36 | ||
42 | -if(CLANG_TIDY_ENABLE_STATIC_ANALYZER) | 37 | +if(CLANG_ENABLE_STATIC_ANALYZER) |
43 | clang_target_link_libraries(clangTidy | 38 | clang_target_link_libraries(clangTidy |
44 | PRIVATE | 39 | PRIVATE |
45 | clangStaticAnalyzerCore | 40 | clangStaticAnalyzerCore |
... | @@ -51,7 +46,6 @@ endif() | ... | @@ -51,7 +46,6 @@ endif() |
51 | # If you add a check, also add it to ClangTidyForceLinker.h in this directory. | 46 | # If you add a check, also add it to ClangTidyForceLinker.h in this directory. |
52 | add_subdirectory(android) | 47 | add_subdirectory(android) |
53 | add_subdirectory(abseil) | 48 | add_subdirectory(abseil) |
54 | -add_subdirectory(altera) | ||
55 | add_subdirectory(boost) | 49 | add_subdirectory(boost) |
56 | add_subdirectory(bugprone) | 50 | add_subdirectory(bugprone) |
57 | add_subdirectory(cert) | 51 | add_subdirectory(cert) |
... | @@ -65,7 +59,7 @@ add_subdirectory(llvm) | ... | @@ -65,7 +59,7 @@ add_subdirectory(llvm) |
65 | add_subdirectory(llvmlibc) | 59 | add_subdirectory(llvmlibc) |
66 | add_subdirectory(misc) | 60 | add_subdirectory(misc) |
67 | add_subdirectory(modernize) | 61 | add_subdirectory(modernize) |
68 | -if(CLANG_TIDY_ENABLE_STATIC_ANALYZER) | 62 | +if(CLANG_ENABLE_STATIC_ANALYZER) |
69 | add_subdirectory(mpi) | 63 | add_subdirectory(mpi) |
70 | endif() | 64 | endif() |
71 | add_subdirectory(objc) | 65 | add_subdirectory(objc) |
... | @@ -77,7 +71,6 @@ add_subdirectory(zircon) | ... | @@ -77,7 +71,6 @@ add_subdirectory(zircon) |
77 | set(ALL_CLANG_TIDY_CHECKS | 71 | set(ALL_CLANG_TIDY_CHECKS |
78 | clangTidyAndroidModule | 72 | clangTidyAndroidModule |
79 | clangTidyAbseilModule | 73 | clangTidyAbseilModule |
80 | - clangTidyAlteraModule | ||
81 | clangTidyBoostModule | 74 | clangTidyBoostModule |
82 | clangTidyBugproneModule | 75 | clangTidyBugproneModule |
83 | clangTidyCERTModule | 76 | clangTidyCERTModule |
... | @@ -98,7 +91,7 @@ set(ALL_CLANG_TIDY_CHECKS | ... | @@ -98,7 +91,7 @@ set(ALL_CLANG_TIDY_CHECKS |
98 | clangTidyReadabilityModule | 91 | clangTidyReadabilityModule |
99 | clangTidyZirconModule | 92 | clangTidyZirconModule |
100 | ) | 93 | ) |
101 | -if(CLANG_TIDY_ENABLE_STATIC_ANALYZER) | 94 | +if(CLANG_ENABLE_STATIC_ANALYZER) |
102 | list(APPEND ALL_CLANG_TIDY_CHECKS clangTidyMPIModule) | 95 | list(APPEND ALL_CLANG_TIDY_CHECKS clangTidyMPIModule) |
103 | endif() | 96 | endif() |
104 | set(ALL_CLANG_TIDY_CHECKS ${ALL_CLANG_TIDY_CHECKS} PARENT_SCOPE) | 97 | set(ALL_CLANG_TIDY_CHECKS ${ALL_CLANG_TIDY_CHECKS} PARENT_SCOPE) | ... | ... |
... | @@ -20,11 +20,11 @@ | ... | @@ -20,11 +20,11 @@ |
20 | #include "ClangTidyModuleRegistry.h" | 20 | #include "ClangTidyModuleRegistry.h" |
21 | #include "ClangTidyProfiling.h" | 21 | #include "ClangTidyProfiling.h" |
22 | #include "ExpandModularHeadersPPCallbacks.h" | 22 | #include "ExpandModularHeadersPPCallbacks.h" |
23 | -#include "clang-tidy-config.h" | ||
24 | #include "clang/AST/ASTConsumer.h" | 23 | #include "clang/AST/ASTConsumer.h" |
25 | #include "clang/AST/ASTContext.h" | 24 | #include "clang/AST/ASTContext.h" |
26 | #include "clang/AST/Decl.h" | 25 | #include "clang/AST/Decl.h" |
27 | #include "clang/ASTMatchers/ASTMatchFinder.h" | 26 | #include "clang/ASTMatchers/ASTMatchFinder.h" |
27 | +#include "clang/Config/config.h" | ||
28 | #include "clang/Format/Format.h" | 28 | #include "clang/Format/Format.h" |
29 | #include "clang/Frontend/ASTConsumers.h" | 29 | #include "clang/Frontend/ASTConsumers.h" |
30 | #include "clang/Frontend/CompilerInstance.h" | 30 | #include "clang/Frontend/CompilerInstance.h" |
... | @@ -47,10 +47,10 @@ | ... | @@ -47,10 +47,10 @@ |
47 | #include <algorithm> | 47 | #include <algorithm> |
48 | #include <utility> | 48 | #include <utility> |
49 | 49 | ||
50 | -#if CLANG_TIDY_ENABLE_STATIC_ANALYZER | 50 | +#if CLANG_ENABLE_STATIC_ANALYZER |
51 | #include "clang/Analysis/PathDiagnostic.h" | 51 | #include "clang/Analysis/PathDiagnostic.h" |
52 | #include "clang/StaticAnalyzer/Frontend/AnalysisConsumer.h" | 52 | #include "clang/StaticAnalyzer/Frontend/AnalysisConsumer.h" |
53 | -#endif // CLANG_TIDY_ENABLE_STATIC_ANALYZER | 53 | +#endif // CLANG_ENABLE_STATIC_ANALYZER |
54 | 54 | ||
55 | using namespace clang::ast_matchers; | 55 | using namespace clang::ast_matchers; |
56 | using namespace clang::driver; | 56 | using namespace clang::driver; |
... | @@ -63,7 +63,7 @@ namespace clang { | ... | @@ -63,7 +63,7 @@ namespace clang { |
63 | namespace tidy { | 63 | namespace tidy { |
64 | 64 | ||
65 | namespace { | 65 | namespace { |
66 | -#if CLANG_TIDY_ENABLE_STATIC_ANALYZER | 66 | +#if CLANG_ENABLE_STATIC_ANALYZER |
67 | static const char *AnalyzerCheckNamePrefix = "clang-analyzer-"; | 67 | static const char *AnalyzerCheckNamePrefix = "clang-analyzer-"; |
68 | 68 | ||
69 | class AnalyzerDiagnosticConsumer : public ento::PathDiagnosticConsumer { | 69 | class AnalyzerDiagnosticConsumer : public ento::PathDiagnosticConsumer { |
... | @@ -95,7 +95,7 @@ public: | ... | @@ -95,7 +95,7 @@ public: |
95 | private: | 95 | private: |
96 | ClangTidyContext &Context; | 96 | ClangTidyContext &Context; |
97 | }; | 97 | }; |
98 | -#endif // CLANG_TIDY_ENABLE_STATIC_ANALYZER | 98 | +#endif // CLANG_ENABLE_STATIC_ANALYZER |
99 | 99 | ||
100 | class ErrorReporter { | 100 | class ErrorReporter { |
101 | public: | 101 | public: |
... | @@ -324,16 +324,17 @@ ClangTidyASTConsumerFactory::ClangTidyASTConsumerFactory( | ... | @@ -324,16 +324,17 @@ ClangTidyASTConsumerFactory::ClangTidyASTConsumerFactory( |
324 | } | 324 | } |
325 | } | 325 | } |
326 | 326 | ||
327 | -#if CLANG_TIDY_ENABLE_STATIC_ANALYZER | 327 | +#if CLANG_ENABLE_STATIC_ANALYZER |
328 | static void setStaticAnalyzerCheckerOpts(const ClangTidyOptions &Opts, | 328 | static void setStaticAnalyzerCheckerOpts(const ClangTidyOptions &Opts, |
329 | AnalyzerOptionsRef AnalyzerOptions) { | 329 | AnalyzerOptionsRef AnalyzerOptions) { |
330 | StringRef AnalyzerPrefix(AnalyzerCheckNamePrefix); | 330 | StringRef AnalyzerPrefix(AnalyzerCheckNamePrefix); |
331 | for (const auto &Opt : Opts.CheckOptions) { | 331 | for (const auto &Opt : Opts.CheckOptions) { |
332 | - StringRef OptName(Opt.getKey()); | 332 | + StringRef OptName(Opt.first); |
333 | - if (!OptName.consume_front(AnalyzerPrefix)) | 333 | + if (!OptName.startswith(AnalyzerPrefix)) |
334 | continue; | 334 | continue; |
335 | // Analyzer options are always local options so we can ignore priority. | 335 | // Analyzer options are always local options so we can ignore priority. |
336 | - AnalyzerOptions->Config[OptName] = Opt.getValue().Value; | 336 | + AnalyzerOptions->Config[OptName.substr(AnalyzerPrefix.size())] = |
337 | + Opt.second.Value; | ||
337 | } | 338 | } |
338 | } | 339 | } |
339 | 340 | ||
... | @@ -369,7 +370,7 @@ static CheckersList getAnalyzerCheckersAndPackages(ClangTidyContext &Context, | ... | @@ -369,7 +370,7 @@ static CheckersList getAnalyzerCheckersAndPackages(ClangTidyContext &Context, |
369 | } | 370 | } |
370 | return List; | 371 | return List; |
371 | } | 372 | } |
372 | -#endif // CLANG_TIDY_ENABLE_STATIC_ANALYZER | 373 | +#endif // CLANG_ENABLE_STATIC_ANALYZER |
373 | 374 | ||
374 | std::unique_ptr<clang::ASTConsumer> | 375 | std::unique_ptr<clang::ASTConsumer> |
375 | ClangTidyASTConsumerFactory::CreateASTConsumer( | 376 | ClangTidyASTConsumerFactory::CreateASTConsumer( |
... | @@ -424,7 +425,7 @@ ClangTidyASTConsumerFactory::CreateASTConsumer( | ... | @@ -424,7 +425,7 @@ ClangTidyASTConsumerFactory::CreateASTConsumer( |
424 | if (!Checks.empty()) | 425 | if (!Checks.empty()) |
425 | Consumers.push_back(Finder->newASTConsumer()); | 426 | Consumers.push_back(Finder->newASTConsumer()); |
426 | 427 | ||
427 | -#if CLANG_TIDY_ENABLE_STATIC_ANALYZER | 428 | +#if CLANG_ENABLE_STATIC_ANALYZER |
428 | AnalyzerOptionsRef AnalyzerOptions = Compiler.getAnalyzerOpts(); | 429 | AnalyzerOptionsRef AnalyzerOptions = Compiler.getAnalyzerOpts(); |
429 | AnalyzerOptions->CheckersAndPackages = getAnalyzerCheckersAndPackages( | 430 | AnalyzerOptions->CheckersAndPackages = getAnalyzerCheckersAndPackages( |
430 | Context, Context.canEnableAnalyzerAlphaCheckers()); | 431 | Context, Context.canEnableAnalyzerAlphaCheckers()); |
... | @@ -440,7 +441,7 @@ ClangTidyASTConsumerFactory::CreateASTConsumer( | ... | @@ -440,7 +441,7 @@ ClangTidyASTConsumerFactory::CreateASTConsumer( |
440 | new AnalyzerDiagnosticConsumer(Context)); | 441 | new AnalyzerDiagnosticConsumer(Context)); |
441 | Consumers.push_back(std::move(AnalysisConsumer)); | 442 | Consumers.push_back(std::move(AnalysisConsumer)); |
442 | } | 443 | } |
443 | -#endif // CLANG_TIDY_ENABLE_STATIC_ANALYZER | 444 | +#endif // CLANG_ENABLE_STATIC_ANALYZER |
444 | return std::make_unique<ClangTidyASTConsumer>( | 445 | return std::make_unique<ClangTidyASTConsumer>( |
445 | std::move(Consumers), std::move(Profiling), std::move(Finder), | 446 | std::move(Consumers), std::move(Profiling), std::move(Finder), |
446 | std::move(Checks)); | 447 | std::move(Checks)); |
... | @@ -449,15 +450,15 @@ ClangTidyASTConsumerFactory::CreateASTConsumer( | ... | @@ -449,15 +450,15 @@ ClangTidyASTConsumerFactory::CreateASTConsumer( |
449 | std::vector<std::string> ClangTidyASTConsumerFactory::getCheckNames() { | 450 | std::vector<std::string> ClangTidyASTConsumerFactory::getCheckNames() { |
450 | std::vector<std::string> CheckNames; | 451 | std::vector<std::string> CheckNames; |
451 | for (const auto &CheckFactory : *CheckFactories) { | 452 | for (const auto &CheckFactory : *CheckFactories) { |
452 | - if (Context.isCheckEnabled(CheckFactory.getKey())) | 453 | + if (Context.isCheckEnabled(CheckFactory.first)) |
453 | - CheckNames.emplace_back(CheckFactory.getKey()); | 454 | + CheckNames.push_back(CheckFactory.first); |
454 | } | 455 | } |
455 | 456 | ||
456 | -#if CLANG_TIDY_ENABLE_STATIC_ANALYZER | 457 | +#if CLANG_ENABLE_STATIC_ANALYZER |
457 | for (const auto &AnalyzerCheck : getAnalyzerCheckersAndPackages( | 458 | for (const auto &AnalyzerCheck : getAnalyzerCheckersAndPackages( |
458 | Context, Context.canEnableAnalyzerAlphaCheckers())) | 459 | Context, Context.canEnableAnalyzerAlphaCheckers())) |
459 | CheckNames.push_back(AnalyzerCheckNamePrefix + AnalyzerCheck.first); | 460 | CheckNames.push_back(AnalyzerCheckNamePrefix + AnalyzerCheck.first); |
460 | -#endif // CLANG_TIDY_ENABLE_STATIC_ANALYZER | 461 | +#endif // CLANG_ENABLE_STATIC_ANALYZER |
461 | 462 | ||
462 | llvm::sort(CheckNames); | 463 | llvm::sort(CheckNames); |
463 | return CheckNames; | 464 | return CheckNames; | ... | ... |
... | @@ -10,7 +10,6 @@ | ... | @@ -10,7 +10,6 @@ |
10 | #include "llvm/ADT/SmallString.h" | 10 | #include "llvm/ADT/SmallString.h" |
11 | #include "llvm/ADT/StringRef.h" | 11 | #include "llvm/ADT/StringRef.h" |
12 | #include "llvm/Support/Error.h" | 12 | #include "llvm/Support/Error.h" |
13 | -#include "llvm/Support/WithColor.h" | ||
14 | #include "llvm/Support/raw_ostream.h" | 13 | #include "llvm/Support/raw_ostream.h" |
15 | 14 | ||
16 | namespace clang { | 15 | namespace clang { |
... | @@ -73,7 +72,7 @@ llvm::Expected<std::string> | ... | @@ -73,7 +72,7 @@ llvm::Expected<std::string> |
73 | ClangTidyCheck::OptionsView::get(StringRef LocalName) const { | 72 | ClangTidyCheck::OptionsView::get(StringRef LocalName) const { |
74 | const auto &Iter = CheckOptions.find(NamePrefix + LocalName.str()); | 73 | const auto &Iter = CheckOptions.find(NamePrefix + LocalName.str()); |
75 | if (Iter != CheckOptions.end()) | 74 | if (Iter != CheckOptions.end()) |
76 | - return Iter->getValue().Value; | 75 | + return Iter->second.Value; |
77 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); | 76 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); |
78 | } | 77 | } |
79 | 78 | ||
... | @@ -86,7 +85,7 @@ findPriorityOption(const ClangTidyOptions::OptionMap &Options, StringRef NamePre | ... | @@ -86,7 +85,7 @@ findPriorityOption(const ClangTidyOptions::OptionMap &Options, StringRef NamePre |
86 | return IterGlobal; | 85 | return IterGlobal; |
87 | if (IterGlobal == Options.end()) | 86 | if (IterGlobal == Options.end()) |
88 | return IterLocal; | 87 | return IterLocal; |
89 | - if (IterLocal->getValue().Priority >= IterGlobal->getValue().Priority) | 88 | + if (IterLocal->second.Priority >= IterGlobal->second.Priority) |
90 | return IterLocal; | 89 | return IterLocal; |
91 | return IterGlobal; | 90 | return IterGlobal; |
92 | } | 91 | } |
... | @@ -95,7 +94,7 @@ llvm::Expected<std::string> | ... | @@ -95,7 +94,7 @@ llvm::Expected<std::string> |
95 | ClangTidyCheck::OptionsView::getLocalOrGlobal(StringRef LocalName) const { | 94 | ClangTidyCheck::OptionsView::getLocalOrGlobal(StringRef LocalName) const { |
96 | auto Iter = findPriorityOption(CheckOptions, NamePrefix, LocalName); | 95 | auto Iter = findPriorityOption(CheckOptions, NamePrefix, LocalName); |
97 | if (Iter != CheckOptions.end()) | 96 | if (Iter != CheckOptions.end()) |
98 | - return Iter->getValue().Value; | 97 | + return Iter->second.Value; |
99 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); | 98 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); |
100 | } | 99 | } |
101 | 100 | ||
... | @@ -127,7 +126,7 @@ bool ClangTidyCheck::OptionsView::get<bool>(StringRef LocalName, | ... | @@ -127,7 +126,7 @@ bool ClangTidyCheck::OptionsView::get<bool>(StringRef LocalName, |
127 | llvm::Expected<bool> ValueOr = get<bool>(LocalName); | 126 | llvm::Expected<bool> ValueOr = get<bool>(LocalName); |
128 | if (ValueOr) | 127 | if (ValueOr) |
129 | return *ValueOr; | 128 | return *ValueOr; |
130 | - logIfOptionParsingError(ValueOr.takeError()); | 129 | + logErrToStdErr(ValueOr.takeError()); |
131 | return Default; | 130 | return Default; |
132 | } | 131 | } |
133 | 132 | ||
... | @@ -136,7 +135,7 @@ llvm::Expected<bool> | ... | @@ -136,7 +135,7 @@ llvm::Expected<bool> |
136 | ClangTidyCheck::OptionsView::getLocalOrGlobal<bool>(StringRef LocalName) const { | 135 | ClangTidyCheck::OptionsView::getLocalOrGlobal<bool>(StringRef LocalName) const { |
137 | auto Iter = findPriorityOption(CheckOptions, NamePrefix, LocalName); | 136 | auto Iter = findPriorityOption(CheckOptions, NamePrefix, LocalName); |
138 | if (Iter != CheckOptions.end()) | 137 | if (Iter != CheckOptions.end()) |
139 | - return getAsBool(Iter->getValue().Value, Iter->getKey()); | 138 | + return getAsBool(Iter->second.Value, Iter->first); |
140 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); | 139 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); |
141 | } | 140 | } |
142 | 141 | ||
... | @@ -146,7 +145,7 @@ bool ClangTidyCheck::OptionsView::getLocalOrGlobal<bool>(StringRef LocalName, | ... | @@ -146,7 +145,7 @@ bool ClangTidyCheck::OptionsView::getLocalOrGlobal<bool>(StringRef LocalName, |
146 | llvm::Expected<bool> ValueOr = getLocalOrGlobal<bool>(LocalName); | 145 | llvm::Expected<bool> ValueOr = getLocalOrGlobal<bool>(LocalName); |
147 | if (ValueOr) | 146 | if (ValueOr) |
148 | return *ValueOr; | 147 | return *ValueOr; |
149 | - logIfOptionParsingError(ValueOr.takeError()); | 148 | + logErrToStdErr(ValueOr.takeError()); |
150 | return Default; | 149 | return Default; |
151 | } | 150 | } |
152 | 151 | ||
... | @@ -169,16 +168,17 @@ void ClangTidyCheck::OptionsView::store<bool>( | ... | @@ -169,16 +168,17 @@ void ClangTidyCheck::OptionsView::store<bool>( |
169 | store(Options, LocalName, Value ? StringRef("true") : StringRef("false")); | 168 | store(Options, LocalName, Value ? StringRef("true") : StringRef("false")); |
170 | } | 169 | } |
171 | 170 | ||
172 | -llvm::Expected<int64_t> ClangTidyCheck::OptionsView::getEnumInt( | 171 | +llvm::Expected<int64_t> |
173 | - StringRef LocalName, ArrayRef<NameAndValue> Mapping, bool CheckGlobal, | 172 | +ClangTidyCheck::OptionsView::getEnumInt(StringRef LocalName, |
174 | - bool IgnoreCase) const { | 173 | + ArrayRef<NameAndValue> Mapping, |
174 | + bool CheckGlobal, bool IgnoreCase) { | ||
175 | auto Iter = CheckGlobal | 175 | auto Iter = CheckGlobal |
176 | ? findPriorityOption(CheckOptions, NamePrefix, LocalName) | 176 | ? findPriorityOption(CheckOptions, NamePrefix, LocalName) |
177 | : CheckOptions.find((NamePrefix + LocalName).str()); | 177 | : CheckOptions.find((NamePrefix + LocalName).str()); |
178 | if (Iter == CheckOptions.end()) | 178 | if (Iter == CheckOptions.end()) |
179 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); | 179 | return llvm::make_error<MissingOptionError>((NamePrefix + LocalName).str()); |
180 | 180 | ||
181 | - StringRef Value = Iter->getValue().Value; | 181 | + StringRef Value = Iter->second.Value; |
182 | StringRef Closest; | 182 | StringRef Closest; |
183 | unsigned EditDistance = -1; | 183 | unsigned EditDistance = -1; |
184 | for (const auto &NameAndEnum : Mapping) { | 184 | for (const auto &NameAndEnum : Mapping) { |
... | @@ -200,38 +200,18 @@ llvm::Expected<int64_t> ClangTidyCheck::OptionsView::getEnumInt( | ... | @@ -200,38 +200,18 @@ llvm::Expected<int64_t> ClangTidyCheck::OptionsView::getEnumInt( |
200 | } | 200 | } |
201 | if (EditDistance < 3) | 201 | if (EditDistance < 3) |
202 | return llvm::make_error<UnparseableEnumOptionError>( | 202 | return llvm::make_error<UnparseableEnumOptionError>( |
203 | - Iter->getKey().str(), Iter->getValue().Value, Closest.str()); | 203 | + Iter->first, Iter->second.Value, std::string(Closest)); |
204 | - return llvm::make_error<UnparseableEnumOptionError>(Iter->getKey().str(), | 204 | + return llvm::make_error<UnparseableEnumOptionError>(Iter->first, |
205 | - Iter->getValue().Value); | 205 | + Iter->second.Value); |
206 | } | 206 | } |
207 | 207 | ||
208 | -void ClangTidyCheck::OptionsView::logIfOptionParsingError(llvm::Error &&Err) { | 208 | +void ClangTidyCheck::OptionsView::logErrToStdErr(llvm::Error &&Err) { |
209 | - if (auto RemainingErrors = | 209 | + llvm::logAllUnhandledErrors( |
210 | - llvm::handleErrors(std::move(Err), [](const MissingOptionError &) {})) | 210 | + llvm::handleErrors(std::move(Err), |
211 | - llvm::logAllUnhandledErrors(std::move(RemainingErrors), | 211 | + [](const MissingOptionError &) -> llvm::Error { |
212 | - llvm::WithColor::warning()); | 212 | + return llvm::Error::success(); |
213 | + }), | ||
214 | + llvm::errs(), "warning: "); | ||
213 | } | 215 | } |
214 | - | ||
215 | -template <> | ||
216 | -Optional<std::string> ClangTidyCheck::OptionsView::getOptional<std::string>( | ||
217 | - StringRef LocalName) const { | ||
218 | - if (auto ValueOr = get(LocalName)) | ||
219 | - return *ValueOr; | ||
220 | - else | ||
221 | - consumeError(ValueOr.takeError()); | ||
222 | - return llvm::None; | ||
223 | -} | ||
224 | - | ||
225 | -template <> | ||
226 | -Optional<std::string> | ||
227 | -ClangTidyCheck::OptionsView::getOptionalLocalOrGlobal<std::string>( | ||
228 | - StringRef LocalName) const { | ||
229 | - if (auto ValueOr = getLocalOrGlobal(LocalName)) | ||
230 | - return *ValueOr; | ||
231 | - else | ||
232 | - consumeError(ValueOr.takeError()); | ||
233 | - return llvm::None; | ||
234 | -} | ||
235 | - | ||
236 | } // namespace tidy | 216 | } // namespace tidy |
237 | } // namespace clang | 217 | } // namespace clang | ... | ... |
... | @@ -268,7 +268,7 @@ public: | ... | @@ -268,7 +268,7 @@ public: |
268 | if (llvm::Expected<T> ValueOr = get<T>(LocalName)) | 268 | if (llvm::Expected<T> ValueOr = get<T>(LocalName)) |
269 | return *ValueOr; | 269 | return *ValueOr; |
270 | else | 270 | else |
271 | - logIfOptionParsingError(ValueOr.takeError()); | 271 | + logErrToStdErr(ValueOr.takeError()); |
272 | return Default; | 272 | return Default; |
273 | } | 273 | } |
274 | 274 | ||
... | @@ -314,7 +314,7 @@ public: | ... | @@ -314,7 +314,7 @@ public: |
314 | if (llvm::Expected<T> ValueOr = getLocalOrGlobal<T>(LocalName)) | 314 | if (llvm::Expected<T> ValueOr = getLocalOrGlobal<T>(LocalName)) |
315 | return *ValueOr; | 315 | return *ValueOr; |
316 | else | 316 | else |
317 | - logIfOptionParsingError(ValueOr.takeError()); | 317 | + logErrToStdErr(ValueOr.takeError()); |
318 | return Default; | 318 | return Default; |
319 | } | 319 | } |
320 | 320 | ||
... | @@ -330,7 +330,7 @@ public: | ... | @@ -330,7 +330,7 @@ public: |
330 | /// supply the mapping required to convert between ``T`` and a string. | 330 | /// supply the mapping required to convert between ``T`` and a string. |
331 | template <typename T> | 331 | template <typename T> |
332 | std::enable_if_t<std::is_enum<T>::value, llvm::Expected<T>> | 332 | std::enable_if_t<std::is_enum<T>::value, llvm::Expected<T>> |
333 | - get(StringRef LocalName, bool IgnoreCase = false) const { | 333 | + get(StringRef LocalName, bool IgnoreCase = false) { |
334 | if (llvm::Expected<int64_t> ValueOr = | 334 | if (llvm::Expected<int64_t> ValueOr = |
335 | getEnumInt(LocalName, typeEraseMapping<T>(), false, IgnoreCase)) | 335 | getEnumInt(LocalName, typeEraseMapping<T>(), false, IgnoreCase)) |
336 | return static_cast<T>(*ValueOr); | 336 | return static_cast<T>(*ValueOr); |
... | @@ -349,11 +349,11 @@ public: | ... | @@ -349,11 +349,11 @@ public: |
349 | /// supply the mapping required to convert between ``T`` and a string. | 349 | /// supply the mapping required to convert between ``T`` and a string. |
350 | template <typename T> | 350 | template <typename T> |
351 | std::enable_if_t<std::is_enum<T>::value, T> | 351 | std::enable_if_t<std::is_enum<T>::value, T> |
352 | - get(StringRef LocalName, T Default, bool IgnoreCase = false) const { | 352 | + get(StringRef LocalName, T Default, bool IgnoreCase = false) { |
353 | if (auto ValueOr = get<T>(LocalName, IgnoreCase)) | 353 | if (auto ValueOr = get<T>(LocalName, IgnoreCase)) |
354 | return *ValueOr; | 354 | return *ValueOr; |
355 | else | 355 | else |
356 | - logIfOptionParsingError(ValueOr.takeError()); | 356 | + logErrToStdErr(ValueOr.takeError()); |
357 | return Default; | 357 | return Default; |
358 | } | 358 | } |
359 | 359 | ||
... | @@ -370,7 +370,8 @@ public: | ... | @@ -370,7 +370,8 @@ public: |
370 | /// supply the mapping required to convert between ``T`` and a string. | 370 | /// supply the mapping required to convert between ``T`` and a string. |
371 | template <typename T> | 371 | template <typename T> |
372 | std::enable_if_t<std::is_enum<T>::value, llvm::Expected<T>> | 372 | std::enable_if_t<std::is_enum<T>::value, llvm::Expected<T>> |
373 | - getLocalOrGlobal(StringRef LocalName, bool IgnoreCase = false) const { | 373 | + getLocalOrGlobal(StringRef LocalName, |
374 | + bool IgnoreCase = false) { | ||
374 | if (llvm::Expected<int64_t> ValueOr = | 375 | if (llvm::Expected<int64_t> ValueOr = |
375 | getEnumInt(LocalName, typeEraseMapping<T>(), true, IgnoreCase)) | 376 | getEnumInt(LocalName, typeEraseMapping<T>(), true, IgnoreCase)) |
376 | return static_cast<T>(*ValueOr); | 377 | return static_cast<T>(*ValueOr); |
... | @@ -390,40 +391,14 @@ public: | ... | @@ -390,40 +391,14 @@ public: |
390 | /// supply the mapping required to convert between ``T`` and a string. | 391 | /// supply the mapping required to convert between ``T`` and a string. |
391 | template <typename T> | 392 | template <typename T> |
392 | std::enable_if_t<std::is_enum<T>::value, T> | 393 | std::enable_if_t<std::is_enum<T>::value, T> |
393 | - getLocalOrGlobal(StringRef LocalName, T Default, | 394 | + getLocalOrGlobal(StringRef LocalName, T Default, bool IgnoreCase = false) { |
394 | - bool IgnoreCase = false) const { | ||
395 | if (auto ValueOr = getLocalOrGlobal<T>(LocalName, IgnoreCase)) | 395 | if (auto ValueOr = getLocalOrGlobal<T>(LocalName, IgnoreCase)) |
396 | return *ValueOr; | 396 | return *ValueOr; |
397 | else | 397 | else |
398 | - logIfOptionParsingError(ValueOr.takeError()); | 398 | + logErrToStdErr(ValueOr.takeError()); |
399 | return Default; | 399 | return Default; |
400 | } | 400 | } |
401 | 401 | ||
402 | - /// Returns the value for the option \p LocalName represented as a ``T``. | ||
403 | - /// If the option is missing returns None, if the option can't be parsed | ||
404 | - /// as a ``T``, log that to stderr and return None. | ||
405 | - template <typename T = std::string> | ||
406 | - llvm::Optional<T> getOptional(StringRef LocalName) const { | ||
407 | - if (auto ValueOr = get<T>(LocalName)) | ||
408 | - return *ValueOr; | ||
409 | - else | ||
410 | - logIfOptionParsingError(ValueOr.takeError()); | ||
411 | - return llvm::None; | ||
412 | - } | ||
413 | - | ||
414 | - /// Returns the value for the local or global option \p LocalName | ||
415 | - /// represented as a ``T``. | ||
416 | - /// If the option is missing returns None, if the | ||
417 | - /// option can't be parsed as a ``T``, log that to stderr and return None. | ||
418 | - template <typename T = std::string> | ||
419 | - llvm::Optional<T> getOptionalLocalOrGlobal(StringRef LocalName) const { | ||
420 | - if (auto ValueOr = getLocalOrGlobal<T>(LocalName)) | ||
421 | - return *ValueOr; | ||
422 | - else | ||
423 | - logIfOptionParsingError(ValueOr.takeError()); | ||
424 | - return llvm::None; | ||
425 | - } | ||
426 | - | ||
427 | /// Stores an option with the check-local name \p LocalName with | 402 | /// Stores an option with the check-local name \p LocalName with |
428 | /// string value \p Value to \p Options. | 403 | /// string value \p Value to \p Options. |
429 | void store(ClangTidyOptions::OptionMap &Options, StringRef LocalName, | 404 | void store(ClangTidyOptions::OptionMap &Options, StringRef LocalName, |
... | @@ -445,8 +420,7 @@ public: | ... | @@ -445,8 +420,7 @@ public: |
445 | /// supply the mapping required to convert between ``T`` and a string. | 420 | /// supply the mapping required to convert between ``T`` and a string. |
446 | template <typename T> | 421 | template <typename T> |
447 | std::enable_if_t<std::is_enum<T>::value> | 422 | std::enable_if_t<std::is_enum<T>::value> |
448 | - store(ClangTidyOptions::OptionMap &Options, StringRef LocalName, | 423 | + store(ClangTidyOptions::OptionMap &Options, StringRef LocalName, T Value) { |
449 | - T Value) const { | ||
450 | ArrayRef<std::pair<T, StringRef>> Mapping = | 424 | ArrayRef<std::pair<T, StringRef>> Mapping = |
451 | OptionEnumMapping<T>::getEnumMapping(); | 425 | OptionEnumMapping<T>::getEnumMapping(); |
452 | auto Iter = llvm::find_if( | 426 | auto Iter = llvm::find_if( |
... | @@ -462,11 +436,11 @@ public: | ... | @@ -462,11 +436,11 @@ public: |
462 | 436 | ||
463 | llvm::Expected<int64_t> getEnumInt(StringRef LocalName, | 437 | llvm::Expected<int64_t> getEnumInt(StringRef LocalName, |
464 | ArrayRef<NameAndValue> Mapping, | 438 | ArrayRef<NameAndValue> Mapping, |
465 | - bool CheckGlobal, bool IgnoreCase) const; | 439 | + bool CheckGlobal, bool IgnoreCase); |
466 | 440 | ||
467 | template <typename T> | 441 | template <typename T> |
468 | std::enable_if_t<std::is_enum<T>::value, std::vector<NameAndValue>> | 442 | std::enable_if_t<std::is_enum<T>::value, std::vector<NameAndValue>> |
469 | - typeEraseMapping() const { | 443 | + typeEraseMapping() { |
470 | ArrayRef<std::pair<T, StringRef>> Mapping = | 444 | ArrayRef<std::pair<T, StringRef>> Mapping = |
471 | OptionEnumMapping<T>::getEnumMapping(); | 445 | OptionEnumMapping<T>::getEnumMapping(); |
472 | std::vector<NameAndValue> Result; | 446 | std::vector<NameAndValue> Result; |
... | @@ -481,8 +455,7 @@ public: | ... | @@ -481,8 +455,7 @@ public: |
481 | void storeInt(ClangTidyOptions::OptionMap &Options, StringRef LocalName, | 455 | void storeInt(ClangTidyOptions::OptionMap &Options, StringRef LocalName, |
482 | int64_t Value) const; | 456 | int64_t Value) const; |
483 | 457 | ||
484 | - /// Logs an Error to stderr if a \p Err is not a MissingOptionError. | 458 | + static void logErrToStdErr(llvm::Error &&Err); |
485 | - static void logIfOptionParsingError(llvm::Error &&Err); | ||
486 | 459 | ||
487 | std::string NamePrefix; | 460 | std::string NamePrefix; |
488 | const ClangTidyOptions::OptionMap &CheckOptions; | 461 | const ClangTidyOptions::OptionMap &CheckOptions; |
... | @@ -550,19 +523,6 @@ void ClangTidyCheck::OptionsView::store<bool>( | ... | @@ -550,19 +523,6 @@ void ClangTidyCheck::OptionsView::store<bool>( |
550 | ClangTidyOptions::OptionMap &Options, StringRef LocalName, | 523 | ClangTidyOptions::OptionMap &Options, StringRef LocalName, |
551 | bool Value) const; | 524 | bool Value) const; |
552 | 525 | ||
553 | -/// Returns the value for the option \p LocalName. | ||
554 | -/// If the option is missing returns None. | ||
555 | -template <> | ||
556 | -Optional<std::string> ClangTidyCheck::OptionsView::getOptional<std::string>( | ||
557 | - StringRef LocalName) const; | ||
558 | - | ||
559 | -/// Returns the value for the local or global option \p LocalName. | ||
560 | -/// If the option is missing returns None. | ||
561 | -template <> | ||
562 | -Optional<std::string> | ||
563 | -ClangTidyCheck::OptionsView::getOptionalLocalOrGlobal<std::string>( | ||
564 | - StringRef LocalName) const; | ||
565 | - | ||
566 | } // namespace tidy | 526 | } // namespace tidy |
567 | } // namespace clang | 527 | } // namespace clang |
568 | 528 | ... | ... |
... | @@ -31,7 +31,6 @@ | ... | @@ -31,7 +31,6 @@ |
31 | #include "llvm/ADT/STLExtras.h" | 31 | #include "llvm/ADT/STLExtras.h" |
32 | #include "llvm/ADT/SmallString.h" | 32 | #include "llvm/ADT/SmallString.h" |
33 | #include "llvm/ADT/StringMap.h" | 33 | #include "llvm/ADT/StringMap.h" |
34 | -#include "llvm/Support/ErrorHandling.h" | ||
35 | #include "llvm/Support/FormatVariadic.h" | 34 | #include "llvm/Support/FormatVariadic.h" |
36 | #include "llvm/Support/Regex.h" | 35 | #include "llvm/Support/Regex.h" |
37 | #include <tuple> | 36 | #include <tuple> |
... | @@ -591,7 +590,6 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { | ... | @@ -591,7 +590,6 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { |
591 | // An event can be either the begin or the end of an interval. | 590 | // An event can be either the begin or the end of an interval. |
592 | enum EventType { | 591 | enum EventType { |
593 | ET_Begin = 1, | 592 | ET_Begin = 1, |
594 | - ET_Insert = 0, | ||
595 | ET_End = -1, | 593 | ET_End = -1, |
596 | }; | 594 | }; |
597 | 595 | ||
... | @@ -623,17 +621,10 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { | ... | @@ -623,17 +621,10 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { |
623 | // one will be processed before, disallowing the second one, and the | 621 | // one will be processed before, disallowing the second one, and the |
624 | // end point of the first one will also be processed before, | 622 | // end point of the first one will also be processed before, |
625 | // disallowing the first one. | 623 | // disallowing the first one. |
626 | - switch (Type) { | 624 | + if (Type == ET_Begin) |
627 | - case ET_Begin: | ||
628 | Priority = std::make_tuple(Begin, Type, -End, -ErrorSize, ErrorId); | 625 | Priority = std::make_tuple(Begin, Type, -End, -ErrorSize, ErrorId); |
629 | - break; | 626 | + else |
630 | - case ET_Insert: | ||
631 | - Priority = std::make_tuple(Begin, Type, -End, ErrorSize, ErrorId); | ||
632 | - break; | ||
633 | - case ET_End: | ||
634 | Priority = std::make_tuple(End, Type, -Begin, ErrorSize, ErrorId); | 627 | Priority = std::make_tuple(End, Type, -Begin, ErrorSize, ErrorId); |
635 | - break; | ||
636 | - } | ||
637 | } | 628 | } |
638 | 629 | ||
639 | bool operator<(const Event &Other) const { | 630 | bool operator<(const Event &Other) const { |
... | @@ -671,19 +662,19 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { | ... | @@ -671,19 +662,19 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { |
671 | } | 662 | } |
672 | 663 | ||
673 | // Build events from error intervals. | 664 | // Build events from error intervals. |
674 | - llvm::StringMap<std::vector<Event>> FileEvents; | 665 | + std::map<std::string, std::vector<Event>> FileEvents; |
675 | for (unsigned I = 0; I < ErrorFixes.size(); ++I) { | 666 | for (unsigned I = 0; I < ErrorFixes.size(); ++I) { |
676 | for (const auto &FileAndReplace : *ErrorFixes[I].second) { | 667 | for (const auto &FileAndReplace : *ErrorFixes[I].second) { |
677 | for (const auto &Replace : FileAndReplace.second) { | 668 | for (const auto &Replace : FileAndReplace.second) { |
678 | unsigned Begin = Replace.getOffset(); | 669 | unsigned Begin = Replace.getOffset(); |
679 | unsigned End = Begin + Replace.getLength(); | 670 | unsigned End = Begin + Replace.getLength(); |
680 | - auto &Events = FileEvents[Replace.getFilePath()]; | 671 | + const std::string &FilePath = std::string(Replace.getFilePath()); |
681 | - if (Begin == End) { | 672 | + // FIXME: Handle empty intervals, such as those from insertions. |
682 | - Events.emplace_back(Begin, End, Event::ET_Insert, I, Sizes[I]); | 673 | + if (Begin == End) |
683 | - } else { | 674 | + continue; |
684 | - Events.emplace_back(Begin, End, Event::ET_Begin, I, Sizes[I]); | 675 | + auto &Events = FileEvents[FilePath]; |
685 | - Events.emplace_back(Begin, End, Event::ET_End, I, Sizes[I]); | 676 | + Events.emplace_back(Begin, End, Event::ET_Begin, I, Sizes[I]); |
686 | - } | 677 | + Events.emplace_back(Begin, End, Event::ET_End, I, Sizes[I]); |
687 | } | 678 | } |
688 | } | 679 | } |
689 | } | 680 | } |
... | @@ -695,20 +686,14 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { | ... | @@ -695,20 +686,14 @@ void ClangTidyDiagnosticConsumer::removeIncompatibleErrors() { |
695 | llvm::sort(Events); | 686 | llvm::sort(Events); |
696 | int OpenIntervals = 0; | 687 | int OpenIntervals = 0; |
697 | for (const auto &Event : Events) { | 688 | for (const auto &Event : Events) { |
698 | - switch (Event.Type) { | 689 | + if (Event.Type == Event::ET_End) |
699 | - case Event::ET_Begin: | 690 | + --OpenIntervals; |
700 | - if (OpenIntervals++ != 0) | 691 | + // This has to be checked after removing the interval from the count if it |
701 | - Apply[Event.ErrorId] = false; | 692 | + // is an end event, or before adding it if it is a begin event. |
702 | - break; | 693 | + if (OpenIntervals != 0) |
703 | - case Event::ET_Insert: | 694 | + Apply[Event.ErrorId] = false; |
704 | - if (OpenIntervals != 0) | 695 | + if (Event.Type == Event::ET_Begin) |
705 | - Apply[Event.ErrorId] = false; | 696 | + ++OpenIntervals; |
706 | - break; | ||
707 | - case Event::ET_End: | ||
708 | - if (--OpenIntervals != 0) | ||
709 | - Apply[Event.ErrorId] = false; | ||
710 | - break; | ||
711 | - } | ||
712 | } | 697 | } |
713 | assert(OpenIntervals == 0 && "Amount of begin/end points doesn't match"); | 698 | assert(OpenIntervals == 0 && "Amount of begin/end points doesn't match"); |
714 | } | 699 | } |
... | @@ -744,7 +729,7 @@ struct EqualClangTidyError { | ... | @@ -744,7 +729,7 @@ struct EqualClangTidyError { |
744 | std::vector<ClangTidyError> ClangTidyDiagnosticConsumer::take() { | 729 | std::vector<ClangTidyError> ClangTidyDiagnosticConsumer::take() { |
745 | finalizeLastError(); | 730 | finalizeLastError(); |
746 | 731 | ||
747 | - llvm::stable_sort(Errors, LessClangTidyError()); | 732 | + llvm::sort(Errors, LessClangTidyError()); |
748 | Errors.erase(std::unique(Errors.begin(), Errors.end(), EqualClangTidyError()), | 733 | Errors.erase(std::unique(Errors.begin(), Errors.end(), EqualClangTidyError()), |
749 | Errors.end()); | 734 | Errors.end()); |
750 | if (RemoveIncompatibleErrors) | 735 | if (RemoveIncompatibleErrors) | ... | ... |
... | @@ -9,7 +9,7 @@ | ... | @@ -9,7 +9,7 @@ |
9 | #ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CLANGTIDYFORCELINKER_H | 9 | #ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CLANGTIDYFORCELINKER_H |
10 | #define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CLANGTIDYFORCELINKER_H | 10 | #define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CLANGTIDYFORCELINKER_H |
11 | 11 | ||
12 | -#include "clang-tidy-config.h" | 12 | +#include "clang/Config/config.h" |
13 | #include "llvm/Support/Compiler.h" | 13 | #include "llvm/Support/Compiler.h" |
14 | 14 | ||
15 | namespace clang { | 15 | namespace clang { |
... | @@ -20,11 +20,6 @@ extern volatile int AbseilModuleAnchorSource; | ... | @@ -20,11 +20,6 @@ extern volatile int AbseilModuleAnchorSource; |
20 | static int LLVM_ATTRIBUTE_UNUSED AbseilModuleAnchorDestination = | 20 | static int LLVM_ATTRIBUTE_UNUSED AbseilModuleAnchorDestination = |
21 | AbseilModuleAnchorSource; | 21 | AbseilModuleAnchorSource; |
22 | 22 | ||
23 | -// This anchor is used to force the linker to link the AlteraModule. | ||
24 | -extern volatile int AlteraModuleAnchorSource; | ||
25 | -static int LLVM_ATTRIBUTE_UNUSED AlteraModuleAnchorDestination = | ||
26 | - AlteraModuleAnchorSource; | ||
27 | - | ||
28 | // This anchor is used to force the linker to link the AndroidModule. | 23 | // This anchor is used to force the linker to link the AndroidModule. |
29 | extern volatile int AndroidModuleAnchorSource; | 24 | extern volatile int AndroidModuleAnchorSource; |
30 | static int LLVM_ATTRIBUTE_UNUSED AndroidModuleAnchorDestination = | 25 | static int LLVM_ATTRIBUTE_UNUSED AndroidModuleAnchorDestination = |
... | @@ -95,7 +90,7 @@ extern volatile int ModernizeModuleAnchorSource; | ... | @@ -95,7 +90,7 @@ extern volatile int ModernizeModuleAnchorSource; |
95 | static int LLVM_ATTRIBUTE_UNUSED ModernizeModuleAnchorDestination = | 90 | static int LLVM_ATTRIBUTE_UNUSED ModernizeModuleAnchorDestination = |
96 | ModernizeModuleAnchorSource; | 91 | ModernizeModuleAnchorSource; |
97 | 92 | ||
98 | -#if CLANG_TIDY_ENABLE_STATIC_ANALYZER && \ | 93 | +#if CLANG_ENABLE_STATIC_ANALYZER && \ |
99 | !defined(CLANG_TIDY_DISABLE_STATIC_ANALYZER_CHECKS) | 94 | !defined(CLANG_TIDY_DISABLE_STATIC_ANALYZER_CHECKS) |
100 | // This anchor is used to force the linker to link the MPIModule. | 95 | // This anchor is used to force the linker to link the MPIModule. |
101 | extern volatile int MPIModuleAnchorSource; | 96 | extern volatile int MPIModuleAnchorSource; | ... | ... |
... | @@ -18,15 +18,15 @@ namespace tidy { | ... | @@ -18,15 +18,15 @@ namespace tidy { |
18 | 18 | ||
19 | void ClangTidyCheckFactories::registerCheckFactory(StringRef Name, | 19 | void ClangTidyCheckFactories::registerCheckFactory(StringRef Name, |
20 | CheckFactory Factory) { | 20 | CheckFactory Factory) { |
21 | - Factories.insert_or_assign(Name, std::move(Factory)); | 21 | + Factories[std::string(Name)] = std::move(Factory); |
22 | } | 22 | } |
23 | 23 | ||
24 | std::vector<std::unique_ptr<ClangTidyCheck>> | 24 | std::vector<std::unique_ptr<ClangTidyCheck>> |
25 | ClangTidyCheckFactories::createChecks(ClangTidyContext *Context) { | 25 | ClangTidyCheckFactories::createChecks(ClangTidyContext *Context) { |
26 | std::vector<std::unique_ptr<ClangTidyCheck>> Checks; | 26 | std::vector<std::unique_ptr<ClangTidyCheck>> Checks; |
27 | for (const auto &Factory : Factories) { | 27 | for (const auto &Factory : Factories) { |
28 | - if (Context->isCheckEnabled(Factory.getKey())) | 28 | + if (Context->isCheckEnabled(Factory.first)) |
29 | - Checks.emplace_back(Factory.getValue()(Factory.getKey(), Context)); | 29 | + Checks.emplace_back(Factory.second(Factory.first, Context)); |
30 | } | 30 | } |
31 | return Checks; | 31 | return Checks; |
32 | } | 32 | } | ... | ... |
... | @@ -69,7 +69,7 @@ public: | ... | @@ -69,7 +69,7 @@ public: |
69 | std::vector<std::unique_ptr<ClangTidyCheck>> | 69 | std::vector<std::unique_ptr<ClangTidyCheck>> |
70 | createChecks(ClangTidyContext *Context); | 70 | createChecks(ClangTidyContext *Context); |
71 | 71 | ||
72 | - typedef llvm::StringMap<CheckFactory> FactoryMap; | 72 | + typedef std::map<std::string, CheckFactory> FactoryMap; |
73 | FactoryMap::const_iterator begin() const { return Factories.begin(); } | 73 | FactoryMap::const_iterator begin() const { return Factories.begin(); } |
74 | FactoryMap::const_iterator end() const { return Factories.end(); } | 74 | FactoryMap::const_iterator end() const { return Factories.end(); } |
75 | bool empty() const { return Factories.empty(); } | 75 | bool empty() const { return Factories.empty(); } | ... | ... |
... | @@ -70,7 +70,7 @@ struct NOptionMap { | ... | @@ -70,7 +70,7 @@ struct NOptionMap { |
70 | NOptionMap(IO &, const ClangTidyOptions::OptionMap &OptionMap) { | 70 | NOptionMap(IO &, const ClangTidyOptions::OptionMap &OptionMap) { |
71 | Options.reserve(OptionMap.size()); | 71 | Options.reserve(OptionMap.size()); |
72 | for (const auto &KeyValue : OptionMap) | 72 | for (const auto &KeyValue : OptionMap) |
73 | - Options.emplace_back(std::string(KeyValue.getKey()), KeyValue.getValue().Value); | 73 | + Options.emplace_back(KeyValue.first, KeyValue.second.Value); |
74 | } | 74 | } |
75 | ClangTidyOptions::OptionMap denormalize(IO &) { | 75 | ClangTidyOptions::OptionMap denormalize(IO &) { |
76 | ClangTidyOptions::OptionMap Map; | 76 | ClangTidyOptions::OptionMap Map; |
... | @@ -114,9 +114,11 @@ ClangTidyOptions ClangTidyOptions::getDefaults() { | ... | @@ -114,9 +114,11 @@ ClangTidyOptions ClangTidyOptions::getDefaults() { |
114 | Options.SystemHeaders = false; | 114 | Options.SystemHeaders = false; |
115 | Options.FormatStyle = "none"; | 115 | Options.FormatStyle = "none"; |
116 | Options.User = llvm::None; | 116 | Options.User = llvm::None; |
117 | + unsigned Priority = 0; | ||
117 | for (const ClangTidyModuleRegistry::entry &Module : | 118 | for (const ClangTidyModuleRegistry::entry &Module : |
118 | ClangTidyModuleRegistry::entries()) | 119 | ClangTidyModuleRegistry::entries()) |
119 | - Options = Options.mergeWith(Module.instantiate()->getModuleOptions(), 0); | 120 | + Options = |
121 | + Options.mergeWith(Module.instantiate()->getModuleOptions(), ++Priority); | ||
120 | return Options; | 122 | return Options; |
121 | } | 123 | } |
122 | 124 | ||
... | @@ -157,10 +159,8 @@ ClangTidyOptions ClangTidyOptions::mergeWith(const ClangTidyOptions &Other, | ... | @@ -157,10 +159,8 @@ ClangTidyOptions ClangTidyOptions::mergeWith(const ClangTidyOptions &Other, |
157 | mergeVectors(Result.ExtraArgsBefore, Other.ExtraArgsBefore); | 159 | mergeVectors(Result.ExtraArgsBefore, Other.ExtraArgsBefore); |
158 | 160 | ||
159 | for (const auto &KeyValue : Other.CheckOptions) { | 161 | for (const auto &KeyValue : Other.CheckOptions) { |
160 | - Result.CheckOptions.insert_or_assign( | 162 | + Result.CheckOptions[KeyValue.first] = ClangTidyValue( |
161 | - KeyValue.getKey(), | 163 | + KeyValue.second.Value, KeyValue.second.Priority + Priority); |
162 | - ClangTidyValue(KeyValue.getValue().Value, | ||
163 | - KeyValue.getValue().Priority + Priority)); | ||
164 | } | 164 | } |
165 | 165 | ||
166 | return Result; | 166 | return Result; | ... | ... |
... | @@ -16,6 +16,7 @@ | ... | @@ -16,6 +16,7 @@ |
16 | #include "llvm/Support/ErrorOr.h" | 16 | #include "llvm/Support/ErrorOr.h" |
17 | #include "llvm/Support/VirtualFileSystem.h" | 17 | #include "llvm/Support/VirtualFileSystem.h" |
18 | #include <functional> | 18 | #include <functional> |
19 | +#include <map> | ||
19 | #include <string> | 20 | #include <string> |
20 | #include <system_error> | 21 | #include <system_error> |
21 | #include <utility> | 22 | #include <utility> |
... | @@ -107,7 +108,7 @@ struct ClangTidyOptions { | ... | @@ -107,7 +108,7 @@ struct ClangTidyOptions { |
107 | unsigned Priority; | 108 | unsigned Priority; |
108 | }; | 109 | }; |
109 | typedef std::pair<std::string, std::string> StringPair; | 110 | typedef std::pair<std::string, std::string> StringPair; |
110 | - typedef llvm::StringMap<ClangTidyValue> OptionMap; | 111 | + typedef std::map<std::string, ClangTidyValue> OptionMap; |
111 | 112 | ||
112 | /// Key-value mapping used to store check-specific options. | 113 | /// Key-value mapping used to store check-specific options. |
113 | OptionMap CheckOptions; | 114 | OptionMap CheckOptions; | ... | ... |
... | @@ -47,18 +47,14 @@ AST_POLYMORPHIC_MATCHER( | ... | @@ -47,18 +47,14 @@ AST_POLYMORPHIC_MATCHER( |
47 | if (PrefixPosition == StringRef::npos) | 47 | if (PrefixPosition == StringRef::npos) |
48 | return false; | 48 | return false; |
49 | Path = Path.drop_front(PrefixPosition + AbslPrefix.size()); | 49 | Path = Path.drop_front(PrefixPosition + AbslPrefix.size()); |
50 | - static const char *AbseilLibraries[] = {"algorithm", "base", | 50 | + static const char *AbseilLibraries[] = { |
51 | - "container", "debugging", | 51 | + "algorithm", "base", "container", "debugging", "flags", |
52 | - "flags", "hash", | 52 | + "hash", "iterator", "memory", "meta", "numeric", |
53 | - "iterator", "memory", | 53 | + "random", "strings", "synchronization", "time", "types", |
54 | - "meta", "numeric", | 54 | + "utility"}; |
55 | - "random", "status", | 55 | + return std::any_of( |
56 | - "strings", "synchronization", | 56 | + std::begin(AbseilLibraries), std::end(AbseilLibraries), |
57 | - "time", "types", | 57 | + [&](const char *Library) { return Path.startswith(Library); }); |
58 | - "utility"}; | ||
59 | - return llvm::any_of(AbseilLibraries, [&](const char *Library) { | ||
60 | - return Path.startswith(Library); | ||
61 | - }); | ||
62 | } | 58 | } |
63 | 59 | ||
64 | } // namespace ast_matchers | 60 | } // namespace ast_matchers | ... | ... |
... | @@ -26,8 +26,8 @@ StringFindStartswithCheck::StringFindStartswithCheck(StringRef Name, | ... | @@ -26,8 +26,8 @@ StringFindStartswithCheck::StringFindStartswithCheck(StringRef Name, |
26 | : ClangTidyCheck(Name, Context), | 26 | : ClangTidyCheck(Name, Context), |
27 | StringLikeClasses(utils::options::parseStringList( | 27 | StringLikeClasses(utils::options::parseStringList( |
28 | Options.get("StringLikeClasses", "::std::basic_string"))), | 28 | Options.get("StringLikeClasses", "::std::basic_string"))), |
29 | - IncludeInserter(Options.getLocalOrGlobal("IncludeStyle", | 29 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
30 | - utils::IncludeSorter::IS_LLVM)), | 30 | + utils::IncludeSorter::IS_LLVM)), |
31 | AbseilStringsMatchHeader( | 31 | AbseilStringsMatchHeader( |
32 | Options.get("AbseilStringsMatchHeader", "absl/strings/match.h")) {} | 32 | Options.get("AbseilStringsMatchHeader", "absl/strings/match.h")) {} |
33 | 33 | ||
... | @@ -105,21 +105,23 @@ void StringFindStartswithCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -105,21 +105,23 @@ void StringFindStartswithCheck::check(const MatchFinder::MatchResult &Result) { |
105 | 105 | ||
106 | // Create a preprocessor #include FixIt hint (CreateIncludeInsertion checks | 106 | // Create a preprocessor #include FixIt hint (CreateIncludeInsertion checks |
107 | // whether this already exists). | 107 | // whether this already exists). |
108 | - Diagnostic << IncludeInserter.createIncludeInsertion( | 108 | + Diagnostic << IncludeInserter->CreateIncludeInsertion( |
109 | - Source.getFileID(ComparisonExpr->getBeginLoc()), | 109 | + Source.getFileID(ComparisonExpr->getBeginLoc()), AbseilStringsMatchHeader, |
110 | - AbseilStringsMatchHeader); | 110 | + false); |
111 | } | 111 | } |
112 | 112 | ||
113 | void StringFindStartswithCheck::registerPPCallbacks( | 113 | void StringFindStartswithCheck::registerPPCallbacks( |
114 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { | 114 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { |
115 | - IncludeInserter.registerPreprocessor(PP); | 115 | + IncludeInserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
116 | + IncludeStyle); | ||
117 | + PP->addPPCallbacks(IncludeInserter->CreatePPCallbacks()); | ||
116 | } | 118 | } |
117 | 119 | ||
118 | void StringFindStartswithCheck::storeOptions( | 120 | void StringFindStartswithCheck::storeOptions( |
119 | ClangTidyOptions::OptionMap &Opts) { | 121 | ClangTidyOptions::OptionMap &Opts) { |
120 | Options.store(Opts, "StringLikeClasses", | 122 | Options.store(Opts, "StringLikeClasses", |
121 | utils::options::serializeStringList(StringLikeClasses)); | 123 | utils::options::serializeStringList(StringLikeClasses)); |
122 | - Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle()); | 124 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
123 | Options.store(Opts, "AbseilStringsMatchHeader", AbseilStringsMatchHeader); | 125 | Options.store(Opts, "AbseilStringsMatchHeader", AbseilStringsMatchHeader); |
124 | } | 126 | } |
125 | 127 | ... | ... |
... | @@ -35,8 +35,9 @@ public: | ... | @@ -35,8 +35,9 @@ public: |
35 | void storeOptions(ClangTidyOptions::OptionMap &Opts) override; | 35 | void storeOptions(ClangTidyOptions::OptionMap &Opts) override; |
36 | 36 | ||
37 | private: | 37 | private: |
38 | + std::unique_ptr<clang::tidy::utils::IncludeInserter> IncludeInserter; | ||
38 | const std::vector<std::string> StringLikeClasses; | 39 | const std::vector<std::string> StringLikeClasses; |
39 | - utils::IncludeInserter IncludeInserter; | 40 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; |
40 | const std::string AbseilStringsMatchHeader; | 41 | const std::string AbseilStringsMatchHeader; |
41 | }; | 42 | }; |
42 | 43 | ... | ... |
... | @@ -136,7 +136,7 @@ void %(check_name)s::registerMatchers(MatchFinder *Finder) { | ... | @@ -136,7 +136,7 @@ void %(check_name)s::registerMatchers(MatchFinder *Finder) { |
136 | void %(check_name)s::check(const MatchFinder::MatchResult &Result) { | 136 | void %(check_name)s::check(const MatchFinder::MatchResult &Result) { |
137 | // FIXME: Add callback implementation. | 137 | // FIXME: Add callback implementation. |
138 | const auto *MatchedDecl = Result.Nodes.getNodeAs<FunctionDecl>("x"); | 138 | const auto *MatchedDecl = Result.Nodes.getNodeAs<FunctionDecl>("x"); |
139 | - if (!MatchedDecl->getIdentifier() || MatchedDecl->getName().startswith("awesome_")) | 139 | + if (MatchedDecl->getName().startswith("awesome_")) |
140 | return; | 140 | return; |
141 | diag(MatchedDecl->getLocation(), "function %%0 is insufficiently awesome") | 141 | diag(MatchedDecl->getLocation(), "function %%0 is insufficiently awesome") |
142 | << MatchedDecl; | 142 | << MatchedDecl; | ... | ... |
1 | -//===--- AlteraTidyModule.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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#include "../ClangTidy.h" | ||
10 | -#include "../ClangTidyModule.h" | ||
11 | -#include "../ClangTidyModuleRegistry.h" | ||
12 | -#include "StructPackAlignCheck.h" | ||
13 | - | ||
14 | -using namespace clang::ast_matchers; | ||
15 | - | ||
16 | -namespace clang { | ||
17 | -namespace tidy { | ||
18 | -namespace altera { | ||
19 | - | ||
20 | -class AlteraModule : public ClangTidyModule { | ||
21 | -public: | ||
22 | - void addCheckFactories(ClangTidyCheckFactories &CheckFactories) override { | ||
23 | - CheckFactories.registerCheck<StructPackAlignCheck>( | ||
24 | - "altera-struct-pack-align"); | ||
25 | - } | ||
26 | -}; | ||
27 | - | ||
28 | -} // namespace altera | ||
29 | - | ||
30 | -// Register the AlteraTidyModule using this statically initialized variable. | ||
31 | -static ClangTidyModuleRegistry::Add<altera::AlteraModule> | ||
32 | - X("altera-module", "Adds Altera FPGA OpenCL lint checks."); | ||
33 | - | ||
34 | -// This anchor is used to force the linker to link in the generated object file | ||
35 | -// and thus register the AlteraModule. | ||
36 | -volatile int AlteraModuleAnchorSource = 0; | ||
37 | - | ||
38 | -} // namespace tidy | ||
39 | -} // namespace clang |
1 | -set(LLVM_LINK_COMPONENTS | ||
2 | - FrontendOpenMP | ||
3 | - support | ||
4 | - ) | ||
5 | - | ||
6 | -add_clang_library(clangTidyAlteraModule | ||
7 | - AlteraTidyModule.cpp | ||
8 | - StructPackAlignCheck.cpp | ||
9 | - | ||
10 | - LINK_LIBS | ||
11 | - clangTidy | ||
12 | - clangTidyUtils | ||
13 | - ) | ||
14 | - | ||
15 | -clang_target_link_libraries(clangTidyAlteraModule | ||
16 | - PRIVATE | ||
17 | - clangAnalysis | ||
18 | - clangAST | ||
19 | - clangASTMatchers | ||
20 | - clangBasic | ||
21 | - clangLex | ||
22 | - ) |
1 | -//===--- StructPackAlignCheck.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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#include "StructPackAlignCheck.h" | ||
10 | -#include "clang/AST/ASTContext.h" | ||
11 | -#include "clang/AST/RecordLayout.h" | ||
12 | -#include "clang/ASTMatchers/ASTMatchFinder.h" | ||
13 | -#include <math.h> | ||
14 | -#include <sstream> | ||
15 | - | ||
16 | -using namespace clang::ast_matchers; | ||
17 | - | ||
18 | -namespace clang { | ||
19 | -namespace tidy { | ||
20 | -namespace altera { | ||
21 | - | ||
22 | -void StructPackAlignCheck::registerMatchers(MatchFinder *Finder) { | ||
23 | - Finder->addMatcher(recordDecl(isStruct(), isDefinition(), | ||
24 | - unless(isExpansionInSystemHeader())) | ||
25 | - .bind("struct"), | ||
26 | - this); | ||
27 | -} | ||
28 | - | ||
29 | -CharUnits | ||
30 | -StructPackAlignCheck::computeRecommendedAlignment(CharUnits MinByteSize) { | ||
31 | - CharUnits NewAlign = CharUnits::fromQuantity(1); | ||
32 | - if (!MinByteSize.isPowerOfTwo()) { | ||
33 | - int MSB = (int)MinByteSize.getQuantity(); | ||
34 | - for (; MSB > 0; MSB /= 2) { | ||
35 | - NewAlign = NewAlign.alignTo( | ||
36 | - CharUnits::fromQuantity(((int)NewAlign.getQuantity()) * 2)); | ||
37 | - // Abort if the computed alignment meets the maximum configured alignment. | ||
38 | - if (NewAlign.getQuantity() >= MaxConfiguredAlignment) | ||
39 | - break; | ||
40 | - } | ||
41 | - } else { | ||
42 | - NewAlign = MinByteSize; | ||
43 | - } | ||
44 | - return NewAlign; | ||
45 | -} | ||
46 | - | ||
47 | -void StructPackAlignCheck::check(const MatchFinder::MatchResult &Result) { | ||
48 | - const auto *Struct = Result.Nodes.getNodeAs<RecordDecl>("struct"); | ||
49 | - | ||
50 | - // Do not trigger on templated struct declarations because the packing and | ||
51 | - // alignment requirements are unknown. | ||
52 | - if (Struct->isTemplated()) | ||
53 | - return; | ||
54 | - | ||
55 | - // Get sizing info for the struct. | ||
56 | - llvm::SmallVector<std::pair<unsigned int, unsigned int>, 10> FieldSizes; | ||
57 | - unsigned int TotalBitSize = 0; | ||
58 | - for (const FieldDecl *StructField : Struct->fields()) { | ||
59 | - // For each StructField, record how big it is (in bits). | ||
60 | - // Would be good to use a pair of <offset, size> to advise a better | ||
61 | - // packing order. | ||
62 | - unsigned int StructFieldWidth = | ||
63 | - (unsigned int)Result.Context | ||
64 | - ->getTypeInfo(StructField->getType().getTypePtr()) | ||
65 | - .Width; | ||
66 | - FieldSizes.emplace_back(StructFieldWidth, StructField->getFieldIndex()); | ||
67 | - // FIXME: Recommend a reorganization of the struct (sort by StructField | ||
68 | - // size, largest to smallest). | ||
69 | - TotalBitSize += StructFieldWidth; | ||
70 | - } | ||
71 | - | ||
72 | - uint64_t CharSize = Result.Context->getCharWidth(); | ||
73 | - CharUnits CurrSize = Result.Context->getASTRecordLayout(Struct).getSize(); | ||
74 | - CharUnits MinByteSize = | ||
75 | - CharUnits::fromQuantity(ceil((float)TotalBitSize / CharSize)); | ||
76 | - CharUnits MaxAlign = CharUnits::fromQuantity( | ||
77 | - ceil((float)Struct->getMaxAlignment() / CharSize)); | ||
78 | - CharUnits CurrAlign = | ||
79 | - Result.Context->getASTRecordLayout(Struct).getAlignment(); | ||
80 | - CharUnits NewAlign = computeRecommendedAlignment(MinByteSize); | ||
81 | - | ||
82 | - bool IsPacked = Struct->hasAttr<PackedAttr>(); | ||
83 | - bool NeedsPacking = (MinByteSize < CurrSize) && (MaxAlign != NewAlign) && | ||
84 | - (CurrSize != NewAlign); | ||
85 | - bool NeedsAlignment = CurrAlign.getQuantity() != NewAlign.getQuantity(); | ||
86 | - | ||
87 | - if (!NeedsAlignment && !NeedsPacking) | ||
88 | - return; | ||
89 | - | ||
90 | - // If it's using much more space than it needs, suggest packing. | ||
91 | - // (Do not suggest packing if it is currently explicitly aligned to what the | ||
92 | - // minimum byte size would suggest as the new alignment.) | ||
93 | - if (NeedsPacking && !IsPacked) { | ||
94 | - diag(Struct->getLocation(), | ||
95 | - "accessing fields in struct %0 is inefficient due to padding; only " | ||
96 | - "needs %1 bytes but is using %2 bytes") | ||
97 | - << Struct << (int)MinByteSize.getQuantity() | ||
98 | - << (int)CurrSize.getQuantity() | ||
99 | - << FixItHint::CreateInsertion(Struct->getEndLoc().getLocWithOffset(1), | ||
100 | - " __attribute__((packed))"); | ||
101 | - diag(Struct->getLocation(), | ||
102 | - "use \"__attribute__((packed))\" to reduce the amount of padding " | ||
103 | - "applied to struct %0", | ||
104 | - DiagnosticIDs::Note) | ||
105 | - << Struct; | ||
106 | - } | ||
107 | - | ||
108 | - FixItHint FixIt; | ||
109 | - AlignedAttr *Attribute = Struct->getAttr<AlignedAttr>(); | ||
110 | - std::string NewAlignQuantity = std::to_string((int)NewAlign.getQuantity()); | ||
111 | - if (Attribute) { | ||
112 | - std::ostringstream FixItString; | ||
113 | - FixItString << "aligned(" << NewAlignQuantity << ")"; | ||
114 | - FixIt = | ||
115 | - FixItHint::CreateReplacement(Attribute->getRange(), FixItString.str()); | ||
116 | - } else { | ||
117 | - std::ostringstream FixItString; | ||
118 | - FixItString << " __attribute__((aligned(" << NewAlignQuantity << ")))"; | ||
119 | - FixIt = FixItHint::CreateInsertion(Struct->getEndLoc().getLocWithOffset(1), | ||
120 | - FixItString.str()); | ||
121 | - } | ||
122 | - | ||
123 | - // And suggest the minimum power-of-two alignment for the struct as a whole | ||
124 | - // (with and without packing). | ||
125 | - if (NeedsAlignment) { | ||
126 | - diag(Struct->getLocation(), | ||
127 | - "accessing fields in struct %0 is inefficient due to poor alignment; " | ||
128 | - "currently aligned to %1 bytes, but recommended alignment is %2 bytes") | ||
129 | - << Struct << (int)CurrAlign.getQuantity() << NewAlignQuantity << FixIt; | ||
130 | - | ||
131 | - diag(Struct->getLocation(), | ||
132 | - "use \"__attribute__((aligned(%0)))\" to align struct %1 to %0 bytes", | ||
133 | - DiagnosticIDs::Note) | ||
134 | - << NewAlignQuantity << Struct; | ||
135 | - } | ||
136 | -} | ||
137 | - | ||
138 | -void StructPackAlignCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { | ||
139 | - Options.store(Opts, "MaxConfiguredAlignment", MaxConfiguredAlignment); | ||
140 | -} | ||
141 | - | ||
142 | -} // namespace altera | ||
143 | -} // namespace tidy | ||
144 | -} // namespace clang |
1 | -//===--- StructPackAlignCheck.h - clang-tidy --------------------*- C++ -*-===// | ||
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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_ALTERA_STRUCTPACKALIGNCHECK_H | ||
10 | -#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_ALTERA_STRUCTPACKALIGNCHECK_H | ||
11 | - | ||
12 | -#include "../ClangTidyCheck.h" | ||
13 | - | ||
14 | -namespace clang { | ||
15 | -namespace tidy { | ||
16 | -namespace altera { | ||
17 | - | ||
18 | -/// Finds structs that are inefficiently packed or aligned, and recommends | ||
19 | -/// packing and/or aligning of said structs as needed. | ||
20 | -/// | ||
21 | -/// For the user-facing documentation see: | ||
22 | -/// http://clang.llvm.org/extra/clang-tidy/checks/altera-struct-pack-align.html | ||
23 | -class StructPackAlignCheck : public ClangTidyCheck { | ||
24 | -public: | ||
25 | - StructPackAlignCheck(StringRef Name, ClangTidyContext *Context) | ||
26 | - : ClangTidyCheck(Name, Context), | ||
27 | - MaxConfiguredAlignment(Options.get("MaxConfiguredAlignment", 128)) {} | ||
28 | - void registerMatchers(ast_matchers::MatchFinder *Finder) override; | ||
29 | - void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | ||
30 | - void storeOptions(ClangTidyOptions::OptionMap &Opts) override; | ||
31 | - | ||
32 | -private: | ||
33 | - const unsigned MaxConfiguredAlignment; | ||
34 | - CharUnits computeRecommendedAlignment(CharUnits MinByteSize); | ||
35 | -}; | ||
36 | - | ||
37 | -} // namespace altera | ||
38 | -} // namespace tidy | ||
39 | -} // namespace clang | ||
40 | - | ||
41 | -#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_ALTERA_STRUCTPACKALIGNCHECK_H |
... | @@ -18,17 +18,32 @@ namespace clang { | ... | @@ -18,17 +18,32 @@ namespace clang { |
18 | namespace tidy { | 18 | namespace tidy { |
19 | namespace android { | 19 | namespace android { |
20 | 20 | ||
21 | -ComparisonInTempFailureRetryCheck::ComparisonInTempFailureRetryCheck( | 21 | +namespace { |
22 | - StringRef Name, ClangTidyContext *Context) | 22 | +AST_MATCHER(BinaryOperator, isRHSATempFailureRetryArg) { |
23 | - : ClangTidyCheck(Name, Context), | 23 | + if (!Node.getBeginLoc().isMacroID()) |
24 | - RawRetryList(Options.get("RetryMacros", "TEMP_FAILURE_RETRY")) { | 24 | + return false; |
25 | - StringRef(RawRetryList).split(RetryMacros, ",", -1, false); | 25 | + |
26 | -} | 26 | + const SourceManager &SM = Finder->getASTContext().getSourceManager(); |
27 | + if (!SM.isMacroArgExpansion(Node.getRHS()->IgnoreParenCasts()->getBeginLoc())) | ||
28 | + return false; | ||
29 | + | ||
30 | + const LangOptions &Opts = Finder->getASTContext().getLangOpts(); | ||
31 | + SourceLocation LocStart = Node.getBeginLoc(); | ||
32 | + while (LocStart.isMacroID()) { | ||
33 | + SourceLocation Invocation = SM.getImmediateMacroCallerLoc(LocStart); | ||
34 | + Token Tok; | ||
35 | + if (!Lexer::getRawToken(SM.getSpellingLoc(Invocation), Tok, SM, Opts, | ||
36 | + /*IgnoreWhiteSpace=*/true)) { | ||
37 | + if (Tok.getKind() == tok::raw_identifier && | ||
38 | + Tok.getRawIdentifier() == "TEMP_FAILURE_RETRY") | ||
39 | + return true; | ||
40 | + } | ||
27 | 41 | ||
28 | -void ComparisonInTempFailureRetryCheck::storeOptions( | 42 | + LocStart = Invocation; |
29 | - ClangTidyOptions::OptionMap &Opts) { | 43 | + } |
30 | - Options.store(Opts, "RetryMacros", RawRetryList); | 44 | + return false; |
31 | } | 45 | } |
46 | +} // namespace | ||
32 | 47 | ||
33 | void ComparisonInTempFailureRetryCheck::registerMatchers(MatchFinder *Finder) { | 48 | void ComparisonInTempFailureRetryCheck::registerMatchers(MatchFinder *Finder) { |
34 | // Both glibc's and Bionic's TEMP_FAILURE_RETRY macros structurally look like: | 49 | // Both glibc's and Bionic's TEMP_FAILURE_RETRY macros structurally look like: |
... | @@ -48,43 +63,15 @@ void ComparisonInTempFailureRetryCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -48,43 +63,15 @@ void ComparisonInTempFailureRetryCheck::registerMatchers(MatchFinder *Finder) { |
48 | Finder->addMatcher( | 63 | Finder->addMatcher( |
49 | binaryOperator(hasOperatorName("="), | 64 | binaryOperator(hasOperatorName("="), |
50 | hasRHS(ignoringParenCasts( | 65 | hasRHS(ignoringParenCasts( |
51 | - binaryOperator(isComparisonOperator()).bind("inner")))) | 66 | + binaryOperator(isComparisonOperator()).bind("binop"))), |
52 | - .bind("outer"), | 67 | + isRHSATempFailureRetryArg()), |
53 | this); | 68 | this); |
54 | } | 69 | } |
55 | 70 | ||
56 | void ComparisonInTempFailureRetryCheck::check( | 71 | void ComparisonInTempFailureRetryCheck::check( |
57 | const MatchFinder::MatchResult &Result) { | 72 | const MatchFinder::MatchResult &Result) { |
58 | - StringRef RetryMacroName; | 73 | + const auto &BinOp = *Result.Nodes.getNodeAs<BinaryOperator>("binop"); |
59 | - const auto &Node = *Result.Nodes.getNodeAs<BinaryOperator>("outer"); | 74 | + diag(BinOp.getOperatorLoc(), "top-level comparison in TEMP_FAILURE_RETRY"); |
60 | - if (!Node.getBeginLoc().isMacroID()) | ||
61 | - return; | ||
62 | - | ||
63 | - const SourceManager &SM = *Result.SourceManager; | ||
64 | - if (!SM.isMacroArgExpansion(Node.getRHS()->IgnoreParenCasts()->getBeginLoc())) | ||
65 | - return; | ||
66 | - | ||
67 | - const LangOptions &Opts = Result.Context->getLangOpts(); | ||
68 | - SourceLocation LocStart = Node.getBeginLoc(); | ||
69 | - while (LocStart.isMacroID()) { | ||
70 | - SourceLocation Invocation = SM.getImmediateMacroCallerLoc(LocStart); | ||
71 | - Token Tok; | ||
72 | - if (!Lexer::getRawToken(SM.getSpellingLoc(Invocation), Tok, SM, Opts, | ||
73 | - /*IgnoreWhiteSpace=*/true)) { | ||
74 | - if (Tok.getKind() == tok::raw_identifier && | ||
75 | - llvm::is_contained(RetryMacros, Tok.getRawIdentifier())) { | ||
76 | - RetryMacroName = Tok.getRawIdentifier(); | ||
77 | - break; | ||
78 | - } | ||
79 | - } | ||
80 | - | ||
81 | - LocStart = Invocation; | ||
82 | - } | ||
83 | - if (RetryMacroName.empty()) | ||
84 | - return; | ||
85 | - | ||
86 | - const auto &Inner = *Result.Nodes.getNodeAs<BinaryOperator>("inner"); | ||
87 | - diag(Inner.getOperatorLoc(), "top-level comparison in %0") << RetryMacroName; | ||
88 | 75 | ||
89 | // FIXME: FixIts would be nice, but potentially nontrivial when nested macros | 76 | // FIXME: FixIts would be nice, but potentially nontrivial when nested macros |
90 | // happen, e.g. `TEMP_FAILURE_RETRY(IS_ZERO(foo()))` | 77 | // happen, e.g. `TEMP_FAILURE_RETRY(IS_ZERO(foo()))` | ... | ... |
... | @@ -10,9 +10,6 @@ | ... | @@ -10,9 +10,6 @@ |
10 | #define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_ANDROID_COMPARISONINTEMPFAILURERETRYCHECK_H | 10 | #define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_ANDROID_COMPARISONINTEMPFAILURERETRYCHECK_H |
11 | 11 | ||
12 | #include "../ClangTidyCheck.h" | 12 | #include "../ClangTidyCheck.h" |
13 | -#include "llvm/ADT/SmallVector.h" | ||
14 | -#include "llvm/ADT/StringRef.h" | ||
15 | -#include <string> | ||
16 | 13 | ||
17 | namespace clang { | 14 | namespace clang { |
18 | namespace tidy { | 15 | namespace tidy { |
... | @@ -25,14 +22,10 @@ namespace android { | ... | @@ -25,14 +22,10 @@ namespace android { |
25 | /// TEMP_FAILURE_RETRY is a macro provided by both glibc and Bionic. | 22 | /// TEMP_FAILURE_RETRY is a macro provided by both glibc and Bionic. |
26 | class ComparisonInTempFailureRetryCheck : public ClangTidyCheck { | 23 | class ComparisonInTempFailureRetryCheck : public ClangTidyCheck { |
27 | public: | 24 | public: |
28 | - ComparisonInTempFailureRetryCheck(StringRef Name, ClangTidyContext *Context); | 25 | + ComparisonInTempFailureRetryCheck(StringRef Name, ClangTidyContext *Context) |
29 | - void storeOptions(ClangTidyOptions::OptionMap &Opts) override; | 26 | + : ClangTidyCheck(Name, Context) {} |
30 | void registerMatchers(ast_matchers::MatchFinder *Finder) override; | 27 | void registerMatchers(ast_matchers::MatchFinder *Finder) override; |
31 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | 28 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; |
32 | - | ||
33 | -private: | ||
34 | - const std::string RawRetryList; | ||
35 | - SmallVector<StringRef, 5> RetryMacros; | ||
36 | }; | 29 | }; |
37 | 30 | ||
38 | } // namespace android | 31 | } // namespace android | ... | ... |
... | @@ -30,8 +30,7 @@ static Preprocessor *PP; | ... | @@ -30,8 +30,7 @@ static Preprocessor *PP; |
30 | 30 | ||
31 | void BadSignalToKillThreadCheck::check(const MatchFinder::MatchResult &Result) { | 31 | void BadSignalToKillThreadCheck::check(const MatchFinder::MatchResult &Result) { |
32 | const auto IsSigterm = [](const auto &KeyValue) -> bool { | 32 | const auto IsSigterm = [](const auto &KeyValue) -> bool { |
33 | - return KeyValue.first->getName() == "SIGTERM" && | 33 | + return KeyValue.first->getName() == "SIGTERM"; |
34 | - KeyValue.first->hasMacroDefinition(); | ||
35 | }; | 34 | }; |
36 | const auto TryExpandAsInteger = | 35 | const auto TryExpandAsInteger = |
37 | [](Preprocessor::macro_iterator It) -> Optional<unsigned> { | 36 | [](Preprocessor::macro_iterator It) -> Optional<unsigned> { |
... | @@ -39,8 +38,6 @@ void BadSignalToKillThreadCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -39,8 +38,6 @@ void BadSignalToKillThreadCheck::check(const MatchFinder::MatchResult &Result) { |
39 | return llvm::None; | 38 | return llvm::None; |
40 | const MacroInfo *MI = PP->getMacroInfo(It->first); | 39 | const MacroInfo *MI = PP->getMacroInfo(It->first); |
41 | const Token &T = MI->tokens().back(); | 40 | const Token &T = MI->tokens().back(); |
42 | - if (!T.isLiteral() || !T.getLiteralData()) | ||
43 | - return llvm::None; | ||
44 | StringRef ValueStr = StringRef(T.getLiteralData(), T.getLength()); | 41 | StringRef ValueStr = StringRef(T.getLiteralData(), T.getLength()); |
45 | 42 | ||
46 | llvm::APInt IntValue; | 43 | llvm::APInt IntValue; | ... | ... |
... | @@ -20,68 +20,53 @@ void BoolPointerImplicitConversionCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -20,68 +20,53 @@ void BoolPointerImplicitConversionCheck::registerMatchers(MatchFinder *Finder) { |
20 | Finder->addMatcher( | 20 | Finder->addMatcher( |
21 | traverse( | 21 | traverse( |
22 | ast_type_traits::TK_AsIs, | 22 | ast_type_traits::TK_AsIs, |
23 | - ifStmt( | 23 | + ifStmt(hasCondition(findAll(implicitCastExpr( |
24 | - hasCondition(findAll(implicitCastExpr( | 24 | + unless(hasParent(unaryOperator(hasOperatorName("!")))), |
25 | - unless(hasParent(unaryOperator(hasOperatorName("!")))), | 25 | + hasSourceExpression(expr( |
26 | - hasSourceExpression(expr( | 26 | + hasType(pointerType(pointee(booleanType()))), |
27 | - hasType(pointerType(pointee(booleanType()))), | 27 | + ignoringParenImpCasts(declRefExpr().bind("expr")))), |
28 | - ignoringParenImpCasts(anyOf(declRefExpr().bind("expr"), | 28 | + hasCastKind(CK_PointerToBoolean)))), |
29 | - memberExpr().bind("expr"))))), | 29 | + unless(isInTemplateInstantiation())) |
30 | - hasCastKind(CK_PointerToBoolean)))), | ||
31 | - unless(isInTemplateInstantiation())) | ||
32 | .bind("if")), | 30 | .bind("if")), |
33 | this); | 31 | this); |
34 | } | 32 | } |
35 | 33 | ||
36 | -static void checkImpl(const MatchFinder::MatchResult &Result, const Expr *Ref, | 34 | +void BoolPointerImplicitConversionCheck::check( |
37 | - const IfStmt *If, | 35 | + const MatchFinder::MatchResult &Result) { |
38 | - const ast_matchers::internal::Matcher<Expr> &RefMatcher, | 36 | + auto *If = Result.Nodes.getNodeAs<IfStmt>("if"); |
39 | - ClangTidyCheck &Check) { | 37 | + auto *Var = Result.Nodes.getNodeAs<DeclRefExpr>("expr"); |
38 | + | ||
40 | // Ignore macros. | 39 | // Ignore macros. |
41 | - if (Ref->getBeginLoc().isMacroID()) | 40 | + if (Var->getBeginLoc().isMacroID()) |
42 | return; | 41 | return; |
43 | 42 | ||
44 | - // Only allow variable accesses and member exprs for now, no function calls. | 43 | + // Only allow variable accesses for now, no function calls or member exprs. |
45 | // Check that we don't dereference the variable anywhere within the if. This | 44 | // Check that we don't dereference the variable anywhere within the if. This |
46 | // avoids false positives for checks of the pointer for nullptr before it is | 45 | // avoids false positives for checks of the pointer for nullptr before it is |
47 | // dereferenced. If there is a dereferencing operator on this variable don't | 46 | // dereferenced. If there is a dereferencing operator on this variable don't |
48 | // emit a diagnostic. Also ignore array subscripts. | 47 | // emit a diagnostic. Also ignore array subscripts. |
49 | - if (!match(findAll(unaryOperator(hasOperatorName("*"), | 48 | + const Decl *D = Var->getDecl(); |
50 | - hasUnaryOperand(RefMatcher))), | 49 | + auto DeclRef = ignoringParenImpCasts(declRefExpr(to(equalsNode(D)))); |
50 | + if (!match(findAll( | ||
51 | + unaryOperator(hasOperatorName("*"), hasUnaryOperand(DeclRef))), | ||
51 | *If, *Result.Context) | 52 | *If, *Result.Context) |
52 | .empty() || | 53 | .empty() || |
53 | - !match(findAll(arraySubscriptExpr(hasBase(RefMatcher))), *If, | 54 | + !match(findAll(arraySubscriptExpr(hasBase(DeclRef))), *If, |
54 | *Result.Context) | 55 | *Result.Context) |
55 | .empty() || | 56 | .empty() || |
56 | // FIXME: We should still warn if the paremater is implicitly converted to | 57 | // FIXME: We should still warn if the paremater is implicitly converted to |
57 | // bool. | 58 | // bool. |
58 | - !match( | 59 | + !match(findAll(callExpr(hasAnyArgument(ignoringParenImpCasts(DeclRef)))), |
59 | - findAll(callExpr(hasAnyArgument(ignoringParenImpCasts(RefMatcher)))), | 60 | + *If, *Result.Context) |
60 | - *If, *Result.Context) | ||
61 | .empty() || | 61 | .empty() || |
62 | - !match( | 62 | + !match(findAll(cxxDeleteExpr(has(ignoringParenImpCasts(expr(DeclRef))))), |
63 | - findAll(cxxDeleteExpr(has(ignoringParenImpCasts(expr(RefMatcher))))), | 63 | + *If, *Result.Context) |
64 | - *If, *Result.Context) | ||
65 | .empty()) | 64 | .empty()) |
66 | return; | 65 | return; |
67 | 66 | ||
68 | - Check.diag(Ref->getBeginLoc(), | 67 | + diag(Var->getBeginLoc(), "dubious check of 'bool *' against 'nullptr', did " |
69 | - "dubious check of 'bool *' against 'nullptr', did " | 68 | + "you mean to dereference it?") |
70 | - "you mean to dereference it?") | 69 | + << FixItHint::CreateInsertion(Var->getBeginLoc(), "*"); |
71 | - << FixItHint::CreateInsertion(Ref->getBeginLoc(), "*"); | ||
72 | -} | ||
73 | - | ||
74 | -void BoolPointerImplicitConversionCheck::check( | ||
75 | - const MatchFinder::MatchResult &Result) { | ||
76 | - const auto *If = Result.Nodes.getNodeAs<IfStmt>("if"); | ||
77 | - if (const auto *E = Result.Nodes.getNodeAs<Expr>("expr")) { | ||
78 | - const Decl *D = isa<DeclRefExpr>(E) ? cast<DeclRefExpr>(E)->getDecl() | ||
79 | - : cast<MemberExpr>(E)->getMemberDecl(); | ||
80 | - const auto M = | ||
81 | - ignoringParenImpCasts(anyOf(declRefExpr(to(equalsNode(D))), | ||
82 | - memberExpr(hasDeclaration(equalsNode(D))))); | ||
83 | - checkImpl(Result, E, If, M, *this); | ||
84 | - } | ||
85 | } | 70 | } |
86 | 71 | ||
87 | } // namespace bugprone | 72 | } // namespace bugprone | ... | ... |
... | @@ -38,7 +38,6 @@ | ... | @@ -38,7 +38,6 @@ |
38 | #include "NotNullTerminatedResultCheck.h" | 38 | #include "NotNullTerminatedResultCheck.h" |
39 | #include "ParentVirtualCallCheck.h" | 39 | #include "ParentVirtualCallCheck.h" |
40 | #include "PosixReturnCheck.h" | 40 | #include "PosixReturnCheck.h" |
41 | -#include "RedundantBranchConditionCheck.h" | ||
42 | #include "ReservedIdentifierCheck.h" | 41 | #include "ReservedIdentifierCheck.h" |
43 | #include "SignedCharMisuseCheck.h" | 42 | #include "SignedCharMisuseCheck.h" |
44 | #include "SizeofContainerCheck.h" | 43 | #include "SizeofContainerCheck.h" |
... | @@ -120,8 +119,6 @@ public: | ... | @@ -120,8 +119,6 @@ public: |
120 | "bugprone-move-forwarding-reference"); | 119 | "bugprone-move-forwarding-reference"); |
121 | CheckFactories.registerCheck<MultipleStatementMacroCheck>( | 120 | CheckFactories.registerCheck<MultipleStatementMacroCheck>( |
122 | "bugprone-multiple-statement-macro"); | 121 | "bugprone-multiple-statement-macro"); |
123 | - CheckFactories.registerCheck<RedundantBranchConditionCheck>( | ||
124 | - "bugprone-redundant-branch-condition"); | ||
125 | CheckFactories.registerCheck<cppcoreguidelines::NarrowingConversionsCheck>( | 122 | CheckFactories.registerCheck<cppcoreguidelines::NarrowingConversionsCheck>( |
126 | "bugprone-narrowing-conversions"); | 123 | "bugprone-narrowing-conversions"); |
127 | CheckFactories.registerCheck<NoEscapeCheck>("bugprone-no-escape"); | 124 | CheckFactories.registerCheck<NoEscapeCheck>("bugprone-no-escape"); | ... | ... |
... | @@ -33,7 +33,6 @@ add_clang_library(clangTidyBugproneModule | ... | @@ -33,7 +33,6 @@ add_clang_library(clangTidyBugproneModule |
33 | NotNullTerminatedResultCheck.cpp | 33 | NotNullTerminatedResultCheck.cpp |
34 | ParentVirtualCallCheck.cpp | 34 | ParentVirtualCallCheck.cpp |
35 | PosixReturnCheck.cpp | 35 | PosixReturnCheck.cpp |
36 | - RedundantBranchConditionCheck.cpp | ||
37 | ReservedIdentifierCheck.cpp | 36 | ReservedIdentifierCheck.cpp |
38 | SignedCharMisuseCheck.cpp | 37 | SignedCharMisuseCheck.cpp |
39 | SizeofContainerCheck.cpp | 38 | SizeofContainerCheck.cpp | ... | ... |
... | @@ -77,9 +77,9 @@ void MisplacedPointerArithmeticInAllocCheck::check( | ... | @@ -77,9 +77,9 @@ void MisplacedPointerArithmeticInAllocCheck::check( |
77 | CallName = "operator new[]"; | 77 | CallName = "operator new[]"; |
78 | } else { | 78 | } else { |
79 | const auto *CtrE = New->getConstructExpr(); | 79 | const auto *CtrE = New->getConstructExpr(); |
80 | - if (!CtrE || !CtrE->getArg(CtrE->getNumArgs() - 1) | 80 | + if (!CtrE->getArg(CtrE->getNumArgs() - 1) |
81 | - ->getType() | 81 | + ->getType() |
82 | - ->isIntegralOrEnumerationType()) | 82 | + ->isIntegralOrEnumerationType()) |
83 | return; | 83 | return; |
84 | CallName = "operator new"; | 84 | CallName = "operator new"; |
85 | } | 85 | } | ... | ... |
... | @@ -802,16 +802,11 @@ void NotNullTerminatedResultCheck::check( | ... | @@ -802,16 +802,11 @@ void NotNullTerminatedResultCheck::check( |
802 | while (It != PP->macro_end() && !AreSafeFunctionsWanted.hasValue()) { | 802 | while (It != PP->macro_end() && !AreSafeFunctionsWanted.hasValue()) { |
803 | if (It->first->getName() == "__STDC_WANT_LIB_EXT1__") { | 803 | if (It->first->getName() == "__STDC_WANT_LIB_EXT1__") { |
804 | const auto *MI = PP->getMacroInfo(It->first); | 804 | const auto *MI = PP->getMacroInfo(It->first); |
805 | - // PP->getMacroInfo() returns nullptr if macro has no definition. | 805 | + const auto &T = MI->tokens().back(); |
806 | - if (MI) { | 806 | + StringRef ValueStr = StringRef(T.getLiteralData(), T.getLength()); |
807 | - const auto &T = MI->tokens().back(); | 807 | + llvm::APInt IntValue; |
808 | - if (T.isLiteral() && T.getLiteralData()) { | 808 | + ValueStr.getAsInteger(10, IntValue); |
809 | - StringRef ValueStr = StringRef(T.getLiteralData(), T.getLength()); | 809 | + AreSafeFunctionsWanted = IntValue.getZExtValue(); |
810 | - llvm::APInt IntValue; | ||
811 | - ValueStr.getAsInteger(10, IntValue); | ||
812 | - AreSafeFunctionsWanted = IntValue.getZExtValue(); | ||
813 | - } | ||
814 | - } | ||
815 | } | 810 | } |
816 | 811 | ||
817 | ++It; | 812 | ++It; | ... | ... |
llvm-project/clang-tools-extra/clang-tidy/bugprone/RedundantBranchConditionCheck.cpp
deleted
100644 → 0
1 | -//===--- RedundantBranchConditionCheck.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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#include "RedundantBranchConditionCheck.h" | ||
10 | -#include "../utils/Aliasing.h" | ||
11 | -#include "clang/AST/ASTContext.h" | ||
12 | -#include "clang/ASTMatchers/ASTMatchFinder.h" | ||
13 | -#include "clang/Analysis/Analyses/ExprMutationAnalyzer.h" | ||
14 | -#include "clang/Lex/Lexer.h" | ||
15 | - | ||
16 | -using namespace clang::ast_matchers; | ||
17 | -using clang::tidy::utils::hasPtrOrReferenceInFunc; | ||
18 | - | ||
19 | -namespace clang { | ||
20 | -namespace tidy { | ||
21 | -namespace bugprone { | ||
22 | - | ||
23 | -static const char CondVarStr[] = "cond_var"; | ||
24 | -static const char OuterIfStr[] = "outer_if"; | ||
25 | -static const char InnerIfStr[] = "inner_if"; | ||
26 | -static const char FuncStr[] = "func"; | ||
27 | - | ||
28 | -/// Returns whether `Var` is changed in `S` before `NextS`. | ||
29 | -static bool isChangedBefore(const Stmt *S, const Stmt *NextS, | ||
30 | - const VarDecl *Var, ASTContext *Context) { | ||
31 | - ExprMutationAnalyzer MutAn(*S, *Context); | ||
32 | - const auto &SM = Context->getSourceManager(); | ||
33 | - const Stmt *MutS = MutAn.findMutation(Var); | ||
34 | - return MutS && | ||
35 | - SM.isBeforeInTranslationUnit(MutS->getEndLoc(), NextS->getBeginLoc()); | ||
36 | -} | ||
37 | - | ||
38 | -void RedundantBranchConditionCheck::registerMatchers(MatchFinder *Finder) { | ||
39 | - const auto ImmutableVar = | ||
40 | - varDecl(anyOf(parmVarDecl(), hasLocalStorage()), hasType(isInteger()), | ||
41 | - unless(hasType(isVolatileQualified()))) | ||
42 | - .bind(CondVarStr); | ||
43 | - Finder->addMatcher( | ||
44 | - ifStmt( | ||
45 | - hasCondition(ignoringParenImpCasts(anyOf( | ||
46 | - declRefExpr(hasDeclaration(ImmutableVar)), | ||
47 | - binaryOperator(hasOperatorName("&&"), | ||
48 | - hasEitherOperand(ignoringParenImpCasts(declRefExpr( | ||
49 | - hasDeclaration(ImmutableVar)))))))), | ||
50 | - hasThen(hasDescendant( | ||
51 | - ifStmt(hasCondition(ignoringParenImpCasts( | ||
52 | - anyOf(declRefExpr(hasDeclaration( | ||
53 | - varDecl(equalsBoundNode(CondVarStr)))), | ||
54 | - binaryOperator( | ||
55 | - hasAnyOperatorName("&&", "||"), | ||
56 | - hasEitherOperand(ignoringParenImpCasts( | ||
57 | - declRefExpr(hasDeclaration(varDecl( | ||
58 | - equalsBoundNode(CondVarStr))))))))))) | ||
59 | - .bind(InnerIfStr))), | ||
60 | - forFunction(functionDecl().bind(FuncStr))) | ||
61 | - .bind(OuterIfStr), | ||
62 | - this); | ||
63 | - // FIXME: Handle longer conjunctive and disjunctive clauses. | ||
64 | -} | ||
65 | - | ||
66 | -void RedundantBranchConditionCheck::check(const MatchFinder::MatchResult &Result) { | ||
67 | - const auto *OuterIf = Result.Nodes.getNodeAs<IfStmt>(OuterIfStr); | ||
68 | - const auto *InnerIf = Result.Nodes.getNodeAs<IfStmt>(InnerIfStr); | ||
69 | - const auto *CondVar = Result.Nodes.getNodeAs<VarDecl>(CondVarStr); | ||
70 | - const auto *Func = Result.Nodes.getNodeAs<FunctionDecl>(FuncStr); | ||
71 | - | ||
72 | - // If the variable has an alias then it can be changed by that alias as well. | ||
73 | - // FIXME: could potentially support tracking pointers and references in the | ||
74 | - // future to improve catching true positives through aliases. | ||
75 | - if (hasPtrOrReferenceInFunc(Func, CondVar)) | ||
76 | - return; | ||
77 | - | ||
78 | - if (isChangedBefore(OuterIf->getThen(), InnerIf, CondVar, Result.Context)) | ||
79 | - return; | ||
80 | - | ||
81 | - auto Diag = diag(InnerIf->getBeginLoc(), "redundant condition %0") << CondVar; | ||
82 | - | ||
83 | - // For standalone condition variables and for "or" binary operations we simply | ||
84 | - // remove the inner `if`. | ||
85 | - const auto *BinOpCond = dyn_cast<BinaryOperator>(InnerIf->getCond()); | ||
86 | - if (isa<DeclRefExpr>(InnerIf->getCond()->IgnoreParenImpCasts()) || | ||
87 | - (BinOpCond && BinOpCond->getOpcode() == BO_LOr)) { | ||
88 | - SourceLocation IfBegin = InnerIf->getBeginLoc(); | ||
89 | - const Stmt *Body = InnerIf->getThen(); | ||
90 | - const Expr *OtherSide = nullptr; | ||
91 | - if (BinOpCond) { | ||
92 | - const auto *LeftDRE = | ||
93 | - dyn_cast<DeclRefExpr>(BinOpCond->getLHS()->IgnoreParenImpCasts()); | ||
94 | - if (LeftDRE && LeftDRE->getDecl() == CondVar) | ||
95 | - OtherSide = BinOpCond->getRHS(); | ||
96 | - else | ||
97 | - OtherSide = BinOpCond->getLHS(); | ||
98 | - } | ||
99 | - | ||
100 | - SourceLocation IfEnd = Body->getBeginLoc().getLocWithOffset(-1); | ||
101 | - | ||
102 | - // For compound statements also remove the left brace. | ||
103 | - if (isa<CompoundStmt>(Body)) | ||
104 | - IfEnd = Body->getBeginLoc(); | ||
105 | - | ||
106 | - // If the other side has side effects then keep it. | ||
107 | - if (OtherSide && OtherSide->HasSideEffects(*Result.Context)) { | ||
108 | - SourceLocation BeforeOtherSide = | ||
109 | - OtherSide->getBeginLoc().getLocWithOffset(-1); | ||
110 | - SourceLocation AfterOtherSide = | ||
111 | - Lexer::findNextToken(OtherSide->getEndLoc(), *Result.SourceManager, | ||
112 | - getLangOpts()) | ||
113 | - ->getLocation(); | ||
114 | - Diag << FixItHint::CreateRemoval( | ||
115 | - CharSourceRange::getTokenRange(IfBegin, BeforeOtherSide)) | ||
116 | - << FixItHint::CreateInsertion(AfterOtherSide, ";") | ||
117 | - << FixItHint::CreateRemoval( | ||
118 | - CharSourceRange::getTokenRange(AfterOtherSide, IfEnd)); | ||
119 | - } else { | ||
120 | - Diag << FixItHint::CreateRemoval( | ||
121 | - CharSourceRange::getTokenRange(IfBegin, IfEnd)); | ||
122 | - } | ||
123 | - | ||
124 | - // For comound statements also remove the right brace at the end. | ||
125 | - if (isa<CompoundStmt>(Body)) | ||
126 | - Diag << FixItHint::CreateRemoval( | ||
127 | - CharSourceRange::getTokenRange(Body->getEndLoc(), Body->getEndLoc())); | ||
128 | - | ||
129 | - // For "and" binary operations we remove the "and" operation with the | ||
130 | - // condition variable from the inner if. | ||
131 | - } else { | ||
132 | - const auto *CondOp = cast<BinaryOperator>(InnerIf->getCond()); | ||
133 | - const auto *LeftDRE = | ||
134 | - dyn_cast<DeclRefExpr>(CondOp->getLHS()->IgnoreParenImpCasts()); | ||
135 | - if (LeftDRE && LeftDRE->getDecl() == CondVar) { | ||
136 | - SourceLocation BeforeRHS = | ||
137 | - CondOp->getRHS()->getBeginLoc().getLocWithOffset(-1); | ||
138 | - Diag << FixItHint::CreateRemoval(CharSourceRange::getTokenRange( | ||
139 | - CondOp->getLHS()->getBeginLoc(), BeforeRHS)); | ||
140 | - } else { | ||
141 | - SourceLocation AfterLHS = | ||
142 | - Lexer::findNextToken(CondOp->getLHS()->getEndLoc(), | ||
143 | - *Result.SourceManager, getLangOpts()) | ||
144 | - ->getLocation(); | ||
145 | - Diag << FixItHint::CreateRemoval(CharSourceRange::getTokenRange( | ||
146 | - AfterLHS, CondOp->getRHS()->getEndLoc())); | ||
147 | - } | ||
148 | - } | ||
149 | -} | ||
150 | - | ||
151 | -} // namespace bugprone | ||
152 | -} // namespace tidy | ||
153 | -} // namespace clang |
llvm-project/clang-tools-extra/clang-tidy/bugprone/RedundantBranchConditionCheck.h
deleted
100644 → 0
1 | -//===--- RedundantBranchConditionCheck.h - clang-tidy -----------*- C++ -*-===// | ||
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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_BUGPRONE_REDUNDANTBRANCHCONDITIONCHECK_H | ||
10 | -#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_BUGPRONE_REDUNDANTBRANCHCONDITIONCHECK_H | ||
11 | - | ||
12 | -#include "../ClangTidyCheck.h" | ||
13 | - | ||
14 | -namespace clang { | ||
15 | -namespace tidy { | ||
16 | -namespace bugprone { | ||
17 | - | ||
18 | -/// Finds condition variables in nested `if` statements that were also checked | ||
19 | -/// in the outer `if` statement and were not changed. | ||
20 | -/// | ||
21 | -/// For the user-facing documentation see: | ||
22 | -/// http://clang.llvm.org/extra/clang-tidy/checks/bugprone-redundant-branch-condition.html | ||
23 | -class RedundantBranchConditionCheck : public ClangTidyCheck { | ||
24 | -public: | ||
25 | - RedundantBranchConditionCheck(StringRef Name, ClangTidyContext *Context) | ||
26 | - : ClangTidyCheck(Name, Context) {} | ||
27 | - void registerMatchers(ast_matchers::MatchFinder *Finder) override; | ||
28 | - void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | ||
29 | -}; | ||
30 | - | ||
31 | -} // namespace bugprone | ||
32 | -} // namespace tidy | ||
33 | -} // namespace clang | ||
34 | - | ||
35 | -#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_BUGPRONE_REDUNDANTBRANCHCONDITIONCHECK_H |
... | @@ -13,7 +13,6 @@ add_clang_library(clangTidyCppCoreGuidelinesModule | ... | @@ -13,7 +13,6 @@ add_clang_library(clangTidyCppCoreGuidelinesModule |
13 | NarrowingConversionsCheck.cpp | 13 | NarrowingConversionsCheck.cpp |
14 | NoMallocCheck.cpp | 14 | NoMallocCheck.cpp |
15 | OwningMemoryCheck.cpp | 15 | OwningMemoryCheck.cpp |
16 | - PreferMemberInitializerCheck.cpp | ||
17 | ProBoundsArrayToPointerDecayCheck.cpp | 16 | ProBoundsArrayToPointerDecayCheck.cpp |
18 | ProBoundsConstantArrayIndexCheck.cpp | 17 | ProBoundsConstantArrayIndexCheck.cpp |
19 | ProBoundsPointerArithmeticCheck.cpp | 18 | ProBoundsPointerArithmeticCheck.cpp | ... | ... |
... | @@ -22,7 +22,6 @@ | ... | @@ -22,7 +22,6 @@ |
22 | #include "NarrowingConversionsCheck.h" | 22 | #include "NarrowingConversionsCheck.h" |
23 | #include "NoMallocCheck.h" | 23 | #include "NoMallocCheck.h" |
24 | #include "OwningMemoryCheck.h" | 24 | #include "OwningMemoryCheck.h" |
25 | -#include "PreferMemberInitializerCheck.h" | ||
26 | #include "ProBoundsArrayToPointerDecayCheck.h" | 25 | #include "ProBoundsArrayToPointerDecayCheck.h" |
27 | #include "ProBoundsConstantArrayIndexCheck.h" | 26 | #include "ProBoundsConstantArrayIndexCheck.h" |
28 | #include "ProBoundsPointerArithmeticCheck.h" | 27 | #include "ProBoundsPointerArithmeticCheck.h" |
... | @@ -67,8 +66,6 @@ public: | ... | @@ -67,8 +66,6 @@ public: |
67 | "cppcoreguidelines-non-private-member-variables-in-classes"); | 66 | "cppcoreguidelines-non-private-member-variables-in-classes"); |
68 | CheckFactories.registerCheck<OwningMemoryCheck>( | 67 | CheckFactories.registerCheck<OwningMemoryCheck>( |
69 | "cppcoreguidelines-owning-memory"); | 68 | "cppcoreguidelines-owning-memory"); |
70 | - CheckFactories.registerCheck<PreferMemberInitializerCheck>( | ||
71 | - "cppcoreguidelines-prefer-member-initializer"); | ||
72 | CheckFactories.registerCheck<ProBoundsArrayToPointerDecayCheck>( | 69 | CheckFactories.registerCheck<ProBoundsArrayToPointerDecayCheck>( |
73 | "cppcoreguidelines-pro-bounds-array-to-pointer-decay"); | 70 | "cppcoreguidelines-pro-bounds-array-to-pointer-decay"); |
74 | CheckFactories.registerCheck<ProBoundsConstantArrayIndexCheck>( | 71 | CheckFactories.registerCheck<ProBoundsConstantArrayIndexCheck>( | ... | ... |
... | @@ -26,12 +26,12 @@ AST_MATCHER(VarDecl, isLocalVarDecl) { return Node.isLocalVarDecl(); } | ... | @@ -26,12 +26,12 @@ AST_MATCHER(VarDecl, isLocalVarDecl) { return Node.isLocalVarDecl(); } |
26 | InitVariablesCheck::InitVariablesCheck(StringRef Name, | 26 | InitVariablesCheck::InitVariablesCheck(StringRef Name, |
27 | ClangTidyContext *Context) | 27 | ClangTidyContext *Context) |
28 | : ClangTidyCheck(Name, Context), | 28 | : ClangTidyCheck(Name, Context), |
29 | - IncludeInserter(Options.getLocalOrGlobal("IncludeStyle", | 29 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
30 | - utils::IncludeSorter::IS_LLVM)), | 30 | + utils::IncludeSorter::IS_LLVM)), |
31 | - MathHeader(Options.get("MathHeader", "<math.h>")) {} | 31 | + MathHeader(Options.get("MathHeader", "math.h")) {} |
32 | 32 | ||
33 | void InitVariablesCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { | 33 | void InitVariablesCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { |
34 | - Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle()); | 34 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
35 | Options.store(Opts, "MathHeader", MathHeader); | 35 | Options.store(Opts, "MathHeader", MathHeader); |
36 | } | 36 | } |
37 | 37 | ||
... | @@ -51,7 +51,9 @@ void InitVariablesCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -51,7 +51,9 @@ void InitVariablesCheck::registerMatchers(MatchFinder *Finder) { |
51 | void InitVariablesCheck::registerPPCallbacks(const SourceManager &SM, | 51 | void InitVariablesCheck::registerPPCallbacks(const SourceManager &SM, |
52 | Preprocessor *PP, | 52 | Preprocessor *PP, |
53 | Preprocessor *ModuleExpanderPP) { | 53 | Preprocessor *ModuleExpanderPP) { |
54 | - IncludeInserter.registerPreprocessor(PP); | 54 | + IncludeInserter = |
55 | + std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), IncludeStyle); | ||
56 | + PP->addPPCallbacks(IncludeInserter->CreatePPCallbacks()); | ||
55 | } | 57 | } |
56 | 58 | ||
57 | void InitVariablesCheck::check(const MatchFinder::MatchResult &Result) { | 59 | void InitVariablesCheck::check(const MatchFinder::MatchResult &Result) { |
... | @@ -102,8 +104,8 @@ void InitVariablesCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -102,8 +104,8 @@ void InitVariablesCheck::check(const MatchFinder::MatchResult &Result) { |
102 | MatchedDecl->getName().size()), | 104 | MatchedDecl->getName().size()), |
103 | InitializationString); | 105 | InitializationString); |
104 | if (AddMathInclude) { | 106 | if (AddMathInclude) { |
105 | - Diagnostic << IncludeInserter.createIncludeInsertion( | 107 | + Diagnostic << IncludeInserter->CreateIncludeInsertion( |
106 | - Source.getFileID(MatchedDecl->getBeginLoc()), MathHeader); | 108 | + Source.getFileID(MatchedDecl->getBeginLoc()), MathHeader, false); |
107 | } | 109 | } |
108 | } | 110 | } |
109 | } | 111 | } | ... | ... |
... | @@ -31,7 +31,8 @@ public: | ... | @@ -31,7 +31,8 @@ public: |
31 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | 31 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; |
32 | 32 | ||
33 | private: | 33 | private: |
34 | - utils::IncludeInserter IncludeInserter; | 34 | + std::unique_ptr<clang::tidy::utils::IncludeInserter> IncludeInserter; |
35 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
35 | const std::string MathHeader; | 36 | const std::string MathHeader; |
36 | }; | 37 | }; |
37 | 38 | ... | ... |
... | @@ -79,8 +79,9 @@ static QualType getUnqualifiedType(const Expr &E) { | ... | @@ -79,8 +79,9 @@ static QualType getUnqualifiedType(const Expr &E) { |
79 | } | 79 | } |
80 | 80 | ||
81 | static APValue getConstantExprValue(const ASTContext &Ctx, const Expr &E) { | 81 | static APValue getConstantExprValue(const ASTContext &Ctx, const Expr &E) { |
82 | - if (auto IntegerConstant = E.getIntegerConstantExpr(Ctx)) | 82 | + llvm::APSInt IntegerConstant; |
83 | - return APValue(*IntegerConstant); | 83 | + if (E.isIntegerConstantExpr(IntegerConstant, Ctx)) |
84 | + return APValue(IntegerConstant); | ||
84 | APValue Constant; | 85 | APValue Constant; |
85 | if (Ctx.getLangOpts().CPlusPlus && E.isCXX11ConstantExpr(Ctx, &Constant)) | 86 | if (Ctx.getLangOpts().CPlusPlus && E.isCXX11ConstantExpr(Ctx, &Constant)) |
86 | return Constant; | 87 | return Constant; | ... | ... |
llvm-project/clang-tools-extra/clang-tidy/cppcoreguidelines/PreferMemberInitializerCheck.cpp
deleted
100644 → 0
1 | -//===--- PreferMemberInitializerCheck.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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#include "PreferMemberInitializerCheck.h" | ||
10 | -#include "clang/AST/ASTContext.h" | ||
11 | -#include "clang/ASTMatchers/ASTMatchFinder.h" | ||
12 | -#include "clang/Lex/Lexer.h" | ||
13 | - | ||
14 | -using namespace clang::ast_matchers; | ||
15 | - | ||
16 | -namespace clang { | ||
17 | -namespace tidy { | ||
18 | -namespace cppcoreguidelines { | ||
19 | - | ||
20 | -static bool isControlStatement(const Stmt *S) { | ||
21 | - return isa<IfStmt, SwitchStmt, ForStmt, WhileStmt, DoStmt, ReturnStmt, | ||
22 | - GotoStmt, CXXTryStmt, CXXThrowExpr>(S); | ||
23 | -} | ||
24 | - | ||
25 | -static bool isNoReturnCallStatement(const Stmt *S) { | ||
26 | - const auto *Call = dyn_cast<CallExpr>(S); | ||
27 | - if (!Call) | ||
28 | - return false; | ||
29 | - | ||
30 | - const FunctionDecl *Func = Call->getDirectCallee(); | ||
31 | - if (!Func) | ||
32 | - return false; | ||
33 | - | ||
34 | - return Func->isNoReturn(); | ||
35 | -} | ||
36 | - | ||
37 | -static bool isLiteral(const Expr *E) { | ||
38 | - return isa<StringLiteral, CharacterLiteral, IntegerLiteral, FloatingLiteral, | ||
39 | - CXXBoolLiteralExpr, CXXNullPtrLiteralExpr>(E); | ||
40 | -} | ||
41 | - | ||
42 | -static bool isUnaryExprOfLiteral(const Expr *E) { | ||
43 | - if (const auto *UnOp = dyn_cast<UnaryOperator>(E)) | ||
44 | - return isLiteral(UnOp->getSubExpr()); | ||
45 | - return false; | ||
46 | -} | ||
47 | - | ||
48 | -static bool shouldBeDefaultMemberInitializer(const Expr *Value) { | ||
49 | - if (isLiteral(Value) || isUnaryExprOfLiteral(Value)) | ||
50 | - return true; | ||
51 | - | ||
52 | - if (const auto *DRE = dyn_cast<DeclRefExpr>(Value)) | ||
53 | - return isa<EnumConstantDecl>(DRE->getDecl()); | ||
54 | - | ||
55 | - return false; | ||
56 | -} | ||
57 | - | ||
58 | -static const std::pair<const FieldDecl *, const Expr *> | ||
59 | -isAssignmentToMemberOf(const RecordDecl *Rec, const Stmt *S) { | ||
60 | - if (const auto *BO = dyn_cast<BinaryOperator>(S)) { | ||
61 | - if (BO->getOpcode() != BO_Assign) | ||
62 | - return std::make_pair(nullptr, nullptr); | ||
63 | - | ||
64 | - const auto *ME = dyn_cast<MemberExpr>(BO->getLHS()->IgnoreParenImpCasts()); | ||
65 | - if (!ME) | ||
66 | - return std::make_pair(nullptr, nullptr); | ||
67 | - | ||
68 | - const auto *Field = dyn_cast<FieldDecl>(ME->getMemberDecl()); | ||
69 | - if (!Field) | ||
70 | - return std::make_pair(nullptr, nullptr); | ||
71 | - | ||
72 | - if (isa<CXXThisExpr>(ME->getBase())) | ||
73 | - return std::make_pair(Field, BO->getRHS()->IgnoreParenImpCasts()); | ||
74 | - } else if (const auto *COCE = dyn_cast<CXXOperatorCallExpr>(S)) { | ||
75 | - if (COCE->getOperator() != OO_Equal) | ||
76 | - return std::make_pair(nullptr, nullptr); | ||
77 | - | ||
78 | - const auto *ME = | ||
79 | - dyn_cast<MemberExpr>(COCE->getArg(0)->IgnoreParenImpCasts()); | ||
80 | - if (!ME) | ||
81 | - return std::make_pair(nullptr, nullptr); | ||
82 | - | ||
83 | - const auto *Field = dyn_cast<FieldDecl>(ME->getMemberDecl()); | ||
84 | - if (!Field) | ||
85 | - return std::make_pair(nullptr, nullptr); | ||
86 | - | ||
87 | - if (isa<CXXThisExpr>(ME->getBase())) | ||
88 | - return std::make_pair(Field, COCE->getArg(1)->IgnoreParenImpCasts()); | ||
89 | - } | ||
90 | - | ||
91 | - return std::make_pair(nullptr, nullptr); | ||
92 | -} | ||
93 | - | ||
94 | -PreferMemberInitializerCheck::PreferMemberInitializerCheck( | ||
95 | - StringRef Name, ClangTidyContext *Context) | ||
96 | - : ClangTidyCheck(Name, Context), | ||
97 | - IsUseDefaultMemberInitEnabled( | ||
98 | - Context->isCheckEnabled("modernize-use-default-member-init")), | ||
99 | - UseAssignment(OptionsView("modernize-use-default-member-init", | ||
100 | - Context->getOptions().CheckOptions) | ||
101 | - .get("UseAssignment", false)) {} | ||
102 | - | ||
103 | -void PreferMemberInitializerCheck::storeOptions( | ||
104 | - ClangTidyOptions::OptionMap &Opts) { | ||
105 | - Options.store(Opts, "UseAssignment", UseAssignment); | ||
106 | -} | ||
107 | - | ||
108 | -void PreferMemberInitializerCheck::registerMatchers(MatchFinder *Finder) { | ||
109 | - Finder->addMatcher( | ||
110 | - cxxConstructorDecl(hasBody(compoundStmt()), unless(isInstantiated())) | ||
111 | - .bind("ctor"), | ||
112 | - this); | ||
113 | -} | ||
114 | - | ||
115 | -void PreferMemberInitializerCheck::check( | ||
116 | - const MatchFinder::MatchResult &Result) { | ||
117 | - const auto *Ctor = Result.Nodes.getNodeAs<CXXConstructorDecl>("ctor"); | ||
118 | - const auto *Body = cast<CompoundStmt>(Ctor->getBody()); | ||
119 | - | ||
120 | - const CXXRecordDecl *Class = Ctor->getParent(); | ||
121 | - SourceLocation InsertPos; | ||
122 | - bool FirstToCtorInits = true; | ||
123 | - | ||
124 | - for (const Stmt *S : Body->body()) { | ||
125 | - if (S->getBeginLoc().isMacroID()) { | ||
126 | - StringRef MacroName = | ||
127 | - Lexer::getImmediateMacroName(S->getBeginLoc(), *Result.SourceManager, | ||
128 | - getLangOpts()); | ||
129 | - if (MacroName.contains_lower("assert")) | ||
130 | - return; | ||
131 | - } | ||
132 | - if (isControlStatement(S)) | ||
133 | - return; | ||
134 | - | ||
135 | - if (isNoReturnCallStatement(S)) | ||
136 | - return; | ||
137 | - | ||
138 | - if (const auto *CondOp = dyn_cast<ConditionalOperator>(S)) { | ||
139 | - if (isNoReturnCallStatement(CondOp->getLHS()) || | ||
140 | - isNoReturnCallStatement(CondOp->getRHS())) | ||
141 | - return; | ||
142 | - } | ||
143 | - | ||
144 | - const FieldDecl *Field; | ||
145 | - const Expr *InitValue; | ||
146 | - std::tie(Field, InitValue) = isAssignmentToMemberOf(Class, S); | ||
147 | - if (Field) { | ||
148 | - if (IsUseDefaultMemberInitEnabled && getLangOpts().CPlusPlus11 && | ||
149 | - Ctor->isDefaultConstructor() && | ||
150 | - (getLangOpts().CPlusPlus20 || !Field->isBitField()) && | ||
151 | - (!isa<RecordDecl>(Class->getDeclContext()) || | ||
152 | - !cast<RecordDecl>(Class->getDeclContext())->isUnion()) && | ||
153 | - shouldBeDefaultMemberInitializer(InitValue)) { | ||
154 | - auto Diag = | ||
155 | - diag(S->getBeginLoc(), "%0 should be initialized in an in-class" | ||
156 | - " default member initializer") | ||
157 | - << Field; | ||
158 | - | ||
159 | - SourceLocation FieldEnd = | ||
160 | - Lexer::getLocForEndOfToken(Field->getSourceRange().getEnd(), 0, | ||
161 | - *Result.SourceManager, getLangOpts()); | ||
162 | - Diag << FixItHint::CreateInsertion(FieldEnd, | ||
163 | - UseAssignment ? " = " : "{") | ||
164 | - << FixItHint::CreateInsertionFromRange( | ||
165 | - FieldEnd, | ||
166 | - CharSourceRange(InitValue->getSourceRange(), true)) | ||
167 | - << FixItHint::CreateInsertion(FieldEnd, UseAssignment ? "" : "}"); | ||
168 | - | ||
169 | - SourceLocation SemiColonEnd = | ||
170 | - Lexer::findNextToken(S->getEndLoc(), *Result.SourceManager, | ||
171 | - getLangOpts()) | ||
172 | - ->getEndLoc(); | ||
173 | - CharSourceRange StmtRange = | ||
174 | - CharSourceRange::getCharRange(S->getBeginLoc(), SemiColonEnd); | ||
175 | - | ||
176 | - Diag << FixItHint::CreateRemoval(StmtRange); | ||
177 | - } else { | ||
178 | - auto Diag = | ||
179 | - diag(S->getBeginLoc(), "%0 should be initialized in a member" | ||
180 | - " initializer of the constructor") | ||
181 | - << Field; | ||
182 | - | ||
183 | - bool AddComma = false; | ||
184 | - if (!Ctor->getNumCtorInitializers() && FirstToCtorInits) { | ||
185 | - SourceLocation BodyPos = Ctor->getBody()->getBeginLoc(); | ||
186 | - SourceLocation NextPos = Ctor->getBeginLoc(); | ||
187 | - do { | ||
188 | - InsertPos = NextPos; | ||
189 | - NextPos = Lexer::findNextToken(NextPos, *Result.SourceManager, | ||
190 | - getLangOpts()) | ||
191 | - ->getLocation(); | ||
192 | - } while (NextPos != BodyPos); | ||
193 | - InsertPos = Lexer::getLocForEndOfToken( | ||
194 | - InsertPos, 0, *Result.SourceManager, getLangOpts()); | ||
195 | - | ||
196 | - Diag << FixItHint::CreateInsertion(InsertPos, " : "); | ||
197 | - } else { | ||
198 | - bool Found = false; | ||
199 | - for (const auto *Init : Ctor->inits()) { | ||
200 | - if (Init->isMemberInitializer()) { | ||
201 | - if (Result.SourceManager->isBeforeInTranslationUnit( | ||
202 | - Field->getLocation(), Init->getMember()->getLocation())) { | ||
203 | - InsertPos = Init->getSourceLocation(); | ||
204 | - Found = true; | ||
205 | - break; | ||
206 | - } | ||
207 | - } | ||
208 | - } | ||
209 | - | ||
210 | - if (!Found) { | ||
211 | - if (Ctor->getNumCtorInitializers()) { | ||
212 | - InsertPos = Lexer::getLocForEndOfToken( | ||
213 | - (*Ctor->init_rbegin())->getSourceRange().getEnd(), 0, | ||
214 | - *Result.SourceManager, getLangOpts()); | ||
215 | - } | ||
216 | - Diag << FixItHint::CreateInsertion(InsertPos, ", "); | ||
217 | - } else { | ||
218 | - AddComma = true; | ||
219 | - } | ||
220 | - } | ||
221 | - Diag << FixItHint::CreateInsertion(InsertPos, Field->getName()) | ||
222 | - << FixItHint::CreateInsertion(InsertPos, "(") | ||
223 | - << FixItHint::CreateInsertionFromRange( | ||
224 | - InsertPos, | ||
225 | - CharSourceRange(InitValue->getSourceRange(), true)) | ||
226 | - << FixItHint::CreateInsertion(InsertPos, ")"); | ||
227 | - if (AddComma) | ||
228 | - Diag << FixItHint::CreateInsertion(InsertPos, ", "); | ||
229 | - | ||
230 | - SourceLocation SemiColonEnd = | ||
231 | - Lexer::findNextToken(S->getEndLoc(), *Result.SourceManager, | ||
232 | - getLangOpts()) | ||
233 | - ->getEndLoc(); | ||
234 | - CharSourceRange StmtRange = | ||
235 | - CharSourceRange::getCharRange(S->getBeginLoc(), SemiColonEnd); | ||
236 | - | ||
237 | - Diag << FixItHint::CreateRemoval(StmtRange); | ||
238 | - FirstToCtorInits = false; | ||
239 | - } | ||
240 | - } | ||
241 | - } | ||
242 | -} | ||
243 | - | ||
244 | -} // namespace cppcoreguidelines | ||
245 | -} // namespace tidy | ||
246 | -} // namespace clang |
llvm-project/clang-tools-extra/clang-tidy/cppcoreguidelines/PreferMemberInitializerCheck.h
deleted
100644 → 0
1 | -//===--- PreferMemberInitializerCheck.h - clang-tidy ------------*- C++ -*-===// | ||
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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CPPCOREGUIDELINES_PREFERMEMBERINITIALIZERCHECK_H | ||
10 | -#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CPPCOREGUIDELINES_PREFERMEMBERINITIALIZERCHECK_H | ||
11 | - | ||
12 | -#include "../ClangTidyCheck.h" | ||
13 | - | ||
14 | -namespace clang { | ||
15 | -namespace tidy { | ||
16 | -namespace cppcoreguidelines { | ||
17 | - | ||
18 | -/// Finds member initializations in the constructor body which can be placed | ||
19 | -/// into the initialization list instead. | ||
20 | -/// | ||
21 | -/// For the user-facing documentation see: | ||
22 | -/// http://clang.llvm.org/extra/clang-tidy/checks/cppcoreguidelines-prefer-member-initializer.html | ||
23 | -class PreferMemberInitializerCheck : public ClangTidyCheck { | ||
24 | -public: | ||
25 | - PreferMemberInitializerCheck(StringRef Name, ClangTidyContext *Context); | ||
26 | - bool isLanguageVersionSupported(const LangOptions &LangOpts) const override { | ||
27 | - return LangOpts.CPlusPlus; | ||
28 | - } | ||
29 | - void storeOptions(ClangTidyOptions::OptionMap &Opts) override; | ||
30 | - void registerMatchers(ast_matchers::MatchFinder *Finder) override; | ||
31 | - void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | ||
32 | - | ||
33 | - const bool IsUseDefaultMemberInitEnabled; | ||
34 | - const bool UseAssignment; | ||
35 | -}; | ||
36 | - | ||
37 | -} // namespace cppcoreguidelines | ||
38 | -} // namespace tidy | ||
39 | -} // namespace clang | ||
40 | - | ||
41 | -#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CPPCOREGUIDELINES_PREFERMEMBERINITIALIZERCHECK_H |
... | @@ -21,18 +21,20 @@ namespace cppcoreguidelines { | ... | @@ -21,18 +21,20 @@ namespace cppcoreguidelines { |
21 | ProBoundsConstantArrayIndexCheck::ProBoundsConstantArrayIndexCheck( | 21 | ProBoundsConstantArrayIndexCheck::ProBoundsConstantArrayIndexCheck( |
22 | StringRef Name, ClangTidyContext *Context) | 22 | StringRef Name, ClangTidyContext *Context) |
23 | : ClangTidyCheck(Name, Context), GslHeader(Options.get("GslHeader", "")), | 23 | : ClangTidyCheck(Name, Context), GslHeader(Options.get("GslHeader", "")), |
24 | - Inserter(Options.getLocalOrGlobal("IncludeStyle", | 24 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
25 | - utils::IncludeSorter::IS_LLVM)) {} | 25 | + utils::IncludeSorter::IS_LLVM)) {} |
26 | 26 | ||
27 | void ProBoundsConstantArrayIndexCheck::storeOptions( | 27 | void ProBoundsConstantArrayIndexCheck::storeOptions( |
28 | ClangTidyOptions::OptionMap &Opts) { | 28 | ClangTidyOptions::OptionMap &Opts) { |
29 | Options.store(Opts, "GslHeader", GslHeader); | 29 | Options.store(Opts, "GslHeader", GslHeader); |
30 | - Options.store(Opts, "IncludeStyle", Inserter.getStyle()); | 30 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
31 | } | 31 | } |
32 | 32 | ||
33 | void ProBoundsConstantArrayIndexCheck::registerPPCallbacks( | 33 | void ProBoundsConstantArrayIndexCheck::registerPPCallbacks( |
34 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { | 34 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { |
35 | - Inserter.registerPreprocessor(PP); | 35 | + Inserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
36 | + IncludeStyle); | ||
37 | + PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
36 | } | 38 | } |
37 | 39 | ||
38 | void ProBoundsConstantArrayIndexCheck::registerMatchers(MatchFinder *Finder) { | 40 | void ProBoundsConstantArrayIndexCheck::registerMatchers(MatchFinder *Finder) { |
... | @@ -63,9 +65,9 @@ void ProBoundsConstantArrayIndexCheck::check( | ... | @@ -63,9 +65,9 @@ void ProBoundsConstantArrayIndexCheck::check( |
63 | if (IndexExpr->isValueDependent()) | 65 | if (IndexExpr->isValueDependent()) |
64 | return; // We check in the specialization. | 66 | return; // We check in the specialization. |
65 | 67 | ||
66 | - Optional<llvm::APSInt> Index = | 68 | + llvm::APSInt Index; |
67 | - IndexExpr->getIntegerConstantExpr(*Result.Context); | 69 | + if (!IndexExpr->isIntegerConstantExpr(Index, *Result.Context, nullptr, |
68 | - if (!Index) { | 70 | + /*isEvaluated=*/true)) { |
69 | SourceRange BaseRange; | 71 | SourceRange BaseRange; |
70 | if (const auto *ArraySubscriptE = dyn_cast<ArraySubscriptExpr>(Matched)) | 72 | if (const auto *ArraySubscriptE = dyn_cast<ArraySubscriptExpr>(Matched)) |
71 | BaseRange = ArraySubscriptE->getBase()->getSourceRange(); | 73 | BaseRange = ArraySubscriptE->getBase()->getSourceRange(); |
... | @@ -85,7 +87,9 @@ void ProBoundsConstantArrayIndexCheck::check( | ... | @@ -85,7 +87,9 @@ void ProBoundsConstantArrayIndexCheck::check( |
85 | IndexRange.getBegin().getLocWithOffset(-1)), | 87 | IndexRange.getBegin().getLocWithOffset(-1)), |
86 | ", ") | 88 | ", ") |
87 | << FixItHint::CreateReplacement(Matched->getEndLoc(), ")") | 89 | << FixItHint::CreateReplacement(Matched->getEndLoc(), ")") |
88 | - << Inserter.createMainFileIncludeInsertion(GslHeader); | 90 | + << Inserter->CreateIncludeInsertion( |
91 | + Result.SourceManager->getMainFileID(), GslHeader, | ||
92 | + /*IsAngled=*/false); | ||
89 | } | 93 | } |
90 | return; | 94 | return; |
91 | } | 95 | } |
... | @@ -97,9 +101,9 @@ void ProBoundsConstantArrayIndexCheck::check( | ... | @@ -97,9 +101,9 @@ void ProBoundsConstantArrayIndexCheck::check( |
97 | if (!StdArrayDecl) | 101 | if (!StdArrayDecl) |
98 | return; | 102 | return; |
99 | 103 | ||
100 | - if (Index->isSigned() && Index->isNegative()) { | 104 | + if (Index.isSigned() && Index.isNegative()) { |
101 | diag(Matched->getExprLoc(), "std::array<> index %0 is negative") | 105 | diag(Matched->getExprLoc(), "std::array<> index %0 is negative") |
102 | - << Index->toString(10); | 106 | + << Index.toString(10); |
103 | return; | 107 | return; |
104 | } | 108 | } |
105 | 109 | ||
... | @@ -114,11 +118,11 @@ void ProBoundsConstantArrayIndexCheck::check( | ... | @@ -114,11 +118,11 @@ void ProBoundsConstantArrayIndexCheck::check( |
114 | 118 | ||
115 | // Get uint64_t values, because different bitwidths would lead to an assertion | 119 | // Get uint64_t values, because different bitwidths would lead to an assertion |
116 | // in APInt::uge. | 120 | // in APInt::uge. |
117 | - if (Index->getZExtValue() >= ArraySize.getZExtValue()) { | 121 | + if (Index.getZExtValue() >= ArraySize.getZExtValue()) { |
118 | diag(Matched->getExprLoc(), | 122 | diag(Matched->getExprLoc(), |
119 | "std::array<> index %0 is past the end of the array " | 123 | "std::array<> index %0 is past the end of the array " |
120 | "(which contains %1 elements)") | 124 | "(which contains %1 elements)") |
121 | - << Index->toString(10) << ArraySize.toString(10, false); | 125 | + << Index.toString(10) << ArraySize.toString(10, false); |
122 | } | 126 | } |
123 | } | 127 | } |
124 | 128 | ... | ... |
... | @@ -23,7 +23,8 @@ namespace cppcoreguidelines { | ... | @@ -23,7 +23,8 @@ namespace cppcoreguidelines { |
23 | /// http://clang.llvm.org/extra/clang-tidy/checks/cppcoreguidelines-pro-bounds-constant-array-index.html | 23 | /// http://clang.llvm.org/extra/clang-tidy/checks/cppcoreguidelines-pro-bounds-constant-array-index.html |
24 | class ProBoundsConstantArrayIndexCheck : public ClangTidyCheck { | 24 | class ProBoundsConstantArrayIndexCheck : public ClangTidyCheck { |
25 | const std::string GslHeader; | 25 | const std::string GslHeader; |
26 | - utils::IncludeInserter Inserter; | 26 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; |
27 | + std::unique_ptr<utils::IncludeInserter> Inserter; | ||
27 | 28 | ||
28 | public: | 29 | public: |
29 | ProBoundsConstantArrayIndexCheck(StringRef Name, ClangTidyContext *Context); | 30 | ProBoundsConstantArrayIndexCheck(StringRef Name, ClangTidyContext *Context); | ... | ... |
... | @@ -500,13 +500,7 @@ static bool retrieveIntegerConstantExpr(const MatchFinder::MatchResult &Result, | ... | @@ -500,13 +500,7 @@ static bool retrieveIntegerConstantExpr(const MatchFinder::MatchResult &Result, |
500 | const Expr *&ConstExpr) { | 500 | const Expr *&ConstExpr) { |
501 | std::string CstId = (Id + "-const").str(); | 501 | std::string CstId = (Id + "-const").str(); |
502 | ConstExpr = Result.Nodes.getNodeAs<Expr>(CstId); | 502 | ConstExpr = Result.Nodes.getNodeAs<Expr>(CstId); |
503 | - if (!ConstExpr) | 503 | + return ConstExpr && ConstExpr->isIntegerConstantExpr(Value, *Result.Context); |
504 | - return false; | ||
505 | - Optional<llvm::APSInt> R = ConstExpr->getIntegerConstantExpr(*Result.Context); | ||
506 | - if (!R) | ||
507 | - return false; | ||
508 | - Value = *R; | ||
509 | - return true; | ||
510 | } | 504 | } |
511 | 505 | ||
512 | // Overloaded `retrieveIntegerConstantExpr` for compatibility. | 506 | // Overloaded `retrieveIntegerConstantExpr` for compatibility. |
... | @@ -679,7 +673,7 @@ static bool retrieveRelationalIntegerConstantExpr( | ... | @@ -679,7 +673,7 @@ static bool retrieveRelationalIntegerConstantExpr( |
679 | 673 | ||
680 | if (const auto *Arg = OverloadedOperatorExpr->getArg(1)) { | 674 | if (const auto *Arg = OverloadedOperatorExpr->getArg(1)) { |
681 | if (!Arg->isValueDependent() && | 675 | if (!Arg->isValueDependent() && |
682 | - !Arg->isIntegerConstantExpr(*Result.Context)) | 676 | + !Arg->isIntegerConstantExpr(Value, *Result.Context)) |
683 | return false; | 677 | return false; |
684 | } | 678 | } |
685 | Symbol = OverloadedOperatorExpr->getArg(0); | 679 | Symbol = OverloadedOperatorExpr->getArg(0); |
... | @@ -1271,23 +1265,21 @@ void RedundantExpressionCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -1271,23 +1265,21 @@ void RedundantExpressionCheck::check(const MatchFinder::MatchResult &Result) { |
1271 | "left-right-shift-confusion")) { | 1265 | "left-right-shift-confusion")) { |
1272 | const auto *ShiftingConst = Result.Nodes.getNodeAs<Expr>("shift-const"); | 1266 | const auto *ShiftingConst = Result.Nodes.getNodeAs<Expr>("shift-const"); |
1273 | assert(ShiftingConst && "Expr* 'ShiftingConst' is nullptr!"); | 1267 | assert(ShiftingConst && "Expr* 'ShiftingConst' is nullptr!"); |
1274 | - Optional<llvm::APSInt> ShiftingValue = | 1268 | + APSInt ShiftingValue; |
1275 | - ShiftingConst->getIntegerConstantExpr(*Result.Context); | ||
1276 | 1269 | ||
1277 | - if (!ShiftingValue) | 1270 | + if (!ShiftingConst->isIntegerConstantExpr(ShiftingValue, *Result.Context)) |
1278 | return; | 1271 | return; |
1279 | 1272 | ||
1280 | const auto *AndConst = Result.Nodes.getNodeAs<Expr>("and-const"); | 1273 | const auto *AndConst = Result.Nodes.getNodeAs<Expr>("and-const"); |
1281 | assert(AndConst && "Expr* 'AndCont' is nullptr!"); | 1274 | assert(AndConst && "Expr* 'AndCont' is nullptr!"); |
1282 | - Optional<llvm::APSInt> AndValue = | 1275 | + APSInt AndValue; |
1283 | - AndConst->getIntegerConstantExpr(*Result.Context); | 1276 | + if (!AndConst->isIntegerConstantExpr(AndValue, *Result.Context)) |
1284 | - if (!AndValue) | ||
1285 | return; | 1277 | return; |
1286 | 1278 | ||
1287 | // If ShiftingConst is shifted left with more bits than the position of the | 1279 | // If ShiftingConst is shifted left with more bits than the position of the |
1288 | // leftmost 1 in the bit representation of AndValue, AndConstant is | 1280 | // leftmost 1 in the bit representation of AndValue, AndConstant is |
1289 | // ineffective. | 1281 | // ineffective. |
1290 | - if (AndValue->getActiveBits() > *ShiftingValue) | 1282 | + if (AndValue.getActiveBits() > ShiftingValue) |
1291 | return; | 1283 | return; |
1292 | 1284 | ||
1293 | auto Diag = diag(BinaryAndExpr->getOperatorLoc(), | 1285 | auto Diag = diag(BinaryAndExpr->getOperatorLoc(), | ... | ... |
... | @@ -438,12 +438,11 @@ static bool arrayMatchesBoundExpr(ASTContext *Context, | ... | @@ -438,12 +438,11 @@ static bool arrayMatchesBoundExpr(ASTContext *Context, |
438 | Context->getAsConstantArrayType(ArrayType); | 438 | Context->getAsConstantArrayType(ArrayType); |
439 | if (!ConstType) | 439 | if (!ConstType) |
440 | return false; | 440 | return false; |
441 | - Optional<llvm::APSInt> ConditionSize = | 441 | + llvm::APSInt ConditionSize; |
442 | - ConditionExpr->getIntegerConstantExpr(*Context); | 442 | + if (!ConditionExpr->isIntegerConstantExpr(ConditionSize, *Context)) |
443 | - if (!ConditionSize) | ||
444 | return false; | 443 | return false; |
445 | llvm::APSInt ArraySize(ConstType->getSize()); | 444 | llvm::APSInt ArraySize(ConstType->getSize()); |
446 | - return llvm::APSInt::isSameValue(*ConditionSize, ArraySize); | 445 | + return llvm::APSInt::isSameValue(ConditionSize, ArraySize); |
447 | } | 446 | } |
448 | 447 | ||
449 | ForLoopIndexUseVisitor::ForLoopIndexUseVisitor(ASTContext *Context, | 448 | ForLoopIndexUseVisitor::ForLoopIndexUseVisitor(ASTContext *Context, | ... | ... |
... | @@ -19,6 +19,7 @@ namespace modernize { | ... | @@ -19,6 +19,7 @@ namespace modernize { |
19 | 19 | ||
20 | namespace { | 20 | namespace { |
21 | 21 | ||
22 | +constexpr char StdMemoryHeader[] = "memory"; | ||
22 | constexpr char ConstructorCall[] = "constructorCall"; | 23 | constexpr char ConstructorCall[] = "constructorCall"; |
23 | constexpr char ResetCall[] = "resetCall"; | 24 | constexpr char ResetCall[] = "resetCall"; |
24 | constexpr char NewExpression[] = "newExpression"; | 25 | constexpr char NewExpression[] = "newExpression"; |
... | @@ -43,16 +44,16 @@ const char MakeSmartPtrCheck::PointerType[] = "pointerType"; | ... | @@ -43,16 +44,16 @@ const char MakeSmartPtrCheck::PointerType[] = "pointerType"; |
43 | MakeSmartPtrCheck::MakeSmartPtrCheck(StringRef Name, ClangTidyContext *Context, | 44 | MakeSmartPtrCheck::MakeSmartPtrCheck(StringRef Name, ClangTidyContext *Context, |
44 | StringRef MakeSmartPtrFunctionName) | 45 | StringRef MakeSmartPtrFunctionName) |
45 | : ClangTidyCheck(Name, Context), | 46 | : ClangTidyCheck(Name, Context), |
46 | - Inserter(Options.getLocalOrGlobal("IncludeStyle", | 47 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
47 | - utils::IncludeSorter::IS_LLVM)), | 48 | + utils::IncludeSorter::IS_LLVM)), |
48 | MakeSmartPtrFunctionHeader( | 49 | MakeSmartPtrFunctionHeader( |
49 | - Options.get("MakeSmartPtrFunctionHeader", "<memory>")), | 50 | + Options.get("MakeSmartPtrFunctionHeader", StdMemoryHeader)), |
50 | MakeSmartPtrFunctionName( | 51 | MakeSmartPtrFunctionName( |
51 | Options.get("MakeSmartPtrFunction", MakeSmartPtrFunctionName)), | 52 | Options.get("MakeSmartPtrFunction", MakeSmartPtrFunctionName)), |
52 | IgnoreMacros(Options.getLocalOrGlobal("IgnoreMacros", true)) {} | 53 | IgnoreMacros(Options.getLocalOrGlobal("IgnoreMacros", true)) {} |
53 | 54 | ||
54 | void MakeSmartPtrCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { | 55 | void MakeSmartPtrCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { |
55 | - Options.store(Opts, "IncludeStyle", Inserter.getStyle()); | 56 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
56 | Options.store(Opts, "MakeSmartPtrFunctionHeader", MakeSmartPtrFunctionHeader); | 57 | Options.store(Opts, "MakeSmartPtrFunctionHeader", MakeSmartPtrFunctionHeader); |
57 | Options.store(Opts, "MakeSmartPtrFunction", MakeSmartPtrFunctionName); | 58 | Options.store(Opts, "MakeSmartPtrFunction", MakeSmartPtrFunctionName); |
58 | Options.store(Opts, "IgnoreMacros", IgnoreMacros); | 59 | Options.store(Opts, "IgnoreMacros", IgnoreMacros); |
... | @@ -66,7 +67,9 @@ bool MakeSmartPtrCheck::isLanguageVersionSupported( | ... | @@ -66,7 +67,9 @@ bool MakeSmartPtrCheck::isLanguageVersionSupported( |
66 | void MakeSmartPtrCheck::registerPPCallbacks(const SourceManager &SM, | 67 | void MakeSmartPtrCheck::registerPPCallbacks(const SourceManager &SM, |
67 | Preprocessor *PP, | 68 | Preprocessor *PP, |
68 | Preprocessor *ModuleExpanderPP) { | 69 | Preprocessor *ModuleExpanderPP) { |
69 | - Inserter.registerPreprocessor(PP); | 70 | + Inserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
71 | + IncludeStyle); | ||
72 | + PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
70 | } | 73 | } |
71 | 74 | ||
72 | void MakeSmartPtrCheck::registerMatchers(ast_matchers::MatchFinder *Finder) { | 75 | void MakeSmartPtrCheck::registerMatchers(ast_matchers::MatchFinder *Finder) { |
... | @@ -429,7 +432,9 @@ void MakeSmartPtrCheck::insertHeader(DiagnosticBuilder &Diag, FileID FD) { | ... | @@ -429,7 +432,9 @@ void MakeSmartPtrCheck::insertHeader(DiagnosticBuilder &Diag, FileID FD) { |
429 | if (MakeSmartPtrFunctionHeader.empty()) { | 432 | if (MakeSmartPtrFunctionHeader.empty()) { |
430 | return; | 433 | return; |
431 | } | 434 | } |
432 | - Diag << Inserter.createIncludeInsertion(FD, MakeSmartPtrFunctionHeader); | 435 | + Diag << Inserter->CreateIncludeInsertion( |
436 | + FD, MakeSmartPtrFunctionHeader, | ||
437 | + /*IsAngled=*/MakeSmartPtrFunctionHeader == StdMemoryHeader); | ||
433 | } | 438 | } |
434 | 439 | ||
435 | } // namespace modernize | 440 | } // namespace modernize | ... | ... |
... | @@ -46,7 +46,8 @@ protected: | ... | @@ -46,7 +46,8 @@ protected: |
46 | static const char PointerType[]; | 46 | static const char PointerType[]; |
47 | 47 | ||
48 | private: | 48 | private: |
49 | - utils::IncludeInserter Inserter; | 49 | + std::unique_ptr<utils::IncludeInserter> Inserter; |
50 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
50 | const std::string MakeSmartPtrFunctionHeader; | 51 | const std::string MakeSmartPtrFunctionHeader; |
51 | const std::string MakeSmartPtrFunctionName; | 52 | const std::string MakeSmartPtrFunctionName; |
52 | const bool IgnoreMacros; | 53 | const bool IgnoreMacros; | ... | ... |
... | @@ -120,12 +120,12 @@ collectParamDecls(const CXXConstructorDecl *Ctor, | ... | @@ -120,12 +120,12 @@ collectParamDecls(const CXXConstructorDecl *Ctor, |
120 | 120 | ||
121 | PassByValueCheck::PassByValueCheck(StringRef Name, ClangTidyContext *Context) | 121 | PassByValueCheck::PassByValueCheck(StringRef Name, ClangTidyContext *Context) |
122 | : ClangTidyCheck(Name, Context), | 122 | : ClangTidyCheck(Name, Context), |
123 | - Inserter(Options.getLocalOrGlobal("IncludeStyle", | 123 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
124 | - utils::IncludeSorter::IS_LLVM)), | 124 | + utils::IncludeSorter::IS_LLVM)), |
125 | ValuesOnly(Options.get("ValuesOnly", false)) {} | 125 | ValuesOnly(Options.get("ValuesOnly", false)) {} |
126 | 126 | ||
127 | void PassByValueCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { | 127 | void PassByValueCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { |
128 | - Options.store(Opts, "IncludeStyle", Inserter.getStyle()); | 128 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
129 | Options.store(Opts, "ValuesOnly", ValuesOnly); | 129 | Options.store(Opts, "ValuesOnly", ValuesOnly); |
130 | } | 130 | } |
131 | 131 | ||
... | @@ -167,7 +167,9 @@ void PassByValueCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -167,7 +167,9 @@ void PassByValueCheck::registerMatchers(MatchFinder *Finder) { |
167 | void PassByValueCheck::registerPPCallbacks(const SourceManager &SM, | 167 | void PassByValueCheck::registerPPCallbacks(const SourceManager &SM, |
168 | Preprocessor *PP, | 168 | Preprocessor *PP, |
169 | Preprocessor *ModuleExpanderPP) { | 169 | Preprocessor *ModuleExpanderPP) { |
170 | - Inserter.registerPreprocessor(PP); | 170 | + Inserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
171 | + IncludeStyle); | ||
172 | + PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
171 | } | 173 | } |
172 | 174 | ||
173 | void PassByValueCheck::check(const MatchFinder::MatchResult &Result) { | 175 | void PassByValueCheck::check(const MatchFinder::MatchResult &Result) { |
... | @@ -214,9 +216,10 @@ void PassByValueCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -214,9 +216,10 @@ void PassByValueCheck::check(const MatchFinder::MatchResult &Result) { |
214 | Diag << FixItHint::CreateInsertion(Initializer->getRParenLoc(), ")") | 216 | Diag << FixItHint::CreateInsertion(Initializer->getRParenLoc(), ")") |
215 | << FixItHint::CreateInsertion( | 217 | << FixItHint::CreateInsertion( |
216 | Initializer->getLParenLoc().getLocWithOffset(1), "std::move(") | 218 | Initializer->getLParenLoc().getLocWithOffset(1), "std::move(") |
217 | - << Inserter.createIncludeInsertion( | 219 | + << Inserter->CreateIncludeInsertion( |
218 | Result.SourceManager->getFileID(Initializer->getSourceLocation()), | 220 | Result.SourceManager->getFileID(Initializer->getSourceLocation()), |
219 | - "<utility>"); | 221 | + "utility", |
222 | + /*IsAngled=*/true); | ||
220 | } | 223 | } |
221 | 224 | ||
222 | } // namespace modernize | 225 | } // namespace modernize | ... | ... |
... | @@ -31,7 +31,8 @@ public: | ... | @@ -31,7 +31,8 @@ public: |
31 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | 31 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; |
32 | 32 | ||
33 | private: | 33 | private: |
34 | - utils::IncludeInserter Inserter; | 34 | + std::unique_ptr<utils::IncludeInserter> Inserter; |
35 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
35 | const bool ValuesOnly; | 36 | const bool ValuesOnly; |
36 | }; | 37 | }; |
37 | 38 | ... | ... |
... | @@ -74,11 +74,11 @@ AST_MATCHER(Decl, isFromStdNamespace) { | ... | @@ -74,11 +74,11 @@ AST_MATCHER(Decl, isFromStdNamespace) { |
74 | ReplaceAutoPtrCheck::ReplaceAutoPtrCheck(StringRef Name, | 74 | ReplaceAutoPtrCheck::ReplaceAutoPtrCheck(StringRef Name, |
75 | ClangTidyContext *Context) | 75 | ClangTidyContext *Context) |
76 | : ClangTidyCheck(Name, Context), | 76 | : ClangTidyCheck(Name, Context), |
77 | - Inserter(Options.getLocalOrGlobal("IncludeStyle", | 77 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
78 | - utils::IncludeSorter::IS_LLVM)) {} | 78 | + utils::IncludeSorter::IS_LLVM)) {} |
79 | 79 | ||
80 | void ReplaceAutoPtrCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { | 80 | void ReplaceAutoPtrCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { |
81 | - Options.store(Opts, "IncludeStyle", Inserter.getStyle()); | 81 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
82 | } | 82 | } |
83 | 83 | ||
84 | void ReplaceAutoPtrCheck::registerMatchers(MatchFinder *Finder) { | 84 | void ReplaceAutoPtrCheck::registerMatchers(MatchFinder *Finder) { |
... | @@ -131,7 +131,9 @@ void ReplaceAutoPtrCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -131,7 +131,9 @@ void ReplaceAutoPtrCheck::registerMatchers(MatchFinder *Finder) { |
131 | void ReplaceAutoPtrCheck::registerPPCallbacks(const SourceManager &SM, | 131 | void ReplaceAutoPtrCheck::registerPPCallbacks(const SourceManager &SM, |
132 | Preprocessor *PP, | 132 | Preprocessor *PP, |
133 | Preprocessor *ModuleExpanderPP) { | 133 | Preprocessor *ModuleExpanderPP) { |
134 | - Inserter.registerPreprocessor(PP); | 134 | + Inserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
135 | + IncludeStyle); | ||
136 | + PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
135 | } | 137 | } |
136 | 138 | ||
137 | void ReplaceAutoPtrCheck::check(const MatchFinder::MatchResult &Result) { | 139 | void ReplaceAutoPtrCheck::check(const MatchFinder::MatchResult &Result) { |
... | @@ -144,10 +146,12 @@ void ReplaceAutoPtrCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -144,10 +146,12 @@ void ReplaceAutoPtrCheck::check(const MatchFinder::MatchResult &Result) { |
144 | if (Range.isInvalid()) | 146 | if (Range.isInvalid()) |
145 | return; | 147 | return; |
146 | 148 | ||
147 | - auto Diag = diag(Range.getBegin(), "use std::move to transfer ownership") | 149 | + auto Diag = |
148 | - << FixItHint::CreateInsertion(Range.getBegin(), "std::move(") | 150 | + diag(Range.getBegin(), "use std::move to transfer ownership") |
149 | - << FixItHint::CreateInsertion(Range.getEnd(), ")") | 151 | + << FixItHint::CreateInsertion(Range.getBegin(), "std::move(") |
150 | - << Inserter.createMainFileIncludeInsertion("<utility>"); | 152 | + << FixItHint::CreateInsertion(Range.getEnd(), ")") |
153 | + << Inserter->CreateIncludeInsertion(SM.getMainFileID(), "utility", | ||
154 | + /*IsAngled=*/true); | ||
151 | 155 | ||
152 | return; | 156 | return; |
153 | } | 157 | } | ... | ... |
... | @@ -53,7 +53,8 @@ public: | ... | @@ -53,7 +53,8 @@ public: |
53 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | 53 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; |
54 | 54 | ||
55 | private: | 55 | private: |
56 | - utils::IncludeInserter Inserter; | 56 | + std::unique_ptr<utils::IncludeInserter> Inserter; |
57 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
57 | }; | 58 | }; |
58 | 59 | ||
59 | } // namespace modernize | 60 | } // namespace modernize | ... | ... |
... | @@ -23,9 +23,8 @@ namespace modernize { | ... | @@ -23,9 +23,8 @@ namespace modernize { |
23 | ReplaceRandomShuffleCheck::ReplaceRandomShuffleCheck(StringRef Name, | 23 | ReplaceRandomShuffleCheck::ReplaceRandomShuffleCheck(StringRef Name, |
24 | ClangTidyContext *Context) | 24 | ClangTidyContext *Context) |
25 | : ClangTidyCheck(Name, Context), | 25 | : ClangTidyCheck(Name, Context), |
26 | - IncludeInserter(Options.getLocalOrGlobal("IncludeStyle", | 26 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
27 | - utils::IncludeSorter::IS_LLVM)) { | 27 | + utils::IncludeSorter::IS_LLVM)) {} |
28 | -} | ||
29 | 28 | ||
30 | void ReplaceRandomShuffleCheck::registerMatchers(MatchFinder *Finder) { | 29 | void ReplaceRandomShuffleCheck::registerMatchers(MatchFinder *Finder) { |
31 | const auto Begin = hasArgument(0, expr()); | 30 | const auto Begin = hasArgument(0, expr()); |
... | @@ -45,12 +44,14 @@ void ReplaceRandomShuffleCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -45,12 +44,14 @@ void ReplaceRandomShuffleCheck::registerMatchers(MatchFinder *Finder) { |
45 | 44 | ||
46 | void ReplaceRandomShuffleCheck::registerPPCallbacks( | 45 | void ReplaceRandomShuffleCheck::registerPPCallbacks( |
47 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { | 46 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { |
48 | - IncludeInserter.registerPreprocessor(PP); | 47 | + IncludeInserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
48 | + IncludeStyle); | ||
49 | + PP->addPPCallbacks(IncludeInserter->CreatePPCallbacks()); | ||
49 | } | 50 | } |
50 | 51 | ||
51 | void ReplaceRandomShuffleCheck::storeOptions( | 52 | void ReplaceRandomShuffleCheck::storeOptions( |
52 | ClangTidyOptions::OptionMap &Opts) { | 53 | ClangTidyOptions::OptionMap &Opts) { |
53 | - Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle()); | 54 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
54 | } | 55 | } |
55 | 56 | ||
56 | void ReplaceRandomShuffleCheck::check(const MatchFinder::MatchResult &Result) { | 57 | void ReplaceRandomShuffleCheck::check(const MatchFinder::MatchResult &Result) { |
... | @@ -91,10 +92,10 @@ void ReplaceRandomShuffleCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -91,10 +92,10 @@ void ReplaceRandomShuffleCheck::check(const MatchFinder::MatchResult &Result) { |
91 | 92 | ||
92 | Diag << FixItHint::CreateRemoval(MatchedDecl->getSourceRange()); | 93 | Diag << FixItHint::CreateRemoval(MatchedDecl->getSourceRange()); |
93 | Diag << FixItHint::CreateInsertion(MatchedDecl->getBeginLoc(), NewName); | 94 | Diag << FixItHint::CreateInsertion(MatchedDecl->getBeginLoc(), NewName); |
94 | - Diag << IncludeInserter.createIncludeInsertion( | 95 | + Diag << IncludeInserter->CreateIncludeInsertion( |
95 | Result.Context->getSourceManager().getFileID( | 96 | Result.Context->getSourceManager().getFileID( |
96 | MatchedCallExpr->getBeginLoc()), | 97 | MatchedCallExpr->getBeginLoc()), |
97 | - "<random>"); | 98 | + "random", /*IsAngled=*/true); |
98 | } | 99 | } |
99 | 100 | ||
100 | } // namespace modernize | 101 | } // namespace modernize | ... | ... |
... | @@ -34,7 +34,8 @@ public: | ... | @@ -34,7 +34,8 @@ public: |
34 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | 34 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; |
35 | 35 | ||
36 | private: | 36 | private: |
37 | - utils::IncludeInserter IncludeInserter; | 37 | + std::unique_ptr<utils::IncludeInserter> IncludeInserter; |
38 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
38 | }; | 39 | }; |
39 | 40 | ||
40 | } // namespace modernize | 41 | } // namespace modernize | ... | ... |
... | @@ -119,11 +119,16 @@ AST_MATCHER_P(QualType, isSugarFor, Matcher<QualType>, SugarMatcher) { | ... | @@ -119,11 +119,16 @@ AST_MATCHER_P(QualType, isSugarFor, Matcher<QualType>, SugarMatcher) { |
119 | /// \endcode | 119 | /// \endcode |
120 | /// | 120 | /// |
121 | /// namedDecl(hasStdIteratorName()) matches \c I and \c CI. | 121 | /// namedDecl(hasStdIteratorName()) matches \c I and \c CI. |
122 | -Matcher<NamedDecl> hasStdIteratorName() { | 122 | +AST_MATCHER(NamedDecl, hasStdIteratorName) { |
123 | - static const StringRef IteratorNames[] = {"iterator", "reverse_iterator", | 123 | + static const char *const IteratorNames[] = {"iterator", "reverse_iterator", |
124 | - "const_iterator", | 124 | + "const_iterator", |
125 | - "const_reverse_iterator"}; | 125 | + "const_reverse_iterator"}; |
126 | - return hasAnyName(IteratorNames); | 126 | + |
127 | + for (const char *Name : IteratorNames) { | ||
128 | + if (hasName(Name).matches(Node, Finder, Builder)) | ||
129 | + return true; | ||
130 | + } | ||
131 | + return false; | ||
127 | } | 132 | } |
128 | 133 | ||
129 | /// Matches named declarations that have one of the standard container | 134 | /// Matches named declarations that have one of the standard container |
... | @@ -138,21 +143,26 @@ Matcher<NamedDecl> hasStdIteratorName() { | ... | @@ -138,21 +143,26 @@ Matcher<NamedDecl> hasStdIteratorName() { |
138 | /// | 143 | /// |
139 | /// recordDecl(hasStdContainerName()) matches \c vector and \c forward_list | 144 | /// recordDecl(hasStdContainerName()) matches \c vector and \c forward_list |
140 | /// but not \c my_vec. | 145 | /// but not \c my_vec. |
141 | -Matcher<NamedDecl> hasStdContainerName() { | 146 | +AST_MATCHER(NamedDecl, hasStdContainerName) { |
142 | - static StringRef ContainerNames[] = {"array", "deque", | 147 | + static const char *const ContainerNames[] = { |
143 | - "forward_list", "list", | 148 | + "array", "deque", |
144 | - "vector", | 149 | + "forward_list", "list", |
150 | + "vector", | ||
145 | 151 | ||
146 | - "map", "multimap", | 152 | + "map", "multimap", |
147 | - "set", "multiset", | 153 | + "set", "multiset", |
148 | 154 | ||
149 | - "unordered_map", "unordered_multimap", | 155 | + "unordered_map", "unordered_multimap", |
150 | - "unordered_set", "unordered_multiset", | 156 | + "unordered_set", "unordered_multiset", |
151 | 157 | ||
152 | - "queue", "priority_queue", | 158 | + "queue", "priority_queue", |
153 | - "stack"}; | 159 | + "stack"}; |
154 | 160 | ||
155 | - return hasAnyName(ContainerNames); | 161 | + for (const char *Name : ContainerNames) { |
162 | + if (hasName(Name).matches(Node, Finder, Builder)) | ||
163 | + return true; | ||
164 | + } | ||
165 | + return false; | ||
156 | } | 166 | } |
157 | 167 | ||
158 | /// Matches declarations whose declaration context is the C++ standard library | 168 | /// Matches declarations whose declaration context is the C++ standard library |
... | @@ -338,7 +348,7 @@ void UseAutoCheck::replaceIterators(const DeclStmt *D, ASTContext *Context) { | ... | @@ -338,7 +348,7 @@ void UseAutoCheck::replaceIterators(const DeclStmt *D, ASTContext *Context) { |
338 | 348 | ||
339 | // Drill down to the as-written initializer. | 349 | // Drill down to the as-written initializer. |
340 | const Expr *E = (*Construct->arg_begin())->IgnoreParenImpCasts(); | 350 | const Expr *E = (*Construct->arg_begin())->IgnoreParenImpCasts(); |
341 | - if (E != E->IgnoreConversionOperatorSingleStep()) { | 351 | + if (E != E->IgnoreConversionOperator()) { |
342 | // We hit a conversion operator. Early-out now as they imply an implicit | 352 | // We hit a conversion operator. Early-out now as they imply an implicit |
343 | // conversion from a different type. Could also mean an explicit | 353 | // conversion from a different type. Could also mean an explicit |
344 | // conversion from the same type but that's pretty rare. | 354 | // conversion from the same type but that's pretty rare. | ... | ... |
... | @@ -36,12 +36,12 @@ void UseEqualsDeleteCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -36,12 +36,12 @@ void UseEqualsDeleteCheck::registerMatchers(MatchFinder *Finder) { |
36 | Finder->addMatcher( | 36 | Finder->addMatcher( |
37 | cxxMethodDecl( | 37 | cxxMethodDecl( |
38 | PrivateSpecialFn, | 38 | PrivateSpecialFn, |
39 | - unless(anyOf(hasAnyBody(stmt()), isDefaulted(), isDeleted(), | 39 | + unless(anyOf(hasBody(stmt()), isDefaulted(), isDeleted(), |
40 | ast_matchers::isTemplateInstantiation(), | 40 | ast_matchers::isTemplateInstantiation(), |
41 | // Ensure that all methods except private special member | 41 | // Ensure that all methods except private special member |
42 | // functions are defined. | 42 | // functions are defined. |
43 | hasParent(cxxRecordDecl(hasMethod(unless( | 43 | hasParent(cxxRecordDecl(hasMethod(unless( |
44 | - anyOf(PrivateSpecialFn, hasAnyBody(stmt()), isPure(), | 44 | + anyOf(PrivateSpecialFn, hasBody(stmt()), isPure(), |
45 | isDefaulted(), isDeleted())))))))) | 45 | isDefaulted(), isDeleted())))))))) |
46 | .bind(SpecialFunction), | 46 | .bind(SpecialFunction), |
47 | this); | 47 | this); | ... | ... |
... | @@ -77,16 +77,13 @@ void UseNoexceptCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -77,16 +77,13 @@ void UseNoexceptCheck::check(const MatchFinder::MatchResult &Result) { |
77 | .getExceptionSpecRange(); | 77 | .getExceptionSpecRange(); |
78 | } | 78 | } |
79 | 79 | ||
80 | - assert(FnTy && "FunctionProtoType is null."); | ||
81 | - if (isUnresolvedExceptionSpec(FnTy->getExceptionSpecType())) | ||
82 | - return; | ||
83 | - | ||
84 | assert(Range.isValid() && "Exception Source Range is invalid."); | 80 | assert(Range.isValid() && "Exception Source Range is invalid."); |
85 | 81 | ||
86 | CharSourceRange CRange = Lexer::makeFileCharRange( | 82 | CharSourceRange CRange = Lexer::makeFileCharRange( |
87 | CharSourceRange::getTokenRange(Range), *Result.SourceManager, | 83 | CharSourceRange::getTokenRange(Range), *Result.SourceManager, |
88 | Result.Context->getLangOpts()); | 84 | Result.Context->getLangOpts()); |
89 | 85 | ||
86 | + assert(FnTy && "FunctionProtoType is null."); | ||
90 | bool IsNoThrow = FnTy->isNothrow(); | 87 | bool IsNoThrow = FnTy->isNothrow(); |
91 | StringRef ReplacementStr = | 88 | StringRef ReplacementStr = |
92 | IsNoThrow | 89 | IsNoThrow | ... | ... |
... | @@ -66,11 +66,6 @@ public: | ... | @@ -66,11 +66,6 @@ public: |
66 | ->getName())) | 66 | ->getName())) |
67 | return false; | 67 | return false; |
68 | break; | 68 | break; |
69 | - case TypeLoc::Typedef: | ||
70 | - if (VisitUnqualName( | ||
71 | - TL.getAs<TypedefTypeLoc>().getTypePtr()->getDecl()->getName())) | ||
72 | - return false; | ||
73 | - break; | ||
74 | default: | 69 | default: |
75 | break; | 70 | break; |
76 | } | 71 | } |
... | @@ -266,8 +261,8 @@ static bool hasAnyNestedLocalQualifiers(QualType Type) { | ... | @@ -266,8 +261,8 @@ static bool hasAnyNestedLocalQualifiers(QualType Type) { |
266 | } | 261 | } |
267 | 262 | ||
268 | SourceRange UseTrailingReturnTypeCheck::findReturnTypeAndCVSourceRange( | 263 | SourceRange UseTrailingReturnTypeCheck::findReturnTypeAndCVSourceRange( |
269 | - const FunctionDecl &F, const TypeLoc &ReturnLoc, const ASTContext &Ctx, | 264 | + const FunctionDecl &F, const ASTContext &Ctx, const SourceManager &SM, |
270 | - const SourceManager &SM, const LangOptions &LangOpts) { | 265 | + const LangOptions &LangOpts) { |
271 | 266 | ||
272 | // We start with the range of the return type and expand to neighboring | 267 | // We start with the range of the return type and expand to neighboring |
273 | // qualifiers (const, volatile and restrict). | 268 | // qualifiers (const, volatile and restrict). |
... | @@ -279,35 +274,6 @@ SourceRange UseTrailingReturnTypeCheck::findReturnTypeAndCVSourceRange( | ... | @@ -279,35 +274,6 @@ SourceRange UseTrailingReturnTypeCheck::findReturnTypeAndCVSourceRange( |
279 | return {}; | 274 | return {}; |
280 | } | 275 | } |
281 | 276 | ||
282 | - // If the return type is a constrained 'auto' or 'decltype(auto)', we need to | ||
283 | - // include the tokens after the concept. Unfortunately, the source range of an | ||
284 | - // AutoTypeLoc, if it is constrained, does not include the 'auto' or | ||
285 | - // 'decltype(auto)'. If the return type is a plain 'decltype(...)', the | ||
286 | - // source range only contains the first 'decltype' token. | ||
287 | - auto ATL = ReturnLoc.getAs<AutoTypeLoc>(); | ||
288 | - if ((ATL && (ATL.isConstrained() || | ||
289 | - ATL.getAutoKeyword() == AutoTypeKeyword::DecltypeAuto)) || | ||
290 | - ReturnLoc.getAs<DecltypeTypeLoc>()) { | ||
291 | - SourceLocation End = | ||
292 | - expandIfMacroId(ReturnLoc.getSourceRange().getEnd(), SM); | ||
293 | - SourceLocation BeginNameF = expandIfMacroId(F.getLocation(), SM); | ||
294 | - | ||
295 | - // Extend the ReturnTypeRange until the last token before the function | ||
296 | - // name. | ||
297 | - std::pair<FileID, unsigned> Loc = SM.getDecomposedLoc(End); | ||
298 | - StringRef File = SM.getBufferData(Loc.first); | ||
299 | - const char *TokenBegin = File.data() + Loc.second; | ||
300 | - Lexer Lexer(SM.getLocForStartOfFile(Loc.first), LangOpts, File.begin(), | ||
301 | - TokenBegin, File.end()); | ||
302 | - Token T; | ||
303 | - SourceLocation LastTLoc = End; | ||
304 | - while (!Lexer.LexFromRawLexer(T) && | ||
305 | - SM.isBeforeInTranslationUnit(T.getLocation(), BeginNameF)) { | ||
306 | - LastTLoc = T.getLocation(); | ||
307 | - } | ||
308 | - ReturnTypeRange.setEnd(LastTLoc); | ||
309 | - } | ||
310 | - | ||
311 | // If the return type has no local qualifiers, it's source range is accurate. | 277 | // If the return type has no local qualifiers, it's source range is accurate. |
312 | if (!hasAnyNestedLocalQualifiers(F.getReturnType())) | 278 | if (!hasAnyNestedLocalQualifiers(F.getReturnType())) |
313 | return ReturnTypeRange; | 279 | return ReturnTypeRange; |
... | @@ -351,7 +317,7 @@ SourceRange UseTrailingReturnTypeCheck::findReturnTypeAndCVSourceRange( | ... | @@ -351,7 +317,7 @@ SourceRange UseTrailingReturnTypeCheck::findReturnTypeAndCVSourceRange( |
351 | return ReturnTypeRange; | 317 | return ReturnTypeRange; |
352 | } | 318 | } |
353 | 319 | ||
354 | -void UseTrailingReturnTypeCheck::keepSpecifiers( | 320 | +bool UseTrailingReturnTypeCheck::keepSpecifiers( |
355 | std::string &ReturnType, std::string &Auto, SourceRange ReturnTypeCVRange, | 321 | std::string &ReturnType, std::string &Auto, SourceRange ReturnTypeCVRange, |
356 | const FunctionDecl &F, const FriendDecl *Fr, const ASTContext &Ctx, | 322 | const FunctionDecl &F, const FriendDecl *Fr, const ASTContext &Ctx, |
357 | const SourceManager &SM, const LangOptions &LangOpts) { | 323 | const SourceManager &SM, const LangOptions &LangOpts) { |
... | @@ -361,14 +327,14 @@ void UseTrailingReturnTypeCheck::keepSpecifiers( | ... | @@ -361,14 +327,14 @@ void UseTrailingReturnTypeCheck::keepSpecifiers( |
361 | if (!F.isConstexpr() && !F.isInlineSpecified() && | 327 | if (!F.isConstexpr() && !F.isInlineSpecified() && |
362 | F.getStorageClass() != SC_Extern && F.getStorageClass() != SC_Static && | 328 | F.getStorageClass() != SC_Extern && F.getStorageClass() != SC_Static && |
363 | !Fr && !(M && M->isVirtualAsWritten())) | 329 | !Fr && !(M && M->isVirtualAsWritten())) |
364 | - return; | 330 | + return true; |
365 | 331 | ||
366 | // Tokenize return type. If it contains macros which contain a mix of | 332 | // Tokenize return type. If it contains macros which contain a mix of |
367 | // qualifiers, specifiers and types, give up. | 333 | // qualifiers, specifiers and types, give up. |
368 | llvm::Optional<SmallVector<ClassifiedToken, 8>> MaybeTokens = | 334 | llvm::Optional<SmallVector<ClassifiedToken, 8>> MaybeTokens = |
369 | classifyTokensBeforeFunctionName(F, Ctx, SM, LangOpts); | 335 | classifyTokensBeforeFunctionName(F, Ctx, SM, LangOpts); |
370 | if (!MaybeTokens) | 336 | if (!MaybeTokens) |
371 | - return; | 337 | + return false; |
372 | 338 | ||
373 | // Find specifiers, remove them from the return type, add them to 'auto'. | 339 | // Find specifiers, remove them from the return type, add them to 'auto'. |
374 | unsigned int ReturnTypeBeginOffset = | 340 | unsigned int ReturnTypeBeginOffset = |
... | @@ -401,12 +367,14 @@ void UseTrailingReturnTypeCheck::keepSpecifiers( | ... | @@ -401,12 +367,14 @@ void UseTrailingReturnTypeCheck::keepSpecifiers( |
401 | ReturnType.erase(TOffsetInRT, TLengthWithWS); | 367 | ReturnType.erase(TOffsetInRT, TLengthWithWS); |
402 | DeletedChars += TLengthWithWS; | 368 | DeletedChars += TLengthWithWS; |
403 | } | 369 | } |
370 | + | ||
371 | + return true; | ||
404 | } | 372 | } |
405 | 373 | ||
406 | void UseTrailingReturnTypeCheck::registerMatchers(MatchFinder *Finder) { | 374 | void UseTrailingReturnTypeCheck::registerMatchers(MatchFinder *Finder) { |
407 | - auto F = functionDecl( | 375 | + auto F = functionDecl(unless(anyOf(hasTrailingReturn(), returns(voidType()), |
408 | - unless(anyOf(hasTrailingReturn(), returns(voidType()), | 376 | + returns(autoType()), cxxConversionDecl(), |
409 | - cxxConversionDecl(), cxxMethodDecl(isImplicit())))) | 377 | + cxxMethodDecl(isImplicit())))) |
410 | .bind("Func"); | 378 | .bind("Func"); |
411 | 379 | ||
412 | Finder->addMatcher(F, this); | 380 | Finder->addMatcher(F, this); |
... | @@ -429,17 +397,11 @@ void UseTrailingReturnTypeCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -429,17 +397,11 @@ void UseTrailingReturnTypeCheck::check(const MatchFinder::MatchResult &Result) { |
429 | if (F->getLocation().isInvalid()) | 397 | if (F->getLocation().isInvalid()) |
430 | return; | 398 | return; |
431 | 399 | ||
432 | - // Skip functions which return just 'auto'. | ||
433 | - const auto *AT = F->getDeclaredReturnType()->getAs<AutoType>(); | ||
434 | - if (AT != nullptr && !AT->isConstrained() && | ||
435 | - AT->getKeyword() == AutoTypeKeyword::Auto && | ||
436 | - !hasAnyNestedLocalQualifiers(F->getDeclaredReturnType())) | ||
437 | - return; | ||
438 | - | ||
439 | // TODO: implement those | 400 | // TODO: implement those |
440 | if (F->getDeclaredReturnType()->isFunctionPointerType() || | 401 | if (F->getDeclaredReturnType()->isFunctionPointerType() || |
441 | F->getDeclaredReturnType()->isMemberFunctionPointerType() || | 402 | F->getDeclaredReturnType()->isMemberFunctionPointerType() || |
442 | - F->getDeclaredReturnType()->isMemberPointerType()) { | 403 | + F->getDeclaredReturnType()->isMemberPointerType() || |
404 | + F->getDeclaredReturnType()->getAs<DecltypeType>() != nullptr) { | ||
443 | diag(F->getLocation(), Message); | 405 | diag(F->getLocation(), Message); |
444 | return; | 406 | return; |
445 | } | 407 | } |
... | @@ -473,7 +435,7 @@ void UseTrailingReturnTypeCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -473,7 +435,7 @@ void UseTrailingReturnTypeCheck::check(const MatchFinder::MatchResult &Result) { |
473 | // discards user formatting and order of const, volatile, type, whitespace, | 435 | // discards user formatting and order of const, volatile, type, whitespace, |
474 | // space before & ... . | 436 | // space before & ... . |
475 | SourceRange ReturnTypeCVRange = | 437 | SourceRange ReturnTypeCVRange = |
476 | - findReturnTypeAndCVSourceRange(*F, FTL.getReturnLoc(), Ctx, SM, LangOpts); | 438 | + findReturnTypeAndCVSourceRange(*F, Ctx, SM, LangOpts); |
477 | if (ReturnTypeCVRange.isInvalid()) | 439 | if (ReturnTypeCVRange.isInvalid()) |
478 | return; | 440 | return; |
479 | 441 | ... | ... |
... | @@ -50,11 +50,10 @@ private: | ... | @@ -50,11 +50,10 @@ private: |
50 | const SourceManager &SM, | 50 | const SourceManager &SM, |
51 | const LangOptions &LangOpts); | 51 | const LangOptions &LangOpts); |
52 | SourceRange findReturnTypeAndCVSourceRange(const FunctionDecl &F, | 52 | SourceRange findReturnTypeAndCVSourceRange(const FunctionDecl &F, |
53 | - const TypeLoc &ReturnLoc, | ||
54 | const ASTContext &Ctx, | 53 | const ASTContext &Ctx, |
55 | const SourceManager &SM, | 54 | const SourceManager &SM, |
56 | const LangOptions &LangOpts); | 55 | const LangOptions &LangOpts); |
57 | - void keepSpecifiers(std::string &ReturnType, std::string &Auto, | 56 | + bool keepSpecifiers(std::string &ReturnType, std::string &Auto, |
58 | SourceRange ReturnTypeCVRange, const FunctionDecl &F, | 57 | SourceRange ReturnTypeCVRange, const FunctionDecl &F, |
59 | const FriendDecl *Fr, const ASTContext &Ctx, | 58 | const FriendDecl *Fr, const ASTContext &Ctx, |
60 | const SourceManager &SM, const LangOptions &LangOpts); | 59 | const SourceManager &SM, const LangOptions &LangOpts); | ... | ... |
... | @@ -23,8 +23,8 @@ namespace performance { | ... | @@ -23,8 +23,8 @@ namespace performance { |
23 | MoveConstructorInitCheck::MoveConstructorInitCheck(StringRef Name, | 23 | MoveConstructorInitCheck::MoveConstructorInitCheck(StringRef Name, |
24 | ClangTidyContext *Context) | 24 | ClangTidyContext *Context) |
25 | : ClangTidyCheck(Name, Context), | 25 | : ClangTidyCheck(Name, Context), |
26 | - Inserter(Options.getLocalOrGlobal("IncludeStyle", | 26 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
27 | - utils::IncludeSorter::IS_LLVM)) {} | 27 | + utils::IncludeSorter::IS_LLVM)) {} |
28 | 28 | ||
29 | void MoveConstructorInitCheck::registerMatchers(MatchFinder *Finder) { | 29 | void MoveConstructorInitCheck::registerMatchers(MatchFinder *Finder) { |
30 | Finder->addMatcher( | 30 | Finder->addMatcher( |
... | @@ -90,11 +90,13 @@ void MoveConstructorInitCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -90,11 +90,13 @@ void MoveConstructorInitCheck::check(const MatchFinder::MatchResult &Result) { |
90 | 90 | ||
91 | void MoveConstructorInitCheck::registerPPCallbacks( | 91 | void MoveConstructorInitCheck::registerPPCallbacks( |
92 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { | 92 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { |
93 | - Inserter.registerPreprocessor(PP); | 93 | + Inserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
94 | + IncludeStyle); | ||
95 | + PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
94 | } | 96 | } |
95 | 97 | ||
96 | void MoveConstructorInitCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { | 98 | void MoveConstructorInitCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) { |
97 | - Options.store(Opts, "IncludeStyle", Inserter.getStyle()); | 99 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
98 | } | 100 | } |
99 | 101 | ||
100 | } // namespace performance | 102 | } // namespace performance | ... | ... |
... | @@ -36,7 +36,8 @@ public: | ... | @@ -36,7 +36,8 @@ public: |
36 | void storeOptions(ClangTidyOptions::OptionMap &Opts) override; | 36 | void storeOptions(ClangTidyOptions::OptionMap &Opts) override; |
37 | 37 | ||
38 | private: | 38 | private: |
39 | - utils::IncludeInserter Inserter; | 39 | + std::unique_ptr<utils::IncludeInserter> Inserter; |
40 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
40 | }; | 41 | }; |
41 | 42 | ||
42 | } // namespace performance | 43 | } // namespace performance | ... | ... |
... | @@ -31,18 +31,19 @@ AST_MATCHER_P(Type, isBuiltinType, BuiltinType::Kind, Kind) { | ... | @@ -31,18 +31,19 @@ AST_MATCHER_P(Type, isBuiltinType, BuiltinType::Kind, Kind) { |
31 | TypePromotionInMathFnCheck::TypePromotionInMathFnCheck( | 31 | TypePromotionInMathFnCheck::TypePromotionInMathFnCheck( |
32 | StringRef Name, ClangTidyContext *Context) | 32 | StringRef Name, ClangTidyContext *Context) |
33 | : ClangTidyCheck(Name, Context), | 33 | : ClangTidyCheck(Name, Context), |
34 | - IncludeInserter(Options.getLocalOrGlobal("IncludeStyle", | 34 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
35 | - utils::IncludeSorter::IS_LLVM)) { | 35 | + utils::IncludeSorter::IS_LLVM)) {} |
36 | -} | ||
37 | 36 | ||
38 | void TypePromotionInMathFnCheck::registerPPCallbacks( | 37 | void TypePromotionInMathFnCheck::registerPPCallbacks( |
39 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { | 38 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { |
40 | - IncludeInserter.registerPreprocessor(PP); | 39 | + IncludeInserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
40 | + IncludeStyle); | ||
41 | + PP->addPPCallbacks(IncludeInserter->CreatePPCallbacks()); | ||
41 | } | 42 | } |
42 | 43 | ||
43 | void TypePromotionInMathFnCheck::storeOptions( | 44 | void TypePromotionInMathFnCheck::storeOptions( |
44 | ClangTidyOptions::OptionMap &Opts) { | 45 | ClangTidyOptions::OptionMap &Opts) { |
45 | - Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle()); | 46 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
46 | } | 47 | } |
47 | 48 | ||
48 | void TypePromotionInMathFnCheck::registerMatchers(MatchFinder *Finder) { | 49 | void TypePromotionInMathFnCheck::registerMatchers(MatchFinder *Finder) { |
... | @@ -190,9 +191,9 @@ void TypePromotionInMathFnCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -190,9 +191,9 @@ void TypePromotionInMathFnCheck::check(const MatchFinder::MatchResult &Result) { |
190 | // <math.h>, because the functions we're suggesting moving away from are all | 191 | // <math.h>, because the functions we're suggesting moving away from are all |
191 | // declared in <math.h>. | 192 | // declared in <math.h>. |
192 | if (FnInCmath) | 193 | if (FnInCmath) |
193 | - Diag << IncludeInserter.createIncludeInsertion( | 194 | + Diag << IncludeInserter->CreateIncludeInsertion( |
194 | Result.Context->getSourceManager().getFileID(Call->getBeginLoc()), | 195 | Result.Context->getSourceManager().getFileID(Call->getBeginLoc()), |
195 | - "<cmath>"); | 196 | + "cmath", /*IsAngled=*/true); |
196 | } | 197 | } |
197 | 198 | ||
198 | } // namespace performance | 199 | } // namespace performance | ... | ... |
... | @@ -36,7 +36,8 @@ public: | ... | @@ -36,7 +36,8 @@ public: |
36 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | 36 | void check(const ast_matchers::MatchFinder::MatchResult &Result) override; |
37 | 37 | ||
38 | private: | 38 | private: |
39 | - utils::IncludeInserter IncludeInserter; | 39 | + std::unique_ptr<utils::IncludeInserter> IncludeInserter; |
40 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
40 | }; | 41 | }; |
41 | 42 | ||
42 | } // namespace performance | 43 | } // namespace performance | ... | ... |
... | @@ -54,8 +54,7 @@ void UnnecessaryCopyInitialization::registerMatchers(MatchFinder *Finder) { | ... | @@ -54,8 +54,7 @@ void UnnecessaryCopyInitialization::registerMatchers(MatchFinder *Finder) { |
54 | on(declRefExpr(to(varDecl().bind("objectArg"))))); | 54 | on(declRefExpr(to(varDecl().bind("objectArg"))))); |
55 | auto ConstRefReturningFunctionCall = | 55 | auto ConstRefReturningFunctionCall = |
56 | callExpr(callee(functionDecl(returns(ConstReference))), | 56 | callExpr(callee(functionDecl(returns(ConstReference))), |
57 | - unless(callee(cxxMethodDecl()))) | 57 | + unless(callee(cxxMethodDecl()))); |
58 | - .bind("initFunctionCall"); | ||
59 | 58 | ||
60 | auto localVarCopiedFrom = [this](const internal::Matcher<Expr> &CopyCtorArg) { | 59 | auto localVarCopiedFrom = [this](const internal::Matcher<Expr> &CopyCtorArg) { |
61 | return compoundStmt( | 60 | return compoundStmt( |
... | @@ -97,8 +96,6 @@ void UnnecessaryCopyInitialization::check( | ... | @@ -97,8 +96,6 @@ void UnnecessaryCopyInitialization::check( |
97 | const auto *ObjectArg = Result.Nodes.getNodeAs<VarDecl>("objectArg"); | 96 | const auto *ObjectArg = Result.Nodes.getNodeAs<VarDecl>("objectArg"); |
98 | const auto *BlockStmt = Result.Nodes.getNodeAs<Stmt>("blockStmt"); | 97 | const auto *BlockStmt = Result.Nodes.getNodeAs<Stmt>("blockStmt"); |
99 | const auto *CtorCall = Result.Nodes.getNodeAs<CXXConstructExpr>("ctorCall"); | 98 | const auto *CtorCall = Result.Nodes.getNodeAs<CXXConstructExpr>("ctorCall"); |
100 | - const auto *InitFunctionCall = | ||
101 | - Result.Nodes.getNodeAs<CallExpr>("initFunctionCall"); | ||
102 | 99 | ||
103 | TraversalKindScope RAII(*Result.Context, ast_type_traits::TK_AsIs); | 100 | TraversalKindScope RAII(*Result.Context, ast_type_traits::TK_AsIs); |
104 | 101 | ||
... | @@ -116,11 +113,6 @@ void UnnecessaryCopyInitialization::check( | ... | @@ -116,11 +113,6 @@ void UnnecessaryCopyInitialization::check( |
116 | return; | 113 | return; |
117 | 114 | ||
118 | if (OldVar == nullptr) { | 115 | if (OldVar == nullptr) { |
119 | - // Only allow initialization of a const reference from a free function if it | ||
120 | - // has no arguments. Otherwise it could return an alias to one of its | ||
121 | - // arguments and the arguments need to be checked for const use as well. | ||
122 | - if (InitFunctionCall != nullptr && InitFunctionCall->getNumArgs() > 0) | ||
123 | - return; | ||
124 | handleCopyFromMethodReturn(*NewVar, *BlockStmt, IssueFix, ObjectArg, | 116 | handleCopyFromMethodReturn(*NewVar, *BlockStmt, IssueFix, ObjectArg, |
125 | *Result.Context); | 117 | *Result.Context); |
126 | } else { | 118 | } else { | ... | ... |
... | @@ -68,8 +68,8 @@ bool isExplicitTemplateSpecialization(const FunctionDecl &Function) { | ... | @@ -68,8 +68,8 @@ bool isExplicitTemplateSpecialization(const FunctionDecl &Function) { |
68 | UnnecessaryValueParamCheck::UnnecessaryValueParamCheck( | 68 | UnnecessaryValueParamCheck::UnnecessaryValueParamCheck( |
69 | StringRef Name, ClangTidyContext *Context) | 69 | StringRef Name, ClangTidyContext *Context) |
70 | : ClangTidyCheck(Name, Context), | 70 | : ClangTidyCheck(Name, Context), |
71 | - Inserter(Options.getLocalOrGlobal("IncludeStyle", | 71 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
72 | - utils::IncludeSorter::IS_LLVM)), | 72 | + utils::IncludeSorter::IS_LLVM)), |
73 | AllowedTypes( | 73 | AllowedTypes( |
74 | utils::options::parseStringList(Options.get("AllowedTypes", ""))) {} | 74 | utils::options::parseStringList(Options.get("AllowedTypes", ""))) {} |
75 | 75 | ||
... | @@ -173,12 +173,14 @@ void UnnecessaryValueParamCheck::check(const MatchFinder::MatchResult &Result) { | ... | @@ -173,12 +173,14 @@ void UnnecessaryValueParamCheck::check(const MatchFinder::MatchResult &Result) { |
173 | 173 | ||
174 | void UnnecessaryValueParamCheck::registerPPCallbacks( | 174 | void UnnecessaryValueParamCheck::registerPPCallbacks( |
175 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { | 175 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { |
176 | - Inserter.registerPreprocessor(PP); | 176 | + Inserter = std::make_unique<utils::IncludeInserter>(SM, getLangOpts(), |
177 | + IncludeStyle); | ||
178 | + PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
177 | } | 179 | } |
178 | 180 | ||
179 | void UnnecessaryValueParamCheck::storeOptions( | 181 | void UnnecessaryValueParamCheck::storeOptions( |
180 | ClangTidyOptions::OptionMap &Opts) { | 182 | ClangTidyOptions::OptionMap &Opts) { |
181 | - Options.store(Opts, "IncludeStyle", Inserter.getStyle()); | 183 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
182 | Options.store(Opts, "AllowedTypes", | 184 | Options.store(Opts, "AllowedTypes", |
183 | utils::options::serializeStringList(AllowedTypes)); | 185 | utils::options::serializeStringList(AllowedTypes)); |
184 | } | 186 | } |
... | @@ -202,8 +204,9 @@ void UnnecessaryValueParamCheck::handleMoveFix(const ParmVarDecl &Var, | ... | @@ -202,8 +204,9 @@ void UnnecessaryValueParamCheck::handleMoveFix(const ParmVarDecl &Var, |
202 | Context.getLangOpts()); | 204 | Context.getLangOpts()); |
203 | Diag << FixItHint::CreateInsertion(CopyArgument.getBeginLoc(), "std::move(") | 205 | Diag << FixItHint::CreateInsertion(CopyArgument.getBeginLoc(), "std::move(") |
204 | << FixItHint::CreateInsertion(EndLoc, ")") | 206 | << FixItHint::CreateInsertion(EndLoc, ")") |
205 | - << Inserter.createIncludeInsertion( | 207 | + << Inserter->CreateIncludeInsertion( |
206 | - SM.getFileID(CopyArgument.getBeginLoc()), "<utility>"); | 208 | + SM.getFileID(CopyArgument.getBeginLoc()), "utility", |
209 | + /*IsAngled=*/true); | ||
207 | } | 210 | } |
208 | 211 | ||
209 | } // namespace performance | 212 | } // namespace performance | ... | ... |
... | @@ -41,7 +41,8 @@ private: | ... | @@ -41,7 +41,8 @@ private: |
41 | 41 | ||
42 | llvm::DenseMap<const FunctionDecl *, FunctionParmMutationAnalyzer> | 42 | llvm::DenseMap<const FunctionDecl *, FunctionParmMutationAnalyzer> |
43 | MutationAnalyzers; | 43 | MutationAnalyzers; |
44 | - utils::IncludeInserter Inserter; | 44 | + std::unique_ptr<utils::IncludeInserter> Inserter; |
45 | + const utils::IncludeSorter::IncludeStyle IncludeStyle; | ||
45 | const std::vector<std::string> AllowedTypes; | 46 | const std::vector<std::string> AllowedTypes; |
46 | }; | 47 | }; |
47 | 48 | ... | ... |
... | @@ -12,7 +12,6 @@ add_clang_library(clangTidyReadabilityModule | ... | @@ -12,7 +12,6 @@ add_clang_library(clangTidyReadabilityModule |
12 | DeleteNullPointerCheck.cpp | 12 | DeleteNullPointerCheck.cpp |
13 | DeletedDefaultCheck.cpp | 13 | DeletedDefaultCheck.cpp |
14 | ElseAfterReturnCheck.cpp | 14 | ElseAfterReturnCheck.cpp |
15 | - FunctionCognitiveComplexityCheck.cpp | ||
16 | FunctionSizeCheck.cpp | 15 | FunctionSizeCheck.cpp |
17 | IdentifierNamingCheck.cpp | 16 | IdentifierNamingCheck.cpp |
18 | ImplicitBoolConversionCheck.cpp | 17 | ImplicitBoolConversionCheck.cpp | ... | ... |
llvm-project/clang-tools-extra/clang-tidy/readability/FunctionCognitiveComplexityCheck.cpp
deleted
100644 → 0
This diff is collapsed. Click to expand it.
llvm-project/clang-tools-extra/clang-tidy/readability/FunctionCognitiveComplexityCheck.h
deleted
100644 → 0
1 | -//===--- FunctionCognitiveComplexityCheck.h - clang-tidy --------*- C++ -*-===// | ||
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 | -//===----------------------------------------------------------------------===// | ||
8 | - | ||
9 | -#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_FUNCTIONCOGNITIVECOMPLEXITYCHECK_H | ||
10 | -#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_FUNCTIONCOGNITIVECOMPLEXITYCHECK_H | ||
11 | - | ||
12 | -#include "../ClangTidyCheck.h" | ||
13 | - | ||
14 | -namespace clang { | ||
15 | -namespace tidy { | ||
16 | -namespace readability { | ||
17 | - | ||
18 | -/// Checks function Cognitive Complexity metric. | ||
19 | -/// | ||
20 | -/// There is only one configuration option: | ||
21 | -/// | ||
22 | -/// * `Threshold` - flag functions with Cognitive Complexity exceeding | ||
23 | -/// this number. The default is `25`. | ||
24 | -/// | ||
25 | -/// For the user-facing documentation see: | ||
26 | -/// http://clang.llvm.org/extra/clang-tidy/checks/readability-function-cognitive-complexity.html | ||
27 | -class FunctionCognitiveComplexityCheck : public ClangTidyCheck { | ||
28 | -public: | ||
29 | - FunctionCognitiveComplexityCheck(StringRef Name, ClangTidyContext *Context); | ||
30 | - | ||
31 | - void storeOptions(ClangTidyOptions::OptionMap &Opts) override; | ||
32 | - void registerMatchers(ast_matchers::MatchFinder *Finder) override; | ||
33 | - void check(const ast_matchers::MatchFinder::MatchResult &Result) override; | ||
34 | - | ||
35 | -private: | ||
36 | - const unsigned Threshold; | ||
37 | -}; | ||
38 | - | ||
39 | -} // namespace readability | ||
40 | -} // namespace tidy | ||
41 | -} // namespace clang | ||
42 | - | ||
43 | -#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_FUNCTIONCOGNITIVECOMPLEXITYCHECK_H |
This diff is collapsed. Click to expand it.
... | @@ -10,7 +10,6 @@ | ... | @@ -10,7 +10,6 @@ |
10 | #define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_IDENTIFIERNAMINGCHECK_H | 10 | #define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_IDENTIFIERNAMINGCHECK_H |
11 | 11 | ||
12 | #include "../utils/RenamerClangTidyCheck.h" | 12 | #include "../utils/RenamerClangTidyCheck.h" |
13 | -#include "llvm/ADT/Optional.h" | ||
14 | namespace clang { | 13 | namespace clang { |
15 | 14 | ||
16 | class MacroInfo; | 15 | class MacroInfo; |
... | @@ -70,17 +69,7 @@ private: | ... | @@ -70,17 +69,7 @@ private: |
70 | DiagInfo GetDiagInfo(const NamingCheckId &ID, | 69 | DiagInfo GetDiagInfo(const NamingCheckId &ID, |
71 | const NamingCheckFailure &Failure) const override; | 70 | const NamingCheckFailure &Failure) const override; |
72 | 71 | ||
73 | - ArrayRef<llvm::Optional<NamingStyle>> | 72 | + std::vector<llvm::Optional<NamingStyle>> NamingStyles; |
74 | - getStyleForFile(StringRef FileName) const; | ||
75 | - | ||
76 | - /// Stores the style options as a vector, indexed by the specified \ref | ||
77 | - /// StyleKind, for a given directory. | ||
78 | - mutable llvm::StringMap<std::vector<llvm::Optional<NamingStyle>>> | ||
79 | - NamingStylesCache; | ||
80 | - ArrayRef<llvm::Optional<NamingStyle>> MainFileStyle; | ||
81 | - ClangTidyContext *const Context; | ||
82 | - const std::string CheckName; | ||
83 | - const bool GetConfigPerFile; | ||
84 | const bool IgnoreFailedSplit; | 73 | const bool IgnoreFailedSplit; |
85 | const bool IgnoreMainLikeFunctions; | 74 | const bool IgnoreMainLikeFunctions; |
86 | }; | 75 | }; | ... | ... |
... | @@ -17,7 +17,6 @@ | ... | @@ -17,7 +17,6 @@ |
17 | #include "DeleteNullPointerCheck.h" | 17 | #include "DeleteNullPointerCheck.h" |
18 | #include "DeletedDefaultCheck.h" | 18 | #include "DeletedDefaultCheck.h" |
19 | #include "ElseAfterReturnCheck.h" | 19 | #include "ElseAfterReturnCheck.h" |
20 | -#include "FunctionCognitiveComplexityCheck.h" | ||
21 | #include "FunctionSizeCheck.h" | 20 | #include "FunctionSizeCheck.h" |
22 | #include "IdentifierNamingCheck.h" | 21 | #include "IdentifierNamingCheck.h" |
23 | #include "ImplicitBoolConversionCheck.h" | 22 | #include "ImplicitBoolConversionCheck.h" |
... | @@ -71,8 +70,6 @@ public: | ... | @@ -71,8 +70,6 @@ public: |
71 | "readability-deleted-default"); | 70 | "readability-deleted-default"); |
72 | CheckFactories.registerCheck<ElseAfterReturnCheck>( | 71 | CheckFactories.registerCheck<ElseAfterReturnCheck>( |
73 | "readability-else-after-return"); | 72 | "readability-else-after-return"); |
74 | - CheckFactories.registerCheck<FunctionCognitiveComplexityCheck>( | ||
75 | - "readability-function-cognitive-complexity"); | ||
76 | CheckFactories.registerCheck<FunctionSizeCheck>( | 73 | CheckFactories.registerCheck<FunctionSizeCheck>( |
77 | "readability-function-size"); | 74 | "readability-function-size"); |
78 | CheckFactories.registerCheck<IdentifierNamingCheck>( | 75 | CheckFactories.registerCheck<IdentifierNamingCheck>( | ... | ... |
... | @@ -58,28 +58,16 @@ const char SimplifyConditionDiagnostic[] = | ... | @@ -58,28 +58,16 @@ const char SimplifyConditionDiagnostic[] = |
58 | const char SimplifyConditionalReturnDiagnostic[] = | 58 | const char SimplifyConditionalReturnDiagnostic[] = |
59 | "redundant boolean literal in conditional return statement"; | 59 | "redundant boolean literal in conditional return statement"; |
60 | 60 | ||
61 | -const Expr *getBoolLiteral(const MatchFinder::MatchResult &Result, | 61 | +const CXXBoolLiteralExpr *getBoolLiteral(const MatchFinder::MatchResult &Result, |
62 | - StringRef Id) { | 62 | + StringRef Id) { |
63 | - if (const Expr *Literal = Result.Nodes.getNodeAs<CXXBoolLiteralExpr>(Id)) | 63 | + const auto *Literal = Result.Nodes.getNodeAs<CXXBoolLiteralExpr>(Id); |
64 | - return Literal->getBeginLoc().isMacroID() ? nullptr : Literal; | 64 | + return (Literal && Literal->getBeginLoc().isMacroID()) ? nullptr : Literal; |
65 | - if (const auto *Negated = Result.Nodes.getNodeAs<UnaryOperator>(Id)) { | ||
66 | - if (Negated->getOpcode() == UO_LNot && | ||
67 | - isa<CXXBoolLiteralExpr>(Negated->getSubExpr())) | ||
68 | - return Negated->getBeginLoc().isMacroID() ? nullptr : Negated; | ||
69 | - } | ||
70 | - return nullptr; | ||
71 | -} | ||
72 | - | ||
73 | -internal::BindableMatcher<Stmt> literalOrNegatedBool(bool Value) { | ||
74 | - return expr(anyOf(cxxBoolLiteral(equals(Value)), | ||
75 | - unaryOperator(hasUnaryOperand(ignoringParenImpCasts( | ||
76 | - cxxBoolLiteral(equals(!Value)))), | ||
77 | - hasOperatorName("!")))); | ||
78 | } | 65 | } |
79 | 66 | ||
80 | internal::Matcher<Stmt> returnsBool(bool Value, StringRef Id = "ignored") { | 67 | internal::Matcher<Stmt> returnsBool(bool Value, StringRef Id = "ignored") { |
81 | - auto SimpleReturnsBool = returnStmt(has(literalOrNegatedBool(Value).bind(Id))) | 68 | + auto SimpleReturnsBool = |
82 | - .bind("returns-bool"); | 69 | + returnStmt(has(cxxBoolLiteral(equals(Value)).bind(Id))) |
70 | + .bind("returns-bool"); | ||
83 | return anyOf(SimpleReturnsBool, | 71 | return anyOf(SimpleReturnsBool, |
84 | compoundStmt(statementCountIs(1), has(SimpleReturnsBool))); | 72 | compoundStmt(statementCountIs(1), has(SimpleReturnsBool))); |
85 | } | 73 | } |
... | @@ -205,7 +193,7 @@ std::string compareExpressionToZero(const MatchFinder::MatchResult &Result, | ... | @@ -205,7 +193,7 @@ std::string compareExpressionToZero(const MatchFinder::MatchResult &Result, |
205 | 193 | ||
206 | std::string replacementExpression(const MatchFinder::MatchResult &Result, | 194 | std::string replacementExpression(const MatchFinder::MatchResult &Result, |
207 | bool Negated, const Expr *E) { | 195 | bool Negated, const Expr *E) { |
208 | - E = E->IgnoreParenBaseCasts(); | 196 | + E = E->ignoreParenBaseCasts(); |
209 | if (const auto *EC = dyn_cast<ExprWithCleanups>(E)) | 197 | if (const auto *EC = dyn_cast<ExprWithCleanups>(E)) |
210 | E = EC->getSubExpr(); | 198 | E = EC->getSubExpr(); |
211 | 199 | ||
... | @@ -281,25 +269,16 @@ std::string replacementExpression(const MatchFinder::MatchResult &Result, | ... | @@ -281,25 +269,16 @@ std::string replacementExpression(const MatchFinder::MatchResult &Result, |
281 | return asBool(getText(Result, *E), NeedsStaticCast); | 269 | return asBool(getText(Result, *E), NeedsStaticCast); |
282 | } | 270 | } |
283 | 271 | ||
284 | -const Expr *stmtReturnsBool(const ReturnStmt *Ret, bool Negated) { | 272 | +const CXXBoolLiteralExpr *stmtReturnsBool(const ReturnStmt *Ret, bool Negated) { |
285 | if (const auto *Bool = dyn_cast<CXXBoolLiteralExpr>(Ret->getRetValue())) { | 273 | if (const auto *Bool = dyn_cast<CXXBoolLiteralExpr>(Ret->getRetValue())) { |
286 | if (Bool->getValue() == !Negated) | 274 | if (Bool->getValue() == !Negated) |
287 | return Bool; | 275 | return Bool; |
288 | } | 276 | } |
289 | - if (const auto *Unary = dyn_cast<UnaryOperator>(Ret->getRetValue())) { | ||
290 | - if (Unary->getOpcode() == UO_LNot) { | ||
291 | - if (const auto *Bool = | ||
292 | - dyn_cast<CXXBoolLiteralExpr>(Unary->getSubExpr())) { | ||
293 | - if (Bool->getValue() == Negated) | ||
294 | - return Bool; | ||
295 | - } | ||
296 | - } | ||
297 | - } | ||
298 | 277 | ||
299 | return nullptr; | 278 | return nullptr; |
300 | } | 279 | } |
301 | 280 | ||
302 | -const Expr *stmtReturnsBool(const IfStmt *IfRet, bool Negated) { | 281 | +const CXXBoolLiteralExpr *stmtReturnsBool(const IfStmt *IfRet, bool Negated) { |
303 | if (IfRet->getElse() != nullptr) | 282 | if (IfRet->getElse() != nullptr) |
304 | return nullptr; | 283 | return nullptr; |
305 | 284 | ||
... | @@ -444,7 +423,7 @@ void SimplifyBooleanExprCheck::matchBoolCondition(MatchFinder *Finder, | ... | @@ -444,7 +423,7 @@ void SimplifyBooleanExprCheck::matchBoolCondition(MatchFinder *Finder, |
444 | StringRef BooleanId) { | 423 | StringRef BooleanId) { |
445 | Finder->addMatcher( | 424 | Finder->addMatcher( |
446 | ifStmt(unless(isInTemplateInstantiation()), | 425 | ifStmt(unless(isInTemplateInstantiation()), |
447 | - hasCondition(literalOrNegatedBool(Value).bind(BooleanId))) | 426 | + hasCondition(cxxBoolLiteral(equals(Value)).bind(BooleanId))) |
448 | .bind(IfStmtId), | 427 | .bind(IfStmtId), |
449 | this); | 428 | this); |
450 | } | 429 | } |
... | @@ -454,8 +433,8 @@ void SimplifyBooleanExprCheck::matchTernaryResult(MatchFinder *Finder, | ... | @@ -454,8 +433,8 @@ void SimplifyBooleanExprCheck::matchTernaryResult(MatchFinder *Finder, |
454 | StringRef TernaryId) { | 433 | StringRef TernaryId) { |
455 | Finder->addMatcher( | 434 | Finder->addMatcher( |
456 | conditionalOperator(unless(isInTemplateInstantiation()), | 435 | conditionalOperator(unless(isInTemplateInstantiation()), |
457 | - hasTrueExpression(literalOrNegatedBool(Value)), | 436 | + hasTrueExpression(cxxBoolLiteral(equals(Value))), |
458 | - hasFalseExpression(literalOrNegatedBool(!Value))) | 437 | + hasFalseExpression(cxxBoolLiteral(equals(!Value)))) |
459 | .bind(TernaryId), | 438 | .bind(TernaryId), |
460 | this); | 439 | this); |
461 | } | 440 | } |
... | @@ -486,12 +465,12 @@ void SimplifyBooleanExprCheck::matchIfAssignsBool(MatchFinder *Finder, | ... | @@ -486,12 +465,12 @@ void SimplifyBooleanExprCheck::matchIfAssignsBool(MatchFinder *Finder, |
486 | auto SimpleThen = | 465 | auto SimpleThen = |
487 | binaryOperator(hasOperatorName("="), hasLHS(anyOf(VarAssign, MemAssign)), | 466 | binaryOperator(hasOperatorName("="), hasLHS(anyOf(VarAssign, MemAssign)), |
488 | hasLHS(expr().bind(IfAssignVariableId)), | 467 | hasLHS(expr().bind(IfAssignVariableId)), |
489 | - hasRHS(literalOrNegatedBool(Value).bind(IfAssignLocId))); | 468 | + hasRHS(cxxBoolLiteral(equals(Value)).bind(IfAssignLocId))); |
490 | auto Then = anyOf(SimpleThen, compoundStmt(statementCountIs(1), | 469 | auto Then = anyOf(SimpleThen, compoundStmt(statementCountIs(1), |
491 | hasAnySubstatement(SimpleThen))); | 470 | hasAnySubstatement(SimpleThen))); |
492 | auto SimpleElse = | 471 | auto SimpleElse = |
493 | binaryOperator(hasOperatorName("="), hasLHS(anyOf(VarRef, MemRef)), | 472 | binaryOperator(hasOperatorName("="), hasLHS(anyOf(VarRef, MemRef)), |
494 | - hasRHS(literalOrNegatedBool(!Value))); | 473 | + hasRHS(cxxBoolLiteral(equals(!Value)))); |
495 | auto Else = anyOf(SimpleElse, compoundStmt(statementCountIs(1), | 474 | auto Else = anyOf(SimpleElse, compoundStmt(statementCountIs(1), |
496 | hasAnySubstatement(SimpleElse))); | 475 | hasAnySubstatement(SimpleElse))); |
497 | if (ChainedConditionalAssignment) | 476 | if (ChainedConditionalAssignment) |
... | @@ -516,7 +495,7 @@ void SimplifyBooleanExprCheck::matchCompoundIfReturnsBool(MatchFinder *Finder, | ... | @@ -516,7 +495,7 @@ void SimplifyBooleanExprCheck::matchCompoundIfReturnsBool(MatchFinder *Finder, |
516 | hasAnySubstatement( | 495 | hasAnySubstatement( |
517 | ifStmt(hasThen(returnsBool(Value)), unless(hasElse(stmt())))), | 496 | ifStmt(hasThen(returnsBool(Value)), unless(hasElse(stmt())))), |
518 | hasAnySubstatement(returnStmt(has(ignoringParenImpCasts( | 497 | hasAnySubstatement(returnStmt(has(ignoringParenImpCasts( |
519 | - literalOrNegatedBool(!Value)))) | 498 | + cxxBoolLiteral(equals(!Value))))) |
520 | .bind(CompoundReturnId))) | 499 | .bind(CompoundReturnId))) |
521 | .bind(Id), | 500 | .bind(Id), |
522 | this); | 501 | this); |
... | @@ -550,10 +529,10 @@ void SimplifyBooleanExprCheck::registerMatchers(MatchFinder *Finder) { | ... | @@ -550,10 +529,10 @@ void SimplifyBooleanExprCheck::registerMatchers(MatchFinder *Finder) { |
550 | void SimplifyBooleanExprCheck::check(const MatchFinder::MatchResult &Result) { | 529 | void SimplifyBooleanExprCheck::check(const MatchFinder::MatchResult &Result) { |
551 | if (Result.Nodes.getNodeAs<TranslationUnitDecl>("top")) | 530 | if (Result.Nodes.getNodeAs<TranslationUnitDecl>("top")) |
552 | Visitor(this, Result).TraverseAST(*Result.Context); | 531 | Visitor(this, Result).TraverseAST(*Result.Context); |
553 | - else if (const Expr *TrueConditionRemoved = | 532 | + else if (const CXXBoolLiteralExpr *TrueConditionRemoved = |
554 | getBoolLiteral(Result, ConditionThenStmtId)) | 533 | getBoolLiteral(Result, ConditionThenStmtId)) |
555 | replaceWithThenStatement(Result, TrueConditionRemoved); | 534 | replaceWithThenStatement(Result, TrueConditionRemoved); |
556 | - else if (const Expr *FalseConditionRemoved = | 535 | + else if (const CXXBoolLiteralExpr *FalseConditionRemoved = |
557 | getBoolLiteral(Result, ConditionElseStmtId)) | 536 | getBoolLiteral(Result, ConditionElseStmtId)) |
558 | replaceWithElseStatement(Result, FalseConditionRemoved); | 537 | replaceWithElseStatement(Result, FalseConditionRemoved); |
559 | else if (const auto *Ternary = | 538 | else if (const auto *Ternary = |
... | @@ -595,7 +574,8 @@ void SimplifyBooleanExprCheck::issueDiag( | ... | @@ -595,7 +574,8 @@ void SimplifyBooleanExprCheck::issueDiag( |
595 | } | 574 | } |
596 | 575 | ||
597 | void SimplifyBooleanExprCheck::replaceWithThenStatement( | 576 | void SimplifyBooleanExprCheck::replaceWithThenStatement( |
598 | - const MatchFinder::MatchResult &Result, const Expr *TrueConditionRemoved) { | 577 | + const MatchFinder::MatchResult &Result, |
578 | + const CXXBoolLiteralExpr *TrueConditionRemoved) { | ||
599 | const auto *IfStatement = Result.Nodes.getNodeAs<IfStmt>(IfStmtId); | 579 | const auto *IfStatement = Result.Nodes.getNodeAs<IfStmt>(IfStmtId); |
600 | issueDiag(Result, TrueConditionRemoved->getBeginLoc(), | 580 | issueDiag(Result, TrueConditionRemoved->getBeginLoc(), |
601 | SimplifyConditionDiagnostic, IfStatement->getSourceRange(), | 581 | SimplifyConditionDiagnostic, IfStatement->getSourceRange(), |
... | @@ -603,7 +583,8 @@ void SimplifyBooleanExprCheck::replaceWithThenStatement( | ... | @@ -603,7 +583,8 @@ void SimplifyBooleanExprCheck::replaceWithThenStatement( |
603 | } | 583 | } |
604 | 584 | ||
605 | void SimplifyBooleanExprCheck::replaceWithElseStatement( | 585 | void SimplifyBooleanExprCheck::replaceWithElseStatement( |
606 | - const MatchFinder::MatchResult &Result, const Expr *FalseConditionRemoved) { | 586 | + const MatchFinder::MatchResult &Result, |
587 | + const CXXBoolLiteralExpr *FalseConditionRemoved) { | ||
607 | const auto *IfStatement = Result.Nodes.getNodeAs<IfStmt>(IfStmtId); | 588 | const auto *IfStatement = Result.Nodes.getNodeAs<IfStmt>(IfStmtId); |
608 | const Stmt *ElseStatement = IfStatement->getElse(); | 589 | const Stmt *ElseStatement = IfStatement->getElse(); |
609 | issueDiag(Result, FalseConditionRemoved->getBeginLoc(), | 590 | issueDiag(Result, FalseConditionRemoved->getBeginLoc(), |
... | @@ -650,7 +631,7 @@ void SimplifyBooleanExprCheck::replaceCompoundReturnWithCondition( | ... | @@ -650,7 +631,7 @@ void SimplifyBooleanExprCheck::replaceCompoundReturnWithCondition( |
650 | for (++After; After != Compound->body_end() && *Current != Ret; | 631 | for (++After; After != Compound->body_end() && *Current != Ret; |
651 | ++Current, ++After) { | 632 | ++Current, ++After) { |
652 | if (const auto *If = dyn_cast<IfStmt>(*Current)) { | 633 | if (const auto *If = dyn_cast<IfStmt>(*Current)) { |
653 | - if (const Expr *Lit = stmtReturnsBool(If, Negated)) { | 634 | + if (const CXXBoolLiteralExpr *Lit = stmtReturnsBool(If, Negated)) { |
654 | if (*After == Ret) { | 635 | if (*After == Ret) { |
655 | if (!ChainedConditionalReturn && BeforeIf) | 636 | if (!ChainedConditionalReturn && BeforeIf) |
656 | continue; | 637 | continue; | ... | ... |
... | @@ -51,11 +51,11 @@ private: | ... | @@ -51,11 +51,11 @@ private: |
51 | 51 | ||
52 | void | 52 | void |
53 | replaceWithThenStatement(const ast_matchers::MatchFinder::MatchResult &Result, | 53 | replaceWithThenStatement(const ast_matchers::MatchFinder::MatchResult &Result, |
54 | - const Expr *BoolLiteral); | 54 | + const CXXBoolLiteralExpr *BoolLiteral); |
55 | 55 | ||
56 | void | 56 | void |
57 | replaceWithElseStatement(const ast_matchers::MatchFinder::MatchResult &Result, | 57 | replaceWithElseStatement(const ast_matchers::MatchFinder::MatchResult &Result, |
58 | - const Expr *FalseConditionRemoved); | 58 | + const CXXBoolLiteralExpr *FalseConditionRemoved); |
59 | 59 | ||
60 | void | 60 | void |
61 | replaceWithCondition(const ast_matchers::MatchFinder::MatchResult &Result, | 61 | replaceWithCondition(const ast_matchers::MatchFinder::MatchResult &Result, | ... | ... |
... | @@ -123,7 +123,12 @@ public: | ... | @@ -123,7 +123,12 @@ public: |
123 | 123 | ||
124 | // Emit warnings for headers that are missing guards. | 124 | // Emit warnings for headers that are missing guards. |
125 | checkGuardlessHeaders(); | 125 | checkGuardlessHeaders(); |
126 | - clearAllState(); | 126 | + |
127 | + // Clear all state. | ||
128 | + Macros.clear(); | ||
129 | + Files.clear(); | ||
130 | + Ifndefs.clear(); | ||
131 | + EndIfs.clear(); | ||
127 | } | 132 | } |
128 | 133 | ||
129 | bool wouldFixEndifComment(StringRef FileName, SourceLocation EndIf, | 134 | bool wouldFixEndifComment(StringRef FileName, SourceLocation EndIf, |
... | @@ -250,13 +255,6 @@ public: | ... | @@ -250,13 +255,6 @@ public: |
250 | } | 255 | } |
251 | 256 | ||
252 | private: | 257 | private: |
253 | - void clearAllState() { | ||
254 | - Macros.clear(); | ||
255 | - Files.clear(); | ||
256 | - Ifndefs.clear(); | ||
257 | - EndIfs.clear(); | ||
258 | - } | ||
259 | - | ||
260 | std::vector<std::pair<Token, const MacroInfo *>> Macros; | 258 | std::vector<std::pair<Token, const MacroInfo *>> Macros; |
261 | llvm::StringMap<const FileEntry *> Files; | 259 | llvm::StringMap<const FileEntry *> Files; |
262 | std::map<const IdentifierInfo *, std::pair<SourceLocation, SourceLocation>> | 260 | std::map<const IdentifierInfo *, std::pair<SourceLocation, SourceLocation>> | ... | ... |
... | @@ -7,8 +7,6 @@ | ... | @@ -7,8 +7,6 @@ |
7 | //===----------------------------------------------------------------------===// | 7 | //===----------------------------------------------------------------------===// |
8 | 8 | ||
9 | #include "IncludeInserter.h" | 9 | #include "IncludeInserter.h" |
10 | -#include "clang/Lex/PPCallbacks.h" | ||
11 | -#include "clang/Lex/Preprocessor.h" | ||
12 | #include "clang/Lex/Token.h" | 10 | #include "clang/Lex/Token.h" |
13 | 11 | ||
14 | namespace clang { | 12 | namespace clang { |
... | @@ -28,7 +26,7 @@ public: | ... | @@ -28,7 +26,7 @@ public: |
28 | StringRef /*SearchPath*/, StringRef /*RelativePath*/, | 26 | StringRef /*SearchPath*/, StringRef /*RelativePath*/, |
29 | const Module * /*ImportedModule*/, | 27 | const Module * /*ImportedModule*/, |
30 | SrcMgr::CharacteristicKind /*FileType*/) override { | 28 | SrcMgr::CharacteristicKind /*FileType*/) override { |
31 | - Inserter->addInclude(FileNameRef, IsAngled, HashLocation, | 29 | + Inserter->AddInclude(FileNameRef, IsAngled, HashLocation, |
32 | IncludeToken.getEndLoc()); | 30 | IncludeToken.getEndLoc()); |
33 | } | 31 | } |
34 | 32 | ||
... | @@ -36,76 +34,45 @@ private: | ... | @@ -36,76 +34,45 @@ private: |
36 | IncludeInserter *Inserter; | 34 | IncludeInserter *Inserter; |
37 | }; | 35 | }; |
38 | 36 | ||
39 | -IncludeInserter::IncludeInserter(IncludeSorter::IncludeStyle Style) | 37 | +IncludeInserter::IncludeInserter(const SourceManager &SourceMgr, |
40 | - : Style(Style) {} | 38 | + const LangOptions &LangOpts, |
39 | + IncludeSorter::IncludeStyle Style) | ||
40 | + : SourceMgr(SourceMgr), Style(Style) {} | ||
41 | 41 | ||
42 | -void IncludeInserter::registerPreprocessor(Preprocessor *PP) { | 42 | +IncludeInserter::~IncludeInserter() {} |
43 | - assert(PP && "PP shouldn't be null"); | ||
44 | - SourceMgr = &PP->getSourceManager(); | ||
45 | 43 | ||
46 | - // If this gets registered multiple times, clear the maps | 44 | +std::unique_ptr<PPCallbacks> IncludeInserter::CreatePPCallbacks() { |
47 | - if (!IncludeSorterByFile.empty()) | 45 | + return std::make_unique<IncludeInserterCallback>(this); |
48 | - IncludeSorterByFile.clear(); | ||
49 | - if (!InsertedHeaders.empty()) | ||
50 | - InsertedHeaders.clear(); | ||
51 | - PP->addPPCallbacks(std::make_unique<IncludeInserterCallback>(this)); | ||
52 | } | 46 | } |
53 | 47 | ||
54 | IncludeSorter &IncludeInserter::getOrCreate(FileID FileID) { | 48 | 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 | 49 | // 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. | 50 | // the lookup needed if we were to insert into the map. |
59 | std::unique_ptr<IncludeSorter> &Entry = IncludeSorterByFile[FileID]; | 51 | std::unique_ptr<IncludeSorter> &Entry = IncludeSorterByFile[FileID]; |
60 | if (!Entry) { | 52 | if (!Entry) { |
61 | // If it wasn't found, Entry will be default constructed to nullptr. | 53 | // If it wasn't found, Entry will be default constructed to nullptr. |
62 | Entry = std::make_unique<IncludeSorter>( | 54 | Entry = std::make_unique<IncludeSorter>( |
63 | - SourceMgr, FileID, | 55 | + &SourceMgr, FileID, |
64 | - SourceMgr->getFilename(SourceMgr->getLocForStartOfFile(FileID)), Style); | 56 | + SourceMgr.getFilename(SourceMgr.getLocForStartOfFile(FileID)), Style); |
65 | } | 57 | } |
66 | return *Entry; | 58 | return *Entry; |
67 | } | 59 | } |
68 | 60 | ||
69 | llvm::Optional<FixItHint> | 61 | llvm::Optional<FixItHint> |
70 | -IncludeInserter::createIncludeInsertion(FileID FileID, StringRef Header, | 62 | +IncludeInserter::CreateIncludeInsertion(FileID FileID, StringRef Header, |
71 | bool IsAngled) { | 63 | bool IsAngled) { |
72 | // We assume the same Header will never be included both angled and not | 64 | // We assume the same Header will never be included both angled and not |
73 | // angled. | 65 | // angled. |
74 | - if (!InsertedHeaders[FileID].insert(Header).second) | 66 | + if (!InsertedHeaders[FileID].insert(std::string(Header)).second) |
75 | return llvm::None; | 67 | return llvm::None; |
76 | 68 | ||
77 | return getOrCreate(FileID).CreateIncludeInsertion(Header, IsAngled); | 69 | return getOrCreate(FileID).CreateIncludeInsertion(Header, IsAngled); |
78 | } | 70 | } |
79 | 71 | ||
80 | -llvm::Optional<FixItHint> | 72 | +void IncludeInserter::AddInclude(StringRef FileName, bool IsAngled, |
81 | -IncludeInserter::createIncludeInsertion(FileID FileID, llvm::StringRef Header) { | ||
82 | - bool IsAngled = Header.consume_front("<"); | ||
83 | - if (IsAngled != Header.consume_back(">")) | ||
84 | - return llvm::None; | ||
85 | - return createIncludeInsertion(FileID, Header, IsAngled); | ||
86 | -} | ||
87 | - | ||
88 | -llvm::Optional<FixItHint> | ||
89 | -IncludeInserter::createMainFileIncludeInsertion(StringRef Header, | ||
90 | - bool IsAngled) { | ||
91 | - assert(SourceMgr && "SourceMgr shouldn't be null; did you remember to call " | ||
92 | - "registerPreprocessor()?"); | ||
93 | - return createIncludeInsertion(SourceMgr->getMainFileID(), Header, IsAngled); | ||
94 | -} | ||
95 | - | ||
96 | -llvm::Optional<FixItHint> | ||
97 | -IncludeInserter::createMainFileIncludeInsertion(StringRef Header) { | ||
98 | - assert(SourceMgr && "SourceMgr shouldn't be null; did you remember to call " | ||
99 | - "registerPreprocessor()?"); | ||
100 | - return createIncludeInsertion(SourceMgr->getMainFileID(), Header); | ||
101 | -} | ||
102 | - | ||
103 | -void IncludeInserter::addInclude(StringRef FileName, bool IsAngled, | ||
104 | SourceLocation HashLocation, | 73 | SourceLocation HashLocation, |
105 | SourceLocation EndLocation) { | 74 | SourceLocation EndLocation) { |
106 | - assert(SourceMgr && "SourceMgr shouldn't be null; did you remember to call " | 75 | + FileID FileID = SourceMgr.getFileID(HashLocation); |
107 | - "registerPreprocessor()?"); | ||
108 | - FileID FileID = SourceMgr->getFileID(HashLocation); | ||
109 | getOrCreate(FileID).AddInclude(FileName, IsAngled, HashLocation, EndLocation); | 76 | getOrCreate(FileID).AddInclude(FileName, IsAngled, HashLocation, EndLocation); |
110 | } | 77 | } |
111 | 78 | ... | ... |
... | @@ -11,11 +11,13 @@ | ... | @@ -11,11 +11,13 @@ |
11 | 11 | ||
12 | #include "IncludeSorter.h" | 12 | #include "IncludeSorter.h" |
13 | #include "clang/Basic/Diagnostic.h" | 13 | #include "clang/Basic/Diagnostic.h" |
14 | -#include "llvm/ADT/StringSet.h" | 14 | +#include "clang/Basic/LangOptions.h" |
15 | +#include "clang/Basic/SourceManager.h" | ||
16 | +#include "clang/Lex/PPCallbacks.h" | ||
15 | #include <memory> | 17 | #include <memory> |
18 | +#include <string> | ||
16 | 19 | ||
17 | namespace clang { | 20 | namespace clang { |
18 | -class Preprocessor; | ||
19 | namespace tidy { | 21 | namespace tidy { |
20 | namespace utils { | 22 | namespace utils { |
21 | 23 | ||
... | @@ -24,17 +26,16 @@ namespace utils { | ... | @@ -24,17 +26,16 @@ namespace utils { |
24 | /// | 26 | /// |
25 | /// ``IncludeInserter`` can be used in clang-tidy checks in the following way: | 27 | /// ``IncludeInserter`` can be used in clang-tidy checks in the following way: |
26 | /// \code | 28 | /// \code |
27 | -/// #include "../ClangTidyCheck.h" | ||
28 | /// #include "../utils/IncludeInserter.h" | 29 | /// #include "../utils/IncludeInserter.h" |
29 | -/// | 30 | +/// #include "clang/Frontend/CompilerInstance.h" |
30 | -/// namespace clang { | ||
31 | -/// namespace tidy { | ||
32 | /// | 31 | /// |
33 | /// class MyCheck : public ClangTidyCheck { | 32 | /// class MyCheck : public ClangTidyCheck { |
34 | /// public: | 33 | /// public: |
35 | /// void registerPPCallbacks(const SourceManager &SM, Preprocessor *PP, | 34 | /// void registerPPCallbacks(const SourceManager &SM, Preprocessor *PP, |
36 | /// Preprocessor *ModuleExpanderPP) override { | 35 | /// Preprocessor *ModuleExpanderPP) override { |
37 | -/// Inserter.registerPreprocessor(); | 36 | +/// Inserter = std::make_unique<IncludeInserter>( |
37 | +/// SM, getLangOpts(), utils::IncludeSorter::IS_Google); | ||
38 | +/// PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
38 | /// } | 39 | /// } |
39 | /// | 40 | /// |
40 | /// void registerMatchers(ast_matchers::MatchFinder* Finder) override { ... } | 41 | /// void registerMatchers(ast_matchers::MatchFinder* Finder) override { ... } |
... | @@ -42,73 +43,39 @@ namespace utils { | ... | @@ -42,73 +43,39 @@ namespace utils { |
42 | /// void check( | 43 | /// void check( |
43 | /// const ast_matchers::MatchFinder::MatchResult& Result) override { | 44 | /// const ast_matchers::MatchFinder::MatchResult& Result) override { |
44 | /// ... | 45 | /// ... |
45 | -/// Inserter.createMainFileIncludeInsertion("path/to/Header.h", | 46 | +/// Inserter->CreateIncludeInsertion( |
46 | -/// /*IsAngled=*/false); | 47 | +/// Result.SourceManager->getMainFileID(), "path/to/Header.h", |
48 | +/// /*IsAngled=*/false); | ||
47 | /// ... | 49 | /// ... |
48 | /// } | 50 | /// } |
49 | /// | 51 | /// |
50 | /// private: | 52 | /// private: |
51 | -/// utils::IncludeInserter Inserter{utils::IncludeSorter::IS_Google}; | 53 | +/// std::unique_ptr<clang::tidy::utils::IncludeInserter> Inserter; |
52 | /// }; | 54 | /// }; |
53 | -/// } // namespace tidy | ||
54 | -/// } // namespace clang | ||
55 | /// \endcode | 55 | /// \endcode |
56 | class IncludeInserter { | 56 | class IncludeInserter { |
57 | public: | 57 | public: |
58 | - /// Initializes the IncludeInserter using the IncludeStyle \p Style. | 58 | + IncludeInserter(const SourceManager &SourceMgr, const LangOptions &LangOpts, |
59 | - /// In most cases the \p Style will be retrieved from the ClangTidyOptions | 59 | + IncludeSorter::IncludeStyle Style); |
60 | - /// using \code | 60 | + ~IncludeInserter(); |
61 | - /// Options.getLocalOrGlobal("IncludeStyle", <DefaultStyle>) | ||
62 | - /// \endcode | ||
63 | - explicit IncludeInserter(IncludeSorter::IncludeStyle Style); | ||
64 | - | ||
65 | - /// Registers this with the Preprocessor \p PP, must be called before this | ||
66 | - /// class is used. | ||
67 | - void registerPreprocessor(Preprocessor *PP); | ||
68 | - | ||
69 | - /// Creates a \p Header inclusion directive fixit in the File \p FileID. | ||
70 | - /// Returns ``llvm::None`` on error or if the inclusion directive already | ||
71 | - /// exists. | ||
72 | - /// FIXME: This should be removed once the clients are migrated to the | ||
73 | - /// overload without the ``IsAngled`` parameter. | ||
74 | - llvm::Optional<FixItHint> | ||
75 | - createIncludeInsertion(FileID FileID, llvm::StringRef Header, bool IsAngled); | ||
76 | 61 | ||
77 | - /// Creates a \p Header inclusion directive fixit in the File \p FileID. | 62 | + /// Create ``PPCallbacks`` for registration with the compiler's preprocessor. |
78 | - /// When \p Header is enclosed in angle brackets, uses angle brackets in the | 63 | + std::unique_ptr<PPCallbacks> CreatePPCallbacks(); |
79 | - /// inclusion directive, otherwise uses quotes. | ||
80 | - /// Returns ``llvm::None`` on error or if the inclusion directive already | ||
81 | - /// exists. | ||
82 | - llvm::Optional<FixItHint> createIncludeInsertion(FileID FileID, | ||
83 | - llvm::StringRef Header); | ||
84 | 64 | ||
85 | - /// Creates a \p Header inclusion directive fixit in the main file. | 65 | + /// Creates a \p Header inclusion directive fixit. Returns ``llvm::None`` on |
86 | - /// Returns``llvm::None`` on error or if the inclusion directive already | 66 | + /// error or if inclusion directive already exists. |
87 | - /// exists. | ||
88 | - /// FIXME: This should be removed once the clients are migrated to the | ||
89 | - /// overload without the ``IsAngled`` parameter. | ||
90 | llvm::Optional<FixItHint> | 67 | llvm::Optional<FixItHint> |
91 | - createMainFileIncludeInsertion(llvm::StringRef Header, bool IsAngled); | 68 | + CreateIncludeInsertion(FileID FileID, llvm::StringRef Header, bool IsAngled); |
92 | - | ||
93 | - /// Creates a \p Header inclusion directive fixit in the main file. | ||
94 | - /// When \p Header is enclosed in angle brackets, uses angle brackets in the | ||
95 | - /// inclusion directive, otherwise uses quotes. | ||
96 | - /// Returns``llvm::None`` on error or if the inclusion directive already | ||
97 | - /// exists. | ||
98 | - llvm::Optional<FixItHint> | ||
99 | - createMainFileIncludeInsertion(llvm::StringRef Header); | ||
100 | - | ||
101 | - IncludeSorter::IncludeStyle getStyle() const { return Style; } | ||
102 | 69 | ||
103 | private: | 70 | private: |
104 | - void addInclude(StringRef FileName, bool IsAngled, | 71 | + void AddInclude(StringRef FileName, bool IsAngled, |
105 | SourceLocation HashLocation, SourceLocation EndLocation); | 72 | SourceLocation HashLocation, SourceLocation EndLocation); |
106 | 73 | ||
107 | IncludeSorter &getOrCreate(FileID FileID); | 74 | IncludeSorter &getOrCreate(FileID FileID); |
108 | 75 | ||
109 | llvm::DenseMap<FileID, std::unique_ptr<IncludeSorter>> IncludeSorterByFile; | 76 | llvm::DenseMap<FileID, std::unique_ptr<IncludeSorter>> IncludeSorterByFile; |
110 | - llvm::DenseMap<FileID, llvm::StringSet<>> InsertedHeaders; | 77 | + llvm::DenseMap<FileID, std::set<std::string>> InsertedHeaders; |
111 | - const SourceManager *SourceMgr{nullptr}; | 78 | + const SourceManager &SourceMgr; |
112 | const IncludeSorter::IncludeStyle Style; | 79 | const IncludeSorter::IncludeStyle Style; |
113 | friend class IncludeInserterCallback; | 80 | friend class IncludeInserterCallback; |
114 | }; | 81 | }; | ... | ... |
... | @@ -32,8 +32,8 @@ TransformerClangTidyCheck::TransformerClangTidyCheck( | ... | @@ -32,8 +32,8 @@ TransformerClangTidyCheck::TransformerClangTidyCheck( |
32 | MakeRule, | 32 | MakeRule, |
33 | StringRef Name, ClangTidyContext *Context) | 33 | StringRef Name, ClangTidyContext *Context) |
34 | : ClangTidyCheck(Name, Context), Rule(MakeRule(getLangOpts(), Options)), | 34 | : ClangTidyCheck(Name, Context), Rule(MakeRule(getLangOpts(), Options)), |
35 | - Inserter( | 35 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
36 | - Options.getLocalOrGlobal("IncludeStyle", IncludeSorter::IS_LLVM)) { | 36 | + IncludeSorter::IS_LLVM)) { |
37 | if (Rule) | 37 | if (Rule) |
38 | assert(llvm::all_of(Rule->Cases, hasExplanation) && | 38 | assert(llvm::all_of(Rule->Cases, hasExplanation) && |
39 | "clang-tidy checks must have an explanation by default;" | 39 | "clang-tidy checks must have an explanation by default;" |
... | @@ -44,8 +44,8 @@ TransformerClangTidyCheck::TransformerClangTidyCheck(RewriteRule R, | ... | @@ -44,8 +44,8 @@ TransformerClangTidyCheck::TransformerClangTidyCheck(RewriteRule R, |
44 | StringRef Name, | 44 | StringRef Name, |
45 | ClangTidyContext *Context) | 45 | ClangTidyContext *Context) |
46 | : ClangTidyCheck(Name, Context), Rule(std::move(R)), | 46 | : ClangTidyCheck(Name, Context), Rule(std::move(R)), |
47 | - Inserter( | 47 | + IncludeStyle(Options.getLocalOrGlobal("IncludeStyle", |
48 | - Options.getLocalOrGlobal("IncludeStyle", IncludeSorter::IS_LLVM)) { | 48 | + IncludeSorter::IS_LLVM)) { |
49 | assert(llvm::all_of(Rule->Cases, hasExplanation) && | 49 | assert(llvm::all_of(Rule->Cases, hasExplanation) && |
50 | "clang-tidy checks must have an explanation by default;" | 50 | "clang-tidy checks must have an explanation by default;" |
51 | " explicitly provide an empty explanation if none is desired"); | 51 | " explicitly provide an empty explanation if none is desired"); |
... | @@ -53,7 +53,15 @@ TransformerClangTidyCheck::TransformerClangTidyCheck(RewriteRule R, | ... | @@ -53,7 +53,15 @@ TransformerClangTidyCheck::TransformerClangTidyCheck(RewriteRule R, |
53 | 53 | ||
54 | void TransformerClangTidyCheck::registerPPCallbacks( | 54 | void TransformerClangTidyCheck::registerPPCallbacks( |
55 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { | 55 | const SourceManager &SM, Preprocessor *PP, Preprocessor *ModuleExpanderPP) { |
56 | - Inserter.registerPreprocessor(PP); | 56 | + // Only allocate and register the IncludeInsert when some `Case` will add |
57 | + // includes. | ||
58 | + if (Rule && llvm::any_of(Rule->Cases, [](const RewriteRule::Case &C) { | ||
59 | + return !C.AddedIncludes.empty(); | ||
60 | + })) { | ||
61 | + Inserter = | ||
62 | + std::make_unique<IncludeInserter>(SM, getLangOpts(), IncludeStyle); | ||
63 | + PP->addPPCallbacks(Inserter->CreatePPCallbacks()); | ||
64 | + } | ||
57 | } | 65 | } |
58 | 66 | ||
59 | void TransformerClangTidyCheck::registerMatchers( | 67 | void TransformerClangTidyCheck::registerMatchers( |
... | @@ -91,24 +99,18 @@ void TransformerClangTidyCheck::check( | ... | @@ -91,24 +99,18 @@ void TransformerClangTidyCheck::check( |
91 | // Associate the diagnostic with the location of the first change. | 99 | // Associate the diagnostic with the location of the first change. |
92 | DiagnosticBuilder Diag = diag((*Edits)[0].Range.getBegin(), *Explanation); | 100 | DiagnosticBuilder Diag = diag((*Edits)[0].Range.getBegin(), *Explanation); |
93 | for (const auto &T : *Edits) | 101 | for (const auto &T : *Edits) |
94 | - switch (T.Kind) { | 102 | + Diag << FixItHint::CreateReplacement(T.Range, T.Replacement); |
95 | - case transformer::EditKind::Range: | 103 | + |
96 | - Diag << FixItHint::CreateReplacement(T.Range, T.Replacement); | 104 | + for (const auto &I : Case.AddedIncludes) { |
97 | - break; | 105 | + Diag << Inserter->CreateIncludeInsertion( |
98 | - case transformer::EditKind::AddInclude: { | 106 | + Result.SourceManager->getMainFileID(), I.first, |
99 | - StringRef FileName = T.Replacement; | 107 | + /*IsAngled=*/I.second == transformer::IncludeFormat::Angled); |
100 | - bool IsAngled = FileName.startswith("<") && FileName.endswith(">"); | 108 | + } |
101 | - Diag << Inserter.createMainFileIncludeInsertion( | ||
102 | - IsAngled ? FileName.substr(1, FileName.size() - 2) : FileName, | ||
103 | - IsAngled); | ||
104 | - break; | ||
105 | - } | ||
106 | - } | ||
107 | } | 109 | } |
108 | 110 | ||
109 | void TransformerClangTidyCheck::storeOptions( | 111 | void TransformerClangTidyCheck::storeOptions( |
110 | ClangTidyOptions::OptionMap &Opts) { | 112 | ClangTidyOptions::OptionMap &Opts) { |
111 | - Options.store(Opts, "IncludeStyle", Inserter.getStyle()); | 113 | + Options.store(Opts, "IncludeStyle", IncludeStyle); |
112 | } | 114 | } |
113 | 115 | ||
114 | } // namespace utils | 116 | } // namespace utils | ... | ... |
... | @@ -70,7 +70,8 @@ public: | ... | @@ -70,7 +70,8 @@ public: |
70 | 70 | ||
71 | private: | 71 | private: |
72 | Optional<transformer::RewriteRule> Rule; | 72 | Optional<transformer::RewriteRule> Rule; |
73 | - IncludeInserter Inserter; | 73 | + const IncludeSorter::IncludeStyle IncludeStyle; |
74 | + std::unique_ptr<IncludeInserter> Inserter; | ||
74 | }; | 75 | }; |
75 | 76 | ||
76 | } // namespace utils | 77 | } // namespace utils | ... | ... |
... | @@ -15,7 +15,6 @@ if (NOT DEFINED CLANGD_BUILD_XPC) | ... | @@ -15,7 +15,6 @@ if (NOT DEFINED CLANGD_BUILD_XPC) |
15 | endif () | 15 | endif () |
16 | 16 | ||
17 | llvm_canonicalize_cmake_booleans(CLANGD_BUILD_XPC) | 17 | llvm_canonicalize_cmake_booleans(CLANGD_BUILD_XPC) |
18 | -llvm_canonicalize_cmake_booleans(CLANGD_ENABLE_REMOTE) | ||
19 | 18 | ||
20 | configure_file( | 19 | configure_file( |
21 | ${CMAKE_CURRENT_SOURCE_DIR}/Features.inc.in | 20 | ${CMAKE_CURRENT_SOURCE_DIR}/Features.inc.in |
... | @@ -28,15 +27,6 @@ set(LLVM_LINK_COMPONENTS | ... | @@ -28,15 +27,6 @@ set(LLVM_LINK_COMPONENTS |
28 | FrontendOpenMP | 27 | FrontendOpenMP |
29 | Option | 28 | Option |
30 | ) | 29 | ) |
31 | - | ||
32 | -include(${CMAKE_CURRENT_SOURCE_DIR}/quality/CompletionModel.cmake) | ||
33 | -gen_decision_forest(${CMAKE_CURRENT_SOURCE_DIR}/quality/model CompletionModel clang::clangd::Example) | ||
34 | - | ||
35 | -if(MSVC AND NOT CLANG_CL) | ||
36 | - set_source_files_properties(CompileCommands.cpp PROPERTIES COMPILE_FLAGS -wd4130) # disables C4130: logical operation on address of string constant | ||
37 | -endif() | ||
38 | - | ||
39 | -include_directories(BEFORE "${CMAKE_CURRENT_BINARY_DIR}/../clang-tidy") | ||
40 | 30 | ||
41 | add_clang_library(clangDaemon | 31 | add_clang_library(clangDaemon |
42 | AST.cpp | 32 | AST.cpp |
... | @@ -80,7 +70,6 @@ add_clang_library(clangDaemon | ... | @@ -80,7 +70,6 @@ add_clang_library(clangDaemon |
80 | TUScheduler.cpp | 70 | TUScheduler.cpp |
81 | URI.cpp | 71 | URI.cpp |
82 | XRefs.cpp | 72 | XRefs.cpp |
83 | - ${CMAKE_CURRENT_BINARY_DIR}/CompletionModel.cpp | ||
84 | 73 | ||
85 | index/Background.cpp | 74 | index/Background.cpp |
86 | index/BackgroundIndexLoader.cpp | 75 | index/BackgroundIndexLoader.cpp |
... | @@ -121,11 +110,6 @@ add_clang_library(clangDaemon | ... | @@ -121,11 +110,6 @@ add_clang_library(clangDaemon |
121 | omp_gen | 110 | omp_gen |
122 | ) | 111 | ) |
123 | 112 | ||
124 | -# Include generated CompletionModel headers. | ||
125 | -target_include_directories(clangDaemon PUBLIC | ||
126 | - $<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}> | ||
127 | -) | ||
128 | - | ||
129 | clang_target_link_libraries(clangDaemon | 113 | clang_target_link_libraries(clangDaemon |
130 | PRIVATE | 114 | PRIVATE |
131 | clangAST | 115 | clangAST | ... | ... |
This diff is collapsed. Click to expand it.
... | @@ -36,24 +36,17 @@ class SymbolIndex; | ... | @@ -36,24 +36,17 @@ class SymbolIndex; |
36 | /// The server also supports $/cancelRequest (MessageHandler provides this). | 36 | /// The server also supports $/cancelRequest (MessageHandler provides this). |
37 | class ClangdLSPServer : private ClangdServer::Callbacks { | 37 | class ClangdLSPServer : private ClangdServer::Callbacks { |
38 | public: | 38 | public: |
39 | - struct Options : ClangdServer::Options { | 39 | + /// If \p CompileCommandsDir has a value, compile_commands.json will be |
40 | - /// Look for compilation databases, rather than using compile commands | 40 | + /// loaded only from \p CompileCommandsDir. Otherwise, clangd will look |
41 | - /// set via LSP (extensions) only. | 41 | + /// for compile_commands.json in all parent directories of each file. |
42 | - bool UseDirBasedCDB = true; | 42 | + /// If UseDirBasedCDB is false, compile commands are not read from disk. |
43 | - /// A fixed directory to search for a compilation database in. | 43 | + // FIXME: Clean up signature around CDBs. |
44 | - /// If not set, we search upward from the source file. | ||
45 | - llvm::Optional<Path> CompileCommandsDir; | ||
46 | - /// The offset-encoding to use, or None to negotiate it over LSP. | ||
47 | - llvm::Optional<OffsetEncoding> Encoding; | ||
48 | - | ||
49 | - /// Per-feature options. Generally ClangdServer lets these vary | ||
50 | - /// per-request, but LSP allows limited/no customizations. | ||
51 | - clangd::CodeCompleteOptions CodeComplete; | ||
52 | - clangd::RenameOptions Rename; | ||
53 | - }; | ||
54 | - | ||
55 | ClangdLSPServer(Transport &Transp, const ThreadsafeFS &TFS, | 44 | ClangdLSPServer(Transport &Transp, const ThreadsafeFS &TFS, |
56 | - const ClangdLSPServer::Options &Opts); | 45 | + const clangd::CodeCompleteOptions &CCOpts, |
46 | + const clangd::RenameOptions &RenameOpts, | ||
47 | + llvm::Optional<Path> CompileCommandsDir, bool UseDirBasedCDB, | ||
48 | + llvm::Optional<OffsetEncoding> ForcedOffsetEncoding, | ||
49 | + const ClangdServer::Options &Opts); | ||
57 | /// The destructor blocks on any outstanding background tasks. | 50 | /// The destructor blocks on any outstanding background tasks. |
58 | ~ClangdLSPServer(); | 51 | ~ClangdLSPServer(); |
59 | 52 | ||
... | @@ -187,39 +180,22 @@ private: | ... | @@ -187,39 +180,22 @@ private: |
187 | std::unique_ptr<MessageHandler> MsgHandler; | 180 | std::unique_ptr<MessageHandler> MsgHandler; |
188 | std::mutex TranspWriter; | 181 | std::mutex TranspWriter; |
189 | 182 | ||
190 | - template <typename T> | ||
191 | - static Expected<T> parse(const llvm::json::Value &Raw, | ||
192 | - llvm::StringRef PayloadName, | ||
193 | - llvm::StringRef PayloadKind) { | ||
194 | - T Result; | ||
195 | - llvm::json::Path::Root Root; | ||
196 | - if (!fromJSON(Raw, Result, Root)) { | ||
197 | - elog("Failed to decode {0} {1}: {2}", PayloadName, PayloadKind, | ||
198 | - Root.getError()); | ||
199 | - // Dump the relevant parts of the broken message. | ||
200 | - std::string Context; | ||
201 | - llvm::raw_string_ostream OS(Context); | ||
202 | - Root.printErrorContext(Raw, OS); | ||
203 | - vlog("{0}", OS.str()); | ||
204 | - // Report the error (e.g. to the client). | ||
205 | - return llvm::make_error<LSPError>( | ||
206 | - llvm::formatv("failed to decode {0} {1}: {2}", PayloadName, | ||
207 | - PayloadKind, fmt_consume(Root.getError())), | ||
208 | - ErrorCode::InvalidParams); | ||
209 | - } | ||
210 | - return std::move(Result); | ||
211 | - } | ||
212 | - | ||
213 | template <typename Response> | 183 | template <typename Response> |
214 | void call(StringRef Method, llvm::json::Value Params, Callback<Response> CB) { | 184 | void call(StringRef Method, llvm::json::Value Params, Callback<Response> CB) { |
215 | // Wrap the callback with LSP conversion and error-handling. | 185 | // Wrap the callback with LSP conversion and error-handling. |
216 | auto HandleReply = | 186 | auto HandleReply = |
217 | - [CB = std::move(CB), Ctx = Context::current().clone(), | 187 | + [CB = std::move(CB), Ctx = Context::current().clone()]( |
218 | - Method = Method.str()]( | ||
219 | llvm::Expected<llvm::json::Value> RawResponse) mutable { | 188 | llvm::Expected<llvm::json::Value> RawResponse) mutable { |
220 | - if (!RawResponse) | 189 | + Response Rsp; |
221 | - return CB(RawResponse.takeError()); | 190 | + if (!RawResponse) { |
222 | - CB(parse<Response>(*RawResponse, Method, "response")); | 191 | + CB(RawResponse.takeError()); |
192 | + } else if (fromJSON(*RawResponse, Rsp)) { | ||
193 | + CB(std::move(Rsp)); | ||
194 | + } else { | ||
195 | + elog("Failed to decode {0} response", *RawResponse); | ||
196 | + CB(llvm::make_error<LSPError>("failed to decode response", | ||
197 | + ErrorCode::InvalidParams)); | ||
198 | + } | ||
223 | }; | 199 | }; |
224 | callRaw(Method, std::move(Params), std::move(HandleReply)); | 200 | callRaw(Method, std::move(Params), std::move(HandleReply)); |
225 | } | 201 | } |
... | @@ -234,6 +210,10 @@ private: | ... | @@ -234,6 +210,10 @@ private: |
234 | } | 210 | } |
235 | 211 | ||
236 | const ThreadsafeFS &TFS; | 212 | const ThreadsafeFS &TFS; |
213 | + /// Options used for code completion | ||
214 | + clangd::CodeCompleteOptions CCOpts; | ||
215 | + /// Options used for rename. | ||
216 | + clangd::RenameOptions RenameOpts; | ||
237 | /// Options used for diagnostics. | 217 | /// Options used for diagnostics. |
238 | ClangdDiagnosticOptions DiagOpts; | 218 | ClangdDiagnosticOptions DiagOpts; |
239 | /// The supported kinds of the client. | 219 | /// The supported kinds of the client. |
... | @@ -271,11 +251,14 @@ private: | ... | @@ -271,11 +251,14 @@ private: |
271 | // Store of the current versions of the open documents. | 251 | // Store of the current versions of the open documents. |
272 | DraftStore DraftMgr; | 252 | DraftStore DraftMgr; |
273 | 253 | ||
274 | - Options Opts; | ||
275 | // The CDB is created by the "initialize" LSP method. | 254 | // The CDB is created by the "initialize" LSP method. |
255 | + bool UseDirBasedCDB; // FIXME: make this a capability. | ||
256 | + llvm::Optional<Path> CompileCommandsDir; // FIXME: merge with capability? | ||
276 | std::unique_ptr<GlobalCompilationDatabase> BaseCDB; | 257 | std::unique_ptr<GlobalCompilationDatabase> BaseCDB; |
277 | // CDB is BaseCDB plus any commands overridden via LSP extensions. | 258 | // CDB is BaseCDB plus any commands overridden via LSP extensions. |
278 | llvm::Optional<OverlayCDB> CDB; | 259 | llvm::Optional<OverlayCDB> CDB; |
260 | + ClangdServer::Options ClangdServerOpts; | ||
261 | + llvm::Optional<OffsetEncoding> NegotiatedOffsetEncoding; | ||
279 | // The ClangdServer is created by the "initialize" LSP method. | 262 | // The ClangdServer is created by the "initialize" LSP method. |
280 | llvm::Optional<ClangdServer> Server; | 263 | llvm::Optional<ClangdServer> Server; |
281 | }; | 264 | }; | ... | ... |
This diff is collapsed. Click to expand it.
... | @@ -111,9 +111,6 @@ public: | ... | @@ -111,9 +111,6 @@ public: |
111 | /// on background threads. The index is stored in the project root. | 111 | /// on background threads. The index is stored in the project root. |
112 | bool BackgroundIndex = false; | 112 | bool BackgroundIndex = false; |
113 | 113 | ||
114 | - /// Store refs to main-file symbols in the index. | ||
115 | - bool CollectMainFileRefs = false; | ||
116 | - | ||
117 | /// If set, use this index to augment code completion results. | 114 | /// If set, use this index to augment code completion results. |
118 | SymbolIndex *StaticIndex = nullptr; | 115 | SymbolIndex *StaticIndex = nullptr; |
119 | 116 | ||
... | @@ -131,7 +128,7 @@ public: | ... | @@ -131,7 +128,7 @@ public: |
131 | bool BuildRecoveryAST = true; | 128 | bool BuildRecoveryAST = true; |
132 | 129 | ||
133 | /// If true, turn on the `-frecovery-ast-type` clang flag. | 130 | /// If true, turn on the `-frecovery-ast-type` clang flag. |
134 | - bool PreserveRecoveryASTType = true; | 131 | + bool PreserveRecoveryASTType = false; |
135 | 132 | ||
136 | /// Clangd's workspace root. Relevant for "workspace" operations not bound | 133 | /// Clangd's workspace root. Relevant for "workspace" operations not bound |
137 | /// to a particular file. | 134 | /// to a particular file. |
... | @@ -273,12 +270,9 @@ public: | ... | @@ -273,12 +270,9 @@ public: |
273 | StringRef TriggerText, Callback<std::vector<TextEdit>> CB); | 270 | StringRef TriggerText, Callback<std::vector<TextEdit>> CB); |
274 | 271 | ||
275 | /// Test the validity of a rename operation. | 272 | /// Test the validity of a rename operation. |
276 | - /// | ||
277 | - /// The returned result describes edits in the main-file only (all | ||
278 | - /// occurrences of the renamed symbol are simply deleted. | ||
279 | void prepareRename(PathRef File, Position Pos, | 273 | void prepareRename(PathRef File, Position Pos, |
280 | const RenameOptions &RenameOpts, | 274 | const RenameOptions &RenameOpts, |
281 | - Callback<RenameResult> CB); | 275 | + Callback<llvm::Optional<Range>> CB); |
282 | 276 | ||
283 | /// Rename all occurrences of the symbol at the \p Pos in \p File to | 277 | /// Rename all occurrences of the symbol at the \p Pos in \p File to |
284 | /// \p NewName. | 278 | /// \p NewName. |
... | @@ -286,12 +280,12 @@ public: | ... | @@ -286,12 +280,12 @@ public: |
286 | /// embedders could use this method to get all occurrences of the symbol (e.g. | 280 | /// embedders could use this method to get all occurrences of the symbol (e.g. |
287 | /// highlighting them in prepare stage). | 281 | /// highlighting them in prepare stage). |
288 | void rename(PathRef File, Position Pos, llvm::StringRef NewName, | 282 | void rename(PathRef File, Position Pos, llvm::StringRef NewName, |
289 | - const RenameOptions &Opts, Callback<RenameResult> CB); | 283 | + const RenameOptions &Opts, Callback<FileEdits> CB); |
290 | 284 | ||
291 | struct TweakRef { | 285 | struct TweakRef { |
292 | std::string ID; /// ID to pass for applyTweak. | 286 | std::string ID; /// ID to pass for applyTweak. |
293 | std::string Title; /// A single-line message to show in the UI. | 287 | std::string Title; /// A single-line message to show in the UI. |
294 | - llvm::StringLiteral Kind; | 288 | + Tweak::Intent Intent; |
295 | }; | 289 | }; |
296 | /// Enumerate the code tweaks available to the user at a specified point. | 290 | /// Enumerate the code tweaks available to the user at a specified point. |
297 | void enumerateTweaks(PathRef File, Range Sel, | 291 | void enumerateTweaks(PathRef File, Range Sel, |
... | @@ -301,6 +295,10 @@ public: | ... | @@ -301,6 +295,10 @@ public: |
301 | void applyTweak(PathRef File, Range Sel, StringRef ID, | 295 | void applyTweak(PathRef File, Range Sel, StringRef ID, |
302 | Callback<Tweak::Effect> CB); | 296 | Callback<Tweak::Effect> CB); |
303 | 297 | ||
298 | + /// Only for testing purposes. | ||
299 | + /// Waits until all requests to worker thread are finished and dumps AST for | ||
300 | + /// \p File. \p File must be in the list of added documents. | ||
301 | + void dumpAST(PathRef File, llvm::unique_function<void(std::string)> Callback); | ||
304 | /// Called when an event occurs for a watched file in the workspace. | 302 | /// Called when an event occurs for a watched file in the workspace. |
305 | void onFileEvent(const DidChangeWatchedFilesParams &Params); | 303 | void onFileEvent(const DidChangeWatchedFilesParams &Params); |
306 | 304 | ||
... | @@ -319,13 +317,6 @@ public: | ... | @@ -319,13 +317,6 @@ public: |
319 | void semanticHighlights(PathRef File, | 317 | void semanticHighlights(PathRef File, |
320 | Callback<std::vector<HighlightingToken>>); | 318 | Callback<std::vector<HighlightingToken>>); |
321 | 319 | ||
322 | - /// Runs an arbitrary action that has access to the AST of the specified file. | ||
323 | - /// The action will execute on one of ClangdServer's internal threads. | ||
324 | - /// The AST is only valid for the duration of the callback. | ||
325 | - /// As with other actions, the file must have been opened. | ||
326 | - void customAction(PathRef File, llvm::StringRef Name, | ||
327 | - Callback<InputsAndAST> Action); | ||
328 | - | ||
329 | /// Returns estimated memory usage and other statistics for each of the | 320 | /// Returns estimated memory usage and other statistics for each of the |
330 | /// currently open files. | 321 | /// currently open files. |
331 | /// Overall memory usage of clangd may be significantly more than reported | 322 | /// Overall memory usage of clangd may be significantly more than reported | ... | ... |
... | @@ -333,7 +333,8 @@ struct CodeCompletionBuilder { | ... | @@ -333,7 +333,8 @@ struct CodeCompletionBuilder { |
333 | return ResolvedInserted.takeError(); | 333 | return ResolvedInserted.takeError(); |
334 | auto Spelled = Includes.calculateIncludePath(*ResolvedInserted, FileName); | 334 | auto Spelled = Includes.calculateIncludePath(*ResolvedInserted, FileName); |
335 | if (!Spelled) | 335 | if (!Spelled) |
336 | - return error("Header not on include path"); | 336 | + return llvm::createStringError(llvm::inconvertibleErrorCode(), |
337 | + "Header not on include path"); | ||
337 | return std::make_pair( | 338 | return std::make_pair( |
338 | std::move(*Spelled), | 339 | std::move(*Spelled), |
339 | Includes.shouldInsertInclude(*ResolvedDeclaring, *ResolvedInserted)); | 340 | Includes.shouldInsertInclude(*ResolvedDeclaring, *ResolvedInserted)); |
... | @@ -1616,52 +1617,13 @@ private: | ... | @@ -1616,52 +1617,13 @@ private: |
1616 | 1617 | ||
1617 | llvm::Optional<float> fuzzyScore(const CompletionCandidate &C) { | 1618 | llvm::Optional<float> fuzzyScore(const CompletionCandidate &C) { |
1618 | // Macros can be very spammy, so we only support prefix completion. | 1619 | // Macros can be very spammy, so we only support prefix completion. |
1619 | - if (((C.SemaResult && | 1620 | + // We won't end up with underfull index results, as macros are sema-only. |
1620 | - C.SemaResult->Kind == CodeCompletionResult::RK_Macro) || | 1621 | + if (C.SemaResult && C.SemaResult->Kind == CodeCompletionResult::RK_Macro && |
1621 | - (C.IndexResult && | ||
1622 | - C.IndexResult->SymInfo.Kind == index::SymbolKind::Macro)) && | ||
1623 | !C.Name.startswith_lower(Filter->pattern())) | 1622 | !C.Name.startswith_lower(Filter->pattern())) |
1624 | return None; | 1623 | return None; |
1625 | return Filter->match(C.Name); | 1624 | return Filter->match(C.Name); |
1626 | } | 1625 | } |
1627 | 1626 | ||
1628 | - CodeCompletion::Scores | ||
1629 | - evaluateCompletion(const SymbolQualitySignals &Quality, | ||
1630 | - const SymbolRelevanceSignals &Relevance) { | ||
1631 | - using RM = CodeCompleteOptions::CodeCompletionRankingModel; | ||
1632 | - CodeCompletion::Scores Scores; | ||
1633 | - switch (Opts.RankingModel) { | ||
1634 | - case RM::Heuristics: | ||
1635 | - Scores.Quality = Quality.evaluateHeuristics(); | ||
1636 | - Scores.Relevance = Relevance.evaluateHeuristics(); | ||
1637 | - Scores.Total = | ||
1638 | - evaluateSymbolAndRelevance(Scores.Quality, Scores.Relevance); | ||
1639 | - // NameMatch is in fact a multiplier on total score, so rescoring is | ||
1640 | - // sound. | ||
1641 | - Scores.ExcludingName = Relevance.NameMatch | ||
1642 | - ? Scores.Total / Relevance.NameMatch | ||
1643 | - : Scores.Quality; | ||
1644 | - return Scores; | ||
1645 | - | ||
1646 | - case RM::DecisionForest: | ||
1647 | - Scores.Quality = 0; | ||
1648 | - Scores.Relevance = 0; | ||
1649 | - // Exponentiating DecisionForest prediction makes the score of each tree a | ||
1650 | - // multiplciative boost (like NameMatch). This allows us to weigh the | ||
1651 | - // prediciton score and NameMatch appropriately. | ||
1652 | - Scores.ExcludingName = pow(Opts.DecisionForestBase, | ||
1653 | - evaluateDecisionForest(Quality, Relevance)); | ||
1654 | - // NeedsFixIts is not part of the DecisionForest as generating training | ||
1655 | - // data that needs fixits is not-feasible. | ||
1656 | - if (Relevance.NeedsFixIts) | ||
1657 | - Scores.ExcludingName *= 0.5; | ||
1658 | - // NameMatch should be a multiplier on total score to support rescoring. | ||
1659 | - Scores.Total = Relevance.NameMatch * Scores.ExcludingName; | ||
1660 | - return Scores; | ||
1661 | - } | ||
1662 | - llvm_unreachable("Unhandled CodeCompletion ranking model."); | ||
1663 | - } | ||
1664 | - | ||
1665 | // Scores a candidate and adds it to the TopN structure. | 1627 | // Scores a candidate and adds it to the TopN structure. |
1666 | void addCandidate(TopN<ScoredBundle, ScoredBundleGreater> &Candidates, | 1628 | void addCandidate(TopN<ScoredBundle, ScoredBundleGreater> &Candidates, |
1667 | CompletionCandidate::Bundle Bundle) { | 1629 | CompletionCandidate::Bundle Bundle) { |
... | @@ -1669,7 +1631,6 @@ private: | ... | @@ -1669,7 +1631,6 @@ private: |
1669 | SymbolRelevanceSignals Relevance; | 1631 | SymbolRelevanceSignals Relevance; |
1670 | Relevance.Context = CCContextKind; | 1632 | Relevance.Context = CCContextKind; |
1671 | Relevance.Name = Bundle.front().Name; | 1633 | Relevance.Name = Bundle.front().Name; |
1672 | - Relevance.FilterLength = HeuristicPrefix.Name.size(); | ||
1673 | Relevance.Query = SymbolRelevanceSignals::CodeComplete; | 1634 | Relevance.Query = SymbolRelevanceSignals::CodeComplete; |
1674 | Relevance.FileProximityMatch = FileProximity.getPointer(); | 1635 | Relevance.FileProximityMatch = FileProximity.getPointer(); |
1675 | if (ScopeProximity) | 1636 | if (ScopeProximity) |
... | @@ -1718,7 +1679,15 @@ private: | ... | @@ -1718,7 +1679,15 @@ private: |
1718 | } | 1679 | } |
1719 | } | 1680 | } |
1720 | 1681 | ||
1721 | - CodeCompletion::Scores Scores = evaluateCompletion(Quality, Relevance); | 1682 | + CodeCompletion::Scores Scores; |
1683 | + Scores.Quality = Quality.evaluate(); | ||
1684 | + Scores.Relevance = Relevance.evaluate(); | ||
1685 | + Scores.Total = evaluateSymbolAndRelevance(Scores.Quality, Scores.Relevance); | ||
1686 | + // NameMatch is in fact a multiplier on total score, so rescoring is sound. | ||
1687 | + Scores.ExcludingName = Relevance.NameMatch | ||
1688 | + ? Scores.Total / Relevance.NameMatch | ||
1689 | + : Scores.Quality; | ||
1690 | + | ||
1722 | if (Opts.RecordCCResult) | 1691 | if (Opts.RecordCCResult) |
1723 | Opts.RecordCCResult(toCodeCompletion(Bundle), Quality, Relevance, | 1692 | Opts.RecordCCResult(toCodeCompletion(Bundle), Quality, Relevance, |
1724 | Scores.Total); | 1693 | Scores.Total); | ... | ... |
... | @@ -147,22 +147,6 @@ struct CodeCompleteOptions { | ... | @@ -147,22 +147,6 @@ struct CodeCompleteOptions { |
147 | std::function<void(const CodeCompletion &, const SymbolQualitySignals &, | 147 | std::function<void(const CodeCompletion &, const SymbolQualitySignals &, |
148 | const SymbolRelevanceSignals &, float Score)> | 148 | const SymbolRelevanceSignals &, float Score)> |
149 | RecordCCResult; | 149 | RecordCCResult; |
150 | - | ||
151 | - /// Model to use for ranking code completion candidates. | ||
152 | - enum CodeCompletionRankingModel { | ||
153 | - Heuristics, | ||
154 | - DecisionForest, | ||
155 | - } RankingModel = Heuristics; | ||
156 | - | ||
157 | - /// Weight for combining NameMatch and Prediction of DecisionForest. | ||
158 | - /// CompletionScore is NameMatch * pow(Base, Prediction). | ||
159 | - /// The optimal value of Base largely depends on the semantics of the model | ||
160 | - /// and prediction score (e.g. algorithm used during training, number of | ||
161 | - /// trees, etc.). Usually if the range of Prediciton is [-20, 20] then a Base | ||
162 | - /// in [1.2, 1.7] works fine. | ||
163 | - /// Semantics: E.g. the completion score reduces by 50% if the Prediciton | ||
164 | - /// score is reduced by 2.6 points for Base = 1.3. | ||
165 | - float DecisionForestBase = 1.3f; | ||
166 | }; | 150 | }; |
167 | 151 | ||
168 | // Semi-structured representation of a code-complete suggestion for our C++ API. | 152 | // Semi-structured representation of a code-complete suggestion for our C++ API. | ... | ... |
... | @@ -12,7 +12,6 @@ | ... | @@ -12,7 +12,6 @@ |
12 | #include "clang/AST/RawCommentList.h" | 12 | #include "clang/AST/RawCommentList.h" |
13 | #include "clang/Basic/SourceManager.h" | 13 | #include "clang/Basic/SourceManager.h" |
14 | #include "clang/Sema/CodeCompleteConsumer.h" | 14 | #include "clang/Sema/CodeCompleteConsumer.h" |
15 | -#include "llvm/Support/JSON.h" | ||
16 | #include <limits> | 15 | #include <limits> |
17 | #include <utility> | 16 | #include <utility> |
18 | 17 | ||
... | @@ -87,12 +86,7 @@ std::string getDeclComment(const ASTContext &Ctx, const NamedDecl &Decl) { | ... | @@ -87,12 +86,7 @@ std::string getDeclComment(const ASTContext &Ctx, const NamedDecl &Decl) { |
87 | assert(!Ctx.getSourceManager().isLoadedSourceLocation(RC->getBeginLoc())); | 86 | assert(!Ctx.getSourceManager().isLoadedSourceLocation(RC->getBeginLoc())); |
88 | std::string Doc = | 87 | std::string Doc = |
89 | RC->getFormattedText(Ctx.getSourceManager(), Ctx.getDiagnostics()); | 88 | RC->getFormattedText(Ctx.getSourceManager(), Ctx.getDiagnostics()); |
90 | - if (!looksLikeDocComment(Doc)) | 89 | + return looksLikeDocComment(Doc) ? Doc : ""; |
91 | - return ""; | ||
92 | - // Clang requires source to be UTF-8, but doesn't enforce this in comments. | ||
93 | - if (!llvm::json::isUTF8(Doc)) | ||
94 | - Doc = llvm::json::fixUTF8(Doc); | ||
95 | - return Doc; | ||
96 | } | 90 | } |
97 | 91 | ||
98 | void getSignature(const CodeCompletionString &CCS, std::string *Signature, | 92 | void getSignature(const CodeCompletionString &CCS, std::string *Signature, | ... | ... |
... | @@ -271,7 +271,6 @@ std::pair<unsigned, unsigned> getArgCount(const llvm::opt::Option &Opt) { | ... | @@ -271,7 +271,6 @@ std::pair<unsigned, unsigned> getArgCount(const llvm::opt::Option &Opt) { |
271 | case Option::RemainingArgsJoinedClass: | 271 | case Option::RemainingArgsJoinedClass: |
272 | return {Rest, Rest}; | 272 | return {Rest, Rest}; |
273 | } | 273 | } |
274 | - llvm_unreachable("Unhandled option kind"); | ||
275 | } | 274 | } |
276 | 275 | ||
277 | // Flag-parsing mode, which affects which flags are available. | 276 | // Flag-parsing mode, which affects which flags are available. |
... | @@ -322,7 +321,7 @@ unsigned char getModes(const llvm::opt::Option &Opt) { | ... | @@ -322,7 +321,7 @@ unsigned char getModes(const llvm::opt::Option &Opt) { |
322 | } | 321 | } |
323 | } | 322 | } |
324 | return Result; | 323 | return Result; |
325 | -} | 324 | +}; |
326 | 325 | ||
327 | } // namespace | 326 | } // namespace |
328 | 327 | ||
... | @@ -476,7 +475,7 @@ void ArgStripper::process(std::vector<std::string> &Args) const { | ... | @@ -476,7 +475,7 @@ void ArgStripper::process(std::vector<std::string> &Args) const { |
476 | bool WasXclang = false; | 475 | bool WasXclang = false; |
477 | while (Read < Args.size()) { | 476 | while (Read < Args.size()) { |
478 | unsigned ArgCount = 0; | 477 | unsigned ArgCount = 0; |
479 | - if (matchingRule(Args[Read], CurrentMode, ArgCount)) { | 478 | + if (const Rule *R = matchingRule(Args[Read], CurrentMode, ArgCount)) { |
480 | // Delete it and its args. | 479 | // Delete it and its args. |
481 | if (WasXclang) { | 480 | if (WasXclang) { |
482 | assert(Write > 0); | 481 | assert(Write > 0); | ... | ... |
... | @@ -78,8 +78,6 @@ buildCompilerInvocation(const ParseInputs &Inputs, clang::DiagnosticConsumer &D, | ... | @@ -78,8 +78,6 @@ buildCompilerInvocation(const ParseInputs &Inputs, clang::DiagnosticConsumer &D, |
78 | CI->getPreprocessorOpts().PCHThroughHeader.clear(); | 78 | CI->getPreprocessorOpts().PCHThroughHeader.clear(); |
79 | CI->getPreprocessorOpts().PCHWithHdrStop = false; | 79 | CI->getPreprocessorOpts().PCHWithHdrStop = false; |
80 | CI->getPreprocessorOpts().PCHWithHdrStopCreate = false; | 80 | CI->getPreprocessorOpts().PCHWithHdrStopCreate = false; |
81 | - // Don't crash on `#pragma clang __debug parser_crash` | ||
82 | - CI->getPreprocessorOpts().DisablePragmaDebugCrash = true; | ||
83 | 81 | ||
84 | // Recovery expression currently only works for C++. | 82 | // Recovery expression currently only works for C++. |
85 | if (CI->getLangOpts()->CPlusPlus) { | 83 | if (CI->getLangOpts()->CPlusPlus) { | ... | ... |
... | @@ -62,14 +62,6 @@ struct Config { | ... | @@ -62,14 +62,6 @@ struct Config { |
62 | /// Whether this TU should be indexed. | 62 | /// Whether this TU should be indexed. |
63 | BackgroundPolicy Background = BackgroundPolicy::Build; | 63 | BackgroundPolicy Background = BackgroundPolicy::Build; |
64 | } Index; | 64 | } Index; |
65 | - | ||
66 | - /// Style of the codebase. | ||
67 | - struct { | ||
68 | - // Namespaces that should always be fully qualified, meaning no "using" | ||
69 | - // declarations, always spell out the whole name (with or without leading | ||
70 | - // ::). All nested namespaces are affected as well. | ||
71 | - std::vector<std::string> FullyQualifiedNamespaces; | ||
72 | - } Style; | ||
73 | }; | 65 | }; |
74 | 66 | ||
75 | } // namespace clangd | 67 | } // namespace clangd | ... | ... |
... | @@ -208,25 +208,6 @@ struct FragmentCompiler { | ... | @@ -208,25 +208,6 @@ struct FragmentCompiler { |
208 | } | 208 | } |
209 | } | 209 | } |
210 | 210 | ||
211 | - void compile(Fragment::StyleBlock &&F) { | ||
212 | - if (!F.FullyQualifiedNamespaces.empty()) { | ||
213 | - std::vector<std::string> FullyQualifiedNamespaces; | ||
214 | - for (auto &N : F.FullyQualifiedNamespaces) { | ||
215 | - // Normalize the data by dropping both leading and trailing :: | ||
216 | - StringRef Namespace(*N); | ||
217 | - Namespace.consume_front("::"); | ||
218 | - Namespace.consume_back("::"); | ||
219 | - FullyQualifiedNamespaces.push_back(Namespace.str()); | ||
220 | - } | ||
221 | - Out.Apply.push_back([FullyQualifiedNamespaces( | ||
222 | - std::move(FullyQualifiedNamespaces))](Config &C) { | ||
223 | - C.Style.FullyQualifiedNamespaces.insert( | ||
224 | - C.Style.FullyQualifiedNamespaces.begin(), | ||
225 | - FullyQualifiedNamespaces.begin(), FullyQualifiedNamespaces.end()); | ||
226 | - }); | ||
227 | - } | ||
228 | - } | ||
229 | - | ||
230 | constexpr static llvm::SourceMgr::DiagKind Error = llvm::SourceMgr::DK_Error; | 211 | constexpr static llvm::SourceMgr::DiagKind Error = llvm::SourceMgr::DK_Error; |
231 | constexpr static llvm::SourceMgr::DiagKind Warning = | 212 | constexpr static llvm::SourceMgr::DiagKind Warning = |
232 | llvm::SourceMgr::DK_Warning; | 213 | llvm::SourceMgr::DK_Warning; | ... | ... |
... | @@ -161,16 +161,6 @@ struct Fragment { | ... | @@ -161,16 +161,6 @@ struct Fragment { |
161 | llvm::Optional<Located<std::string>> Background; | 161 | llvm::Optional<Located<std::string>> Background; |
162 | }; | 162 | }; |
163 | IndexBlock Index; | 163 | IndexBlock Index; |
164 | - | ||
165 | - // Describes the style of the codebase, beyond formatting. | ||
166 | - struct StyleBlock { | ||
167 | - // Namespaces that should always be fully qualified, meaning no "using" | ||
168 | - // declarations, always spell out the whole name (with or without leading | ||
169 | - // ::). All nested namespaces are affected as well. | ||
170 | - // Affects availability of the AddUsing tweak. | ||
171 | - std::vector<Located<std::string>> FullyQualifiedNamespaces; | ||
172 | - }; | ||
173 | - StyleBlock Style; | ||
174 | }; | 164 | }; |
175 | 165 | ||
176 | } // namespace config | 166 | } // namespace config | ... | ... |
... | @@ -209,11 +209,7 @@ Provider::combine(std::vector<const Provider *> Providers) { | ... | @@ -209,11 +209,7 @@ Provider::combine(std::vector<const Provider *> Providers) { |
209 | }; | 209 | }; |
210 | auto Result = std::make_unique<CombinedProvider>(); | 210 | auto Result = std::make_unique<CombinedProvider>(); |
211 | Result->Providers = std::move(Providers); | 211 | Result->Providers = std::move(Providers); |
212 | - // FIXME: This is a workaround for a bug in older versions of clang (< 3.9) | 212 | + return Result; |
213 | - // The constructor that is supposed to allow for Derived to Base | ||
214 | - // conversion does not work. Remove this if we drop support for such | ||
215 | - // configurations. | ||
216 | - return std::unique_ptr<Provider>(Result.release()); | ||
217 | } | 213 | } |
218 | 214 | ||
219 | Config Provider::getConfig(const Params &P, DiagnosticCallback DC) const { | 215 | Config Provider::getConfig(const Params &P, DiagnosticCallback DC) const { | ... | ... |
... | @@ -39,7 +39,6 @@ public: | ... | @@ -39,7 +39,6 @@ public: |
39 | Dict.handle("If", [&](Node &N) { parse(F.If, N); }); | 39 | Dict.handle("If", [&](Node &N) { parse(F.If, N); }); |
40 | Dict.handle("CompileFlags", [&](Node &N) { parse(F.CompileFlags, N); }); | 40 | Dict.handle("CompileFlags", [&](Node &N) { parse(F.CompileFlags, N); }); |
41 | Dict.handle("Index", [&](Node &N) { parse(F.Index, N); }); | 41 | Dict.handle("Index", [&](Node &N) { parse(F.Index, N); }); |
42 | - Dict.handle("Style", [&](Node &N) { parse(F.Style, N); }); | ||
43 | Dict.parse(N); | 42 | Dict.parse(N); |
44 | return !(N.failed() || HadError); | 43 | return !(N.failed() || HadError); |
45 | } | 44 | } |
... | @@ -73,15 +72,6 @@ private: | ... | @@ -73,15 +72,6 @@ private: |
73 | Dict.parse(N); | 72 | Dict.parse(N); |
74 | } | 73 | } |
75 | 74 | ||
76 | - void parse(Fragment::StyleBlock &F, Node &N) { | ||
77 | - DictParser Dict("Style", this); | ||
78 | - Dict.handle("FullyQualifiedNamespaces", [&](Node &N) { | ||
79 | - if (auto Values = scalarValues(N)) | ||
80 | - F.FullyQualifiedNamespaces = std::move(*Values); | ||
81 | - }); | ||
82 | - Dict.parse(N); | ||
83 | - } | ||
84 | - | ||
85 | void parse(Fragment::IndexBlock &F, Node &N) { | 75 | void parse(Fragment::IndexBlock &F, Node &N) { |
86 | DictParser Dict("Index", this); | 76 | DictParser Dict("Index", this); |
87 | Dict.handle("Background", | 77 | Dict.handle("Background", | ... | ... |
... | @@ -411,8 +411,6 @@ void toLSPDiags( | ... | @@ -411,8 +411,6 @@ void toLSPDiags( |
411 | Main.codeActions.emplace(); | 411 | Main.codeActions.emplace(); |
412 | for (const auto &Fix : D.Fixes) | 412 | for (const auto &Fix : D.Fixes) |
413 | Main.codeActions->push_back(toCodeAction(Fix, File)); | 413 | Main.codeActions->push_back(toCodeAction(Fix, File)); |
414 | - if (Main.codeActions->size() == 1) | ||
415 | - Main.codeActions->front().isPreferred = true; | ||
416 | } | 414 | } |
417 | if (Opts.SendDiagnosticCategory && !D.Category.empty()) | 415 | if (Opts.SendDiagnosticCategory && !D.Category.empty()) |
418 | Main.category = D.Category; | 416 | Main.category = D.Category; |
... | @@ -520,17 +518,13 @@ std::vector<Diag> StoreDiags::take(const clang::tidy::ClangTidyContext *Tidy) { | ... | @@ -520,17 +518,13 @@ std::vector<Diag> StoreDiags::take(const clang::tidy::ClangTidyContext *Tidy) { |
520 | } | 518 | } |
521 | 519 | ||
522 | void StoreDiags::BeginSourceFile(const LangOptions &Opts, | 520 | void StoreDiags::BeginSourceFile(const LangOptions &Opts, |
523 | - const Preprocessor *PP) { | 521 | + const Preprocessor *) { |
524 | LangOpts = Opts; | 522 | LangOpts = Opts; |
525 | - if (PP) { | ||
526 | - OrigSrcMgr = &PP->getSourceManager(); | ||
527 | - } | ||
528 | } | 523 | } |
529 | 524 | ||
530 | void StoreDiags::EndSourceFile() { | 525 | void StoreDiags::EndSourceFile() { |
531 | flushLastDiag(); | 526 | flushLastDiag(); |
532 | LangOpts = None; | 527 | LangOpts = None; |
533 | - OrigSrcMgr = nullptr; | ||
534 | } | 528 | } |
535 | 529 | ||
536 | /// Sanitizes a piece for presenting it in a synthesized fix message. Ensures | 530 | /// Sanitizes a piece for presenting it in a synthesized fix message. Ensures |
... | @@ -566,16 +560,6 @@ static void fillNonLocationData(DiagnosticsEngine::Level DiagLevel, | ... | @@ -566,16 +560,6 @@ static void fillNonLocationData(DiagnosticsEngine::Level DiagLevel, |
566 | 560 | ||
567 | void StoreDiags::HandleDiagnostic(DiagnosticsEngine::Level DiagLevel, | 561 | void StoreDiags::HandleDiagnostic(DiagnosticsEngine::Level DiagLevel, |
568 | const clang::Diagnostic &Info) { | 562 | const clang::Diagnostic &Info) { |
569 | - // If the diagnostic was generated for a different SourceManager, skip it. | ||
570 | - // This happens when a module is imported and needs to be implicitly built. | ||
571 | - // The compilation of that module will use the same StoreDiags, but different | ||
572 | - // SourceManager. | ||
573 | - if (OrigSrcMgr && Info.hasSourceManager() && | ||
574 | - OrigSrcMgr != &Info.getSourceManager()) { | ||
575 | - IgnoreDiagnostics::log(DiagLevel, Info); | ||
576 | - return; | ||
577 | - } | ||
578 | - | ||
579 | DiagnosticConsumer::HandleDiagnostic(DiagLevel, Info); | 563 | DiagnosticConsumer::HandleDiagnostic(DiagLevel, Info); |
580 | bool OriginallyError = | 564 | bool OriginallyError = |
581 | Info.getDiags()->getDiagnosticIDs()->isDefaultMappingAsError( | 565 | Info.getDiags()->getDiagnosticIDs()->isDefaultMappingAsError( | ... | ... |
... | @@ -122,8 +122,7 @@ public: | ... | @@ -122,8 +122,7 @@ public: |
122 | // The ClangTidyContext populates Source and Name for clang-tidy diagnostics. | 122 | // The ClangTidyContext populates Source and Name for clang-tidy diagnostics. |
123 | std::vector<Diag> take(const clang::tidy::ClangTidyContext *Tidy = nullptr); | 123 | std::vector<Diag> take(const clang::tidy::ClangTidyContext *Tidy = nullptr); |
124 | 124 | ||
125 | - void BeginSourceFile(const LangOptions &Opts, | 125 | + void BeginSourceFile(const LangOptions &Opts, const Preprocessor *) override; |
126 | - const Preprocessor *PP) override; | ||
127 | void EndSourceFile() override; | 126 | void EndSourceFile() override; |
128 | void HandleDiagnostic(DiagnosticsEngine::Level DiagLevel, | 127 | void HandleDiagnostic(DiagnosticsEngine::Level DiagLevel, |
129 | const clang::Diagnostic &Info) override; | 128 | const clang::Diagnostic &Info) override; |
... | @@ -149,7 +148,6 @@ private: | ... | @@ -149,7 +148,6 @@ private: |
149 | llvm::Optional<Diag> LastDiag; | 148 | llvm::Optional<Diag> LastDiag; |
150 | llvm::Optional<FullSourceLoc> LastDiagLoc; // Valid only when LastDiag is set. | 149 | llvm::Optional<FullSourceLoc> LastDiagLoc; // Valid only when LastDiag is set. |
151 | bool LastDiagOriginallyError = false; // Valid only when LastDiag is set. | 150 | bool LastDiagOriginallyError = false; // Valid only when LastDiag is set. |
152 | - SourceManager *OrigSrcMgr = nullptr; | ||
153 | 151 | ||
154 | llvm::DenseSet<std::pair<unsigned, unsigned>> IncludedErrorLocations; | 152 | llvm::DenseSet<std::pair<unsigned, unsigned>> IncludedErrorLocations; |
155 | bool LastPrimaryDiagnosticWasSuppressed = false; | 153 | bool LastPrimaryDiagnosticWasSuppressed = false; | ... | ... |
... | @@ -64,9 +64,9 @@ llvm::Expected<DraftStore::Draft> DraftStore::updateDraft( | ... | @@ -64,9 +64,9 @@ llvm::Expected<DraftStore::Draft> DraftStore::updateDraft( |
64 | 64 | ||
65 | auto EntryIt = Drafts.find(File); | 65 | auto EntryIt = Drafts.find(File); |
66 | if (EntryIt == Drafts.end()) { | 66 | if (EntryIt == Drafts.end()) { |
67 | - return error(llvm::errc::invalid_argument, | 67 | + return llvm::make_error<llvm::StringError>( |
68 | - "Trying to do incremental update on non-added document: {0}", | 68 | + "Trying to do incremental update on non-added document: " + File, |
69 | - File); | 69 | + llvm::errc::invalid_argument); |
70 | } | 70 | } |
71 | Draft &D = EntryIt->second; | 71 | Draft &D = EntryIt->second; |
72 | std::string Contents = EntryIt->second.Contents; | 72 | std::string Contents = EntryIt->second.Contents; |
... | @@ -89,9 +89,11 @@ llvm::Expected<DraftStore::Draft> DraftStore::updateDraft( | ... | @@ -89,9 +89,11 @@ llvm::Expected<DraftStore::Draft> DraftStore::updateDraft( |
89 | return EndIndex.takeError(); | 89 | return EndIndex.takeError(); |
90 | 90 | ||
91 | if (*EndIndex < *StartIndex) | 91 | if (*EndIndex < *StartIndex) |
92 | - return error(llvm::errc::invalid_argument, | 92 | + return llvm::make_error<llvm::StringError>( |
93 | - "Range's end position ({0}) is before start position ({1})", | 93 | + llvm::formatv( |
94 | - End, Start); | 94 | + "Range's end position ({0}) is before start position ({1})", End, |
95 | + Start), | ||
96 | + llvm::errc::invalid_argument); | ||
95 | 97 | ||
96 | // Since the range length between two LSP positions is dependent on the | 98 | // Since the range length between two LSP positions is dependent on the |
97 | // contents of the buffer we compute the range length between the start and | 99 | // contents of the buffer we compute the range length between the start and |
... | @@ -104,10 +106,11 @@ llvm::Expected<DraftStore::Draft> DraftStore::updateDraft( | ... | @@ -104,10 +106,11 @@ llvm::Expected<DraftStore::Draft> DraftStore::updateDraft( |
104 | lspLength(Contents.substr(*StartIndex, *EndIndex - *StartIndex)); | 106 | lspLength(Contents.substr(*StartIndex, *EndIndex - *StartIndex)); |
105 | 107 | ||
106 | if (Change.rangeLength && ComputedRangeLength != *Change.rangeLength) | 108 | if (Change.rangeLength && ComputedRangeLength != *Change.rangeLength) |
107 | - return error(llvm::errc::invalid_argument, | 109 | + return llvm::make_error<llvm::StringError>( |
108 | - "Change's rangeLength ({0}) doesn't match the " | 110 | + llvm::formatv("Change's rangeLength ({0}) doesn't match the " |
109 | - "computed range length ({1}).", | 111 | + "computed range length ({1}).", |
110 | - *Change.rangeLength, ComputedRangeLength); | 112 | + *Change.rangeLength, ComputedRangeLength), |
113 | + llvm::errc::invalid_argument); | ||
111 | 114 | ||
112 | std::string NewContents; | 115 | std::string NewContents; |
113 | NewContents.reserve(*StartIndex + Change.text.length() + | 116 | NewContents.reserve(*StartIndex + Change.text.length() + | ... | ... |
... | @@ -43,9 +43,12 @@ struct ScoredSymbolGreater { | ... | @@ -43,9 +43,12 @@ struct ScoredSymbolGreater { |
43 | llvm::Expected<Location> indexToLSPLocation(const SymbolLocation &Loc, | 43 | llvm::Expected<Location> indexToLSPLocation(const SymbolLocation &Loc, |
44 | llvm::StringRef TUPath) { | 44 | llvm::StringRef TUPath) { |
45 | auto Path = URI::resolve(Loc.FileURI, TUPath); | 45 | auto Path = URI::resolve(Loc.FileURI, TUPath); |
46 | - if (!Path) | 46 | + if (!Path) { |
47 | - return error("Could not resolve path for file '{0}': {1}", Loc.FileURI, | 47 | + return llvm::make_error<llvm::StringError>( |
48 | - Path.takeError()); | 48 | + llvm::formatv("Could not resolve path for file '{0}': {1}", Loc.FileURI, |
49 | + llvm::toString(Path.takeError())), | ||
50 | + llvm::inconvertibleErrorCode()); | ||
51 | + } | ||
49 | Location L; | 52 | Location L; |
50 | L.uri = URIForFile::canonicalize(*Path, TUPath); | 53 | L.uri = URIForFile::canonicalize(*Path, TUPath); |
51 | Position Start, End; | 54 | Position Start, End; |
... | @@ -116,8 +119,8 @@ getWorkspaceSymbols(llvm::StringRef Query, int Limit, | ... | @@ -116,8 +119,8 @@ getWorkspaceSymbols(llvm::StringRef Query, int Limit, |
116 | return; | 119 | return; |
117 | } | 120 | } |
118 | Relevance.merge(Sym); | 121 | Relevance.merge(Sym); |
119 | - auto Score = evaluateSymbolAndRelevance(Quality.evaluateHeuristics(), | 122 | + auto Score = |
120 | - Relevance.evaluateHeuristics()); | 123 | + evaluateSymbolAndRelevance(Quality.evaluate(), Relevance.evaluate()); |
121 | dlog("FindSymbols: {0}{1} = {2}\n{3}{4}\n", Sym.Scope, Sym.Name, Score, | 124 | dlog("FindSymbols: {0}{1} = {2}\n{3}{4}\n", Sym.Scope, Sym.Name, Score, |
122 | Quality, Relevance); | 125 | Quality, Relevance); |
123 | 126 | ||
... | @@ -185,7 +188,7 @@ public: | ... | @@ -185,7 +188,7 @@ public: |
185 | } | 188 | } |
186 | 189 | ||
187 | private: | 190 | private: |
188 | - enum class VisitKind { No, OnlyDecl, OnlyChildren, DeclAndChildren }; | 191 | + enum class VisitKind { No, OnlyDecl, DeclAndChildren }; |
189 | 192 | ||
190 | void traverseDecl(Decl *D, std::vector<DocumentSymbol> &Results) { | 193 | void traverseDecl(Decl *D, std::vector<DocumentSymbol> &Results) { |
191 | if (auto *Templ = llvm::dyn_cast<TemplateDecl>(D)) { | 194 | if (auto *Templ = llvm::dyn_cast<TemplateDecl>(D)) { |
... | @@ -193,25 +196,18 @@ private: | ... | @@ -193,25 +196,18 @@ private: |
193 | if (auto *TD = Templ->getTemplatedDecl()) | 196 | if (auto *TD = Templ->getTemplatedDecl()) |
194 | D = TD; | 197 | D = TD; |
195 | } | 198 | } |
196 | - | 199 | + auto *ND = llvm::dyn_cast<NamedDecl>(D); |
197 | - VisitKind Visit = shouldVisit(D); | 200 | + if (!ND) |
201 | + return; | ||
202 | + VisitKind Visit = shouldVisit(ND); | ||
198 | if (Visit == VisitKind::No) | 203 | if (Visit == VisitKind::No) |
199 | return; | 204 | return; |
200 | - | 205 | + llvm::Optional<DocumentSymbol> Sym = declToSym(AST.getASTContext(), *ND); |
201 | - if (Visit == VisitKind::OnlyChildren) | ||
202 | - return traverseChildren(D, Results); | ||
203 | - | ||
204 | - auto *ND = llvm::cast<NamedDecl>(D); | ||
205 | - auto Sym = declToSym(AST.getASTContext(), *ND); | ||
206 | if (!Sym) | 206 | if (!Sym) |
207 | return; | 207 | return; |
208 | + if (Visit == VisitKind::DeclAndChildren) | ||
209 | + traverseChildren(D, Sym->children); | ||
208 | Results.push_back(std::move(*Sym)); | 210 | Results.push_back(std::move(*Sym)); |
209 | - | ||
210 | - if (Visit == VisitKind::OnlyDecl) | ||
211 | - return; | ||
212 | - | ||
213 | - assert(Visit == VisitKind::DeclAndChildren && "Unexpected VisitKind"); | ||
214 | - traverseChildren(ND, Results.back().children); | ||
215 | } | 211 | } |
216 | 212 | ||
217 | void traverseChildren(Decl *D, std::vector<DocumentSymbol> &Results) { | 213 | void traverseChildren(Decl *D, std::vector<DocumentSymbol> &Results) { |
... | @@ -222,16 +218,10 @@ private: | ... | @@ -222,16 +218,10 @@ private: |
222 | traverseDecl(C, Results); | 218 | traverseDecl(C, Results); |
223 | } | 219 | } |
224 | 220 | ||
225 | - VisitKind shouldVisit(Decl *D) { | 221 | + VisitKind shouldVisit(NamedDecl *D) { |
226 | if (D->isImplicit()) | 222 | if (D->isImplicit()) |
227 | return VisitKind::No; | 223 | return VisitKind::No; |
228 | 224 | ||
229 | - if (llvm::isa<LinkageSpecDecl>(D) || llvm::isa<ExportDecl>(D)) | ||
230 | - return VisitKind::OnlyChildren; | ||
231 | - | ||
232 | - if (!llvm::isa<NamedDecl>(D)) | ||
233 | - return VisitKind::No; | ||
234 | - | ||
235 | if (auto Func = llvm::dyn_cast<FunctionDecl>(D)) { | 225 | if (auto Func = llvm::dyn_cast<FunctionDecl>(D)) { |
236 | // Some functions are implicit template instantiations, those should be | 226 | // Some functions are implicit template instantiations, those should be |
237 | // ignored. | 227 | // ignored. | ... | ... |
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang-tools-extra/clangd/benchmarks/CompletionModel/DecisionForestBenchmark.cpp
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang-tools-extra/clangd/unittests/decision_forest_model/CategoricalFeature.h
deleted
100644 → 0
This diff is collapsed. Click to expand it.
llvm-project/clang-tools-extra/clangd/unittests/decision_forest_model/features.json
deleted
100644 → 0
This diff is collapsed. Click to expand it.
llvm-project/clang-tools-extra/clangd/unittests/decision_forest_model/forest.json
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang-tools-extra/docs/clang-tidy/checks/altera-struct-pack-align.rst
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang-tools-extra/test/clang-tidy/checkers/altera-struct-pack-align.cpp
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/include/clang/AST/DeclTemplate.h
100644 → 100755
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/include/clang/Format/Format.h
100644 → 100755
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/lib/AST/DeclTemplate.cpp
100644 → 100755
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/lib/Basic/FixedPoint.cpp
0 → 100644
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/lib/Sema/SemaConcept.cpp
100644 → 100755
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/lib/StaticAnalyzer/Checkers/WebKit/UncountedLambdaCapturesChecker.cpp
deleted
100644 → 0
This diff is collapsed. Click to expand it.
llvm-project/clang/lib/StaticAnalyzer/Checkers/WebKit/UncountedLocalVarsChecker.cpp
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/test/AST/ast-dump-openmp-begin-declare-variant-varying-return.c
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/test/Analysis/scan-build/Inputs/null_dereference_and_division_by_zero.c
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/test/Analysis/std-c-library-functions-POSIX-socket-sockaddr.cpp
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
llvm-project/clang/test/Analysis/std-c-library-functions-arg-cstring-dependency.c
deleted
100644 → 0
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff could not be displayed because it is too large.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
-
Please register or login to post a comment