SemaInit.cpp revision ed8a93d17b8936dc7978cdc37f3f00fc49d24f71
10cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//===--- SemaInit.cpp - Semantic Analysis for Initializers ----------------===//
20cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//
30cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//                     The LLVM Compiler Infrastructure
40cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//
50cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff// This file is distributed under the University of Illinois Open Source
60cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff// License. See LICENSE.TXT for details.
70cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//
80cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//===----------------------------------------------------------------------===//
90cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//
10dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner// This file implements semantic analysis for initializers. The main entry
11dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner// point is Sema::CheckInitList(), but all of the work is performed
12dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner// within the InitListChecker class.
13dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner//
148b419b9b5f21cf948cf6fe788f67bf1efd97524cChris Lattner// This file also implements Sema::CheckInitializerTypes.
150cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//
160cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff//===----------------------------------------------------------------------===//
170cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
180cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff#include "Sema.h"
1905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor#include "clang/Parse/Designator.h"
200cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff#include "clang/AST/ASTContext.h"
2179e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner#include "clang/AST/ExprObjC.h"
22c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor#include <map>
2305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregorusing namespace clang;
240cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
25dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner//===----------------------------------------------------------------------===//
26dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner// Sema Initialization Checking
27dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner//===----------------------------------------------------------------------===//
28dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
2979e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattnerstatic Expr *IsStringInit(Expr *Init, QualType DeclType, ASTContext &Context) {
308879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  const ArrayType *AT = Context.getAsArrayType(DeclType);
318879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  if (!AT) return 0;
328879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner
338879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // See if this is a string literal or @encode.
348879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  Init = Init->IgnoreParens();
358879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner
368879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // Handle @encode, which is a narrow string.
378879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  if (isa<ObjCEncodeExpr>(Init) && AT->getElementType()->isCharType())
388879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner    return Init;
398879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner
408879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // Otherwise we can only handle string literals.
418879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  StringLiteral *SL = dyn_cast<StringLiteral>(Init);
42220b6369d7717bfe6894b46cef055d3e763827f2Chris Lattner  if (SL == 0) return 0;
438879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner
448879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // char array can be initialized with a narrow string.
458879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // Only allow char x[] = "foo";  not char x[] = L"foo";
468879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  if (!SL->isWide())
478879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner    return AT->getElementType()->isCharType() ? Init : 0;
488879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner
498879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // wchar_t array can be initialized with a wide string: C99 6.7.8p15:
508879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // "An array with element type compatible with wchar_t may be initialized by a
518879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner  // wide string literal, optionally enclosed in braces."
5219753cfa6059b237880a91f21ef58f2d8984845fChris Lattner  if (Context.typesAreCompatible(Context.getWCharType(), AT->getElementType()))
538879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner    // Only allow wchar_t x[] = L"foo";  not wchar_t x[] = "foo";
548879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner    return Init;
558879e3b29d2527260c401bce0ed0e401901ef601Chris Lattner
56dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  return 0;
57dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner}
58dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
5995e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattnerstatic bool CheckSingleInitializer(Expr *&Init, QualType DeclType,
6095e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner                                   bool DirectInit, Sema &S) {
61dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  // Get the type before calling CheckSingleAssignmentConstraints(), since
62dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  // it can promote the expression.
63dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  QualType InitType = Init->getType();
64dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
6595e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner  if (S.getLangOptions().CPlusPlus) {
66dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    // FIXME: I dislike this error message. A lot.
6795e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner    if (S.PerformImplicitConversion(Init, DeclType, "initializing", DirectInit))
6895e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner      return S.Diag(Init->getSourceRange().getBegin(),
6995e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner                    diag::err_typecheck_convert_incompatible)
7095e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner        << DeclType << Init->getType() << "initializing"
7195e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner        << Init->getSourceRange();
72dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    return false;
73dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  }
74dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
7595e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner  Sema::AssignConvertType ConvTy =
7695e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner    S.CheckSingleAssignmentConstraints(DeclType, Init);
7795e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner  return S.DiagnoseAssignmentResult(ConvTy, Init->getLocStart(), DeclType,
78dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner                                  InitType, Init, "initializing");
79dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner}
80dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
8179e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattnerstatic void CheckStringInit(Expr *Str, QualType &DeclT, Sema &S) {
8279e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner  // Get the length of the string as parsed.
8379e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner  uint64_t StrLength =
8479e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner    cast<ConstantArrayType>(Str->getType())->getSize().getZExtValue();
8579e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner
86dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
8779e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner  const ArrayType *AT = S.Context.getAsArrayType(DeclT);
88dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  if (const IncompleteArrayType *IAT = dyn_cast<IncompleteArrayType>(AT)) {
89dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    // C99 6.7.8p14. We have an array of character type with unknown size
90dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    // being initialized to a string literal.
91dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    llvm::APSInt ConstVal(32);
9219da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner    ConstVal = StrLength;
93dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    // Return a new array type (C99 6.7.8p22).
94f71ae8d8024561f92dd7916363e7a791684563ccChris Lattner    DeclT = S.Context.getConstantArrayType(IAT->getElementType(), ConstVal,
95f71ae8d8024561f92dd7916363e7a791684563ccChris Lattner                                           ArrayType::Normal, 0);
9619da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner    return;
97dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  }
9819da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner
9919da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  const ConstantArrayType *CAT = cast<ConstantArrayType>(AT);
10019da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner
10119da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  // C99 6.7.8p14. We have an array of character type with known size.  However,
10219da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  // the size may be smaller or larger than the string we are initializing.
10319da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  // FIXME: Avoid truncation for 64-bit length strings.
10479e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner  if (StrLength-1 > CAT->getSize().getZExtValue())
10519da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner    S.Diag(Str->getSourceRange().getBegin(),
10619da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner           diag::warn_initializer_string_for_char_array_too_long)
10719da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner      << Str->getSourceRange();
10819da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner
10919da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  // Set the type to the actual size that we are initializing.  If we have
11019da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  // something like:
11119da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  //   char x[1] = "foo";
11219da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner  // then this will set the string literal's type to char[1].
113f71ae8d8024561f92dd7916363e7a791684563ccChris Lattner  Str->setType(DeclT);
114dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner}
115dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
116dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattnerbool Sema::CheckInitializerTypes(Expr *&Init, QualType &DeclType,
117dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner                                 SourceLocation InitLoc,
118dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner                                 DeclarationName InitEntity,
119dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner                                 bool DirectInit) {
120dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  if (DeclType->isDependentType() || Init->isTypeDependent())
121dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    return false;
122dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
123dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  // C++ [dcl.init.ref]p1:
124dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  //   A variable declared to be a T&, that is "reference to type T"
125dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  //   (8.3.2), shall be initialized by an object, or function, of
126dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  //   type T or by an object that can be converted into a T.
127dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  if (DeclType->isReferenceType())
128dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    return CheckReferenceInit(Init, DeclType, 0, false, DirectInit);
129dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
130dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  // C99 6.7.8p3: The type of the entity to be initialized shall be an array
131dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  // of unknown size ("[]") or an object type that is not a variable array type.
132dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  if (const VariableArrayType *VAT = Context.getAsVariableArrayType(DeclType))
133dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    return Diag(InitLoc,  diag::err_variable_object_no_init)
134dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    << VAT->getSizeExpr()->getSourceRange();
135dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
136dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  InitListExpr *InitList = dyn_cast<InitListExpr>(Init);
137dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  if (!InitList) {
138dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    // FIXME: Handle wide strings
13979e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner    if (Expr *Str = IsStringInit(Init, DeclType, Context)) {
14079e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner      CheckStringInit(Str, DeclType, *this);
14119da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner      return false;
14219da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner    }
143dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
144dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    // C++ [dcl.init]p14:
145dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    //   -- If the destination type is a (possibly cv-qualified) class
146dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    //      type:
147dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    if (getLangOptions().CPlusPlus && DeclType->isRecordType()) {
148dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      QualType DeclTypeC = Context.getCanonicalType(DeclType);
149dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      QualType InitTypeC = Context.getCanonicalType(Init->getType());
150dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
151dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //   -- If the initialization is direct-initialization, or if it is
152dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      copy-initialization where the cv-unqualified version of the
153dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      source type is the same class as, or a derived class of, the
154dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      class of the destination, constructors are considered.
155dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      if ((DeclTypeC.getUnqualifiedType() == InitTypeC.getUnqualifiedType()) ||
156dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner          IsDerivedFrom(InitTypeC, DeclTypeC)) {
157dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        CXXConstructorDecl *Constructor
158dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        = PerformInitializationByConstructor(DeclType, &Init, 1,
159dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner                                             InitLoc, Init->getSourceRange(),
160dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner                                             InitEntity,
161dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner                                             DirectInit? IK_Direct : IK_Copy);
162dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        return Constructor == 0;
163dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      }
164dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
165dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //   -- Otherwise (i.e., for the remaining copy-initialization
166dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      cases), user-defined conversion sequences that can
167dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      convert from the source type to the destination type or
168dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      (when a conversion function is used) to a derived class
169dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      thereof are enumerated as described in 13.3.1.4, and the
170dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      best one is chosen through overload resolution
171dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      (13.3). If the conversion cannot be done or is
172dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      ambiguous, the initialization is ill-formed. The
173dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      function selected is called with the initializer
174dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      expression as its argument; if the function is a
175dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      constructor, the call initializes a temporary of the
176dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      //      destination type.
177dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      // FIXME: We're pretending to do copy elision here; return to
178dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      // this when we have ASTs for such things.
179dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      if (!PerformImplicitConversion(Init, DeclType, "initializing"))
180dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        return false;
181dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
182dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      if (InitEntity)
183dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        return Diag(InitLoc, diag::err_cannot_initialize_decl)
184dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        << InitEntity << (int)(Init->isLvalue(Context) == Expr::LV_Valid)
185dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        << Init->getType() << Init->getSourceRange();
186dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      else
187dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        return Diag(InitLoc, diag::err_cannot_initialize_decl_noname)
188dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        << DeclType << (int)(Init->isLvalue(Context) == Expr::LV_Valid)
189dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner        << Init->getType() << Init->getSourceRange();
190dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    }
191dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
192dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    // C99 6.7.8p16.
193dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner    if (DeclType->isArrayType())
194dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      return Diag(Init->getLocStart(), diag::err_array_init_list_required)
195dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner      << Init->getSourceRange();
196dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
19795e8d658fbea5b53c5e77c48f883fe6c9f7f620fChris Lattner    return CheckSingleInitializer(Init, DeclType, DirectInit, *this);
198dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  }
199dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
200dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  bool hadError = CheckInitList(InitList, DeclType);
201dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  Init = InitList;
202dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner  return hadError;
203dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner}
204dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
205dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner//===----------------------------------------------------------------------===//
206dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner// Semantic checking for initializer lists.
207dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner//===----------------------------------------------------------------------===//
208dd8e0065207e953bb28b95ad9cb6b2c13f56b3b8Chris Lattner
2099e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// @brief Semantic checking for initializer lists.
2109e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor///
2119e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// The InitListChecker class contains a set of routines that each
2129e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// handle the initialization of a certain kind of entity, e.g.,
2139e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// arrays, vectors, struct/union types, scalars, etc. The
2149e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// InitListChecker itself performs a recursive walk of the subobject
2159e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// structure of the type to be initialized, while stepping through
2169e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// the initializer list one element at a time. The IList and Index
2179e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// parameters to each of the Check* routines contain the active
2189e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// (syntactic) initializer list and the index into that initializer
2199e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// list that represents the current initializer. Each routine is
2209e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// responsible for moving that Index forward as it consumes elements.
2219e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor///
2229e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// Each Check* routine also has a StructuredList/StructuredIndex
2239e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// arguments, which contains the current the "structured" (semantic)
2249e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// initializer list and the index into that initializer list where we
2259e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// are copying initializers as we map them over to the semantic
2269e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// list. Once we have completed our recursive walk of the subobject
2279e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// structure, we will have constructed a full semantic initializer
2289e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// list.
2299e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor///
2309e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// C99 designators cause changes in the initializer list traversal,
2319e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// because they make the initialization "jump" into a specific
2329e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// subobject and then continue the initialization from that
2339e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// point. CheckDesignatedInitializer() recursively steps into the
2349e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// designated subobject and manages backing out the recursion to
2359e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor/// initialize the subobjects after the one designated.
2368b419b9b5f21cf948cf6fe788f67bf1efd97524cChris Lattnernamespace {
237c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregorclass InitListChecker {
2380820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  Sema &SemaRef;
239c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  bool hadError;
240c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  std::map<InitListExpr *, InitListExpr *> SyntacticToSemantic;
241c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  InitListExpr *FullyStructuredList;
242c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor
243c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  void CheckImplicitInitList(InitListExpr *ParentIList, QualType T,
2449e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                             unsigned &Index, InitListExpr *StructuredList,
245eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             unsigned &StructuredIndex,
246eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             bool TopLevelObject = false);
247c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  void CheckExplicitInitList(InitListExpr *IList, QualType &T,
2489e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                             unsigned &Index, InitListExpr *StructuredList,
249eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             unsigned &StructuredIndex,
250eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             bool TopLevelObject = false);
251c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  void CheckListElementTypes(InitListExpr *IList, QualType &DeclType,
252c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                             bool SubobjectIsDesignatorContext,
253c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                             unsigned &Index,
2549e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                             InitListExpr *StructuredList,
255eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             unsigned &StructuredIndex,
256eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             bool TopLevelObject = false);
257c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  void CheckSubElementType(InitListExpr *IList, QualType ElemType,
258c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                           unsigned &Index,
2599e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                           InitListExpr *StructuredList,
2609e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                           unsigned &StructuredIndex);
261930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  void CheckScalarType(InitListExpr *IList, QualType DeclType,
262c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                       unsigned &Index,
2639e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                       InitListExpr *StructuredList,
2649e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                       unsigned &StructuredIndex);
265930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  void CheckReferenceType(InitListExpr *IList, QualType DeclType,
266930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                          unsigned &Index,
267930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                          InitListExpr *StructuredList,
268930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                          unsigned &StructuredIndex);
269c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  void CheckVectorType(InitListExpr *IList, QualType DeclType, unsigned &Index,
2709e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                       InitListExpr *StructuredList,
2719e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                       unsigned &StructuredIndex);
272c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  void CheckStructUnionTypes(InitListExpr *IList, QualType DeclType,
273c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                             RecordDecl::field_iterator Field,
274c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                             bool SubobjectIsDesignatorContext, unsigned &Index,
2759e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                             InitListExpr *StructuredList,
276eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             unsigned &StructuredIndex,
277eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                             bool TopLevelObject = false);
278c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  void CheckArrayType(InitListExpr *IList, QualType &DeclType,
279c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                      llvm::APSInt elementIndex,
280c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                      bool SubobjectIsDesignatorContext, unsigned &Index,
2819e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                      InitListExpr *StructuredList,
2829e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                      unsigned &StructuredIndex);
283c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  bool CheckDesignatedInitializer(InitListExpr *IList, DesignatedInitExpr *DIE,
284c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                  DesignatedInitExpr::designators_iterator D,
285c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                  QualType &CurrentObjectType,
286c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                  RecordDecl::field_iterator *NextField,
287c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                  llvm::APSInt *NextElementIndex,
288c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                  unsigned &Index,
289c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                  InitListExpr *StructuredList,
290c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                  unsigned &StructuredIndex,
291eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                  bool FinishSubobjectInit,
292eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                  bool TopLevelObject);
293c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  InitListExpr *getStructuredSubobjectInit(InitListExpr *IList, unsigned Index,
294c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                           QualType CurrentObjectType,
295c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                           InitListExpr *StructuredList,
296c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                           unsigned StructuredIndex,
297c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                           SourceRange InitRange);
2989e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor  void UpdateStructuredListElement(InitListExpr *StructuredList,
2999e80f7252ec1b91142e41790e4491c61e14b9472Douglas Gregor                                   unsigned &StructuredIndex,
300c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor                                   Expr *expr);
301c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  int numArrayElements(QualType DeclType);
302c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  int numStructUnionElements(QualType DeclType);
303930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor
304930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  void FillInValueInitializations(InitListExpr *ILE);
305c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregorpublic:
3060820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  InitListChecker(Sema &S, InitListExpr *IL, QualType &T);
307c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  bool HadError() { return hadError; }
308c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor
309c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  // @brief Retrieves the fully-structured initializer list used for
310c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  // semantic analysis and code generation.
311c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  InitListExpr *getFullyStructuredList() const { return FullyStructuredList; }
312c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor};
3138b419b9b5f21cf948cf6fe788f67bf1efd97524cChris Lattner} // end anonymous namespace
31468355a57bb9d5daccd3fc73e92370ba2b1a6eafbChris Lattner
3154c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// Recursively replaces NULL values within the given initializer list
3164c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// with expressions that perform value-initialization of the
3174c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// appropriate type.
318930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregorvoid InitListChecker::FillInValueInitializations(InitListExpr *ILE) {
3190820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  assert((ILE->getType() != SemaRef.Context.VoidTy) &&
320930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor         "Should not have void type");
32187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  SourceLocation Loc = ILE->getSourceRange().getBegin();
32287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  if (ILE->getSyntacticForm())
32387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    Loc = ILE->getSyntacticForm()->getSourceRange().getBegin();
32487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
3254c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  if (const RecordType *RType = ILE->getType()->getAsRecordType()) {
3264c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    unsigned Init = 0, NumInits = ILE->getNumInits();
3274c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    for (RecordDecl::field_iterator Field = RType->getDecl()->field_begin(),
3284c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                 FieldEnd = RType->getDecl()->field_end();
3294c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor         Field != FieldEnd; ++Field) {
3304c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      if (Field->isUnnamedBitfield())
3314c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor        continue;
3324c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
33387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      if (Init >= NumInits || !ILE->getInit(Init)) {
334930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        if (Field->getType()->isReferenceType()) {
335930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor          // C++ [dcl.init.aggr]p9:
336930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor          //   If an incomplete or empty initializer-list leaves a
337930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor          //   member of reference type uninitialized, the program is
338930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor          //   ill-formed.
3390820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner          SemaRef.Diag(Loc, diag::err_init_reference_member_uninitialized)
340930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor            << Field->getType()
341930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor            << ILE->getSyntacticForm()->getSourceRange();
3420820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner          SemaRef.Diag(Field->getLocation(),
343930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                        diag::note_uninit_reference_member);
344930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor          hadError = true;
34587fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor          return;
3460820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        } else if (SemaRef.CheckValueInitialization(Field->getType(), Loc)) {
34787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor          hadError = true;
34887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor          return;
349930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        }
35087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
35187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        // FIXME: If value-initialization involves calling a
35287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        // constructor, should we make that call explicit in the
35387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        // representation (even when it means extending the
35487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        // initializer list)?
35587fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        if (Init < NumInits && !hadError)
35687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor          ILE->setInit(Init,
3570820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner              new (SemaRef.Context) ImplicitValueInitExpr(Field->getType()));
35887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      } else if (InitListExpr *InnerILE
3593498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor                 = dyn_cast<InitListExpr>(ILE->getInit(Init)))
360930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        FillInValueInitializations(InnerILE);
3614c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      ++Init;
362930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor
363930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // Only look at the first initialization of a union.
364930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      if (RType->getDecl()->isUnion())
365930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        break;
3664c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    }
3674c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
3684c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    return;
3694c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  }
3704c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
3714c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  QualType ElementType;
3724c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
37387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  unsigned NumInits = ILE->getNumInits();
37487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  unsigned NumElements = NumInits;
3750820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  if (const ArrayType *AType = SemaRef.Context.getAsArrayType(ILE->getType())) {
3764c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ElementType = AType->getElementType();
37787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    if (const ConstantArrayType *CAType = dyn_cast<ConstantArrayType>(AType))
37887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      NumElements = CAType->getSize().getZExtValue();
37987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  } else if (const VectorType *VType = ILE->getType()->getAsVectorType()) {
3804c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ElementType = VType->getElementType();
38187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    NumElements = VType->getNumElements();
38287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  } else
3834c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ElementType = ILE->getType();
3844c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
38587fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  for (unsigned Init = 0; Init != NumElements; ++Init) {
38687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    if (Init >= NumInits || !ILE->getInit(Init)) {
3870820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      if (SemaRef.CheckValueInitialization(ElementType, Loc)) {
38887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        hadError = true;
38987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        return;
39087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      }
39187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
39287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      // FIXME: If value-initialization involves calling a
39387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      // constructor, should we make that call explicit in the
39487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      // representation (even when it means extending the
39587fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      // initializer list)?
39687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      if (Init < NumInits && !hadError)
39787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        ILE->setInit(Init,
3980820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner                     new (SemaRef.Context) ImplicitValueInitExpr(ElementType));
39987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    }
40068355a57bb9d5daccd3fc73e92370ba2b1a6eafbChris Lattner    else if (InitListExpr *InnerILE =dyn_cast<InitListExpr>(ILE->getInit(Init)))
401930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      FillInValueInitializations(InnerILE);
4024c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  }
4034c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor}
4044c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
40568355a57bb9d5daccd3fc73e92370ba2b1a6eafbChris Lattner
4060820254f97bb8925d933a3664ea1c6fca3997b97Chris LattnerInitListChecker::InitListChecker(Sema &S, InitListExpr *IL, QualType &T)
4070820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  : SemaRef(S) {
4080cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  hadError = false;
409c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman
410b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  unsigned newIndex = 0;
4114c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  unsigned newStructuredIndex = 0;
4124c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  FullyStructuredList
413ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor    = getStructuredSubobjectInit(IL, newIndex, T, 0, 0, IL->getSourceRange());
414eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor  CheckExplicitInitList(IL, T, newIndex, FullyStructuredList, newStructuredIndex,
415eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                        /*TopLevelObject=*/true);
416c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman
417930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  if (!hadError)
418930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    FillInValueInitializations(FullyStructuredList);
4190cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
4200cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
4210cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroffint InitListChecker::numArrayElements(QualType DeclType) {
422638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman  // FIXME: use a proper constant
423638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman  int maxElements = 0x7FFFFFFF;
424c63a1f276f7b324fd9a4be82098b1c8f7bf30733Chris Lattner  if (const ConstantArrayType *CAT =
4250820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Context.getAsConstantArrayType(DeclType)) {
4260cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    maxElements = static_cast<int>(CAT->getSize().getZExtValue());
4270cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
4280cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  return maxElements;
4290cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
4300cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
4310cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroffint InitListChecker::numStructUnionElements(QualType DeclType) {
4320cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  RecordDecl *structDecl = DeclType->getAsRecordType()->getDecl();
4334c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  int InitializableMembers = 0;
4344c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  for (RecordDecl::field_iterator Field = structDecl->field_begin(),
4354c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                               FieldEnd = structDecl->field_end();
4364c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor       Field != FieldEnd; ++Field) {
4374c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    if ((*Field)->getIdentifier() || !(*Field)->isBitField())
4384c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      ++InitializableMembers;
4394c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  }
44039ba4aeca296b1c9f04bde7d9d3cbbf129f1abd3Argyrios Kyrtzidis  if (structDecl->isUnion())
441f84eda37251c679e2f20343c47a4a3586d9a8e21Eli Friedman    return std::min(InitializableMembers, 1);
442f84eda37251c679e2f20343c47a4a3586d9a8e21Eli Friedman  return InitializableMembers - structDecl->hasFlexibleArrayMember();
4430cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
4440cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
4450cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroffvoid InitListChecker::CheckImplicitInitList(InitListExpr *ParentIList,
4464c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            QualType T, unsigned &Index,
4474c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            InitListExpr *StructuredList,
448eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            unsigned &StructuredIndex,
449eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            bool TopLevelObject) {
4500cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  int maxElements = 0;
4510cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
4520cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  if (T->isArrayType())
4530cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    maxElements = numArrayElements(T);
4540cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  else if (T->isStructureType() || T->isUnionType())
4550cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    maxElements = numStructUnionElements(T);
456b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  else if (T->isVectorType())
457b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman    maxElements = T->getAsVectorType()->getNumElements();
4580cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  else
4590cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    assert(0 && "CheckImplicitInitList(): Illegal type");
460b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman
461402256fc665ba179873ffcb4d630e28cbea42f27Eli Friedman  if (maxElements == 0) {
4620820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(ParentIList->getInit(Index)->getLocStart(),
463402256fc665ba179873ffcb4d630e28cbea42f27Eli Friedman                  diag::err_implicit_empty_initializer);
4644c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++Index;
465402256fc665ba179873ffcb4d630e28cbea42f27Eli Friedman    hadError = true;
466402256fc665ba179873ffcb4d630e28cbea42f27Eli Friedman    return;
467402256fc665ba179873ffcb4d630e28cbea42f27Eli Friedman  }
468402256fc665ba179873ffcb4d630e28cbea42f27Eli Friedman
4694c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // Build a structured initializer list corresponding to this subobject.
4704c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  InitListExpr *StructuredSubobjectInitList
4714c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    = getStructuredSubobjectInit(ParentIList, Index, T, StructuredList,
4724c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                 StructuredIndex,
473ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor          SourceRange(ParentIList->getInit(Index)->getSourceRange().getBegin(),
474ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor                      ParentIList->getSourceRange().getEnd()));
4754c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  unsigned StructuredSubobjectInitIndex = 0;
4764c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
4774c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // Check the element types and build the structural subobject.
47887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  unsigned StartIndex = Index;
4794c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  CheckListElementTypes(ParentIList, T, false, Index,
4804c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                        StructuredSubobjectInitList,
481eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                        StructuredSubobjectInitIndex,
482eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                        TopLevelObject);
48387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  unsigned EndIndex = (Index == StartIndex? StartIndex : Index - 1);
48487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
485ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor  // Update the structured sub-object initializer so that it's ending
48687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  // range corresponds with the end of the last initializer it used.
48787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  if (EndIndex < ParentIList->getNumInits()) {
48887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    SourceLocation EndLoc
48987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      = ParentIList->getInit(EndIndex)->getSourceRange().getEnd();
49087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    StructuredSubobjectInitList->setRBraceLoc(EndLoc);
49187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  }
4920cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
4930cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
494a647caad2dec67ac25b763f06237cfe3c3968b51Steve Naroffvoid InitListChecker::CheckExplicitInitList(InitListExpr *IList, QualType &T,
4954c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            unsigned &Index,
4964c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            InitListExpr *StructuredList,
497eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            unsigned &StructuredIndex,
498eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            bool TopLevelObject) {
499c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman  assert(IList->isExplicit() && "Illegal Implicit InitListExpr");
5004c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  SyntacticToSemantic[IList] = StructuredList;
5014c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  StructuredList->setSyntacticForm(IList);
5024c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  CheckListElementTypes(IList, T, true, Index, StructuredList,
503eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                        StructuredIndex, TopLevelObject);
504a647caad2dec67ac25b763f06237cfe3c3968b51Steve Naroff  IList->setType(T);
5054c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  StructuredList->setType(T);
506638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman  if (hadError)
507638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman    return;
508c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman
509638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman  if (Index < IList->getNumInits()) {
510c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman    // We have leftover initializers
511c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman    if (IList->getNumInits() > 0 &&
5120820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        IsStringInit(IList->getInit(Index), T, SemaRef.Context)) {
5137c53ca6e03833adab4465462b7d5c888741b715dDouglas Gregor      unsigned DK = diag::warn_excess_initializers_in_char_array_initializer;
5140820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      if (SemaRef.getLangOptions().CPlusPlus)
5157c53ca6e03833adab4465462b7d5c888741b715dDouglas Gregor        DK = diag::err_excess_initializers_in_char_array_initializer;
516bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman      // Special-case
5170820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(IList->getInit(Index)->getLocStart(), DK)
518dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner        << IList->getInit(Index)->getSourceRange();
519c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman      hadError = true;
520d8dc2100487640d8f5ce53201fdcfac7b5ca32b2Eli Friedman    } else if (!T->isIncompleteType()) {
521b574e5630d66629ccc8f2432e60b59ae42f1f363Douglas Gregor      // Don't complain for incomplete types, since we'll get an error
522b574e5630d66629ccc8f2432e60b59ae42f1f363Douglas Gregor      // elsewhere
523eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      QualType CurrentObjectType = StructuredList->getType();
524eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      int initKind =
525eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        CurrentObjectType->isArrayType()? 0 :
526eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        CurrentObjectType->isVectorType()? 1 :
527eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        CurrentObjectType->isScalarType()? 2 :
528eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        CurrentObjectType->isUnionType()? 3 :
529eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        4;
5307c53ca6e03833adab4465462b7d5c888741b715dDouglas Gregor
5317c53ca6e03833adab4465462b7d5c888741b715dDouglas Gregor      unsigned DK = diag::warn_excess_initializers;
5320820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      if (SemaRef.getLangOptions().CPlusPlus)
5337c53ca6e03833adab4465462b7d5c888741b715dDouglas Gregor          DK = diag::err_excess_initializers;
5347c53ca6e03833adab4465462b7d5c888741b715dDouglas Gregor
5350820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(IList->getInit(Index)->getLocStart(), DK)
536eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        << initKind << IList->getInit(Index)->getSourceRange();
537c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman    }
538c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman  }
539cda25a977e4b7fe4e080b87586410eaeab7b62f6Eli Friedman
540638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman  if (T->isScalarType())
5410820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(IList->getLocStart(), diag::warn_braces_around_scalar_init)
542dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner      << IList->getSourceRange();
5430cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
5440cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
545b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedmanvoid InitListChecker::CheckListElementTypes(InitListExpr *IList,
546b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman                                            QualType &DeclType,
54787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                            bool SubobjectIsDesignatorContext,
5484c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            unsigned &Index,
5494c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            InitListExpr *StructuredList,
550eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            unsigned &StructuredIndex,
551eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            bool TopLevelObject) {
552c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman  if (DeclType->isScalarType()) {
5536fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    CheckScalarType(IList, DeclType, Index, StructuredList, StructuredIndex);
554c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman  } else if (DeclType->isVectorType()) {
5554c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    CheckVectorType(IList, DeclType, Index, StructuredList, StructuredIndex);
556d7eb846aaf5ee4a8d22c3cd0796d1e7229d46013Douglas Gregor  } else if (DeclType->isAggregateType()) {
557d7eb846aaf5ee4a8d22c3cd0796d1e7229d46013Douglas Gregor    if (DeclType->isRecordType()) {
55887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      RecordDecl *RD = DeclType->getAsRecordType()->getDecl();
55987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      CheckStructUnionTypes(IList, DeclType, RD->field_begin(),
5604c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                            SubobjectIsDesignatorContext, Index,
561eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                            StructuredList, StructuredIndex,
562eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                            TopLevelObject);
56387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    } else if (DeclType->isArrayType()) {
564f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor      llvm::APSInt Zero(
5650820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner                      SemaRef.Context.getTypeSize(SemaRef.Context.getSizeType()),
566f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor                      false);
5674c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      CheckArrayType(IList, DeclType, Zero, SubobjectIsDesignatorContext, Index,
5684c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                     StructuredList, StructuredIndex);
56987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    }
5700cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    else
5714c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      assert(0 && "Aggregate that isn't a structure or array?!");
572613535273b90dc5cbd0f9fa056dedc93801ea35aSteve Naroff  } else if (DeclType->isVoidType() || DeclType->isFunctionType()) {
573613535273b90dc5cbd0f9fa056dedc93801ea35aSteve Naroff    // This type is invalid, issue a diagnostic.
5744c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++Index;
5750820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(IList->getLocStart(), diag::err_illegal_initializer_type)
576d162584991885ab004a02573a73ce06422b921fcChris Lattner      << DeclType;
577d8dc2100487640d8f5ce53201fdcfac7b5ca32b2Eli Friedman    hadError = true;
578930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  } else if (DeclType->isRecordType()) {
579930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // C++ [dcl.init]p14:
580930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //   [...] If the class is an aggregate (8.5.1), and the initializer
581930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //   is a brace-enclosed list, see 8.5.1.
582930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //
583930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // Note: 8.5.1 is handled below; here, we diagnose the case where
584930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // we have an initializer list and a destination type that is not
585930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // an aggregate.
586930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // FIXME: In C++0x, this is yet another form of initialization.
5870820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(IList->getLocStart(), diag::err_init_non_aggr_init_list)
588930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      << DeclType << IList->getSourceRange();
589930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    hadError = true;
590930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  } else if (DeclType->isReferenceType()) {
591930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    CheckReferenceType(IList, DeclType, Index, StructuredList, StructuredIndex);
5920cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  } else {
5930cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    // In C, all types are either scalars or aggregates, but
5940cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    // additional handling is needed here for C++ (and possibly others?).
5950cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    assert(0 && "Unsupported initializer type");
5960cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
5970cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
5980cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
599b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedmanvoid InitListChecker::CheckSubElementType(InitListExpr *IList,
600b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman                                          QualType ElemType,
6014c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                          unsigned &Index,
6024c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                          InitListExpr *StructuredList,
6034c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                          unsigned &StructuredIndex) {
6046fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor  Expr *expr = IList->getInit(Index);
605c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman  if (InitListExpr *SubInitList = dyn_cast<InitListExpr>(expr)) {
606c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman    unsigned newIndex = 0;
6074c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    unsigned newStructuredIndex = 0;
6084c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    InitListExpr *newStructuredList
6094c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      = getStructuredSubobjectInit(IList, Index, ElemType,
6104c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                   StructuredList, StructuredIndex,
6114c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                   SubInitList->getSourceRange());
6124c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    CheckExplicitInitList(SubInitList, ElemType, newIndex,
6134c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                          newStructuredList, newStructuredIndex);
6144c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++StructuredIndex;
6154c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++Index;
61679e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner  } else if (Expr *Str = IsStringInit(expr, ElemType, SemaRef.Context)) {
61779e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner    CheckStringInit(Str, ElemType, SemaRef);
618f71ae8d8024561f92dd7916363e7a791684563ccChris Lattner    UpdateStructuredListElement(StructuredList, StructuredIndex, Str);
6194c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++Index;
620c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman  } else if (ElemType->isScalarType()) {
6216fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    CheckScalarType(IList, ElemType, Index, StructuredList, StructuredIndex);
622930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  } else if (ElemType->isReferenceType()) {
623930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    CheckReferenceType(IList, ElemType, Index, StructuredList, StructuredIndex);
624b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  } else {
6250820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    if (SemaRef.getLangOptions().CPlusPlus) {
626930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // C++ [dcl.init.aggr]p12:
627930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   All implicit type conversions (clause 4) are considered when
628930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   initializing the aggregate member with an ini- tializer from
629930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   an initializer-list. If the initializer can initialize a
630930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   member, the member is initialized. [...]
631930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      ImplicitConversionSequence ICS
6320820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        = SemaRef.TryCopyInitialization(expr, ElemType);
633930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      if (ICS.ConversionKind != ImplicitConversionSequence::BadConversion) {
6340820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        if (SemaRef.PerformImplicitConversion(expr, ElemType, ICS,
635930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                                               "initializing"))
636930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor          hadError = true;
637930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        UpdateStructuredListElement(StructuredList, StructuredIndex, expr);
638930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        ++Index;
639930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        return;
640930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      }
641930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor
642930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // Fall through for subaggregate initialization
643930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    } else {
644930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // C99 6.7.8p13:
645930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //
646930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   The initializer for a structure or union object that has
647930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   automatic storage duration shall be either an initializer
648930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   list as described below, or a single expression that has
649930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   compatible structure or union type. In the latter case, the
650930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   initial value of the object, including unnamed members, is
651930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      //   that of the expression.
6520820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      QualType ExprType = SemaRef.Context.getCanonicalType(expr->getType());
6530820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      QualType ElemTypeCanon = SemaRef.Context.getCanonicalType(ElemType);
6540820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      if (SemaRef.Context.typesAreCompatible(ExprType.getUnqualifiedType(),
655930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                                          ElemTypeCanon.getUnqualifiedType())) {
656930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        UpdateStructuredListElement(StructuredList, StructuredIndex, expr);
657930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        ++Index;
658930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        return;
659930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      }
660930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor
661930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // Fall through for subaggregate initialization
662930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    }
663930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor
664930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // C++ [dcl.init.aggr]p12:
665930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //
666930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //   [...] Otherwise, if the member is itself a non-empty
667930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //   subaggregate, brace elision is assumed and the initializer is
668930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //   considered for the initialization of the first member of
669930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    //   the subaggregate.
670930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    if (ElemType->isAggregateType() || ElemType->isVectorType()) {
671930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      CheckImplicitInitList(IList, ElemType, Index, StructuredList,
672930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                            StructuredIndex);
673930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      ++StructuredIndex;
674930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    } else {
675930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // We cannot initialize this element, so let
676930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // PerformCopyInitialization produce the appropriate diagnostic.
6770820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.PerformCopyInitialization(expr, ElemType, "initializing");
678930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      hadError = true;
679930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      ++Index;
680930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      ++StructuredIndex;
681930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    }
682930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  }
683b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman}
684b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman
685930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregorvoid InitListChecker::CheckScalarType(InitListExpr *IList, QualType DeclType,
6866fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor                                      unsigned &Index,
6874c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                      InitListExpr *StructuredList,
6884c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                      unsigned &StructuredIndex) {
6890cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  if (Index < IList->getNumInits()) {
6906fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    Expr *expr = IList->getInit(Index);
691c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman    if (isa<InitListExpr>(expr)) {
6920820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(IList->getLocStart(),
693dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner                    diag::err_many_braces_around_scalar_init)
694dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner        << IList->getSourceRange();
695bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman      hadError = true;
696bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman      ++Index;
6974c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      ++StructuredIndex;
698bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman      return;
69905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    } else if (isa<DesignatedInitExpr>(expr)) {
7000820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(expr->getSourceRange().getBegin(),
70105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                    diag::err_designator_for_scalar_init)
70205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor        << DeclType << expr->getSourceRange();
70305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      hadError = true;
70405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      ++Index;
7054c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      ++StructuredIndex;
70605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      return;
7070cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    }
70805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
709c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman    Expr *savExpr = expr; // Might be promoted by CheckSingleInitializer.
7100820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    if (CheckSingleInitializer(expr, DeclType, false, SemaRef))
711bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman      hadError = true; // types weren't compatible.
71205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    else if (savExpr != expr) {
713c9c0ea6576666eb7e96508f6b8ce2b4d33af3f02Eli Friedman      // The type was promoted, update initializer list.
7146fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor      IList->setInit(Index, expr);
71505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
7164c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    if (hadError)
7174c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      ++StructuredIndex;
7184c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    else
7194c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      UpdateStructuredListElement(StructuredList, StructuredIndex, expr);
7200cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    ++Index;
721bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman  } else {
7220820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(IList->getLocStart(), diag::err_empty_scalar_initializer)
723dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner      << IList->getSourceRange();
724bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman    hadError = true;
7254c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++Index;
7264c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++StructuredIndex;
727bb504d3a63e0e4b2439900ba6d77b620fb6de857Eli Friedman    return;
7280cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
7290cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
7300cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
731930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregorvoid InitListChecker::CheckReferenceType(InitListExpr *IList, QualType DeclType,
732930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                                         unsigned &Index,
733930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                                         InitListExpr *StructuredList,
734930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                                         unsigned &StructuredIndex) {
735930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  if (Index < IList->getNumInits()) {
736930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    Expr *expr = IList->getInit(Index);
737930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    if (isa<InitListExpr>(expr)) {
7380820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(IList->getLocStart(), diag::err_init_non_aggr_init_list)
739930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor        << DeclType << IList->getSourceRange();
740930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      hadError = true;
741930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      ++Index;
742930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      ++StructuredIndex;
743930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      return;
744930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    }
745930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor
746930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    Expr *savExpr = expr; // Might be promoted by CheckSingleInitializer.
7470820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    if (SemaRef.CheckReferenceInit(expr, DeclType))
748930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      hadError = true;
749930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    else if (savExpr != expr) {
750930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      // The type was promoted, update initializer list.
751930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      IList->setInit(Index, expr);
752930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    }
753930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    if (hadError)
754930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      ++StructuredIndex;
755930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    else
756930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      UpdateStructuredListElement(StructuredList, StructuredIndex, expr);
757930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    ++Index;
758930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  } else {
759930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // FIXME: It would be wonderful if we could point at the actual
760930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // member. In general, it would be useful to pass location
761930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // information down the stack, so that we know the location (or
762930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    // decl) of the "current object" being initialized.
7630820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(IList->getLocStart(),
764930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor                  diag::err_init_reference_member_uninitialized)
765930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      << DeclType
766930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor      << IList->getSourceRange();
767930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    hadError = true;
768930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    ++Index;
769930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    ++StructuredIndex;
770930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor    return;
771930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor  }
772930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor}
773930d8b5ecc074cca01ecd9a522a55f55f3b72396Douglas Gregor
7740cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroffvoid InitListChecker::CheckVectorType(InitListExpr *IList, QualType DeclType,
7754c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                      unsigned &Index,
7764c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                      InitListExpr *StructuredList,
7774c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                      unsigned &StructuredIndex) {
7780cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  if (Index < IList->getNumInits()) {
7790cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    const VectorType *VT = DeclType->getAsVectorType();
7800cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    int maxElements = VT->getNumElements();
7810cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    QualType elementType = VT->getElementType();
7820cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
7830cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    for (int i = 0; i < maxElements; ++i) {
7840cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff      // Don't attempt to go past the end of the init list
7850cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff      if (Index >= IList->getNumInits())
7860cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff        break;
7876fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor      CheckSubElementType(IList, elementType, Index,
7884c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                          StructuredList, StructuredIndex);
7890cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    }
7900cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
7910cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
7920cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
7930cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroffvoid InitListChecker::CheckArrayType(InitListExpr *IList, QualType &DeclType,
79487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                     llvm::APSInt elementIndex,
79587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                     bool SubobjectIsDesignatorContext,
7964c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                     unsigned &Index,
7974c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                     InitListExpr *StructuredList,
7984c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                     unsigned &StructuredIndex) {
7990cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  // Check for the special-case of initializing an array with a string.
8000cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  if (Index < IList->getNumInits()) {
80179e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner    if (Expr *Str = IsStringInit(IList->getInit(Index), DeclType,
80279e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner                                 SemaRef.Context)) {
80379e079d3caecc0ddd7128dc038d3f8960bbab62eChris Lattner      CheckStringInit(Str, DeclType, SemaRef);
8044c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // We place the string literal directly into the resulting
8054c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // initializer list. This is the only place where the structure
8064c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // of the structured initializer list doesn't match exactly,
8074c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // because doing so would involve allocating one character
8084c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // constant for each string.
809f71ae8d8024561f92dd7916363e7a791684563ccChris Lattner      UpdateStructuredListElement(StructuredList, StructuredIndex, Str);
8100820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      StructuredList->resizeInits(SemaRef.Context, StructuredIndex);
8110cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff      ++Index;
8120cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff      return;
8130cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    }
8140cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
815c63a1f276f7b324fd9a4be82098b1c8f7bf30733Chris Lattner  if (const VariableArrayType *VAT =
8160820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Context.getAsVariableArrayType(DeclType)) {
817638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman    // Check for VLAs; in standard C it would be possible to check this
818638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman    // earlier, but I don't know where clang accepts VLAs (gcc accepts
819638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman    // them in all sorts of strange places).
8200820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(VAT->getSizeExpr()->getLocStart(),
821dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner                  diag::err_variable_object_no_init)
822dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner      << VAT->getSizeExpr()->getSourceRange();
823638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman    hadError = true;
8244c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++Index;
8254c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++StructuredIndex;
826638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman    return;
827638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman  }
828638e14413a4557c399fa2b7da2be5e4e9c1330a2Eli Friedman
82905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // We might know the maximum number of elements in advance.
8304c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  llvm::APSInt maxElements(elementIndex.getBitWidth(),
8314c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                           elementIndex.isUnsigned());
83205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  bool maxElementsKnown = false;
83305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  if (const ConstantArrayType *CAT =
8340820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Context.getAsConstantArrayType(DeclType)) {
83505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    maxElements = CAT->getSize();
836f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor    elementIndex.extOrTrunc(maxElements.getBitWidth());
837e3fa2de90ea1666bf4504b8fd557b09a57aac222Douglas Gregor    elementIndex.setIsUnsigned(maxElements.isUnsigned());
83805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    maxElementsKnown = true;
83905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  }
84005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
8410820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  QualType elementType = SemaRef.Context.getAsArrayType(DeclType)
842c63a1f276f7b324fd9a4be82098b1c8f7bf30733Chris Lattner                             ->getElementType();
84305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  while (Index < IList->getNumInits()) {
84405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    Expr *Init = IList->getInit(Index);
84505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    if (DesignatedInitExpr *DIE = dyn_cast<DesignatedInitExpr>(Init)) {
84687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // If we're not the subobject that matches up with the '{' for
84787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // the designator, we shouldn't be handling the
84887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // designator. Return immediately.
84987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      if (!SubobjectIsDesignatorContext)
85087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor        return;
85187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
85287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // Handle this designated initializer. elementIndex will be
85387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // updated to be the next array element we'll initialize.
85487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      if (CheckDesignatedInitializer(IList, DIE, DIE->designators_begin(),
8554c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                     DeclType, 0, &elementIndex, Index,
856eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                     StructuredList, StructuredIndex, true,
857eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                     false)) {
85805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor        hadError = true;
85987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor        continue;
86087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      }
86187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
862f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor      if (elementIndex.getBitWidth() > maxElements.getBitWidth())
863f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor        maxElements.extend(elementIndex.getBitWidth());
864f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor      else if (elementIndex.getBitWidth() < maxElements.getBitWidth())
865f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor        elementIndex.extend(maxElements.getBitWidth());
866e3fa2de90ea1666bf4504b8fd557b09a57aac222Douglas Gregor      elementIndex.setIsUnsigned(maxElements.isUnsigned());
867f6c717c3dca839dcd189b4a6fa46c8fe7a8bec1dDouglas Gregor
86887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // If the array is of incomplete type, keep track of the number of
86987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // elements in the initializer.
87087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      if (!maxElementsKnown && elementIndex > maxElements)
87187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor        maxElements = elementIndex;
87205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
87305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      continue;
87405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
87505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
87605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    // If we know the maximum number of elements, and we've already
87705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    // hit it, stop consuming elements in the initializer list.
87805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    if (maxElementsKnown && elementIndex == maxElements)
8790cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff      break;
88005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
88105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    // Check this element.
8826fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    CheckSubElementType(IList, elementType, Index,
8834c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                        StructuredList, StructuredIndex);
88405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    ++elementIndex;
88505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
88605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    // If the array is of incomplete type, keep track of the number of
88705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    // elements in the initializer.
88805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    if (!maxElementsKnown && elementIndex > maxElements)
88905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      maxElements = elementIndex;
8900cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
8910cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  if (DeclType->isIncompleteArrayType()) {
8920cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    // If this is an incomplete array type, the actual type needs to
893396f0bfd4b2189452914893ce69f5fb068d0ec22Daniel Dunbar    // be calculated here.
894e3fa2de90ea1666bf4504b8fd557b09a57aac222Douglas Gregor    llvm::APSInt Zero(maxElements.getBitWidth(), maxElements.isUnsigned());
89505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    if (maxElements == Zero) {
896396f0bfd4b2189452914893ce69f5fb068d0ec22Daniel Dunbar      // Sizing an array implicitly to zero is not allowed by ISO C,
897396f0bfd4b2189452914893ce69f5fb068d0ec22Daniel Dunbar      // but is supported by GNU.
8980820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(IList->getLocStart(),
899396f0bfd4b2189452914893ce69f5fb068d0ec22Daniel Dunbar                    diag::ext_typecheck_zero_array_size);
9000cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    }
901396f0bfd4b2189452914893ce69f5fb068d0ec22Daniel Dunbar
9020820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    DeclType = SemaRef.Context.getConstantArrayType(elementType, maxElements,
903396f0bfd4b2189452914893ce69f5fb068d0ec22Daniel Dunbar                                                     ArrayType::Normal, 0);
9040cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
9050cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
9060cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
9070cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroffvoid InitListChecker::CheckStructUnionTypes(InitListExpr *IList,
9080cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff                                            QualType DeclType,
90987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                            RecordDecl::field_iterator Field,
91087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                            bool SubobjectIsDesignatorContext,
9114c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            unsigned &Index,
9124c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            InitListExpr *StructuredList,
913eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            unsigned &StructuredIndex,
914eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            bool TopLevelObject) {
915b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  RecordDecl* structDecl = DeclType->getAsRecordType()->getDecl();
9160cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
917b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  // If the record is invalid, some of it's members are invalid. To avoid
918b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  // confusion, we forgo checking the intializer for the entire record.
919b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  if (structDecl->isInvalidDecl()) {
920b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman    hadError = true;
921b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman    return;
922b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman  }
9233498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor
9243498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor  if (DeclType->isUnionType() && IList->getNumInits() == 0) {
9253498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor    // Value-initialize the first named member of the union.
9263498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor    RecordDecl *RD = DeclType->getAsRecordType()->getDecl();
9273498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor    for (RecordDecl::field_iterator FieldEnd = RD->field_end();
9283498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor         Field != FieldEnd; ++Field) {
9293498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor      if (Field->getDeclName()) {
9303498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor        StructuredList->setInitializedFieldInUnion(*Field);
9313498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor        break;
9323498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor      }
9333498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor    }
9343498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor    return;
9353498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor  }
9363498bdb9e9cb300de74c7b51c92608e2902b2348Douglas Gregor
93705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // If structDecl is a forward declaration, this loop won't do
93805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // anything except look at designated initializers; That's okay,
93905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // because an error should get printed out elsewhere. It might be
94005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // worthwhile to skip over the rest of the initializer, though.
94144b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor  RecordDecl *RD = DeclType->getAsRecordType()->getDecl();
94287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  RecordDecl::field_iterator FieldEnd = RD->field_end();
943dfb5e597e033c8fa09c0e178bd93cfcdf060862eDouglas Gregor  bool InitializedSomething = false;
94405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  while (Index < IList->getNumInits()) {
94505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    Expr *Init = IList->getInit(Index);
94605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
94705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    if (DesignatedInitExpr *DIE = dyn_cast<DesignatedInitExpr>(Init)) {
94887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // If we're not the subobject that matches up with the '{' for
94987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // the designator, we shouldn't be handling the
95087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // designator. Return immediately.
95187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      if (!SubobjectIsDesignatorContext)
95287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor        return;
95387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
95487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // Handle this designated initializer. Field will be updated to
95587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      // the next field that we'll be initializing.
95687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      if (CheckDesignatedInitializer(IList, DIE, DIE->designators_begin(),
9574c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                     DeclType, &Field, 0, Index,
958eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                     StructuredList, StructuredIndex,
959eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                     true, TopLevelObject))
96005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor        hadError = true;
96105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
962dfb5e597e033c8fa09c0e178bd93cfcdf060862eDouglas Gregor      InitializedSomething = true;
96305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      continue;
96405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
96505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
96605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    if (Field == FieldEnd) {
96705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      // We've run out of fields. We're done.
96844b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor      break;
96905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
97044b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor
971dfb5e597e033c8fa09c0e178bd93cfcdf060862eDouglas Gregor    // We've already initialized a member of a union. We're done.
972dfb5e597e033c8fa09c0e178bd93cfcdf060862eDouglas Gregor    if (InitializedSomething && DeclType->isUnionType())
973dfb5e597e033c8fa09c0e178bd93cfcdf060862eDouglas Gregor      break;
974dfb5e597e033c8fa09c0e178bd93cfcdf060862eDouglas Gregor
97505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    // If we've hit the flexible array member at the end, we're done.
97605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    if (Field->getType()->isIncompleteArrayType())
977b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman      break;
97844b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor
9790bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor    if (Field->isUnnamedBitfield()) {
9804c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // Don't initialize unnamed bitfields, e.g. "int : 20;"
98105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      ++Field;
982b85f70719da9ce5a3ca9c801ee0748732e2660eeEli Friedman      continue;
9830cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff    }
98444b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor
9856fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    CheckSubElementType(IList, Field->getType(), Index,
9864c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                        StructuredList, StructuredIndex);
987dfb5e597e033c8fa09c0e178bd93cfcdf060862eDouglas Gregor    InitializedSomething = true;
9880bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor
9890bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor    if (DeclType->isUnionType()) {
9900bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor      // Initialize the first field within the union.
9910bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor      StructuredList->setInitializedFieldInUnion(*Field);
9920bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor    }
99305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
99405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    ++Field;
9950cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff  }
99644b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor
997eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor  if (Field == FieldEnd || !Field->getType()->isIncompleteArrayType() ||
998eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      Index >= IList->getNumInits() ||
999eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      !isa<InitListExpr>(IList->getInit(Index)))
1000eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor    return;
1001eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor
1002eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor  // Handle GNU flexible array initializers.
1003eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor  if (!TopLevelObject &&
1004eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      cast<InitListExpr>(IList->getInit(Index))->getNumInits() > 0) {
10050820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(IList->getInit(Index)->getSourceRange().getBegin(),
1006eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                  diag::err_flexible_array_init_nonempty)
1007eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      << IList->getInit(Index)->getSourceRange().getBegin();
10080820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(Field->getLocation(), diag::note_flexible_array_member)
1009eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      << *Field;
1010eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor    hadError = true;
1011eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor  }
1012eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor
1013eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor  CheckSubElementType(IList, Field->getType(), Index, StructuredList,
1014eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                      StructuredIndex);
10150cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff}
10160cca749f64ff54476df3a4fc084821b8a8d712d5Steve Naroff
101705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// @brief Check the well-formedness of a C99 designated initializer.
101805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
101905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// Determines whether the designated initializer @p DIE, which
102005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// resides at the given @p Index within the initializer list @p
102105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// IList, is well-formed for a current object of type @p DeclType
102205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// (C99 6.7.8). The actual subobject that this designator refers to
102305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// within the current subobject is returned in either
10244c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// @p NextField or @p NextElementIndex (whichever is appropriate).
102505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
102605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// @param IList  The initializer list in which this designated
102705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// initializer occurs.
102805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
102905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// @param DIE  The designated initializer and its initialization
103005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// expression.
103105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
103205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// @param DeclType  The type of the "current object" (C99 6.7.8p17),
103305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// into which the designation in @p DIE should refer.
103405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
103587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor/// @param NextField  If non-NULL and the first designator in @p DIE is
103687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor/// a field, this will be set to the field declaration corresponding
103787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor/// to the field named by the designator.
103805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
103987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor/// @param NextElementIndex  If non-NULL and the first designator in @p
104087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor/// DIE is an array designator or GNU array-range designator, this
104187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor/// will be set to the last index initialized by this designator.
104205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
104305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// @param Index  Index into @p IList where the designated initializer
104405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// @p DIE occurs.
104505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor///
10464c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// @param StructuredList  The initializer list expression that
10474c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// describes all of the subobject initializers in the order they'll
10484c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// actually be initialized.
10494c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor///
105005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// @returns true if there was an error, false otherwise.
105187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregorbool
105287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas GregorInitListChecker::CheckDesignatedInitializer(InitListExpr *IList,
105387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                      DesignatedInitExpr *DIE,
105419da8cdfb3d5cd31e06d02c7bab1eb1bd41a7949Chris Lattner                                     DesignatedInitExpr::designators_iterator D,
105587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                      QualType &CurrentObjectType,
105687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                      RecordDecl::field_iterator *NextField,
105787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                                      llvm::APSInt *NextElementIndex,
10584c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                      unsigned &Index,
10594c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                      InitListExpr *StructuredList,
106034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor                                      unsigned &StructuredIndex,
1061eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            bool FinishSubobjectInit,
1062eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                            bool TopLevelObject) {
106387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  if (D == DIE->designators_end()) {
106487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // Check the actual initialization for the designated object type.
106587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    bool prevHadError = hadError;
10666fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor
10676fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    // Temporarily remove the designator expression from the
10686fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    // initializer list that the child calls see, so that we don't try
10696fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    // to re-process the designator.
10706fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    unsigned OldIndex = Index;
10716fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    IList->setInit(OldIndex, DIE->getInit());
10726fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor
10736fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    CheckSubElementType(IList, CurrentObjectType, Index,
10744c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                        StructuredList, StructuredIndex);
10756fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor
10766fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    // Restore the designated initializer expression in the syntactic
10776fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    // form of the initializer list.
10786fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    if (IList->getInit(OldIndex) != DIE->getInit())
10796fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor      DIE->setInit(IList->getInit(OldIndex));
10806fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor    IList->setInit(OldIndex, DIE);
10816fbdc6bd38cc51232223ae3539c32f23c45ea852Douglas Gregor
108287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    return hadError && !prevHadError;
108387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  }
108405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
10854c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  bool IsFirstDesignator = (D == DIE->designators_begin());
10864c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  assert((IsFirstDesignator || StructuredList) &&
10874c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor         "Need a non-designated initializer list to start from");
10884c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
10894c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // Determine the structural initializer list that corresponds to the
10904c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // current subobject.
10914c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  StructuredList = IsFirstDesignator? SyntacticToSemantic[IList]
1092ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor    : getStructuredSubobjectInit(IList, Index, CurrentObjectType,
1093ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor                                 StructuredList, StructuredIndex,
10944c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                 SourceRange(D->getStartLocation(),
10954c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                             DIE->getSourceRange().getEnd()));
10964c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  assert(StructuredList && "Expected a structured initializer list");
10974c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
109887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  if (D->isFieldDesignator()) {
109987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // C99 6.7.8p7:
110087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //
110187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //   If a designator has the form
110287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //
110387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //      . identifier
110487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //
110587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //   then the current object (defined below) shall have
110687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //   structure or union type and the identifier shall be the
110787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    //   name of a member of that type.
110887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    const RecordType *RT = CurrentObjectType->getAsRecordType();
110987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    if (!RT) {
111087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      SourceLocation Loc = D->getDotLoc();
111187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      if (Loc.isInvalid())
111287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor        Loc = D->getFieldLoc();
11130820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(Loc, diag::err_field_designator_non_aggr)
11140820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        << SemaRef.getLangOptions().CPlusPlus << CurrentObjectType;
111587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      ++Index;
111687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      return true;
111787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    }
111887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
11194c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // Note: we perform a linear search of the fields here, despite
11204c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // the fact that we have a faster lookup method, because we always
11214c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // need to compute the field's index.
112287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    IdentifierInfo *FieldName = D->getFieldName();
11234c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    unsigned FieldIndex = 0;
11244c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    RecordDecl::field_iterator Field = RT->getDecl()->field_begin(),
11254c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                            FieldEnd = RT->getDecl()->field_end();
11264c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    for (; Field != FieldEnd; ++Field) {
11274c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      if (Field->isUnnamedBitfield())
11284c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor        continue;
11294c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
11304c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      if (Field->getIdentifier() == FieldName)
11314c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor        break;
11324c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
11334c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      ++FieldIndex;
113487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    }
113587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
11364c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    if (Field == FieldEnd) {
11374c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // We did not find the field we're looking for. Produce a
11384c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      // suitable diagnostic and return a failure.
11394c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      DeclContext::lookup_result Lookup = RT->getDecl()->lookup(FieldName);
11404c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      if (Lookup.first == Lookup.second) {
11414c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor        // Name lookup didn't find anything.
11420820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(D->getFieldLoc(), diag::err_field_designator_unknown)
11434c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor          << FieldName << CurrentObjectType;
11444c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      } else {
11454c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor        // Name lookup found something, but it wasn't a field.
11460820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(D->getFieldLoc(), diag::err_field_designator_nonfield)
11474c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor          << FieldName;
11480820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag((*Lookup.first)->getLocation(),
11494c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                      diag::note_field_designator_found);
11504c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      }
11514c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
11524c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      ++Index;
11534c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      return true;
11544c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    } else if (cast<RecordDecl>((*Field)->getDeclContext())
11554c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                 ->isAnonymousStructOrUnion()) {
11560820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(D->getFieldLoc(), diag::err_field_designator_anon_class)
11574c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor        << FieldName
11584c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor        << (cast<RecordDecl>((*Field)->getDeclContext())->isUnion()? 2 :
11590820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner            (int)SemaRef.getLangOptions().CPlusPlus);
11600820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag((*Field)->getLocation(), diag::note_field_designator_found);
116187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      ++Index;
116287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      return true;
116387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    }
11644c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
11654c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // All of the fields of a union are located at the same place in
11664c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // the initializer list.
11670bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor    if (RT->getDecl()->isUnion()) {
11684c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      FieldIndex = 0;
11690bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor      StructuredList->setInitializedFieldInUnion(*Field);
11700bb76897bedb8b747efc6523efb432fc24966118Douglas Gregor    }
11714c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
117287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // Update the designator with the field declaration.
11734c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    D->setField(*Field);
117405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
11754c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // Make sure that our non-designated initializer list has space
11764c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // for a subobject corresponding to this field.
11774c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    if (FieldIndex >= StructuredList->getNumInits())
11780820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      StructuredList->resizeInits(SemaRef.Context, FieldIndex + 1);
11794c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
1180eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor    // This designator names a flexible array member.
1181eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor    if (Field->getType()->isIncompleteArrayType()) {
1182eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      bool Invalid = false;
1183eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      DesignatedInitExpr::designators_iterator NextD = D;
1184eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      ++NextD;
1185eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      if (NextD != DIE->designators_end()) {
1186eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        // We can't designate an object within the flexible array
1187eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        // member (because GCC doesn't allow it).
11880820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(NextD->getStartLocation(),
1189eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                      diag::err_designator_into_flexible_array_member)
1190eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          << SourceRange(NextD->getStartLocation(),
1191eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                         DIE->getSourceRange().getEnd());
11920820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(Field->getLocation(), diag::note_flexible_array_member)
1193eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          << *Field;
1194eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        Invalid = true;
1195eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      }
1196eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor
1197eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      if (!hadError && !isa<InitListExpr>(DIE->getInit())) {
1198eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        // The initializer is not an initializer list.
11990820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(DIE->getInit()->getSourceRange().getBegin(),
1200eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                      diag::err_flexible_array_init_needs_braces)
1201eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          << DIE->getInit()->getSourceRange();
12020820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(Field->getLocation(), diag::note_flexible_array_member)
1203eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          << *Field;
1204eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        Invalid = true;
1205eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      }
1206eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor
1207eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      // Handle GNU flexible array initializers.
1208eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      if (!Invalid && !TopLevelObject &&
1209eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          cast<InitListExpr>(DIE->getInit())->getNumInits() > 0) {
12100820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(DIE->getSourceRange().getBegin(),
1211eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                      diag::err_flexible_array_init_nonempty)
1212eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          << DIE->getSourceRange().getBegin();
12130820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner        SemaRef.Diag(Field->getLocation(), diag::note_flexible_array_member)
1214eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          << *Field;
1215eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        Invalid = true;
1216eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      }
1217eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor
1218eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      if (Invalid) {
1219eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        ++Index;
1220eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        return true;
1221eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      }
1222eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor
1223eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      // Initialize the array.
1224eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      bool prevHadError = hadError;
1225eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      unsigned newStructuredIndex = FieldIndex;
1226eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      unsigned OldIndex = Index;
1227eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      IList->setInit(Index, DIE->getInit());
1228eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      CheckSubElementType(IList, Field->getType(), Index,
1229eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                          StructuredList, newStructuredIndex);
1230eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      IList->setInit(OldIndex, DIE);
1231eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      if (hadError && !prevHadError) {
1232eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        ++Field;
1233eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        ++FieldIndex;
1234eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        if (NextField)
1235eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor          *NextField = Field;
1236eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        StructuredIndex = FieldIndex;
1237eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        return true;
1238eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      }
1239eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor    } else {
1240eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      // Recurse to check later designated subobjects.
1241eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      QualType FieldType = (*Field)->getType();
1242eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      unsigned newStructuredIndex = FieldIndex;
1243eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor      if (CheckDesignatedInitializer(IList, DIE, ++D, FieldType, 0, 0, Index,
1244eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                     StructuredList, newStructuredIndex,
1245eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                     true, false))
1246eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor        return true;
1247eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor    }
124887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
124987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // Find the position of the next field to be initialized in this
125087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // subobject.
125187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    ++Field;
12524c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ++FieldIndex;
125305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
125487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // If this the first designator, our caller will continue checking
125587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // the rest of this struct/class/union subobject.
125687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    if (IsFirstDesignator) {
125787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      if (NextField)
125887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor        *NextField = Field;
12594c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      StructuredIndex = FieldIndex;
126087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      return false;
126187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    }
126205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
126334e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    if (!FinishSubobjectInit)
126434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor      return false;
126534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
126687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    // Check the remaining fields within this class/struct/union subobject.
126787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    bool prevHadError = hadError;
12684c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    CheckStructUnionTypes(IList, CurrentObjectType, Field, false, Index,
12694c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                          StructuredList, FieldIndex);
127087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    return hadError && !prevHadError;
127187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  }
127205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
127387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  // C99 6.7.8p6:
127487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //
127587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //   If a designator has the form
127687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //
127787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //      [ constant-expression ]
127887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //
127987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //   then the current object (defined below) shall have array
128087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //   type and the expression shall be an integer constant
128187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //   expression. If the array is of unknown size, any
128287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //   nonnegative value is valid.
128387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //
128487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  // Additionally, cope with the GNU extension that permits
128587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  // designators of the form
128687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //
128787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  //      [ constant-expression ... constant-expression ]
12880820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  const ArrayType *AT = SemaRef.Context.getAsArrayType(CurrentObjectType);
128987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  if (!AT) {
12900820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(D->getLBracketLoc(), diag::err_array_designator_non_array)
129187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      << CurrentObjectType;
129287f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    ++Index;
129387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    return true;
129487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  }
129505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
129687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  Expr *IndexExpr = 0;
129734e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  llvm::APSInt DesignatedStartIndex, DesignatedEndIndex;
129834e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  if (D->isArrayDesignator()) {
129987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    IndexExpr = DIE->getArrayIndex(*D);
130034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
130134e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    bool ConstExpr
13020820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      = IndexExpr->isIntegerConstantExpr(DesignatedStartIndex, SemaRef.Context);
130334e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    assert(ConstExpr && "Expression must be constant"); (void)ConstExpr;
130434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
130534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    DesignatedEndIndex = DesignatedStartIndex;
130634e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  } else {
130787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    assert(D->isArrayRangeDesignator() && "Need array-range designator");
130834e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
130934e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    bool StartConstExpr
131034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor      = DIE->getArrayRangeStart(*D)->isIntegerConstantExpr(DesignatedStartIndex,
13110820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner                                                           SemaRef.Context);
131234e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    assert(StartConstExpr && "Expression must be constant"); (void)StartConstExpr;
131334e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
131434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    bool EndConstExpr
131534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor      = DIE->getArrayRangeEnd(*D)->isIntegerConstantExpr(DesignatedEndIndex,
13160820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner                                                         SemaRef.Context);
131734e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    assert(EndConstExpr && "Expression must be constant"); (void)EndConstExpr;
131834e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
131987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    IndexExpr = DIE->getArrayRangeEnd(*D);
132034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
132134e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    if (DesignatedStartIndex.getZExtValue() != DesignatedEndIndex.getZExtValue())
1322a9c878086036de36482cc21e35a33cabe9699b0aDouglas Gregor      FullyStructuredList->sawArrayRangeDesignator();
132387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  }
132405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
132587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  if (isa<ConstantArrayType>(AT)) {
132687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    llvm::APSInt MaxElements(cast<ConstantArrayType>(AT)->getSize(), false);
132734e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    DesignatedStartIndex.extOrTrunc(MaxElements.getBitWidth());
132834e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    DesignatedStartIndex.setIsUnsigned(MaxElements.isUnsigned());
132934e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    DesignatedEndIndex.extOrTrunc(MaxElements.getBitWidth());
133034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    DesignatedEndIndex.setIsUnsigned(MaxElements.isUnsigned());
133134e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    if (DesignatedEndIndex >= MaxElements) {
13320820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner      SemaRef.Diag(IndexExpr->getSourceRange().getBegin(),
133387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor                    diag::err_array_designator_too_large)
133434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor        << DesignatedEndIndex.toString(10) << MaxElements.toString(10)
133587f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor        << IndexExpr->getSourceRange();
133687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      ++Index;
133787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor      return true;
133805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
133934e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  } else {
134034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    // Make sure the bit-widths and signedness match.
134134e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    if (DesignatedStartIndex.getBitWidth() > DesignatedEndIndex.getBitWidth())
134234e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor      DesignatedEndIndex.extend(DesignatedStartIndex.getBitWidth());
134334e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    else if (DesignatedStartIndex.getBitWidth() < DesignatedEndIndex.getBitWidth())
134434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor      DesignatedStartIndex.extend(DesignatedEndIndex.getBitWidth());
134534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    DesignatedStartIndex.setIsUnsigned(true);
134634e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    DesignatedEndIndex.setIsUnsigned(true);
134705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  }
134887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
13494c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // Make sure that our non-designated initializer list has space
13504c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // for a subobject corresponding to this array element.
135134e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  if (DesignatedEndIndex.getZExtValue() >= StructuredList->getNumInits())
13520820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    StructuredList->resizeInits(SemaRef.Context,
135334e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor                                DesignatedEndIndex.getZExtValue() + 1);
135434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
135534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  // Repeatedly perform subobject initializations in the range
135634e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  // [DesignatedStartIndex, DesignatedEndIndex].
135734e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
135834e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  // Move to the next designator
135934e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  unsigned ElementIndex = DesignatedStartIndex.getZExtValue();
136034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  unsigned OldIndex = Index;
136134e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  ++D;
136234e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  while (DesignatedStartIndex <= DesignatedEndIndex) {
136334e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    // Recurse to check later designated subobjects.
136434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    QualType ElementType = AT->getElementType();
136534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    Index = OldIndex;
136634e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    if (CheckDesignatedInitializer(IList, DIE, D, ElementType, 0, 0, Index,
136734e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor                                   StructuredList, ElementIndex,
1368eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                   (DesignatedStartIndex == DesignatedEndIndex),
1369eeb15d499f032bb89773ddaca2d17475122a37bbDouglas Gregor                                   false))
137034e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor      return true;
137187f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
137234e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    // Move to the next index in the array that we'll be initializing.
137334e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    ++DesignatedStartIndex;
137434e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    ElementIndex = DesignatedStartIndex.getZExtValue();
137534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  }
137687f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor
137787f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  // If this the first designator, our caller will continue checking
137887f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  // the rest of this array subobject.
137987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  if (IsFirstDesignator) {
138087f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    if (NextElementIndex)
138134e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor      *NextElementIndex = DesignatedStartIndex;
13824c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    StructuredIndex = ElementIndex;
138387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor    return false;
138487f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  }
138534e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
138634e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor  if (!FinishSubobjectInit)
138734e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor    return false;
138834e7946831a63f96d3ba3478c74ca8e25ee52d7eDouglas Gregor
138987f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  // Check the remaining elements within this array subobject.
139005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  bool prevHadError = hadError;
1391fdf556936f94344d5482747403f27822cf0ae37fDouglas Gregor  CheckArrayType(IList, CurrentObjectType, DesignatedStartIndex, false, Index,
13924c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                 StructuredList, ElementIndex);
139387f55cf59e82f246d8605733e9300d0c5f6830a6Douglas Gregor  return hadError && !prevHadError;
139405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor}
139505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
13964c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor// Get the structured initializer list for a subobject of type
13974c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor// @p CurrentObjectType.
13984c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas GregorInitListExpr *
13994c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas GregorInitListChecker::getStructuredSubobjectInit(InitListExpr *IList, unsigned Index,
14004c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            QualType CurrentObjectType,
14014c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            InitListExpr *StructuredList,
14024c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            unsigned StructuredIndex,
14034c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                            SourceRange InitRange) {
14044c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  Expr *ExistingInit = 0;
14054c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  if (!StructuredList)
14064c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ExistingInit = SyntacticToSemantic[IList];
14074c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  else if (StructuredIndex < StructuredList->getNumInits())
14084c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    ExistingInit = StructuredList->getInit(StructuredIndex);
14094c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14104c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  if (InitListExpr *Result = dyn_cast_or_null<InitListExpr>(ExistingInit))
14114c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    return Result;
14124c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14134c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  if (ExistingInit) {
14144c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // We are creating an initializer list that initializes the
14154c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // subobjects of the current object, but there was already an
14164c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // initialization that completely initialized the current
14174c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // subobject, e.g., by a compound literal:
14184c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    //
14194c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // struct X { int a, b; };
14204c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // struct X xs[] = { [0] = (struct X) { 1, 2 }, [0].b = 3 };
14214c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    //
14224c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // Here, xs[0].a == 0 and xs[0].b == 3, since the second,
14234c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // designated initializer re-initializes the whole
14244c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // subobject [0], overwriting previous initializers.
1425ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor    SemaRef.Diag(InitRange.getBegin(),
1426ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor                 diag::warn_subobject_initializer_overrides)
14274c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      << InitRange;
14280820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(ExistingInit->getSourceRange().getBegin(),
14294c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                  diag::note_previous_initializer)
143054f0728c2ab0f967e976300478b2f5cdfed78415Douglas Gregor      << /*FIXME:has side effects=*/0
14314c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      << ExistingInit->getSourceRange();
14324c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  }
14334c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14344c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  InitListExpr *Result
1435ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor    = new (SemaRef.Context) InitListExpr(InitRange.getBegin(), 0, 0,
1436ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor                                         InitRange.getEnd());
1437ed8a93d17b8936dc7978cdc37f3f00fc49d24f71Douglas Gregor
14384c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  Result->setType(CurrentObjectType);
14394c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14404c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // Link this new initializer list into the structured initializer
14414c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // lists.
14424c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  if (StructuredList)
14434c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    StructuredList->updateInit(StructuredIndex, Result);
14444c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  else {
14454c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    Result->setSyntacticForm(IList);
14464c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    SyntacticToSemantic[IList] = Result;
14474c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  }
14484c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14494c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  return Result;
14504c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor}
14514c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14524c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// Update the initializer at index @p StructuredIndex within the
14534c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor/// structured initializer list to the value @p expr.
14544c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregorvoid InitListChecker::UpdateStructuredListElement(InitListExpr *StructuredList,
14554c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                                  unsigned &StructuredIndex,
14564c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                                                  Expr *expr) {
14574c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  // No structured initializer list to update
14584c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  if (!StructuredList)
14594c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    return;
14604c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14614c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  if (Expr *PrevInit = StructuredList->updateInit(StructuredIndex, expr)) {
14624c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor    // This initializer overwrites a previous initializer. Warn.
14630820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(expr->getSourceRange().getBegin(),
14644c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                  diag::warn_initializer_overrides)
14654c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      << expr->getSourceRange();
14660820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner    SemaRef.Diag(PrevInit->getSourceRange().getBegin(),
14674c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor                  diag::note_previous_initializer)
146854f0728c2ab0f967e976300478b2f5cdfed78415Douglas Gregor      << /*FIXME:has side effects=*/0
14694c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor      << PrevInit->getSourceRange();
14704c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  }
14714c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
14724c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor  ++StructuredIndex;
14734c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor}
14744c67834407ca6ab344dcf44fc599ad4938cfa96dDouglas Gregor
147505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// Check that the given Index expression is a valid array designator
147605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// value. This is essentailly just a wrapper around
147705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// Expr::isIntegerConstantExpr that also checks for negative values
147805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// and produces a reasonable diagnostic if there is a
147905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// failure. Returns true if there was an error, false otherwise.  If
148005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// everything went okay, Value will receive the value of the constant
148105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor/// expression.
148205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregorstatic bool
148305c13a3411782108d65aab3c77b1a231a4963bc0Douglas GregorCheckArrayDesignatorExpr(Sema &Self, Expr *Index, llvm::APSInt &Value) {
148405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  SourceLocation Loc = Index->getSourceRange().getBegin();
148505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
148605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // Make sure this is an integer constant expression.
148705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  if (!Index->isIntegerConstantExpr(Value, Self.Context, &Loc))
148805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    return Self.Diag(Loc, diag::err_array_designator_nonconstant)
148905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      << Index->getSourceRange();
149005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
149105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // Make sure this constant expression is non-negative.
1492e3fa2de90ea1666bf4504b8fd557b09a57aac222Douglas Gregor  llvm::APSInt Zero(llvm::APSInt::getNullValue(Value.getBitWidth()),
1493e3fa2de90ea1666bf4504b8fd557b09a57aac222Douglas Gregor                    Value.isUnsigned());
149405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  if (Value < Zero)
149505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    return Self.Diag(Loc, diag::err_array_designator_negative)
149605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      << Value.toString(10) << Index->getSourceRange();
149705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
149853d3d8e0662197f7245d8f5ff697a72a2b4b3f54Douglas Gregor  Value.setIsUnsigned(true);
149905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  return false;
150005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor}
150105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
150205c13a3411782108d65aab3c77b1a231a4963bc0Douglas GregorSema::OwningExprResult Sema::ActOnDesignatedInitializer(Designation &Desig,
150305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                                        SourceLocation Loc,
150405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                                        bool UsedColonSyntax,
150505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                                        OwningExprResult Init) {
150605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  typedef DesignatedInitExpr::Designator ASTDesignator;
150705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
150805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  bool Invalid = false;
150905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  llvm::SmallVector<ASTDesignator, 32> Designators;
151005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  llvm::SmallVector<Expr *, 32> InitExpressions;
151105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
151205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // Build designators and check array designator expressions.
151305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  for (unsigned Idx = 0; Idx < Desig.getNumDesignators(); ++Idx) {
151405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    const Designator &D = Desig.getDesignator(Idx);
151505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    switch (D.getKind()) {
151605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    case Designator::FieldDesignator:
151705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      Designators.push_back(ASTDesignator(D.getField(), D.getDotLoc(),
151805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                          D.getFieldLoc()));
151905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      break;
152005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
152105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    case Designator::ArrayDesignator: {
152205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      Expr *Index = static_cast<Expr *>(D.getArrayIndex());
152305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      llvm::APSInt IndexValue;
152405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      if (CheckArrayDesignatorExpr(*this, Index, IndexValue))
152505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor        Invalid = true;
152605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      else {
152705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor        Designators.push_back(ASTDesignator(InitExpressions.size(),
152805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                            D.getLBracketLoc(),
152905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                            D.getRBracketLoc()));
153005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor        InitExpressions.push_back(Index);
153105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      }
153205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      break;
153305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
153405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
153505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    case Designator::ArrayRangeDesignator: {
153605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      Expr *StartIndex = static_cast<Expr *>(D.getArrayRangeStart());
153705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      Expr *EndIndex = static_cast<Expr *>(D.getArrayRangeEnd());
153805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      llvm::APSInt StartValue;
153905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      llvm::APSInt EndValue;
154005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      if (CheckArrayDesignatorExpr(*this, StartIndex, StartValue) ||
154105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor          CheckArrayDesignatorExpr(*this, EndIndex, EndValue))
154205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor        Invalid = true;
1543d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor      else {
1544d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor        // Make sure we're comparing values with the same bit width.
1545d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor        if (StartValue.getBitWidth() > EndValue.getBitWidth())
1546d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor          EndValue.extend(StartValue.getBitWidth());
1547d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor        else if (StartValue.getBitWidth() < EndValue.getBitWidth())
1548d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor          StartValue.extend(EndValue.getBitWidth());
1549d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor
1550d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor        if (EndValue < StartValue) {
1551d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor          Diag(D.getEllipsisLoc(), diag::err_array_designator_empty_range)
1552d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor            << StartValue.toString(10) << EndValue.toString(10)
1553d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor            << StartIndex->getSourceRange() << EndIndex->getSourceRange();
1554d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor          Invalid = true;
1555d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor        } else {
1556d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor          Designators.push_back(ASTDesignator(InitExpressions.size(),
1557d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor                                              D.getLBracketLoc(),
1558d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor                                              D.getEllipsisLoc(),
1559d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor                                              D.getRBracketLoc()));
1560d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor          InitExpressions.push_back(StartIndex);
1561d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor          InitExpressions.push_back(EndIndex);
1562d6f584ff262f51b40f4c9e317b13f1f21db29755Douglas Gregor        }
156305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      }
156405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor      break;
156505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
156605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    }
156705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  }
156805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
156905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  if (Invalid || Init.isInvalid())
157005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    return ExprError();
157105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
157205c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  // Clear out the expressions within the designation.
157305c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  Desig.ClearExprs(*this);
157405c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor
157505c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  DesignatedInitExpr *DIE
157605c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor    = DesignatedInitExpr::Create(Context, &Designators[0], Designators.size(),
157705c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                 &InitExpressions[0], InitExpressions.size(),
157805c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                 Loc, UsedColonSyntax,
157905c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor                                 static_cast<Expr *>(Init.release()));
158005c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor  return Owned(DIE);
158105c13a3411782108d65aab3c77b1a231a4963bc0Douglas Gregor}
1582c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor
1583c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregorbool Sema::CheckInitList(InitListExpr *&InitList, QualType &DeclType) {
15840820254f97bb8925d933a3664ea1c6fca3997b97Chris Lattner  InitListChecker CheckInitList(*this, InitList, DeclType);
1585c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  if (!CheckInitList.HadError())
1586c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor    InitList = CheckInitList.getFullyStructuredList();
1587c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor
1588c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor  return CheckInitList.HadError();
1589c34ee5ef2b267a683c432ba0c342f7c3a14889d6Douglas Gregor}
159087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
159187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// \brief Diagnose any semantic errors with value-initialization of
159287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// the given type.
159387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor///
159487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// Value-initialization effectively zero-initializes any types
159587fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// without user-declared constructors, and calls the default
159687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// constructor for a for any type that has a user-declared
159787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// constructor (C++ [dcl.init]p5). Value-initialization can fail when
159887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// a type with a user-declared constructor does not have an
159987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// accessible, non-deleted default constructor. In C, everything can
160087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// be value-initialized, which corresponds to C's notion of
160187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// initializing objects with static storage duration when no
160287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// initializer is provided for that object.
160387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor///
160487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor/// \returns true if there was an error, false otherwise.
160587fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregorbool Sema::CheckValueInitialization(QualType Type, SourceLocation Loc) {
160687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  // C++ [dcl.init]p5:
160787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  //
160887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  //   To value-initialize an object of type T means:
160987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
161087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  //     -- if T is an array type, then each element is value-initialized;
161187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  if (const ArrayType *AT = Context.getAsArrayType(Type))
161287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    return CheckValueInitialization(AT->getElementType(), Loc);
161387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
161487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  if (const RecordType *RT = Type->getAsRecordType()) {
1615c1efaecf0373f1a55c5ef4c234357cf726fc0600Douglas Gregor    if (CXXRecordDecl *ClassDecl = dyn_cast<CXXRecordDecl>(RT->getDecl())) {
161687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      // -- if T is a class type (clause 9) with a user-declared
161787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      //    constructor (12.1), then the default constructor for T is
161887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      //    called (and the initialization is ill-formed if T has no
161987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor      //    accessible default constructor);
1620c1efaecf0373f1a55c5ef4c234357cf726fc0600Douglas Gregor      if (ClassDecl->hasUserDeclaredConstructor())
162187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        // FIXME: Eventually, we'll need to put the constructor decl
162287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        // into the AST.
162387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor        return PerformInitializationByConstructor(Type, 0, 0, Loc,
162487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor                                                  SourceRange(Loc),
162587fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor                                                  DeclarationName(),
162687fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor                                                  IK_Direct);
162787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    }
162887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  }
162987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
163087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  if (Type->isReferenceType()) {
163187fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    // C++ [dcl.init]p5:
163287fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    //   [...] A program that calls for default-initialization or
163387fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    //   value-initialization of an entity of reference type is
163487fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor    //   ill-formed. [...]
1635d863517ab7e936cbc3244a0fc431c8b672f5ece4Douglas Gregor    // FIXME: Once we have code that goes through this path, add an
1636d863517ab7e936cbc3244a0fc431c8b672f5ece4Douglas Gregor    // actual diagnostic :)
163787fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  }
163887fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor
163987fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor  return false;
164087fd703e097c27d63479cb83b687d4000a22bbb1Douglas Gregor}
1641