aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnders Carlsson <andersca@mac.com>2010-02-04 17:26:01 +0000
committerAnders Carlsson <andersca@mac.com>2010-02-04 17:26:01 +0000
commitc1b32f69687ed289fb1150df34965ada250caf70 (patch)
tree484c7935c335aec5d610e86a1d9b73e67b180a7a
parent4e3014be0606d6be5554d76f317d5908be3bccfc (diff)
Fix a bug where we would not mark temporaries as conditional when emitting a conditional operator as an lvalue.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@95311 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--lib/CodeGen/CGExpr.cpp8
-rw-r--r--test/CodeGenCXX/conditional-temporaries.cpp6
2 files changed, 13 insertions, 1 deletions
diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp
index 2ceefae0a0..563db0b2be 100644
--- a/lib/CodeGen/CGExpr.cpp
+++ b/lib/CodeGen/CGExpr.cpp
@@ -1538,9 +1538,12 @@ CodeGenFunction::EmitConditionalOperatorLValue(const ConditionalOperator* E) {
EmitBranchOnBoolExpr(E->getCond(), LHSBlock, RHSBlock);
+ // Any temporaries created here are conditional.
+ BeginConditionalBranch();
EmitBlock(LHSBlock);
-
LValue LHS = EmitLValue(E->getLHS());
+ EndConditionalBranch();
+
if (!LHS.isSimple())
return EmitUnsupportedLValue(E, "conditional operator");
@@ -1548,8 +1551,11 @@ CodeGenFunction::EmitConditionalOperatorLValue(const ConditionalOperator* E) {
Builder.CreateStore(LHS.getAddress(), Temp);
EmitBranch(ContBlock);
+ // Any temporaries created here are conditional.
+ BeginConditionalBranch();
EmitBlock(RHSBlock);
LValue RHS = EmitLValue(E->getRHS());
+ EndConditionalBranch();
if (!RHS.isSimple())
return EmitUnsupportedLValue(E, "conditional operator");
diff --git a/test/CodeGenCXX/conditional-temporaries.cpp b/test/CodeGenCXX/conditional-temporaries.cpp
index 66fd803c2e..b8ea5129d4 100644
--- a/test/CodeGenCXX/conditional-temporaries.cpp
+++ b/test/CodeGenCXX/conditional-temporaries.cpp
@@ -9,14 +9,20 @@ struct A {
A() : i(0) { ctorcalls++; }
~A() { dtorcalls++; }
int i;
+
+ friend const A& operator<<(const A& a, int n) {
+ return a;
+ }
};
void g(int) { }
+void g(const A&) { }
void f1(bool b) {
g(b ? A().i : 0);
g(b || A().i);
g(b && A().i);
+ g(b ? A() << 1 : A() << 2);
}
struct Checker {