1 | //===--- TodoCommentCheck.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 "TodoCommentCheck.h" |
10 | #include "clang/Frontend/CompilerInstance.h" |
11 | #include "clang/Lex/Preprocessor.h" |
12 | #include <optional> |
13 | |
14 | namespace clang::tidy::google::readability { |
15 | |
16 | class TodoCommentCheck::TodoCommentHandler : public CommentHandler { |
17 | public: |
18 | TodoCommentHandler(TodoCommentCheck &Check, std::optional<std::string> User) |
19 | : Check(Check), User(User ? *User : "unknown" ), |
20 | TodoMatch("^// *TODO *(\\(.*\\))?:?( )?(.*)$" ) {} |
21 | |
22 | bool HandleComment(Preprocessor &PP, SourceRange Range) override { |
23 | StringRef Text = |
24 | Lexer::getSourceText(Range: CharSourceRange::getCharRange(R: Range), |
25 | SM: PP.getSourceManager(), LangOpts: PP.getLangOpts()); |
26 | |
27 | SmallVector<StringRef, 4> Matches; |
28 | if (!TodoMatch.match(String: Text, Matches: &Matches)) |
29 | return false; |
30 | |
31 | StringRef Username = Matches[1]; |
32 | StringRef = Matches[3]; |
33 | |
34 | if (!Username.empty()) |
35 | return false; |
36 | |
37 | std::string NewText = ("// TODO(" + Twine(User) + "): " + Comment).str(); |
38 | |
39 | Check.diag(Loc: Range.getBegin(), Description: "missing username/bug in TODO" ) |
40 | << FixItHint::CreateReplacement(RemoveRange: CharSourceRange::getCharRange(R: Range), |
41 | Code: NewText); |
42 | return false; |
43 | } |
44 | |
45 | private: |
46 | TodoCommentCheck &Check; |
47 | std::string User; |
48 | llvm::Regex TodoMatch; |
49 | }; |
50 | |
51 | TodoCommentCheck::(StringRef Name, ClangTidyContext *Context) |
52 | : ClangTidyCheck(Name, Context), |
53 | Handler(std::make_unique<TodoCommentHandler>( |
54 | args&: *this, args: Context->getOptions().User)) {} |
55 | |
56 | TodoCommentCheck::() = default; |
57 | |
58 | void TodoCommentCheck::(const SourceManager &SM, |
59 | Preprocessor *PP, |
60 | Preprocessor *ModuleExpanderPP) { |
61 | PP->addCommentHandler(Handler: Handler.get()); |
62 | } |
63 | |
64 | } // namespace clang::tidy::google::readability |
65 | |