Author: serge-sans-paille Date: 2026-10-10T07:12:06Z New Revision: e3f3b3e565d9fe9d5c261487eb8df68b19acffa8
URL: https://github.com/llvm/llvm-project/commit/e3f3b3e565d9fe9d5c261487eb8df68b19acffa8 DIFF: https://github.com/llvm/llvm-project/commit/e3f3b3e565d9fe9d5c261487eb8df68b19acffa8.diff LOG: [clang-tidy] Improve modernize-use-equals-default check to handle explicit parent constructor calls (#226456) Now capture this pattern: struct Base {}; struct C : Base { C() : Base() {} }; And turn it into struct Base {}; struct C : Base { C() = default; }; Added: Modified: clang-tools-extra/clang-tidy/modernize/UseEqualsDefaultCheck.cpp clang-tools-extra/docs/ReleaseNotes.md clang-tools-extra/test/clang-tidy/checkers/modernize/use-equals-default.cpp Removed: ################################################################################ diff --git a/clang-tools-extra/clang-tidy/modernize/UseEqualsDefaultCheck.cpp b/clang-tools-extra/clang-tidy/modernize/UseEqualsDefaultCheck.cpp index 1535fa79676abf..af8774dc09f359 100644 --- a/clang-tools-extra/clang-tidy/modernize/UseEqualsDefaultCheck.cpp +++ b/clang-tools-extra/clang-tidy/modernize/UseEqualsDefaultCheck.cpp @@ -247,7 +247,9 @@ void UseEqualsDefaultCheck::registerMatchers(MatchFinder *Finder) { anyOf( // Default constructor. allOf(parameterCountIs(0), - unless(hasAnyConstructorInitializer(isWritten())), + unless(hasAnyConstructorInitializer(allOf( + isWritten(), unless(withInitializer(cxxConstructExpr( + argumentCountIs(0))))))), unless(isVariadic()), IsPublicOrOutOfLineUntilCPP20), // Copy constructor. allOf(isCopyConstructor(), @@ -319,11 +321,13 @@ void UseEqualsDefaultCheck::check(const MatchFinder::MatchResult &Result) { if (!isCopyConstructorAndCanBeDefaulted(Result.Context, Ctor)) return; MemberType = 1; - // If there are constructor initializers, they must be removed. - for (const auto *Init : Ctor->inits()) { - RemoveInitializers.emplace_back( - FixItHint::CreateRemoval(Init->getSourceRange())); - } + } + // If there are constructor initializers, they must be removed. + for (const auto *Init : Ctor->inits()) { + if (!Init->isWritten()) + continue; + RemoveInitializers.emplace_back( + FixItHint::CreateRemoval(Init->getSourceRange())); } } else if (isa<CXXDestructorDecl>(SpecialFunctionDecl)) { MemberType = 2; diff --git a/clang-tools-extra/docs/ReleaseNotes.md b/clang-tools-extra/docs/ReleaseNotes.md index ce498ff6a4388b..25bc3ba0ed73fe 100644 --- a/clang-tools-extra/docs/ReleaseNotes.md +++ b/clang-tools-extra/docs/ReleaseNotes.md @@ -273,6 +273,10 @@ infrastructure are described first, followed by tool-specific sections. <clang-tidy/checks/modernize/use-designated-initializers>` when analyzing malformed code with nested classes and ambiguous initializer. +- Improved {doc}`modernize-use-equals-default + <clang-tidy/checks/modernize/use-equals-default>` check to also capture + default constructor with explicit default-initialization of parents. + - Fixed a crash in {doc}`modernize-use-noexcept <clang-tidy/checks/modernize/use-noexcept>` when analyzing malformed template code with an unparsed exception specification. diff --git a/clang-tools-extra/test/clang-tidy/checkers/modernize/use-equals-default.cpp b/clang-tools-extra/test/clang-tidy/checkers/modernize/use-equals-default.cpp index 2eefdf9d6460ca..00264c7d51f5c8 100644 --- a/clang-tools-extra/test/clang-tidy/checkers/modernize/use-equals-default.cpp +++ b/clang-tools-extra/test/clang-tidy/checkers/modernize/use-equals-default.cpp @@ -236,11 +236,39 @@ ODef::~ODef() = default; // Delegating constructor and overriden destructor. struct DC : KW { DC() : KW() {} + // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use '= default' + // CHECK-FIXES: DC() = default; ~DC() override {} // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use '= default' // CHECK-FIXES: ~DC() override = default; }; +// Delegating constructor with multiple initializers. +struct DCM : KW, N { + DCM() : KW(), N() {} + // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use '= default' + // CHECK-FIXES: DCM() = default; +}; + +struct dummy {}; + +// Delegating constructor with field initializer. +struct DCF : KW { + + DCF() : KW(), d() {} + // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use '= default' + // CHECK-FIXES: DCF() = default; + + dummy d; +}; + +// Delegating constructor with noexcept. +struct DCNE : KW { + DCNE() noexcept : KW() {} + // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use '= default' + // CHECK-FIXES: DCNE() noexcept = default; +}; + struct OverrideWithSemiColon : KW { ~OverrideWithSemiColon() override {}; // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use '= default' _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
