aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/libs/clang16/tools/extra/clang-tidy/performance/TriviallyDestructibleCheck.cpp
diff options
context:
space:
mode:
authorthegeorg <thegeorg@yandex-team.com>2024-03-13 13:58:24 +0300
committerthegeorg <thegeorg@yandex-team.com>2024-03-13 14:11:53 +0300
commit11a895b7e15d1c5a1f52706396b82e3f9db953cb (patch)
treefabc6d883b0f946151f61ae7865cee9f529a1fdd /contrib/libs/clang16/tools/extra/clang-tidy/performance/TriviallyDestructibleCheck.cpp
parent9685917341315774aad5733b1793b1e533a88bbb (diff)
downloadydb-11a895b7e15d1c5a1f52706396b82e3f9db953cb.tar.gz
Export clang-format16 via ydblib project
6e6be3a95868fde888d801b7590af4044049563f
Diffstat (limited to 'contrib/libs/clang16/tools/extra/clang-tidy/performance/TriviallyDestructibleCheck.cpp')
-rw-r--r--contrib/libs/clang16/tools/extra/clang-tidy/performance/TriviallyDestructibleCheck.cpp75
1 files changed, 75 insertions, 0 deletions
diff --git a/contrib/libs/clang16/tools/extra/clang-tidy/performance/TriviallyDestructibleCheck.cpp b/contrib/libs/clang16/tools/extra/clang-tidy/performance/TriviallyDestructibleCheck.cpp
new file mode 100644
index 0000000000..adfedb4e84
--- /dev/null
+++ b/contrib/libs/clang16/tools/extra/clang-tidy/performance/TriviallyDestructibleCheck.cpp
@@ -0,0 +1,75 @@
+//===--- TriviallyDestructibleCheck.cpp - clang-tidy ----------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "TriviallyDestructibleCheck.h"
+#include "../utils/LexerUtils.h"
+#include "../utils/Matchers.h"
+#include "clang/AST/ASTContext.h"
+#include "clang/ASTMatchers/ASTMatchFinder.h"
+
+using namespace clang::ast_matchers;
+using namespace clang::ast_matchers::internal;
+using namespace clang::tidy::matchers;
+
+namespace clang::tidy::performance {
+
+namespace {
+
+AST_MATCHER(Decl, isFirstDecl) { return Node.isFirstDecl(); }
+
+AST_MATCHER_P(CXXRecordDecl, hasBase, Matcher<QualType>, InnerMatcher) {
+ for (const CXXBaseSpecifier &BaseSpec : Node.bases()) {
+ QualType BaseType = BaseSpec.getType();
+ if (InnerMatcher.matches(BaseType, Finder, Builder))
+ return true;
+ }
+ return false;
+}
+
+} // namespace
+
+void TriviallyDestructibleCheck::registerMatchers(MatchFinder *Finder) {
+ Finder->addMatcher(
+ cxxDestructorDecl(
+ isDefaulted(),
+ unless(anyOf(isFirstDecl(), isVirtual(),
+ ofClass(cxxRecordDecl(
+ anyOf(hasBase(unless(isTriviallyDestructible())),
+ has(fieldDecl(unless(
+ hasType(isTriviallyDestructible()))))))))))
+ .bind("decl"),
+ this);
+}
+
+void TriviallyDestructibleCheck::check(const MatchFinder::MatchResult &Result) {
+ const auto *MatchedDecl = Result.Nodes.getNodeAs<CXXDestructorDecl>("decl");
+
+ // Get locations of both first and out-of-line declarations.
+ SourceManager &SM = *Result.SourceManager;
+ const auto *FirstDecl = cast<CXXMethodDecl>(MatchedDecl->getFirstDecl());
+ const SourceLocation FirstDeclEnd = utils::lexer::findNextTerminator(
+ FirstDecl->getEndLoc(), SM, getLangOpts());
+ const CharSourceRange SecondDeclRange = CharSourceRange::getTokenRange(
+ MatchedDecl->getBeginLoc(),
+ utils::lexer::findNextTerminator(MatchedDecl->getEndLoc(), SM,
+ getLangOpts()));
+ if (FirstDeclEnd.isInvalid() || SecondDeclRange.isInvalid())
+ return;
+
+ // Report diagnostic.
+ diag(FirstDecl->getLocation(),
+ "class %0 can be made trivially destructible by defaulting the "
+ "destructor on its first declaration")
+ << FirstDecl->getParent()
+ << FixItHint::CreateInsertion(FirstDeclEnd, " = default")
+ << FixItHint::CreateRemoval(SecondDeclRange);
+ diag(MatchedDecl->getLocation(), "destructor definition is here",
+ DiagnosticIDs::Note);
+}
+
+} // namespace clang::tidy::performance