r237999 - [Sema] Don't crash on out-of-line virtual constexpr functions

David Majnemer david.majnemer at gmail.com
Thu May 21 22:49:41 PDT 2015


Author: majnemer
Date: Fri May 22 00:49:41 2015
New Revision: 237999

URL: http://llvm.org/viewvc/llvm-project?rev=237999&view=rev
Log:
[Sema] Don't crash on out-of-line virtual constexpr functions

The method wasn't an overrider but didn't have 'virtual' textually
written because our CXXMethodDecl was an out-of-line definition.  Make
sure we use the canonical decl instead.

This fixes PR23629.

Modified:
    cfe/trunk/lib/Sema/SemaDeclCXX.cpp
    cfe/trunk/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p3.cpp

Modified: cfe/trunk/lib/Sema/SemaDeclCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclCXX.cpp?rev=237999&r1=237998&r2=237999&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclCXX.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclCXX.cpp Fri May 22 00:49:41 2015
@@ -828,7 +828,8 @@ bool Sema::CheckConstexprFunctionDecl(co
     // - it shall not be virtual;
     const CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(NewFD);
     if (Method && Method->isVirtual()) {
-      Diag(NewFD->getLocation(), diag::err_constexpr_virtual);
+      Method = Method->getCanonicalDecl();
+      Diag(Method->getLocation(), diag::err_constexpr_virtual);
 
       // If it's not obvious why this function is virtual, find an overridden
       // function which uses the 'virtual' keyword.

Modified: cfe/trunk/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p3.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p3.cpp?rev=237999&r1=237998&r2=237999&view=diff
==============================================================================
--- cfe/trunk/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p3.cpp (original)
+++ cfe/trunk/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p3.cpp Fri May 22 00:49:41 2015
@@ -36,6 +36,8 @@ struct T : SS, NonLiteral {
 
   constexpr int ImplicitlyVirtual() const { return 0; } // expected-error {{virtual function cannot be constexpr}}
 
+  virtual constexpr int OutOfLineVirtual() const; // expected-error {{virtual function cannot be constexpr}}
+
   //  - its return type shall be a literal type;
   constexpr NonLiteral NonLiteralReturn() const { return {}; } // expected-error {{constexpr function's return type 'NonLiteral' is not a literal type}}
   constexpr void VoidReturn() const { return; }
@@ -67,6 +69,8 @@ struct T : SS, NonLiteral {
   // expected-error at -5 {{defaulted definition of copy assignment operator is not constexpr}}
 #endif
 };
+
+constexpr int T::OutOfLineVirtual() const { return 0; }
 #ifdef CXX1Y
 struct T2 {
   int n = 0;





More information about the cfe-commits mailing list