From f545ede91c9d9f271e7504282cab7bf509607ead Mon Sep 17 00:00:00 2001 From: Richard Smith Date: Wed, 4 Mar 2020 13:18:46 -0800 Subject: [PATCH] Fix regression in bdad0a1: force rebuilding of StmtExpr nodes in TreeTransform if the 'dependent' flag would change. --- clang/include/clang/Sema/Sema.h | 4 +++- clang/lib/Sema/SemaExpr.cpp | 18 ++++++++---------- clang/lib/Sema/TreeTransform.h | 14 +++++++++----- clang/test/SemaTemplate/dependent-expr.cpp | 7 +++++++ 4 files changed, 27 insertions(+), 16 deletions(-) diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h index 5739808..8e4d082 100644 --- a/clang/include/clang/Sema/Sema.h +++ b/clang/include/clang/Sema/Sema.h @@ -4965,7 +4965,9 @@ public: void ActOnStartStmtExpr(); ExprResult ActOnStmtExpr(Scope *S, SourceLocation LPLoc, Stmt *SubStmt, - SourceLocation RPLoc); // "({..})" + SourceLocation RPLoc); + ExprResult BuildStmtExpr(SourceLocation LPLoc, Stmt *SubStmt, + SourceLocation RPLoc, bool IsDependent); // Handle the final expression in a statement expression. ExprResult ActOnStmtExprResult(ExprResult E); void ActOnStmtExprError(); diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index 1870e44..291c38a 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -13912,7 +13912,13 @@ void Sema::ActOnStmtExprError() { } ExprResult Sema::ActOnStmtExpr(Scope *S, SourceLocation LPLoc, Stmt *SubStmt, - SourceLocation RPLoc) { // "({..})" + SourceLocation RPLoc) { + return BuildStmtExpr(LPLoc, SubStmt, RPLoc, + S->getTemplateParamParent() != nullptr); +} + +ExprResult Sema::BuildStmtExpr(SourceLocation LPLoc, Stmt *SubStmt, + SourceLocation RPLoc, bool IsDependent) { assert(SubStmt && isa(SubStmt) && "Invalid action invocation!"); CompoundStmt *Compound = cast(SubStmt); @@ -13941,18 +13947,10 @@ ExprResult Sema::ActOnStmtExpr(Scope *S, SourceLocation LPLoc, Stmt *SubStmt, } } - bool IsDependentContext = false; - if (S) - IsDependentContext = S->getTemplateParamParent() != nullptr; - else - // FIXME: This is not correct when substituting inside a templated - // context that isn't a DeclContext (such as a variable template). - IsDependentContext = CurContext->isDependentContext(); - // FIXME: Check that expression type is complete/non-abstract; statement // expressions are not lvalues. Expr *ResStmtExpr = - new (Context) StmtExpr(Compound, Ty, LPLoc, RPLoc, IsDependentContext); + new (Context) StmtExpr(Compound, Ty, LPLoc, RPLoc, IsDependent); if (StmtExprMayBindToTemp) return MaybeBindToTemporary(ResStmtExpr); return ResStmtExpr; diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 05b41aa..382496d 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -2550,8 +2550,8 @@ public: /// By default, performs semantic analysis to build the new expression. /// Subclasses may override this routine to provide different behavior. ExprResult RebuildStmtExpr(SourceLocation LParenLoc, Stmt *SubStmt, - SourceLocation RParenLoc) { - return getSema().ActOnStmtExpr(nullptr, LParenLoc, SubStmt, RParenLoc); + SourceLocation RParenLoc, bool IsDependent) { + return getSema().BuildStmtExpr(LParenLoc, SubStmt, RParenLoc, IsDependent); } /// Build a new __builtin_choose_expr expression. @@ -10432,16 +10432,20 @@ TreeTransform::TransformStmtExpr(StmtExpr *E) { return ExprError(); } + // FIXME: This is not correct when substituting inside a templated + // context that isn't a DeclContext (such as a variable template). + bool IsDependent = getSema().CurContext->isDependentContext(); + if (!getDerived().AlwaysRebuild() && + IsDependent == E->isInstantiationDependent() && SubStmt.get() == E->getSubStmt()) { // Calling this an 'error' is unintuitive, but it does the right thing. SemaRef.ActOnStmtExprError(); return SemaRef.MaybeBindToTemporary(E); } - return getDerived().RebuildStmtExpr(E->getLParenLoc(), - SubStmt.get(), - E->getRParenLoc()); + return getDerived().RebuildStmtExpr(E->getLParenLoc(), SubStmt.get(), + E->getRParenLoc(), IsDependent); } template diff --git a/clang/test/SemaTemplate/dependent-expr.cpp b/clang/test/SemaTemplate/dependent-expr.cpp index e333ed9..97d157f 100644 --- a/clang/test/SemaTemplate/dependent-expr.cpp +++ b/clang/test/SemaTemplate/dependent-expr.cpp @@ -125,4 +125,11 @@ namespace PR45083 { }; template void B::f(); + + // Make sure we properly rebuild statement expression AST nodes even if the + // only thing that changes is the "is dependent" flag. + template void f() { + decltype(({})) x; // expected-error {{incomplete type}} + } + template void f(); // expected-note {{instantiation of}} } -- 2.7.4