Izaron created this revision. Izaron added reviewers: aaron.ballman, erichkeane, rsmith. Izaron requested review of this revision. Herald added a project: clang. Herald added a subscriber: cfe-commits.
When instantiating a VarDecl initializing sub-AST, the evaluation context was only PotentiallyEvaluated, even if we are inside a consteval function. It dictated clang to construct a redundant ConstantExpr node, which could be not evaluable. Fixes https://github.com/llvm/llvm-project/issues/51182 and https://github.com/llvm/llvm-project/issues/52648 Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D119651 Files: clang/lib/Sema/SemaTemplateInstantiateDecl.cpp clang/test/SemaCXX/cxx2a-consteval.cpp Index: clang/test/SemaCXX/cxx2a-consteval.cpp =================================================================== --- clang/test/SemaCXX/cxx2a-consteval.cpp +++ clang/test/SemaCXX/cxx2a-consteval.cpp @@ -613,6 +613,23 @@ } // namespace unevaluated +namespace templated { + +consteval int f(int v) { + return v; +} + +template <typename T> +consteval int g(T a) { + // Previously this call was rejected due to incorrect evaluation context type in instantiations. Now we show that this call is OK. + int n = f(a); + return n; +} + +static_assert(g(100) == 100); + +} // namespace templated + namespace PR50779 { struct derp { int b = 0; Index: clang/lib/Sema/SemaTemplateInstantiateDecl.cpp =================================================================== --- clang/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ clang/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -5326,8 +5326,13 @@ Var->setImplicitlyInline(); if (OldVar->getInit()) { - EnterExpressionEvaluationContext Evaluated( - *this, Sema::ExpressionEvaluationContext::PotentiallyEvaluated, Var); + ExpressionEvaluationContext Context = + ExpressionEvaluationContext::PotentiallyEvaluated; + // If current context is constant evaluated, the variable initializer + // context is also constant evaluated + if (isConstantEvaluated()) + Context = ExpressionEvaluationContext::ConstantEvaluated; + EnterExpressionEvaluationContext Evaluated(*this, Context, Var); // Instantiate the initializer. ExprResult Init;
Index: clang/test/SemaCXX/cxx2a-consteval.cpp =================================================================== --- clang/test/SemaCXX/cxx2a-consteval.cpp +++ clang/test/SemaCXX/cxx2a-consteval.cpp @@ -613,6 +613,23 @@ } // namespace unevaluated +namespace templated { + +consteval int f(int v) { + return v; +} + +template <typename T> +consteval int g(T a) { + // Previously this call was rejected due to incorrect evaluation context type in instantiations. Now we show that this call is OK. + int n = f(a); + return n; +} + +static_assert(g(100) == 100); + +} // namespace templated + namespace PR50779 { struct derp { int b = 0; Index: clang/lib/Sema/SemaTemplateInstantiateDecl.cpp =================================================================== --- clang/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ clang/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -5326,8 +5326,13 @@ Var->setImplicitlyInline(); if (OldVar->getInit()) { - EnterExpressionEvaluationContext Evaluated( - *this, Sema::ExpressionEvaluationContext::PotentiallyEvaluated, Var); + ExpressionEvaluationContext Context = + ExpressionEvaluationContext::PotentiallyEvaluated; + // If current context is constant evaluated, the variable initializer + // context is also constant evaluated + if (isConstantEvaluated()) + Context = ExpressionEvaluationContext::ConstantEvaluated; + EnterExpressionEvaluationContext Evaluated(*this, Context, Var); // Instantiate the initializer. ExprResult Init;
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits