aboutsummaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorRichard Smith <richard-llvm@metafoo.co.uk>2012-07-10 22:12:55 +0000
committerRichard Smith <richard-llvm@metafoo.co.uk>2012-07-10 22:12:55 +0000
commita4334dffde250c22c339a974a7131914fe723180 (patch)
tree7a73181251ea1f6079501b93d42b9e70d96655ca /lib
parent48b6247804eacc262cc5508e0fbb74ed819fbb6e (diff)
Fix crash when constant-evaluating a CXXConstructExpr representing
value-initialization for an array of class type with a trivial default constructor. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@160024 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib')
-rw-r--r--lib/AST/ExprConstant.cpp17
1 files changed, 9 insertions, 8 deletions
diff --git a/lib/AST/ExprConstant.cpp b/lib/AST/ExprConstant.cpp
index f9583deadc..ad5aa54e48 100644
--- a/lib/AST/ExprConstant.cpp
+++ b/lib/AST/ExprConstant.cpp
@@ -3911,10 +3911,6 @@ bool ArrayExprEvaluator::VisitInitListExpr(const InitListExpr *E) {
}
bool ArrayExprEvaluator::VisitCXXConstructExpr(const CXXConstructExpr *E) {
- const ConstantArrayType *CAT = Info.Ctx.getAsConstantArrayType(E->getType());
- if (!CAT)
- return Error(E);
-
// FIXME: The Subobject here isn't necessarily right. This rarely matters,
// but sometimes does:
// struct S { constexpr S() : p(&p) {} void *p; };
@@ -3923,17 +3919,22 @@ bool ArrayExprEvaluator::VisitCXXConstructExpr(const CXXConstructExpr *E) {
APValue *Value = &Result;
bool HadZeroInit = true;
- while (CAT) {
+ QualType ElemTy = E->getType();
+ while (const ConstantArrayType *CAT =
+ Info.Ctx.getAsConstantArrayType(ElemTy)) {
Subobject.addArray(Info, E, CAT);
HadZeroInit &= !Value->isUninit();
if (!HadZeroInit)
*Value = APValue(APValue::UninitArray(), 0, CAT->getSize().getZExtValue());
if (!Value->hasArrayFiller())
return true;
- CAT = Info.Ctx.getAsConstantArrayType(CAT->getElementType());
Value = &Value->getArrayFiller();
+ ElemTy = CAT->getElementType();
}
+ if (!ElemTy->isRecordType())
+ return Error(E);
+
const CXXConstructorDecl *FD = E->getConstructor();
bool ZeroInit = E->requiresZeroInitialization();
@@ -3942,7 +3943,7 @@ bool ArrayExprEvaluator::VisitCXXConstructExpr(const CXXConstructExpr *E) {
return true;
if (ZeroInit) {
- ImplicitValueInitExpr VIE(CAT->getElementType());
+ ImplicitValueInitExpr VIE(ElemTy);
return EvaluateInPlace(*Value, Info, Subobject, &VIE);
}
@@ -3963,7 +3964,7 @@ bool ArrayExprEvaluator::VisitCXXConstructExpr(const CXXConstructExpr *E) {
return false;
if (ZeroInit && !HadZeroInit) {
- ImplicitValueInitExpr VIE(CAT->getElementType());
+ ImplicitValueInitExpr VIE(ElemTy);
if (!EvaluateInPlace(*Value, Info, Subobject, &VIE))
return false;
}