From: Richard Smith Date: Mon, 7 Nov 2011 03:22:51 +0000 (+0000) Subject: Allow constexpr variables' initializers to be folded in C++11 mode. This X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=cd689927139d3ab52c0c088521633c661bd2d807;p=clang Allow constexpr variables' initializers to be folded in C++11 mode. This partially undoes the revert in r143491, but does not introduce any new instances of the underlying issue (which is not yet fixed) in code which does not use the 'constexpr' keyword. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@143905 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/AST/ExprConstant.cpp b/lib/AST/ExprConstant.cpp index 9c9e473f7b..6456376d48 100644 --- a/lib/AST/ExprConstant.cpp +++ b/lib/AST/ExprConstant.cpp @@ -558,12 +558,14 @@ bool HandleLValueToRValueConversion(EvalInfo &Info, QualType Type, // them are not permitted. const VarDecl *VD = dyn_cast(D); QualType VT = VD->getType(); - if (!VD) + if (!VD || VD->isInvalidDecl()) return false; if (!isa(VD)) { if (!IsConstNonVolatile(VT)) return false; - if (!VT->isIntegralOrEnumerationType() && !VT->isRealFloatingType()) + // FIXME: Allow folding of values of any literal type in all languages. + if (!VT->isIntegralOrEnumerationType() && !VT->isRealFloatingType() && + !VD->isConstexpr()) return false; } if (!EvaluateVarDeclInit(Info, VD, Frame, RVal)) diff --git a/test/SemaCXX/constant-expression-cxx11.cpp b/test/SemaCXX/constant-expression-cxx11.cpp index 782b6a1d5b..92159a7b6a 100644 --- a/test/SemaCXX/constant-expression-cxx11.cpp +++ b/test/SemaCXX/constant-expression-cxx11.cpp @@ -135,7 +135,6 @@ namespace ParameterScopes { } -#if 0 namespace Pointers { constexpr int f(int n, const int *a, const int *b, const int *c) { @@ -165,10 +164,9 @@ namespace FunctionPointers { static_assert_fold(1 + Apply(Select(4), 5) + Apply(Select(3), 7) == 42, ""); - constexpr int Invalid = Apply(Select(0), 0); // xpected-error {{must be initialized by a constant expression}} + constexpr int Invalid = Apply(Select(0), 0); // expected-error {{must be initialized by a constant expression}} } -#endif namespace PointerComparison { @@ -211,12 +209,10 @@ static_assert_fold(&x >= &x, ""); static_assert_fold(&x < &x, "false"); // expected-error {{false}} static_assert_fold(&x > &x, "false"); // expected-error {{false}} -#if 0 constexpr S* sptr = &s; // FIXME: This is not a constant expression; check we reject this and move this // test elsewhere. constexpr bool dyncast = sptr == dynamic_cast(sptr); -#endif extern char externalvar[]; // FIXME: This is not a constant expression; check we reject this and move this