diff options
author | Eli Friedman <eli.friedman@gmail.com> | 2009-11-16 23:53:01 +0000 |
---|---|---|
committer | Eli Friedman <eli.friedman@gmail.com> | 2009-11-16 23:53:01 +0000 |
commit | 4d26b43f7c6fc9d2974da7e7389337fe32dc29d0 (patch) | |
tree | 93eb433cf93005189c415f40632853717dbd9341 /lib/CodeGen/CGCXX.cpp | |
parent | 39f36e37f53bfec22a4bc2a594f2dd314395c86c (diff) |
Fix up EmitMemberInitializer to handle many more cases.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@88999 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen/CGCXX.cpp')
-rw-r--r-- | lib/CodeGen/CGCXX.cpp | 35 |
1 files changed, 24 insertions, 11 deletions
diff --git a/lib/CodeGen/CGCXX.cpp b/lib/CodeGen/CGCXX.cpp index 442d4fc30e..97e1868f55 100644 --- a/lib/CodeGen/CGCXX.cpp +++ b/lib/CodeGen/CGCXX.cpp @@ -1543,6 +1543,18 @@ static void EmitMemberInitializer(CodeGenFunction &CGF, if (Array) FieldType = CGF.getContext().getBaseElementType(FieldType); + // We lose the constructor for anonymous union members, so handle them + // explicitly. + // FIXME: This is somwhat ugly. + if (MemberInit->getAnonUnionMember() && FieldType->getAs<RecordType>()) { + if (MemberInit->getNumArgs()) + CGF.EmitAggExpr(*MemberInit->arg_begin(), LHS.getAddress(), + LHS.isVolatileQualified()); + else + CGF.EmitAggregateClear(LHS.getAddress(), Field->getType()); + return; + } + if (FieldType->getAs<RecordType>()) { assert(MemberInit->getConstructor() && "EmitCtorPrologue - no constructor to initialize member"); @@ -1565,21 +1577,22 @@ static void EmitMemberInitializer(CodeGenFunction &CGF, assert(MemberInit->getNumArgs() == 1 && "Initializer count must be 1 only"); Expr *RhsExpr = *MemberInit->arg_begin(); RValue RHS; - if (FieldType->isReferenceType()) + if (FieldType->isReferenceType()) { RHS = CGF.EmitReferenceBindingToExpr(RhsExpr, FieldType, /*IsInitializer=*/true); - else if (FieldType->isMemberFunctionPointerType()) - RHS = RValue::get(CGF.CGM.EmitConstantExpr(RhsExpr, FieldType, &CGF)); - else + CGF.EmitStoreThroughLValue(RHS, LHS, FieldType); + } else if (Array) { + CGF.EmitMemSetToZero(LHS.getAddress(), Field->getType()); + } else if (!CGF.hasAggregateLLVMType(RhsExpr->getType())) { RHS = RValue::get(CGF.EmitScalarExpr(RhsExpr, true)); - if (Array && !FieldType->getAs<RecordType>()) { - // value initialize a non-class array data member using arr() syntax in - // initializer list. - QualType Ty = CGF.getContext().getCanonicalType((Field)->getType()); - CGF.EmitMemSetToZero(LHS.getAddress(), Ty); - } - else CGF.EmitStoreThroughLValue(RHS, LHS, FieldType); + } else if (RhsExpr->getType()->isAnyComplexType()) { + CGF.EmitComplexExprIntoAddr(RhsExpr, LHS.getAddress(), + LHS.isVolatileQualified()); + } else { + // Handle member function pointers; other aggregates shouldn't get this far. + CGF.EmitAggExpr(RhsExpr, LHS.getAddress(), LHS.isVolatileQualified()); + } } /// EmitCtorPrologue - This routine generates necessary code to initialize |