Skip to content

Commit

Permalink
Improve error message for constexpr constructors of virtual base classes
Browse files Browse the repository at this point in the history
The changes are for better diagnostic/error-messages. The error message
of Clang, MSVC, and GCC were compared and MSVC gives more detailed
error message so that is used now.

Fixes #64843
Differential Revision: https://reviews.llvm.org/D158540
  • Loading branch information
NoumanAmir657 authored and AaronBallman committed Oct 3, 2023
1 parent 980e024 commit af16a4e
Show file tree
Hide file tree
Showing 4 changed files with 25 additions and 4 deletions.
3 changes: 3 additions & 0 deletions clang/docs/ReleaseNotes.rst
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,9 @@ Improvements to Clang's diagnostics
- The fix-it emitted by ``-Wformat`` for scoped enumerations now take the
enumeration's underlying type into account instead of suggesting a type just
based on the format string specifier being used.
- Clang now displays an improved diagnostic and a note when a defaulted special
member is marked ``constexpr`` in a class with a virtual base class
(`#64843: <https://github.com/llvm/llvm-project/issues/64843>`_).

Bug Fixes in This Version
-------------------------
Expand Down
2 changes: 2 additions & 0 deletions clang/include/clang/Basic/DiagnosticSemaKinds.td
Original file line number Diff line number Diff line change
Expand Up @@ -9454,6 +9454,8 @@ def err_defaulted_copy_assign_not_ref : Error<
def err_incorrect_defaulted_constexpr : Error<
"defaulted definition of %sub{select_special_member_kind}0 "
"is not constexpr">;
def err_incorrect_defaulted_constexpr_with_vb: Error<
"%sub{select_special_member_kind}0 cannot be 'constexpr' in a class with virtual base class">;
def err_incorrect_defaulted_consteval : Error<
"defaulted declaration of %sub{select_special_member_kind}0 "
"cannot be consteval because implicit definition is not constexpr">;
Expand Down
15 changes: 11 additions & 4 deletions clang/lib/Sema/SemaDeclCXX.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7819,10 +7819,17 @@ bool Sema::CheckExplicitlyDefaultedSpecialMember(CXXMethodDecl *MD,
: isa<CXXConstructorDecl>(MD))) &&
MD->isConstexpr() && !Constexpr &&
MD->getTemplatedKind() == FunctionDecl::TK_NonTemplate) {
Diag(MD->getBeginLoc(), MD->isConsteval()
? diag::err_incorrect_defaulted_consteval
: diag::err_incorrect_defaulted_constexpr)
<< CSM;
if (!MD->isConsteval() && RD->getNumVBases()) {
Diag(MD->getBeginLoc(), diag::err_incorrect_defaulted_constexpr_with_vb)
<< CSM;
for (const auto &I : RD->vbases())
Diag(I.getBeginLoc(), diag::note_constexpr_virtual_base_here);
} else {
Diag(MD->getBeginLoc(), MD->isConsteval()
? diag::err_incorrect_defaulted_consteval
: diag::err_incorrect_defaulted_constexpr)
<< CSM;
}
// FIXME: Explain why the special member can't be constexpr.
HadError = true;
}
Expand Down
9 changes: 9 additions & 0 deletions clang/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p3.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -283,3 +283,12 @@ namespace std_example {
return r;
}
}

struct Base {
constexpr Base() = default;
};
struct Derived : virtual Base { // expected-note 3{{virtual base class declared here}}
constexpr Derived() = default; // expected-error {{default constructor cannot be 'constexpr' in a class with virtual base class}}
constexpr Derived(const Derived&) = default; // expected-error {{copy constructor cannot be 'constexpr' in a class with virtual base class}}
constexpr Derived(Derived&&) = default; // expected-error {{move constructor cannot be 'constexpr' in a class with virtual base class}}
};

0 comments on commit af16a4e

Please sign in to comment.