diff options
author | Richard Smith <richard-llvm@metafoo.co.uk> | 2019-06-11 17:50:32 +0000 |
---|---|---|
committer | Richard Smith <richard-llvm@metafoo.co.uk> | 2019-06-11 17:50:32 +0000 |
commit | 715f7a1bd058c64a39cc4773114dfb46ae8cc8a3 (patch) | |
tree | d9f4369bedcbe50c9dc03ee5498544702d86616e /clang/lib/AST/Decl.cpp | |
parent | ef2d6d99c0d35e46dce7fff6b999a3a1fc08aecc (diff) | |
download | bcm5719-llvm-715f7a1bd058c64a39cc4773114dfb46ae8cc8a3.tar.gz bcm5719-llvm-715f7a1bd058c64a39cc4773114dfb46ae8cc8a3.zip |
For DR712: store on a DeclRefExpr whether it constitutes an odr-use.
Begin restructuring to support the forms of non-odr-use reference
permitted by DR712.
llvm-svn: 363086
Diffstat (limited to 'clang/lib/AST/Decl.cpp')
-rw-r--r-- | clang/lib/AST/Decl.cpp | 22 |
1 files changed, 21 insertions, 1 deletions
diff --git a/clang/lib/AST/Decl.cpp b/clang/lib/AST/Decl.cpp index 8b77e01f4e8..1b744c82a09 100644 --- a/clang/lib/AST/Decl.cpp +++ b/clang/lib/AST/Decl.cpp @@ -2245,12 +2245,16 @@ void VarDecl::setInit(Expr *I) { Init = I; } -bool VarDecl::isUsableInConstantExpressions(ASTContext &C) const { +bool VarDecl::mightBeUsableInConstantExpressions(ASTContext &C) const { const LangOptions &Lang = C.getLangOpts(); if (!Lang.CPlusPlus) return false; + // Function parameters are never usable in constant expressions. + if (isa<ParmVarDecl>(this)) + return false; + // In C++11, any variable of reference type can be used in a constant // expression if it is initialized by a constant expression. if (Lang.CPlusPlus11 && getType()->isReferenceType()) @@ -2272,6 +2276,22 @@ bool VarDecl::isUsableInConstantExpressions(ASTContext &C) const { return Lang.CPlusPlus11 && isConstexpr(); } +bool VarDecl::isUsableInConstantExpressions(ASTContext &Context) const { + // C++2a [expr.const]p3: + // A variable is usable in constant expressions after its initializing + // declaration is encountered... + const VarDecl *DefVD = nullptr; + const Expr *Init = getAnyInitializer(DefVD); + if (!Init || Init->isValueDependent()) + return false; + // ... if it is a constexpr variable, or it is of reference type or of + // const-qualified integral or enumeration type, ... + if (!DefVD->mightBeUsableInConstantExpressions(Context)) + return false; + // ... and its initializer is a constant initializer. + return DefVD->checkInitIsICE(); +} + /// Convert the initializer for this declaration to the elaborated EvaluatedStmt /// form, which contains extra information on the evaluated value of the /// initializer. |