https://github.com/charmitro updated https://github.com/llvm/llvm-project/pull/74510
>From 7961a90a020f6fde5c6cd892024ff0fe329450ee Mon Sep 17 00:00:00 2001 From: Charalampos Mitrodimas <charmi...@posteo.net> Date: Tue, 5 Dec 2023 11:46:56 +0200 Subject: [PATCH] [clang] Disable missing definition warning on pure virtual functions Warning '-Wundefined-func-template' incorrectly indicates that no definition is available for a pure virtual function. However, a definition is not needed for a pure virtual function. Fixes #74016 Signed-off-by: Charalampos Mitrodimas <charmi...@posteo.net> --- clang/docs/ReleaseNotes.rst | 4 ++ clang/lib/Sema/SemaExpr.cpp | 2 +- .../instantiate-pure-virtual-function.cpp | 67 +++++++++++++++++++ 3 files changed, 72 insertions(+), 1 deletion(-) create mode 100644 clang/test/SemaTemplate/instantiate-pure-virtual-function.cpp diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index 8054d90fc70f93..643eb6cc157732 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -294,6 +294,10 @@ Improvements to Clang's time-trace Bug Fixes in This Version ------------------------- +- Clang's ``-Wundefined-func-template`` no longer warns on pure virtual + functions. + (`#74016 <https://github.com/llvm/llvm-project/issues/74016>`_) + - Fixed missing warnings when comparing mismatched enumeration constants in C (`#29217 <https://github.com/llvm/llvm-project/issues/29217>`). diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index 5f03b981428251..7eb252f663d43e 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -18952,7 +18952,7 @@ void Sema::MarkFunctionReferenced(SourceLocation Loc, FunctionDecl *Func, // constant evaluated bool NeededForConstantEvaluation = isPotentiallyConstantEvaluatedContext(*this) && - isImplicitlyDefinableConstexprFunction(Func); + isImplicitlyDefinableConstexprFunction(Func) && !Func->isPure(); // Determine whether we require a function definition to exist, per // C++11 [temp.inst]p3: diff --git a/clang/test/SemaTemplate/instantiate-pure-virtual-function.cpp b/clang/test/SemaTemplate/instantiate-pure-virtual-function.cpp new file mode 100644 index 00000000000000..caec42b6b77f95 --- /dev/null +++ b/clang/test/SemaTemplate/instantiate-pure-virtual-function.cpp @@ -0,0 +1,67 @@ +// RUN: %clang_cc1 -fsyntax-only -verify -Wundefined-func-template %s + +namespace GH74016 { + template <typename T> class B { + public: + constexpr void foo(const T &) { bar(1); } + virtual constexpr void bar(unsigned int) = 0; + }; + + template <typename T> class D : public B<T> { + public: + constexpr void bar(unsigned int) override {} + }; + + void test() { + auto t = D<int>(); + t.foo(0); + } +}; + +namespace call_pure_virtual_function_from_virtual { + template <typename T> class B { + public: + const void foo(const T &) { B::bar(1); } // expected-warning {{instantiation of function 'call_pure_virtual_function_from_virtual::B<int>::bar' required here, but no definition is available}} + // expected-note@-1 {{add an explicit instantiation declaration to suppress this warning if 'call_pure_virtual_function_from_virtual::B<int>::bar' is explicitly instantiated in another translation unit}} + virtual const void bar(unsigned int) = 0; // expected-note {{forward declaration of template entity is here}} + }; + + template <typename T> class D : public B<T> { + public: + const void bar(unsigned int) override {} + }; + + void test() { + auto t = D<int>(); + t.foo(0); // expected-note {{in instantiation of member function 'call_pure_virtual_function_from_virtual::B<int>::foo' requested here}} + } +}; + +namespace non_pure_virtual_function { + template <typename T> class B { + public: + constexpr void foo(const T &) { bar(1); } + + virtual constexpr void bar(unsigned int); // expected-warning {{inline function 'non_pure_virtual_function::B<int>::bar' is not defined}} + // expected-note@-1 {{forward declaration of template entity is here}} + // expected-note@-2 {{forward declaration of template entity is here}} + // expected-note@-3 {{forward declaration of template entity is here}} + }; + + template <typename T> class D : public B<T> { // expected-warning {{instantiation of function 'non_pure_virtual_function::B<int>::bar' required here, but no definition is available}} +// expected-warning@-1 {{instantiation of function 'non_pure_virtual_function::B<int>::bar' required here, but no definition is available}} +// expected-warning@-2 {{instantiation of function 'non_pure_virtual_function::B<int>::bar' required here, but no definition is available}} +// expected-note@-3 {{add an explicit instantiation declaration to suppress this warning if 'non_pure_virtual_function::B<int>::bar' is explicitly instantiated in another translation unit}} +// expected-note@-4 {{add an explicit instantiation declaration to suppress this warning if 'non_pure_virtual_function::B<int>::bar' is explicitly instantiated in another translation unit}} +// expected-note@-5 {{add an explicit instantiation declaration to suppress this warning if 'non_pure_virtual_function::B<int>::bar' is explicitly instantiated in another translation unit}} +// expected-note@-6 {{used here}} + + public: + constexpr void bar(unsigned int) override { } + }; + + void test() { + auto t = D<int>(); + t.foo(0); + } +}; _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits