From: Eli Friedman Date: Mon, 19 May 2008 17:51:16 +0000 (+0000) Subject: Fix the emission of expressions like char a[10] = "asdf"; previously, X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=922696f03ec9637449e2cba260493808b4977cd3;p=clang Fix the emission of expressions like char a[10] = "asdf"; previously, they were causing bad code to be emitted. There are two fixes here: one makes sure we emit a string that is long enough, and one makes sure we properly handle string initialization in init lists. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@51259 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp index 840ed4314f..8d36c8e26d 100644 --- a/lib/CodeGen/CGExpr.cpp +++ b/lib/CodeGen/CGExpr.cpp @@ -395,9 +395,16 @@ LValue CodeGenFunction::EmitUnaryOpLValue(const UnaryOperator *E) { LValue CodeGenFunction::EmitStringLiteralLValue(const StringLiteral *E) { assert(!E->isWide() && "FIXME: Wide strings not supported yet!"); + // Get the string data const char *StrData = E->getStrData(); unsigned Len = E->getByteLength(); std::string StringLiteral(StrData, StrData+Len); + + // Resize the string to the right size + const ConstantArrayType *CAT = E->getType()->getAsConstantArrayType(); + uint64_t RealLen = CAT->getSize().getZExtValue(); + StringLiteral.resize(RealLen, '\0'); + return LValue::MakeAddr(CGM.GetAddrOfConstantString(StringLiteral)); } diff --git a/lib/CodeGen/CGExprAgg.cpp b/lib/CodeGen/CGExprAgg.cpp index 6b68705af7..c7c250ee7b 100644 --- a/lib/CodeGen/CGExprAgg.cpp +++ b/lib/CodeGen/CGExprAgg.cpp @@ -53,7 +53,7 @@ public: void EmitAggregateClear(llvm::Value *DestPtr, QualType Ty); void EmitNonConstInit(InitListExpr *E); - + //===--------------------------------------------------------------------===// // Visitor Methods //===--------------------------------------------------------------------===// @@ -336,7 +336,6 @@ void AggExprEmitter::EmitNullInitializationToLValue(LValue LV, QualType T) { } } - void AggExprEmitter::VisitInitListExpr(InitListExpr *E) { if (E->isConstantExpr(CGF.getContext(), 0)) { // FIXME: call into const expr emitter so that we can emit @@ -355,6 +354,14 @@ void AggExprEmitter::VisitInitListExpr(InitListExpr *E) { cast(APType->getElementType()); uint64_t NumInitElements = E->getNumInits(); + + if (E->getNumInits() > 0 && + E->getType().getCanonicalType().getUnqualifiedType() == + E->getInit(0)->getType().getCanonicalType().getUnqualifiedType()) { + EmitAggLoadOfLValue(E->getInit(0)); + return; + } + uint64_t NumArrayElements = AType->getNumElements(); QualType ElementType = E->getType()->getAsArrayType()->getElementType(); diff --git a/test/CodeGen/string-init.c b/test/CodeGen/string-init.c new file mode 100644 index 0000000000..1d1a740faa --- /dev/null +++ b/test/CodeGen/string-init.c @@ -0,0 +1,8 @@ +// RUN: clang -emit-llvm %s -o - | not grep "[5 x i8]" +// RUN: clang -emit-llvm %s -o - | not grep "store" + +void test(void) { + char a[10] = "asdf"; + char b[10] = { "asdf" }; +} +