diff options
author | Eli Friedman <eli.friedman@gmail.com> | 2012-02-29 04:03:55 +0000 |
---|---|---|
committer | Eli Friedman <eli.friedman@gmail.com> | 2012-02-29 04:03:55 +0000 |
commit | e4f22dfa95be88c79b4a19eb63bfd289930822d2 (patch) | |
tree | f9f9d39255fc8e203c8eb72d7dcbbbc5e6817721 /clang | |
parent | 3dbeb55874f6424a81400da1b5ac34eff2c0a43a (diff) | |
download | bcm5719-llvm-e4f22dfa95be88c79b4a19eb63bfd289930822d2.tar.gz bcm5719-llvm-e4f22dfa95be88c79b4a19eb63bfd289930822d2.zip |
A couple minor bug-fixes for template instantiation for expressions which are sometimes potentially evaluated.
llvm-svn: 151707
Diffstat (limited to 'clang')
-rw-r--r-- | clang/lib/Sema/SemaExpr.cpp | 2 | ||||
-rw-r--r-- | clang/lib/Sema/TreeTransform.h | 25 | ||||
-rw-r--r-- | clang/test/SemaTemplate/instantiate-sizeof.cpp | 10 | ||||
-rw-r--r-- | clang/test/SemaTemplate/instantiate-typeof.cpp | 10 |
4 files changed, 35 insertions, 12 deletions
diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index 5a2b2dc7e90..56debcf2087 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -9308,6 +9308,8 @@ namespace { } ExprResult Sema::TranformToPotentiallyEvaluated(Expr *E) { + assert(ExprEvalContexts.back().Context == Unevaluated && + "Should only transform unevaluated expressions"); ExprEvalContexts.back().Context = ExprEvalContexts[ExprEvalContexts.size()-2].Context; if (ExprEvalContexts.back().Context == Unevaluated) diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 82bfe6fa706..363e2c408db 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -4274,6 +4274,10 @@ QualType TreeTransform<Derived>::TransformTypeOfExprType(TypeLocBuilder &TLB, if (E.isInvalid()) return QualType(); + E = SemaRef.HandleExprEvaluationContextForTypeof(E.get()); + if (E.isInvalid()) + return QualType(); + QualType Result = TL.getType(); if (getDerived().AlwaysRebuild() || E.get() != TL.getUnderlyingExpr()) { @@ -6234,20 +6238,17 @@ TreeTransform<Derived>::TransformUnaryExprOrTypeTraitExpr( E->getSourceRange()); } - ExprResult SubExpr; - { - // C++0x [expr.sizeof]p1: - // The operand is either an expression, which is an unevaluated operand - // [...] - EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated); + // C++0x [expr.sizeof]p1: + // The operand is either an expression, which is an unevaluated operand + // [...] + EnterExpressionEvaluationContext Unevaluated(SemaRef, Sema::Unevaluated); - SubExpr = getDerived().TransformExpr(E->getArgumentExpr()); - if (SubExpr.isInvalid()) - return ExprError(); + ExprResult SubExpr = getDerived().TransformExpr(E->getArgumentExpr()); + if (SubExpr.isInvalid()) + return ExprError(); - if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getArgumentExpr()) - return SemaRef.Owned(E); - } + if (!getDerived().AlwaysRebuild() && SubExpr.get() == E->getArgumentExpr()) + return SemaRef.Owned(E); return getDerived().RebuildUnaryExprOrTypeTrait(SubExpr.get(), E->getOperatorLoc(), diff --git a/clang/test/SemaTemplate/instantiate-sizeof.cpp b/clang/test/SemaTemplate/instantiate-sizeof.cpp new file mode 100644 index 00000000000..00d63d0c2fe --- /dev/null +++ b/clang/test/SemaTemplate/instantiate-sizeof.cpp @@ -0,0 +1,10 @@ +// RUN: %clang_cc1 -fsyntax-only -verify -std=c++11 %s + +// Make sure we handle contexts correctly with sizeof +template<typename T> void f(T n) { + int buffer[n]; + [] { int x = sizeof(sizeof(buffer)); }(); +} +int main() { + f<int>(1); +} diff --git a/clang/test/SemaTemplate/instantiate-typeof.cpp b/clang/test/SemaTemplate/instantiate-typeof.cpp new file mode 100644 index 00000000000..92873cb4b0b --- /dev/null +++ b/clang/test/SemaTemplate/instantiate-typeof.cpp @@ -0,0 +1,10 @@ +// RUN: %clang_cc1 -fsyntax-only -verify -std=c++11 %s + +// Make sure we correctly treat __typeof as potentially-evaluated when appropriate +template<typename T> void f(T n) { + int buffer[n]; // expected-note {{declared here}} + [] { __typeof(buffer) x; }(); // expected-error {{variable 'buffer' with variably modified type cannot be captured in a lambda expression}} +} +int main() { + f<int>(1); // expected-note {{in instantiation}} +} |