From 04a913b9584319d3f5d68c08168c217b8ffd186f Mon Sep 17 00:00:00 2001 From: Chris Lattner Date: Fri, 31 Aug 2007 22:09:40 +0000 Subject: [PATCH] implement code generation for scalar stmt expressions. llvm-svn: 41656 --- clang/CodeGen/CGExprScalar.cpp | 7 +++++++ clang/CodeGen/CGStmt.cpp | 23 ++++++++++++++++++++--- clang/CodeGen/CodeGenFunction.h | 2 +- 3 files changed, 28 insertions(+), 4 deletions(-) diff --git a/clang/CodeGen/CGExprScalar.cpp b/clang/CodeGen/CGExprScalar.cpp index 1499054b6cce..db0e6bf492e5 100644 --- a/clang/CodeGen/CGExprScalar.cpp +++ b/clang/CodeGen/CGExprScalar.cpp @@ -129,6 +129,8 @@ public: return CGF.EmitCallExpr(E).getVal(); } + Value *VisitStmtExpr(const StmtExpr *E); + // Unary Operators. Value *VisitPrePostIncDec(const UnaryOperator *E, bool isInc, bool isPre); Value *VisitUnaryPostDec(const UnaryOperator *E) { @@ -437,6 +439,11 @@ Value *ScalarExprEmitter::EmitCastExpr(const Expr *E, QualType DestTy) { DestTy); } +Value *ScalarExprEmitter::VisitStmtExpr(const StmtExpr *E) { + return CGF.EmitCompoundStmt(*E->getSubStmt(), true).getVal(); +} + + //===----------------------------------------------------------------------===// // Unary Operators //===----------------------------------------------------------------------===// diff --git a/clang/CodeGen/CGStmt.cpp b/clang/CodeGen/CGStmt.cpp index 04c9c1d3eb70..85a6ca8705ed 100644 --- a/clang/CodeGen/CGStmt.cpp +++ b/clang/CodeGen/CGStmt.cpp @@ -60,12 +60,29 @@ void CodeGenFunction::EmitStmt(const Stmt *S) { } } -void CodeGenFunction::EmitCompoundStmt(const CompoundStmt &S) { +/// EmitCompoundStmt - Emit a compound statement {..} node. If GetLast is true, +/// this captures the expression result of the last sub-statement and returns it +/// (for use by the statement expression extension). +RValue CodeGenFunction::EmitCompoundStmt(const CompoundStmt &S, bool GetLast) { // FIXME: handle vla's etc. + if (S.body_empty() || !isa(S.body_back())) GetLast = false; - for (CompoundStmt::const_body_iterator I = S.body_begin(), E = S.body_end(); - I != E; ++I) + for (CompoundStmt::const_body_iterator I = S.body_begin(), + E = S.body_end()-GetLast; I != E; ++I) EmitStmt(*I); + + + if (!GetLast) + return RValue::get(0); + + const Expr *Last = cast(S.body_back()); + if (!hasAggregateLLVMType(Last->getType())) + return RValue::get(EmitScalarExpr(Last)); + assert(0 && "Unimp"); + //else if (Last->getType()->isComplexType()) + // EmitComplexExpr(Last); + //else + // EmitAggExpr(E, 0, false); } void CodeGenFunction::EmitBlock(llvm::BasicBlock *BB) { diff --git a/clang/CodeGen/CodeGenFunction.h b/clang/CodeGen/CodeGenFunction.h index af8d80bbb279..a597f4326869 100644 --- a/clang/CodeGen/CodeGenFunction.h +++ b/clang/CodeGen/CodeGenFunction.h @@ -265,7 +265,7 @@ public: //===--------------------------------------------------------------------===// void EmitStmt(const Stmt *S); - void EmitCompoundStmt(const CompoundStmt &S); + RValue EmitCompoundStmt(const CompoundStmt &S, bool GetLast = false); void EmitLabelStmt(const LabelStmt &S); void EmitGotoStmt(const GotoStmt &S); void EmitIfStmt(const IfStmt &S);