From: Chris Lattner Date: Sat, 25 Apr 2009 19:35:26 +0000 (+0000) Subject: fix PR4067: [Linux kernel] cannot aggregate codegen stmtexpr as lvalue X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=654599454c8e6cc83b1b9b3af43c49c2f66a26cb;p=clang fix PR4067: [Linux kernel] cannot aggregate codegen stmtexpr as lvalue git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@70067 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp index c49592eae8..86993fbe15 100644 --- a/lib/CodeGen/CGExpr.cpp +++ b/lib/CodeGen/CGExpr.cpp @@ -168,8 +168,10 @@ LValue CodeGenFunction::EmitLValue(const Expr *E) { case Expr::ObjCKVCRefExprClass: return EmitObjCKVCRefLValue(cast(E)); case Expr::ObjCSuperExprClass: - return EmitObjCSuperExpr(cast(E)); + return EmitObjCSuperExprLValue(cast(E)); + case Expr::StmtExprClass: + return EmitStmtExprLValue(cast(E)); case Expr::UnaryOperatorClass: return EmitUnaryOpLValue(cast(E)); case Expr::ArraySubscriptExprClass: @@ -1195,10 +1197,21 @@ CodeGenFunction::EmitObjCKVCRefLValue(const ObjCKVCRefExpr *E) { } LValue -CodeGenFunction::EmitObjCSuperExpr(const ObjCSuperExpr *E) { +CodeGenFunction::EmitObjCSuperExprLValue(const ObjCSuperExpr *E) { return EmitUnsupportedLValue(E, "use of super"); } +LValue CodeGenFunction::EmitStmtExprLValue(const StmtExpr *E) { + + // Can only get l-value for message expression returning aggregate type + RValue RV = EmitAnyExprToTemp(E); + // FIXME: can this be volatile? + return LValue::MakeAddr(RV.getAggregateAddr(), + E->getType().getCVRQualifiers(), + getContext().getObjCGCAttrKind(E->getType())); +} + + RValue CodeGenFunction::EmitCallExpr(llvm::Value *Callee, QualType CalleeType, CallExpr::const_arg_iterator ArgBeg, CallExpr::const_arg_iterator ArgEnd, diff --git a/lib/CodeGen/CGExprAgg.cpp b/lib/CodeGen/CGExprAgg.cpp index 2e45f2017b..a74741290b 100644 --- a/lib/CodeGen/CGExprAgg.cpp +++ b/lib/CodeGen/CGExprAgg.cpp @@ -78,8 +78,6 @@ public: } // Operators. - // case Expr::UnaryOperatorClass: - // case Expr::CastExprClass: void VisitCStyleCastExpr(CStyleCastExpr *E); void VisitImplicitCastExpr(ImplicitCastExpr *E); void VisitCallExpr(const CallExpr *E); diff --git a/lib/CodeGen/CodeGenFunction.h b/lib/CodeGen/CodeGenFunction.h index 2cad46ed01..9fc59527ce 100644 --- a/lib/CodeGen/CodeGenFunction.h +++ b/lib/CodeGen/CodeGenFunction.h @@ -645,7 +645,8 @@ public: LValue EmitObjCIvarRefLValue(const ObjCIvarRefExpr *E); LValue EmitObjCPropertyRefLValue(const ObjCPropertyRefExpr *E); LValue EmitObjCKVCRefLValue(const ObjCKVCRefExpr *E); - LValue EmitObjCSuperExpr(const ObjCSuperExpr *E); + LValue EmitObjCSuperExprLValue(const ObjCSuperExpr *E); + LValue EmitStmtExprLValue(const StmtExpr *E); //===--------------------------------------------------------------------===// // Scalar Expression Emission diff --git a/test/CodeGen/exprs.c b/test/CodeGen/exprs.c index f80ee41958..ad3e4e0956 100644 --- a/test/CodeGen/exprs.c +++ b/test/CodeGen/exprs.c @@ -99,3 +99,8 @@ int f6(int a0, struct s6 a1, struct s6 a2) { void f7() { __func__; } + +// PR4067 +int f8() { + return ({ foo(); }).Y; +}