void updated this revision to Diff 486710.
void added a comment.

Put assert in correct place.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D140584/new/

https://reviews.llvm.org/D140584

Files:
  clang-tools-extra/clangd/FindTarget.cpp
  clang/include/clang/AST/Designator.h
  clang/include/clang/AST/Expr.h
  clang/include/clang/Sema/Designator.h
  clang/include/clang/Tooling/Refactoring/RecursiveSymbolVisitor.h
  clang/lib/AST/ASTImporter.cpp
  clang/lib/AST/Expr.cpp
  clang/lib/AST/StmtPrinter.cpp
  clang/lib/AST/StmtProfile.cpp
  clang/lib/Index/IndexBody.cpp
  clang/lib/Parse/ParseInit.cpp
  clang/lib/Sema/SemaCodeComplete.cpp
  clang/lib/Sema/SemaExpr.cpp
  clang/lib/Sema/SemaInit.cpp
  clang/lib/Sema/TreeTransform.h
  clang/lib/Serialization/ASTReaderStmt.cpp
  clang/lib/Serialization/ASTWriterStmt.cpp
  clang/lib/Tooling/Refactoring/Rename/USRLocFinder.cpp
  clang/tools/libclang/CIndex.cpp

Index: clang/tools/libclang/CIndex.cpp
===================================================================
--- clang/tools/libclang/CIndex.cpp
+++ clang/tools/libclang/CIndex.cpp
@@ -2846,8 +2846,7 @@
 }
 void EnqueueVisitor::VisitDesignatedInitExpr(const DesignatedInitExpr *E) {
   AddStmt(E->getInit());
-  for (const DesignatedInitExpr::Designator &D :
-       llvm::reverse(E->designators())) {
+  for (const Designator &D : llvm::reverse(E->designators())) {
     if (D.isFieldDesignator()) {
       if (FieldDecl *Field = D.getField())
         AddMemberRef(Field, D.getFieldLoc());
Index: clang/lib/Tooling/Refactoring/Rename/USRLocFinder.cpp
===================================================================
--- clang/lib/Tooling/Refactoring/Rename/USRLocFinder.cpp
+++ clang/lib/Tooling/Refactoring/Rename/USRLocFinder.cpp
@@ -227,7 +227,7 @@
   }
 
   bool VisitDesignatedInitExpr(const DesignatedInitExpr *E) {
-    for (const DesignatedInitExpr::Designator &D : E->designators()) {
+    for (const Designator &D : E->designators()) {
       if (D.isFieldDesignator() && D.getField()) {
         const FieldDecl *Decl = D.getField();
         if (isInUSRSet(Decl)) {
Index: clang/lib/Serialization/ASTWriterStmt.cpp
===================================================================
--- clang/lib/Serialization/ASTWriterStmt.cpp
+++ clang/lib/Serialization/ASTWriterStmt.cpp
@@ -1085,7 +1085,7 @@
     Record.AddStmt(E->getSubExpr(I));
   Record.AddSourceLocation(E->getEqualOrColonLoc());
   Record.push_back(E->usesGNUSyntax());
-  for (const DesignatedInitExpr::Designator &D : E->designators()) {
+  for (const Designator &D : E->designators()) {
     if (D.isFieldDesignator()) {
       if (FieldDecl *Field = D.getField()) {
         Record.push_back(serialization::DESIG_FIELD_DECL);
Index: clang/lib/Serialization/ASTReaderStmt.cpp
===================================================================
--- clang/lib/Serialization/ASTReaderStmt.cpp
+++ clang/lib/Serialization/ASTReaderStmt.cpp
@@ -1198,8 +1198,6 @@
 }
 
 void ASTStmtReader::VisitDesignatedInitExpr(DesignatedInitExpr *E) {
-  using Designator = DesignatedInitExpr::Designator;
-
   VisitExpr(E);
   unsigned NumSubExprs = Record.readInt();
   assert(NumSubExprs == E->getNumSubExprs() && "Wrong number of subexprs");
@@ -1215,8 +1213,8 @@
       auto *Field = readDeclAs<FieldDecl>();
       SourceLocation DotLoc = readSourceLocation();
       SourceLocation FieldLoc = readSourceLocation();
-      Designators.push_back(Designator(Field->getIdentifier(), DotLoc,
-                                       FieldLoc));
+      Designators.push_back(Designator::CreateFieldDesignator(
+          Field->getIdentifier(), DotLoc, FieldLoc));
       Designators.back().setField(Field);
       break;
     }
@@ -1225,7 +1223,8 @@
       const IdentifierInfo *Name = Record.readIdentifier();
       SourceLocation DotLoc = readSourceLocation();
       SourceLocation FieldLoc = readSourceLocation();
-      Designators.push_back(Designator(Name, DotLoc, FieldLoc));
+      Designators.push_back(
+          Designator::CreateFieldDesignator(Name, DotLoc, FieldLoc));
       break;
     }
 
@@ -1233,7 +1232,8 @@
       unsigned Index = Record.readInt();
       SourceLocation LBracketLoc = readSourceLocation();
       SourceLocation RBracketLoc = readSourceLocation();
-      Designators.push_back(Designator(Index, LBracketLoc, RBracketLoc));
+      Designators.push_back(
+          Designator::CreateArrayDesignator(Index, LBracketLoc, RBracketLoc));
       break;
     }
 
@@ -1242,8 +1242,8 @@
       SourceLocation LBracketLoc = readSourceLocation();
       SourceLocation EllipsisLoc = readSourceLocation();
       SourceLocation RBracketLoc = readSourceLocation();
-      Designators.push_back(Designator(Index, LBracketLoc, EllipsisLoc,
-                                       RBracketLoc));
+      Designators.push_back(Designator::CreateArrayRangeDesignator(
+          Index, LBracketLoc, EllipsisLoc, RBracketLoc));
       break;
     }
     }
Index: clang/lib/Sema/TreeTransform.h
===================================================================
--- clang/lib/Sema/TreeTransform.h
+++ clang/lib/Sema/TreeTransform.h
@@ -18,9 +18,10 @@
 #include "clang/AST/Decl.h"
 #include "clang/AST/DeclObjC.h"
 #include "clang/AST/DeclTemplate.h"
+#include "clang/AST/Designator.h"
 #include "clang/AST/Expr.h"
-#include "clang/AST/ExprConcepts.h"
 #include "clang/AST/ExprCXX.h"
+#include "clang/AST/ExprConcepts.h"
 #include "clang/AST/ExprObjC.h"
 #include "clang/AST/ExprOpenMP.h"
 #include "clang/AST/OpenMPClause.h"
@@ -30,7 +31,6 @@
 #include "clang/AST/StmtOpenMP.h"
 #include "clang/Basic/DiagnosticParse.h"
 #include "clang/Basic/OpenMPKinds.h"
-#include "clang/Sema/Designator.h"
 #include "clang/Sema/Lookup.h"
 #include "clang/Sema/Ownership.h"
 #include "clang/Sema/ParsedTemplate.h"
@@ -11573,11 +11573,10 @@
   // transform the designators.
   SmallVector<Expr*, 4> ArrayExprs;
   bool ExprChanged = false;
-  for (const DesignatedInitExpr::Designator &D : E->designators()) {
+  for (const Designator &D : E->designators()) {
     if (D.isFieldDesignator()) {
-      Desig.AddDesignator(Designator::getField(D.getFieldName(),
-                                               D.getDotLoc(),
-                                               D.getFieldLoc()));
+      Desig.AddDesignator(Designator::CreateFieldDesignator(
+          D.getFieldName(), D.getDotLoc(), D.getFieldLoc()));
       if (D.getField()) {
         FieldDecl *Field = cast_or_null<FieldDecl>(
             getDerived().TransformDecl(D.getFieldLoc(), D.getField()));
@@ -11600,7 +11599,7 @@
         return ExprError();
 
       Desig.AddDesignator(
-          Designator::getArray(Index.get(), D.getLBracketLoc()));
+          Designator::CreateArrayDesignator(Index.get(), D.getLBracketLoc()));
 
       ExprChanged = ExprChanged || Init.get() != E->getArrayIndex(D);
       ArrayExprs.push_back(Index.get());
@@ -11617,10 +11616,8 @@
     if (End.isInvalid())
       return ExprError();
 
-    Desig.AddDesignator(Designator::getArrayRange(Start.get(),
-                                                  End.get(),
-                                                  D.getLBracketLoc(),
-                                                  D.getEllipsisLoc()));
+    Desig.AddDesignator(Designator::CreateArrayRangeDesignator(
+        Start.get(), End.get(), D.getLBracketLoc(), D.getEllipsisLoc()));
 
     ExprChanged = ExprChanged || Start.get() != E->getArrayRangeStart(D) ||
                   End.get() != E->getArrayRangeEnd(D);
Index: clang/lib/Sema/SemaInit.cpp
===================================================================
--- clang/lib/Sema/SemaInit.cpp
+++ clang/lib/Sema/SemaInit.cpp
@@ -12,6 +12,7 @@
 
 #include "clang/AST/ASTContext.h"
 #include "clang/AST/DeclObjC.h"
+#include "clang/AST/Designator.h"
 #include "clang/AST/ExprCXX.h"
 #include "clang/AST/ExprObjC.h"
 #include "clang/AST/ExprOpenMP.h"
@@ -19,7 +20,6 @@
 #include "clang/Basic/CharInfo.h"
 #include "clang/Basic/SourceManager.h"
 #include "clang/Basic/TargetInfo.h"
-#include "clang/Sema/Designator.h"
 #include "clang/Sema/Initialization.h"
 #include "clang/Sema/Lookup.h"
 #include "clang/Sema/SemaInternal.h"
@@ -2339,19 +2339,17 @@
                                            DesignatedInitExpr *DIE,
                                            unsigned DesigIdx,
                                            IndirectFieldDecl *IndirectField) {
-  typedef DesignatedInitExpr::Designator Designator;
-
   // Build the replacement designators.
   SmallVector<Designator, 4> Replacements;
   for (IndirectFieldDecl::chain_iterator PI = IndirectField->chain_begin(),
        PE = IndirectField->chain_end(); PI != PE; ++PI) {
     if (PI + 1 == PE)
-      Replacements.push_back(Designator((IdentifierInfo *)nullptr,
-                                    DIE->getDesignator(DesigIdx)->getDotLoc(),
-                                DIE->getDesignator(DesigIdx)->getFieldLoc()));
+      Replacements.push_back(Designator::CreateFieldDesignator(
+          nullptr, DIE->getDesignator(DesigIdx)->getDotLoc(),
+          DIE->getDesignator(DesigIdx)->getFieldLoc()));
     else
-      Replacements.push_back(Designator((IdentifierInfo *)nullptr,
-                                        SourceLocation(), SourceLocation()));
+      Replacements.push_back(Designator::CreateFieldDesignator(
+          nullptr, SourceLocation(), SourceLocation()));
     assert(isa<FieldDecl>(*PI));
     Replacements.back().setField(cast<FieldDecl>(*PI));
   }
@@ -2494,7 +2492,7 @@
     return hadError && !prevHadError;
   }
 
-  DesignatedInitExpr::Designator *D = DIE->getDesignator(DesigIdx);
+  Designator *D = DIE->getDesignator(DesigIdx);
   bool IsFirstDesignator = (DesigIdx == 0);
   if (IsFirstDesignator ? FullyStructuredList : StructuredList) {
     // Determine the structural initializer list that corresponds to the
@@ -2576,7 +2574,7 @@
 
     FieldDecl *KnownField = D->getField();
     if (!KnownField) {
-      IdentifierInfo *FieldName = D->getFieldName();
+      const IdentifierInfo *FieldName = D->getFieldName();
       DeclContext::lookup_result Lookup = RT->getDecl()->lookup(FieldName);
       for (NamedDecl *ND : Lookup) {
         if (auto *FD = dyn_cast<FieldDecl>(ND)) {
@@ -2752,8 +2750,7 @@
         // We can't designate an object within the flexible array
         // member (because GCC doesn't allow it).
         if (!VerifyOnly) {
-          DesignatedInitExpr::Designator *NextD
-            = DIE->getDesignator(DesigIdx + 1);
+          Designator *NextD = DIE->getDesignator(DesigIdx + 1);
           SemaRef.Diag(NextD->getBeginLoc(),
                        diag::err_designator_into_flexible_array_member)
               << SourceRange(NextD->getBeginLoc(), DIE->getEndLoc());
@@ -3213,40 +3210,32 @@
 
 ExprResult Sema::ActOnDesignatedInitializer(Designation &Desig,
                                             SourceLocation EqualOrColonLoc,
-                                            bool GNUSyntax,
-                                            ExprResult Init) {
-  typedef DesignatedInitExpr::Designator ASTDesignator;
-
+                                            bool GNUSyntax, ExprResult Init) {
   bool Invalid = false;
-  SmallVector<ASTDesignator, 32> Designators;
+  SmallVector<Designator, 32> Designators;
   SmallVector<Expr *, 32> InitExpressions;
 
   // Build designators and check array designator expressions.
   for (unsigned Idx = 0; Idx < Desig.getNumDesignators(); ++Idx) {
     const Designator &D = Desig.getDesignator(Idx);
-    switch (D.getKind()) {
-    case Designator::FieldDesignator:
-      Designators.push_back(ASTDesignator(D.getField(), D.getDotLoc(),
-                                          D.getFieldLoc()));
-      break;
 
-    case Designator::ArrayDesignator: {
+    if (D.isFieldDesignator()) {
+      Designators.push_back(Designator::CreateFieldDesignator(
+          D.getFieldName(), D.getDotLoc(), D.getFieldLoc()));
+    } else if (D.isArrayDesignator()) {
       Expr *Index = static_cast<Expr *>(D.getArrayIndex());
       llvm::APSInt IndexValue;
+
       if (!Index->isTypeDependent() && !Index->isValueDependent())
         Index = CheckArrayDesignatorExpr(*this, Index, IndexValue).get();
       if (!Index)
         Invalid = true;
       else {
-        Designators.push_back(ASTDesignator(InitExpressions.size(),
-                                            D.getLBracketLoc(),
-                                            D.getRBracketLoc()));
+        Designators.push_back(Designator::CreateArrayDesignator(
+            InitExpressions.size(), D.getLBracketLoc(), D.getRBracketLoc()));
         InitExpressions.push_back(Index);
       }
-      break;
-    }
-
-    case Designator::ArrayRangeDesignator: {
+    } else if (D.isArrayRangeDesignator()) {
       Expr *StartIndex = static_cast<Expr *>(D.getArrayRangeStart());
       Expr *EndIndex = static_cast<Expr *>(D.getArrayRangeEnd());
       llvm::APSInt StartValue;
@@ -3255,9 +3244,11 @@
                             StartIndex->isValueDependent();
       bool EndDependent = EndIndex->isTypeDependent() ||
                           EndIndex->isValueDependent();
+
       if (!StartDependent)
         StartIndex =
             CheckArrayDesignatorExpr(*this, StartIndex, StartValue).get();
+
       if (!EndDependent)
         EndIndex = CheckArrayDesignatorExpr(*this, EndIndex, EndValue).get();
 
@@ -3278,25 +3269,19 @@
             << StartIndex->getSourceRange() << EndIndex->getSourceRange();
           Invalid = true;
         } else {
-          Designators.push_back(ASTDesignator(InitExpressions.size(),
-                                              D.getLBracketLoc(),
-                                              D.getEllipsisLoc(),
-                                              D.getRBracketLoc()));
+          Designators.push_back(Designator::CreateArrayRangeDesignator(
+              InitExpressions.size(), D.getLBracketLoc(), D.getEllipsisLoc(),
+              D.getRBracketLoc()));
           InitExpressions.push_back(StartIndex);
           InitExpressions.push_back(EndIndex);
         }
       }
-      break;
-    }
     }
   }
 
   if (Invalid || Init.isInvalid())
     return ExprError();
 
-  // Clear out the expressions within the designation.
-  Desig.ClearExprs(*this);
-
   return DesignatedInitExpr::Create(Context, Designators, InitExpressions,
                                     EqualOrColonLoc, GNUSyntax,
                                     Init.getAs<Expr>());
Index: clang/lib/Sema/SemaExpr.cpp
===================================================================
--- clang/lib/Sema/SemaExpr.cpp
+++ clang/lib/Sema/SemaExpr.cpp
@@ -19,6 +19,7 @@
 #include "clang/AST/CXXInheritance.h"
 #include "clang/AST/DeclObjC.h"
 #include "clang/AST/DeclTemplate.h"
+#include "clang/AST/Designator.h"
 #include "clang/AST/EvaluatedExprVisitor.h"
 #include "clang/AST/Expr.h"
 #include "clang/AST/ExprCXX.h"
@@ -40,7 +41,6 @@
 #include "clang/Sema/AnalysisBasedWarnings.h"
 #include "clang/Sema/DeclSpec.h"
 #include "clang/Sema/DelayedDiagnostic.h"
-#include "clang/Sema/Designator.h"
 #include "clang/Sema/Initialization.h"
 #include "clang/Sema/Lookup.h"
 #include "clang/Sema/Overload.h"
Index: clang/lib/Sema/SemaCodeComplete.cpp
===================================================================
--- clang/lib/Sema/SemaCodeComplete.cpp
+++ clang/lib/Sema/SemaCodeComplete.cpp
@@ -15,6 +15,7 @@
 #include "clang/AST/DeclCXX.h"
 #include "clang/AST/DeclObjC.h"
 #include "clang/AST/DeclTemplate.h"
+#include "clang/AST/Designator.h"
 #include "clang/AST/Expr.h"
 #include "clang/AST/ExprCXX.h"
 #include "clang/AST/ExprConcepts.h"
@@ -32,7 +33,6 @@
 #include "clang/Lex/Preprocessor.h"
 #include "clang/Sema/CodeCompleteConsumer.h"
 #include "clang/Sema/DeclSpec.h"
-#include "clang/Sema/Designator.h"
 #include "clang/Sema/Lookup.h"
 #include "clang/Sema/Overload.h"
 #include "clang/Sema/ParsedAttr.h"
@@ -6215,7 +6215,7 @@
 
   // Look for designated initializers.
   // They're in their syntactic form, not yet resolved to fields.
-  IdentifierInfo *DesignatedFieldName = nullptr;
+  const IdentifierInfo *DesignatedFieldName = nullptr;
   unsigned ArgsAfterDesignator = 0;
   for (const Expr *Arg : Args) {
     if (const auto *DIE = dyn_cast<DesignatedInitExpr>(Arg)) {
@@ -6421,7 +6421,7 @@
       assert(D.isFieldDesignator());
       auto *RD = getAsRecordDecl(BaseType);
       if (RD && RD->isCompleteDefinition()) {
-        for (const auto *Member : RD->lookup(D.getField()))
+        for (const auto *Member : RD->lookup(D.getFieldName()))
           if (const FieldDecl *FD = llvm::dyn_cast<FieldDecl>(Member)) {
             NextType = FD->getType();
             break;
Index: clang/lib/Parse/ParseInit.cpp
===================================================================
--- clang/lib/Parse/ParseInit.cpp
+++ clang/lib/Parse/ParseInit.cpp
@@ -10,11 +10,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+#include "clang/AST/Designator.h"
 #include "clang/Basic/TokenKinds.h"
 #include "clang/Parse/ParseDiagnostic.h"
 #include "clang/Parse/Parser.h"
 #include "clang/Parse/RAIIObjectsForParser.h"
-#include "clang/Sema/Designator.h"
 #include "clang/Sema/Ownership.h"
 #include "clang/Sema/Scope.h"
 #include "llvm/ADT/STLExtras.h"
@@ -181,7 +181,8 @@
                                       NewSyntax);
 
     Designation D;
-    D.AddDesignator(Designator::getField(FieldName, SourceLocation(), NameLoc));
+    D.AddDesignator(Designator::CreateFieldDesignator(
+        FieldName, SourceLocation(), NameLoc));
     PreferredType.enterDesignatedInitializer(
         Tok.getLocation(), DesignatorCompletion.PreferredBaseType, D);
     return Actions.ActOnDesignatedInitializer(D, ColonLoc, true,
@@ -210,8 +211,8 @@
         return ExprError();
       }
 
-      Desig.AddDesignator(Designator::getField(Tok.getIdentifierInfo(), DotLoc,
-                                               Tok.getLocation()));
+      Desig.AddDesignator(Designator::CreateFieldDesignator(
+          Tok.getIdentifierInfo(), DotLoc, Tok.getLocation()));
       ConsumeToken(); // Eat the identifier.
       continue;
     }
@@ -360,7 +361,8 @@
 
     // If this is a normal array designator, remember it.
     if (Tok.isNot(tok::ellipsis)) {
-      Desig.AddDesignator(Designator::getArray(Idx.get(), StartLoc));
+      Desig.AddDesignator(
+          Designator::CreateArrayDesignator(Idx.get(), StartLoc));
     } else {
       // Handle the gnu array range extension.
       Diag(Tok, diag::ext_gnu_array_range);
@@ -371,9 +373,8 @@
         SkipUntil(tok::r_square, StopAtSemi);
         return RHS;
       }
-      Desig.AddDesignator(Designator::getArrayRange(Idx.get(),
-                                                    RHS.get(),
-                                                    StartLoc, EllipsisLoc));
+      Desig.AddDesignator(Designator::CreateArrayRangeDesignator(
+          Idx.get(), RHS.get(), StartLoc, EllipsisLoc));
     }
 
     T.consumeClose();
Index: clang/lib/Index/IndexBody.cpp
===================================================================
--- clang/lib/Index/IndexBody.cpp
+++ clang/lib/Index/IndexBody.cpp
@@ -202,7 +202,7 @@
   }
 
   bool VisitDesignatedInitExpr(DesignatedInitExpr *E) {
-    for (DesignatedInitExpr::Designator &D : llvm::reverse(E->designators())) {
+    for (Designator &D : llvm::reverse(E->designators())) {
       if (D.isFieldDesignator() && D.getField())
         return IndexCtx.handleReference(D.getField(), D.getFieldLoc(), Parent,
                                         ParentDC, SymbolRoleSet(), {}, E);
@@ -416,7 +416,7 @@
     };
 
     auto visitSyntacticDesignatedInitExpr = [&](DesignatedInitExpr *E) -> bool {
-      for (DesignatedInitExpr::Designator &D : llvm::reverse(E->designators())) {
+      for (Designator &D : llvm::reverse(E->designators())) {
         if (D.isFieldDesignator() && D.getField())
           return IndexCtx.handleReference(D.getField(), D.getFieldLoc(),
                                           Parent, ParentDC, SymbolRoleSet(),
Index: clang/lib/AST/StmtProfile.cpp
===================================================================
--- clang/lib/AST/StmtProfile.cpp
+++ clang/lib/AST/StmtProfile.cpp
@@ -1500,7 +1500,7 @@
 void StmtProfiler::VisitDesignatedInitExpr(const DesignatedInitExpr *S) {
   VisitExpr(S);
   ID.AddBoolean(S->usesGNUSyntax());
-  for (const DesignatedInitExpr::Designator &D : S->designators()) {
+  for (const Designator &D : S->designators()) {
     if (D.isFieldDesignator()) {
       ID.AddInteger(0);
       VisitName(D.getFieldName());
Index: clang/lib/AST/StmtPrinter.cpp
===================================================================
--- clang/lib/AST/StmtPrinter.cpp
+++ clang/lib/AST/StmtPrinter.cpp
@@ -1736,10 +1736,10 @@
 
 void StmtPrinter::VisitDesignatedInitExpr(DesignatedInitExpr *Node) {
   bool NeedsEquals = true;
-  for (const DesignatedInitExpr::Designator &D : Node->designators()) {
+  for (const Designator &D : Node->designators()) {
     if (D.isFieldDesignator()) {
       if (D.getDotLoc().isInvalid()) {
-        if (IdentifierInfo *II = D.getFieldName()) {
+        if (const IdentifierInfo *II = D.getFieldName()) {
           OS << II->getName() << ":";
           NeedsEquals = false;
         }
Index: clang/lib/AST/Expr.cpp
===================================================================
--- clang/lib/AST/Expr.cpp
+++ clang/lib/AST/Expr.cpp
@@ -4387,11 +4387,11 @@
 //  DesignatedInitExpr
 //===----------------------------------------------------------------------===//
 
-IdentifierInfo *DesignatedInitExpr::Designator::getFieldName() const {
-  assert(Kind == FieldDesignator && "Only valid on a field designator");
-  if (Field.NameOrField & 0x01)
-    return reinterpret_cast<IdentifierInfo *>(Field.NameOrField & ~0x01);
-  return getField()->getIdentifier();
+const IdentifierInfo *Designator::getFieldName() const {
+  assert(isFieldDesignator() && "Invalid accessor");
+  if (auto *II = FieldInfo.getIdentifierInfo())
+    return II;
+  return FieldInfo.getFieldDecl()->getIdentifier();
 }
 
 DesignatedInitExpr::DesignatedInitExpr(const ASTContext &C, QualType Ty,
@@ -4466,14 +4466,9 @@
 }
 
 SourceLocation DesignatedInitExpr::getBeginLoc() const {
-  SourceLocation StartLoc;
   auto *DIE = const_cast<DesignatedInitExpr *>(this);
   Designator &First = *DIE->getDesignator(0);
-  if (First.isFieldDesignator())
-    StartLoc = GNUSyntax ? First.Field.FieldLoc : First.Field.DotLoc;
-  else
-    StartLoc = First.ArrayOrRange.LBracketLoc;
-  return StartLoc;
+  return First.getBeginLoc();
 }
 
 SourceLocation DesignatedInitExpr::getEndLoc() const {
@@ -4481,20 +4476,18 @@
 }
 
 Expr *DesignatedInitExpr::getArrayIndex(const Designator& D) const {
-  assert(D.Kind == Designator::ArrayDesignator && "Requires array designator");
-  return getSubExpr(D.ArrayOrRange.Index + 1);
+  assert(D.isArrayDesignator() && "Requires array designator");
+  return getSubExpr(D.getFirstExprIndex() + 1);
 }
 
 Expr *DesignatedInitExpr::getArrayRangeStart(const Designator &D) const {
-  assert(D.Kind == Designator::ArrayRangeDesignator &&
-         "Requires array range designator");
-  return getSubExpr(D.ArrayOrRange.Index + 1);
+  assert(D.isArrayRangeDesignator() && "Requires array range designator");
+  return getSubExpr(D.getFirstExprIndex() + 1);
 }
 
 Expr *DesignatedInitExpr::getArrayRangeEnd(const Designator &D) const {
-  assert(D.Kind == Designator::ArrayRangeDesignator &&
-         "Requires array range designator");
-  return getSubExpr(D.ArrayOrRange.Index + 2);
+  assert(D.isArrayRangeDesignator() && "Requires array range designator");
+  return getSubExpr(D.getFirstExprIndex() + 2);
 }
 
 /// Replaces the designator at index @p Idx with the series
Index: clang/lib/AST/ASTImporter.cpp
===================================================================
--- clang/lib/AST/ASTImporter.cpp
+++ clang/lib/AST/ASTImporter.cpp
@@ -27,6 +27,7 @@
 #include "clang/AST/DeclTemplate.h"
 #include "clang/AST/DeclVisitor.h"
 #include "clang/AST/DeclarationName.h"
+#include "clang/AST/Designator.h"
 #include "clang/AST/Expr.h"
 #include "clang/AST/ExprCXX.h"
 #include "clang/AST/ExprObjC.h"
@@ -437,8 +438,6 @@
     Expected<CXXCastPath> ImportCastPath(CastExpr *E);
     Expected<APValue> ImportAPValue(const APValue &FromValue);
 
-    using Designator = DesignatedInitExpr::Designator;
-
     /// What we should import from the definition.
     enum ImportDefinitionKind {
       /// Import the default subset of the definition, which might be
@@ -961,9 +960,7 @@
                               NumDecls);
 }
 
-template <>
-Expected<ASTNodeImporter::Designator>
-ASTNodeImporter::import(const Designator &D) {
+template <> Expected<Designator> ASTNodeImporter::import(const Designator &D) {
   if (D.isFieldDesignator()) {
     IdentifierInfo *ToFieldName = Importer.Import(D.getFieldName());
 
@@ -975,7 +972,8 @@
     if (!ToFieldLocOrErr)
       return ToFieldLocOrErr.takeError();
 
-    return Designator(ToFieldName, *ToDotLocOrErr, *ToFieldLocOrErr);
+    return Designator::CreateFieldDesignator(ToFieldName, *ToDotLocOrErr,
+                                             *ToFieldLocOrErr);
   }
 
   ExpectedSLoc ToLBracketLocOrErr = import(D.getLBracketLoc());
@@ -987,15 +985,15 @@
     return ToRBracketLocOrErr.takeError();
 
   if (D.isArrayDesignator())
-    return Designator(D.getFirstExprIndex(),
-                      *ToLBracketLocOrErr, *ToRBracketLocOrErr);
+    return Designator::CreateArrayDesignator(
+        D.getFirstExprIndex(), *ToLBracketLocOrErr, *ToRBracketLocOrErr);
 
   ExpectedSLoc ToEllipsisLocOrErr = import(D.getEllipsisLoc());
   if (!ToEllipsisLocOrErr)
     return ToEllipsisLocOrErr.takeError();
 
   assert(D.isArrayRangeDesignator());
-  return Designator(
+  return Designator::CreateArrayRangeDesignator(
       D.getFirstExprIndex(), *ToLBracketLocOrErr, *ToEllipsisLocOrErr,
       *ToRBracketLocOrErr);
 }
Index: clang/include/clang/Tooling/Refactoring/RecursiveSymbolVisitor.h
===================================================================
--- clang/include/clang/Tooling/Refactoring/RecursiveSymbolVisitor.h
+++ clang/include/clang/Tooling/Refactoring/RecursiveSymbolVisitor.h
@@ -123,7 +123,7 @@
   }
 
   bool VisitDesignatedInitExpr(const DesignatedInitExpr *E) {
-    for (const DesignatedInitExpr::Designator &D : E->designators()) {
+    for (const Designator &D : E->designators()) {
       if (D.isFieldDesignator() && D.getField()) {
         const FieldDecl *Decl = D.getField();
         if (!visit(Decl, D.getFieldLoc(), D.getFieldLoc()))
Index: clang/include/clang/Sema/Designator.h
===================================================================
--- clang/include/clang/Sema/Designator.h
+++ /dev/null
@@ -1,214 +0,0 @@
-//===--- Designator.h - Initialization Designator ---------------*- C++ -*-===//
-//
-// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
-// See https://llvm.org/LICENSE.txt for license information.
-// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
-//
-//===----------------------------------------------------------------------===//
-//
-// This file defines interfaces used to represent designators (a la
-// C99 designated initializers) during parsing.
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_CLANG_SEMA_DESIGNATOR_H
-#define LLVM_CLANG_SEMA_DESIGNATOR_H
-
-#include "clang/Basic/SourceLocation.h"
-#include "llvm/ADT/SmallVector.h"
-
-namespace clang {
-
-class Expr;
-class IdentifierInfo;
-class Sema;
-
-/// Designator - A designator in a C99 designated initializer.
-///
-/// This class is a discriminated union which holds the various
-/// different sorts of designators possible.  A Designation is an array of
-/// these.  An example of a designator are things like this:
-///     [8] .field [47]        // C99 designation: 3 designators
-///     [8 ... 47]  field:     // GNU extensions: 2 designators
-/// These occur in initializers, e.g.:
-///  int a[10] = {2, 4, [8]=9, 10};
-///
-class Designator {
-public:
-  enum DesignatorKind {
-    FieldDesignator, ArrayDesignator, ArrayRangeDesignator
-  };
-private:
-  Designator() {};
-
-  DesignatorKind Kind;
-
-  struct FieldDesignatorInfo {
-    const IdentifierInfo *II;
-    SourceLocation DotLoc;
-    SourceLocation NameLoc;
-  };
-  struct ArrayDesignatorInfo {
-    Expr *Index;
-    SourceLocation LBracketLoc;
-    mutable SourceLocation RBracketLoc;
-  };
-  struct ArrayRangeDesignatorInfo {
-    Expr *Start, *End;
-    SourceLocation LBracketLoc, EllipsisLoc;
-    mutable SourceLocation RBracketLoc;
-  };
-
-  union {
-    FieldDesignatorInfo FieldInfo;
-    ArrayDesignatorInfo ArrayInfo;
-    ArrayRangeDesignatorInfo ArrayRangeInfo;
-  };
-
-public:
-
-  DesignatorKind getKind() const { return Kind; }
-  bool isFieldDesignator() const { return Kind == FieldDesignator; }
-  bool isArrayDesignator() const { return Kind == ArrayDesignator; }
-  bool isArrayRangeDesignator() const { return Kind == ArrayRangeDesignator; }
-
-  const IdentifierInfo *getField() const {
-    assert(isFieldDesignator() && "Invalid accessor");
-    return FieldInfo.II;
-  }
-
-  SourceLocation getDotLoc() const {
-    assert(isFieldDesignator() && "Invalid accessor");
-    return FieldInfo.DotLoc;
-  }
-
-  SourceLocation getFieldLoc() const {
-    assert(isFieldDesignator() && "Invalid accessor");
-    return FieldInfo.NameLoc;
-  }
-
-  Expr *getArrayIndex() const {
-    assert(isArrayDesignator() && "Invalid accessor");
-    return ArrayInfo.Index;
-  }
-
-  Expr *getArrayRangeStart() const {
-    assert(isArrayRangeDesignator() && "Invalid accessor");
-    return ArrayRangeInfo.Start;
-  }
-  Expr *getArrayRangeEnd() const {
-    assert(isArrayRangeDesignator() && "Invalid accessor");
-    return ArrayRangeInfo.End;
-  }
-
-  SourceLocation getLBracketLoc() const {
-    assert((isArrayDesignator() || isArrayRangeDesignator()) &&
-           "Invalid accessor");
-    if (isArrayDesignator())
-      return ArrayInfo.LBracketLoc;
-    else
-      return ArrayRangeInfo.LBracketLoc;
-  }
-
-  SourceLocation getRBracketLoc() const {
-    assert((isArrayDesignator() || isArrayRangeDesignator()) &&
-           "Invalid accessor");
-    if (isArrayDesignator())
-      return ArrayInfo.RBracketLoc;
-    else
-      return ArrayRangeInfo.RBracketLoc;
-  }
-
-  SourceLocation getEllipsisLoc() const {
-    assert(isArrayRangeDesignator() && "Invalid accessor");
-    return ArrayRangeInfo.EllipsisLoc;
-  }
-
-  static Designator getField(const IdentifierInfo *II, SourceLocation DotLoc,
-                             SourceLocation NameLoc) {
-    Designator D;
-    D.Kind = FieldDesignator;
-    new (&D.FieldInfo) FieldDesignatorInfo;
-    D.FieldInfo.II = II;
-    D.FieldInfo.DotLoc = DotLoc;
-    D.FieldInfo.NameLoc = NameLoc;
-    return D;
-  }
-
-  static Designator getArray(Expr *Index,
-                             SourceLocation LBracketLoc) {
-    Designator D;
-    D.Kind = ArrayDesignator;
-    new (&D.ArrayInfo) ArrayDesignatorInfo;
-    D.ArrayInfo.Index = Index;
-    D.ArrayInfo.LBracketLoc = LBracketLoc;
-    D.ArrayInfo.RBracketLoc = SourceLocation();
-    return D;
-  }
-
-  static Designator getArrayRange(Expr *Start,
-                                  Expr *End,
-                                  SourceLocation LBracketLoc,
-                                  SourceLocation EllipsisLoc) {
-    Designator D;
-    D.Kind = ArrayRangeDesignator;
-    new (&D.ArrayRangeInfo) ArrayRangeDesignatorInfo;
-    D.ArrayRangeInfo.Start = Start;
-    D.ArrayRangeInfo.End = End;
-    D.ArrayRangeInfo.LBracketLoc = LBracketLoc;
-    D.ArrayRangeInfo.EllipsisLoc = EllipsisLoc;
-    D.ArrayRangeInfo.RBracketLoc = SourceLocation();
-    return D;
-  }
-
-  void setRBracketLoc(SourceLocation RBracketLoc) const {
-    assert((isArrayDesignator() || isArrayRangeDesignator()) &&
-           "Invalid accessor");
-    if (isArrayDesignator())
-      ArrayInfo.RBracketLoc = RBracketLoc;
-    else
-      ArrayRangeInfo.RBracketLoc = RBracketLoc;
-  }
-
-  /// ClearExprs - Null out any expression references, which prevents
-  /// them from being 'delete'd later.
-  void ClearExprs(Sema &Actions) {}
-
-  /// FreeExprs - Release any unclaimed memory for the expressions in
-  /// this designator.
-  void FreeExprs(Sema &Actions) {}
-};
-
-
-/// Designation - Represent a full designation, which is a sequence of
-/// designators.  This class is mostly a helper for InitListDesignations.
-class Designation {
-  /// Designators - The actual designators for this initializer.
-  SmallVector<Designator, 2> Designators;
-
-public:
-  /// AddDesignator - Add a designator to the end of this list.
-  void AddDesignator(Designator D) {
-    Designators.push_back(D);
-  }
-
-  bool empty() const { return Designators.empty(); }
-
-  unsigned getNumDesignators() const { return Designators.size(); }
-  const Designator &getDesignator(unsigned Idx) const {
-    assert(Idx < Designators.size());
-    return Designators[Idx];
-  }
-
-  /// ClearExprs - Null out any expression references, which prevents them from
-  /// being 'delete'd later.
-  void ClearExprs(Sema &Actions) {}
-
-  /// FreeExprs - Release any unclaimed memory for the expressions in this
-  /// designation.
-  void FreeExprs(Sema &Actions) {}
-};
-
-} // end namespace clang
-
-#endif
Index: clang/include/clang/AST/Expr.h
===================================================================
--- clang/include/clang/AST/Expr.h
+++ clang/include/clang/AST/Expr.h
@@ -19,6 +19,7 @@
 #include "clang/AST/Decl.h"
 #include "clang/AST/DeclAccessPair.h"
 #include "clang/AST/DependenceFlags.h"
+#include "clang/AST/Designator.h"
 #include "clang/AST/OperationKinds.h"
 #include "clang/AST/Stmt.h"
 #include "clang/AST/TemplateBase.h"
@@ -5035,10 +5036,6 @@
 class DesignatedInitExpr final
     : public Expr,
       private llvm::TrailingObjects<DesignatedInitExpr, Stmt *> {
-public:
-  /// Forward declaration of the Designator class.
-  class Designator;
-
 private:
   /// The location of the '=' or ':' prior to the actual initializer
   /// expression.
@@ -5070,161 +5067,6 @@
       NumDesignators(0), NumSubExprs(NumSubExprs), Designators(nullptr) { }
 
 public:
-  /// A field designator, e.g., ".x".
-  struct FieldDesignator {
-    /// Refers to the field that is being initialized. The low bit
-    /// of this field determines whether this is actually a pointer
-    /// to an IdentifierInfo (if 1) or a FieldDecl (if 0). When
-    /// initially constructed, a field designator will store an
-    /// IdentifierInfo*. After semantic analysis has resolved that
-    /// name, the field designator will instead store a FieldDecl*.
-    uintptr_t NameOrField;
-
-    /// The location of the '.' in the designated initializer.
-    SourceLocation DotLoc;
-
-    /// The location of the field name in the designated initializer.
-    SourceLocation FieldLoc;
-  };
-
-  /// An array or GNU array-range designator, e.g., "[9]" or "[10..15]".
-  struct ArrayOrRangeDesignator {
-    /// Location of the first index expression within the designated
-    /// initializer expression's list of subexpressions.
-    unsigned Index;
-    /// The location of the '[' starting the array range designator.
-    SourceLocation LBracketLoc;
-    /// The location of the ellipsis separating the start and end
-    /// indices. Only valid for GNU array-range designators.
-    SourceLocation EllipsisLoc;
-    /// The location of the ']' terminating the array range designator.
-    SourceLocation RBracketLoc;
-  };
-
-  /// Represents a single C99 designator.
-  ///
-  /// @todo This class is infuriatingly similar to clang::Designator,
-  /// but minor differences (storing indices vs. storing pointers)
-  /// keep us from reusing it. Try harder, later, to rectify these
-  /// differences.
-  class Designator {
-    /// The kind of designator this describes.
-    enum {
-      FieldDesignator,
-      ArrayDesignator,
-      ArrayRangeDesignator
-    } Kind;
-
-    union {
-      /// A field designator, e.g., ".x".
-      struct FieldDesignator Field;
-      /// An array or GNU array-range designator, e.g., "[9]" or "[10..15]".
-      struct ArrayOrRangeDesignator ArrayOrRange;
-    };
-    friend class DesignatedInitExpr;
-
-  public:
-    Designator() {}
-
-    /// Initializes a field designator.
-    Designator(const IdentifierInfo *FieldName, SourceLocation DotLoc,
-               SourceLocation FieldLoc)
-      : Kind(FieldDesignator) {
-      new (&Field) DesignatedInitExpr::FieldDesignator;
-      Field.NameOrField = reinterpret_cast<uintptr_t>(FieldName) | 0x01;
-      Field.DotLoc = DotLoc;
-      Field.FieldLoc = FieldLoc;
-    }
-
-    /// Initializes an array designator.
-    Designator(unsigned Index, SourceLocation LBracketLoc,
-               SourceLocation RBracketLoc)
-      : Kind(ArrayDesignator) {
-      new (&ArrayOrRange) DesignatedInitExpr::ArrayOrRangeDesignator;
-      ArrayOrRange.Index = Index;
-      ArrayOrRange.LBracketLoc = LBracketLoc;
-      ArrayOrRange.EllipsisLoc = SourceLocation();
-      ArrayOrRange.RBracketLoc = RBracketLoc;
-    }
-
-    /// Initializes a GNU array-range designator.
-    Designator(unsigned Index, SourceLocation LBracketLoc,
-               SourceLocation EllipsisLoc, SourceLocation RBracketLoc)
-      : Kind(ArrayRangeDesignator) {
-      new (&ArrayOrRange) DesignatedInitExpr::ArrayOrRangeDesignator;
-      ArrayOrRange.Index = Index;
-      ArrayOrRange.LBracketLoc = LBracketLoc;
-      ArrayOrRange.EllipsisLoc = EllipsisLoc;
-      ArrayOrRange.RBracketLoc = RBracketLoc;
-    }
-
-    bool isFieldDesignator() const { return Kind == FieldDesignator; }
-    bool isArrayDesignator() const { return Kind == ArrayDesignator; }
-    bool isArrayRangeDesignator() const { return Kind == ArrayRangeDesignator; }
-
-    IdentifierInfo *getFieldName() const;
-
-    FieldDecl *getField() const {
-      assert(Kind == FieldDesignator && "Only valid on a field designator");
-      if (Field.NameOrField & 0x01)
-        return nullptr;
-      else
-        return reinterpret_cast<FieldDecl *>(Field.NameOrField);
-    }
-
-    void setField(FieldDecl *FD) {
-      assert(Kind == FieldDesignator && "Only valid on a field designator");
-      Field.NameOrField = reinterpret_cast<uintptr_t>(FD);
-    }
-
-    SourceLocation getDotLoc() const {
-      assert(Kind == FieldDesignator && "Only valid on a field designator");
-      return Field.DotLoc;
-    }
-
-    SourceLocation getFieldLoc() const {
-      assert(Kind == FieldDesignator && "Only valid on a field designator");
-      return Field.FieldLoc;
-    }
-
-    SourceLocation getLBracketLoc() const {
-      assert((Kind == ArrayDesignator || Kind == ArrayRangeDesignator) &&
-             "Only valid on an array or array-range designator");
-      return ArrayOrRange.LBracketLoc;
-    }
-
-    SourceLocation getRBracketLoc() const {
-      assert((Kind == ArrayDesignator || Kind == ArrayRangeDesignator) &&
-             "Only valid on an array or array-range designator");
-      return ArrayOrRange.RBracketLoc;
-    }
-
-    SourceLocation getEllipsisLoc() const {
-      assert(Kind == ArrayRangeDesignator &&
-             "Only valid on an array-range designator");
-      return ArrayOrRange.EllipsisLoc;
-    }
-
-    unsigned getFirstExprIndex() const {
-      assert((Kind == ArrayDesignator || Kind == ArrayRangeDesignator) &&
-             "Only valid on an array or array-range designator");
-      return ArrayOrRange.Index;
-    }
-
-    SourceLocation getBeginLoc() const LLVM_READONLY {
-      if (Kind == FieldDesignator)
-        return getDotLoc().isInvalid()? getFieldLoc() : getDotLoc();
-      else
-        return getLBracketLoc();
-    }
-    SourceLocation getEndLoc() const LLVM_READONLY {
-      return Kind == FieldDesignator ? getFieldLoc() : getRBracketLoc();
-    }
-    SourceRange getSourceRange() const LLVM_READONLY {
-      return SourceRange(getBeginLoc(), getEndLoc());
-    }
-  };
-
   static DesignatedInitExpr *Create(const ASTContext &C,
                                     llvm::ArrayRef<Designator> Designators,
                                     ArrayRef<Expr*> IndexExprs,
Index: clang/include/clang/AST/Designator.h
===================================================================
--- /dev/null
+++ clang/include/clang/AST/Designator.h
@@ -0,0 +1,326 @@
+//===--- Designator.h - Initialization Designator ---------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+//
+// This file defines interfaces used to represent designators (i.e. C99
+// designated initializers) during parsing and sema.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_AST_DESIGNATOR_H
+#define LLVM_CLANG_AST_DESIGNATOR_H
+
+#include "clang/Basic/SourceLocation.h"
+#include "llvm/ADT/SmallVector.h"
+
+namespace clang {
+
+class Expr;
+class FieldDecl;
+class IdentifierInfo;
+class Sema;
+
+/// Designator - A designator in a C99 designated initializer.
+///
+/// This class is a discriminated union which holds the various
+/// different sorts of designators possible. A Designation is an array of
+/// these.  An example of a designator are things like this:
+///
+///      [8] .field [47]        // C99 designation: 3 designators
+///      [8 ... 47]  field:     // GNU extensions: 2 designators
+///
+/// These occur in initializers, e.g.:
+///
+///      int a[10] = {2, 4, [8]=9, 10};
+///
+class Designator {
+  enum DesignatorKind {
+    FieldDesignator,
+    ArrayDesignatorExpr,
+    ArrayDesignatorInt,
+    ArrayRangeDesignatorExpr,
+    ArrayRangeDesignatorInt,
+  };
+
+  DesignatorKind Kind;
+
+  /// A field designator, e.g., ".x = 42".
+  class FieldDesignatorInfo {
+    /// Refers to the field that is being initialized. The low bit of this
+    /// field determines whether this is actually a pointer to an
+    /// IdentifierInfo (if 1) or a FieldDecl (if 0). When initially
+    /// constructed, a field designator will store an IdentifierInfo*. After
+    /// semantic analysis has resolved that name, the field designator will
+    /// instead store a FieldDecl*.
+    uintptr_t NameOrField;
+
+  public:
+    /// The location of the '.' in the designated initializer.
+    SourceLocation DotLoc;
+
+    /// The location of the field name in the designated initializer.
+    SourceLocation NameLoc;
+
+    FieldDesignatorInfo(const IdentifierInfo *II, SourceLocation DotLoc,
+                        SourceLocation NameLoc)
+        : NameOrField(reinterpret_cast<uintptr_t>(II) | 0x01), DotLoc(DotLoc),
+          NameLoc(NameLoc) {}
+
+    FieldDecl *getFieldDecl() const {
+      if (NameOrField & 0x01)
+        return nullptr;
+      return reinterpret_cast<FieldDecl *>(NameOrField);
+    }
+    const IdentifierInfo *getIdentifierInfo() const {
+      if (NameOrField & 0x01)
+        return reinterpret_cast<const IdentifierInfo *>(NameOrField & ~0x1);
+      return nullptr;
+    }
+
+    void set(FieldDecl *FD) { NameOrField = reinterpret_cast<uintptr_t>(FD); }
+  };
+
+  /// An array designator, e.g., "[42] = 0" and "[42 ... 50] = 1".
+  template <typename Ty> struct ArrayDesignatorInfo {
+    /// Location of the first and last index expression within the designated
+    /// initializer expression's list of subexpressions.
+    Ty Start;
+    Ty End;
+
+    /// The location of the '[' starting the array designator.
+    SourceLocation LBracketLoc;
+
+    /// The location of the ellipsis separating the start and end indices.
+    /// Only valid for GNU array-range designators.
+    SourceLocation EllipsisLoc;
+
+    /// The location of the ']' terminating the array designator.
+    SourceLocation RBracketLoc;
+
+    ArrayDesignatorInfo(Ty Start, Ty End, SourceLocation LBracketLoc,
+                        SourceLocation EllipsisLoc, SourceLocation RBracketLoc)
+        : Start(Start), End(End), LBracketLoc(LBracketLoc),
+          EllipsisLoc(EllipsisLoc), RBracketLoc(RBracketLoc) {}
+
+    Ty getStart() const { return Start; }
+    Ty getEnd() const { return End; }
+  };
+
+  union {
+    FieldDesignatorInfo FieldInfo;
+    ArrayDesignatorInfo<Expr *> ArrayInfoExpr;
+    ArrayDesignatorInfo<unsigned> ArrayInfoInt;
+  };
+
+  Designator(DesignatorKind Kind) : Kind(Kind) {}
+
+public:
+  Designator() {}
+
+  bool isFieldDesignator() const { return Kind == FieldDesignator; }
+  bool isArrayDesignator() const {
+    return Kind == ArrayDesignatorExpr || Kind == ArrayDesignatorInt;
+  }
+  bool isArrayRangeDesignator() const {
+    return Kind == ArrayRangeDesignatorExpr || Kind == ArrayRangeDesignatorInt;
+  }
+
+  /// FieldDesignatorInfo:
+  static Designator CreateFieldDesignator(const IdentifierInfo *FieldName,
+                                          SourceLocation DotLoc,
+                                          SourceLocation NameLoc) {
+    Designator D(FieldDesignator);
+    new (&D.FieldInfo) FieldDesignatorInfo(FieldName, DotLoc, NameLoc);
+    return D;
+  }
+
+  const IdentifierInfo *getFieldName() const;
+
+  FieldDecl *getField() const {
+    assert(isFieldDesignator() && "Invalid accessor");
+    return FieldInfo.getFieldDecl();
+  }
+
+  void setField(FieldDecl *FD) {
+    assert(isFieldDesignator() && "Invalid accessor");
+    FieldInfo.set(FD);
+  }
+
+  SourceLocation getDotLoc() const {
+    assert(isFieldDesignator() && "Invalid accessor");
+    return FieldInfo.DotLoc;
+  }
+
+  SourceLocation getFieldLoc() const {
+    assert(isFieldDesignator() && "Invalid accessor");
+    return FieldInfo.NameLoc;
+  }
+
+  /// ArrayDesignatorInfo:
+  static Designator
+  CreateArrayDesignator(Expr *Start, SourceLocation LBracketLoc,
+                        SourceLocation RBracketLoc = SourceLocation()) {
+    Designator D(ArrayDesignatorExpr);
+    new (&D.ArrayInfoExpr) ArrayDesignatorInfo<Expr *>(
+        Start, nullptr, LBracketLoc, SourceLocation(), RBracketLoc);
+    return D;
+  }
+  static Designator
+  CreateArrayDesignator(unsigned Start, SourceLocation LBracketLoc,
+                        SourceLocation RBracketLoc = SourceLocation()) {
+    Designator D(ArrayDesignatorInt);
+    new (&D.ArrayInfoInt) ArrayDesignatorInfo<unsigned>(
+        Start, 0, LBracketLoc, SourceLocation(), RBracketLoc);
+    return D;
+  }
+
+  template <typename Ty = Expr *> Ty getArrayIndex() const {
+    assert(isArrayDesignator() && "Invalid accessor");
+    return ArrayInfoExpr.getStart();
+  }
+
+  /// ArrayRangeDesignatorInfo:
+  static Designator
+  CreateArrayRangeDesignator(Expr *Start, Expr *End, SourceLocation LBracketLoc,
+                             SourceLocation EllipsisLoc,
+                             SourceLocation RBracketLoc = SourceLocation()) {
+    Designator D(ArrayRangeDesignatorExpr);
+    new (&D.ArrayInfoExpr) ArrayDesignatorInfo<Expr *>(
+        Start, End, LBracketLoc, EllipsisLoc, RBracketLoc);
+    return D;
+  }
+  static Designator
+  CreateArrayRangeDesignator(unsigned Index, SourceLocation LBracketLoc,
+                             SourceLocation EllipsisLoc,
+                             SourceLocation RBracketLoc = SourceLocation()) {
+    Designator D(ArrayRangeDesignatorInt);
+    new (&D.ArrayInfoInt) ArrayDesignatorInfo<unsigned>(
+        Index, 0, LBracketLoc, EllipsisLoc, RBracketLoc);
+    return D;
+  }
+
+  Expr *getArrayRangeStart() const {
+    assert(isArrayRangeDesignator() && "Invalid accessor");
+    return ArrayInfoExpr.getStart();
+  }
+
+  Expr *getArrayRangeEnd() const {
+    assert(isArrayRangeDesignator() && "Invalid accessor");
+    return ArrayInfoExpr.getEnd();
+  }
+
+  SourceLocation getLBracketLoc() const {
+    switch (Kind) {
+    default:
+      break;
+    case ArrayDesignatorExpr:
+    case ArrayRangeDesignatorExpr:
+      return ArrayInfoExpr.LBracketLoc;
+    case ArrayDesignatorInt:
+    case ArrayRangeDesignatorInt:
+      return ArrayInfoInt.LBracketLoc;
+    }
+
+    assert(false && "Invalid accessor");
+    return SourceLocation();
+  }
+
+  SourceLocation getEllipsisLoc() const {
+    switch (Kind) {
+    default:
+      break;
+    case ArrayRangeDesignatorExpr:
+      return ArrayInfoExpr.LBracketLoc;
+    case ArrayRangeDesignatorInt:
+      return ArrayInfoInt.LBracketLoc;
+    }
+
+    assert(false && "Invalid accessor");
+    return SourceLocation();
+  }
+
+  SourceLocation getRBracketLoc() const {
+    switch (Kind) {
+    default:
+      break;
+    case ArrayDesignatorExpr:
+    case ArrayRangeDesignatorExpr:
+      return ArrayInfoExpr.RBracketLoc;
+    case ArrayDesignatorInt:
+    case ArrayRangeDesignatorInt:
+      return ArrayInfoInt.RBracketLoc;
+    }
+
+    assert(false && "Invalid accessor");
+    return SourceLocation();
+  }
+
+  void setRBracketLoc(SourceLocation RBracketLoc) {
+    switch (Kind) {
+    default:
+      assert(false && "Invalid accessor");
+      break;
+    case ArrayDesignatorExpr:
+    case ArrayRangeDesignatorExpr:
+      ArrayInfoExpr.RBracketLoc = RBracketLoc;
+      break;
+    case ArrayDesignatorInt:
+    case ArrayRangeDesignatorInt:
+      ArrayInfoInt.RBracketLoc = RBracketLoc;
+      break;
+    }
+  }
+
+  unsigned getFirstExprIndex() const {
+    if (Kind == ArrayDesignatorInt || Kind == ArrayRangeDesignatorInt)
+      return ArrayInfoInt.getStart();
+
+    assert(false && "Invalid accessor");
+    return 0;
+  }
+
+  /// Source location accessors.
+  SourceLocation getBeginLoc() const LLVM_READONLY {
+    if (isFieldDesignator())
+      return getDotLoc().isInvalid() ? getFieldLoc() : getDotLoc();
+    return getLBracketLoc();
+  }
+  SourceLocation getEndLoc() const LLVM_READONLY {
+    return isFieldDesignator() ? getFieldLoc() : getRBracketLoc();
+  }
+  SourceRange getSourceRange() const LLVM_READONLY {
+    return SourceRange(getBeginLoc(), getEndLoc());
+  }
+};
+
+/// Designation - Represent a full designation, which is a sequence of
+/// designators.  This class is mostly a helper for InitListDesignations.
+class Designation {
+  /// Designators - The actual designators for this initializer.
+  SmallVector<Designator, 2> Designators;
+
+public:
+  /// AddDesignator - Add a designator to the end of this list.
+  void AddDesignator(Designator D) { Designators.push_back(D); }
+
+  bool empty() const { return Designators.empty(); }
+
+  unsigned getNumDesignators() const { return Designators.size(); }
+
+  const Designator &getDesignator(unsigned Idx) const {
+    assert(Idx < getNumDesignators());
+    return Designators[Idx];
+  }
+  Designator &getDesignator(unsigned Idx) {
+    assert(Idx < getNumDesignators());
+    return Designators[Idx];
+  }
+};
+
+} // end namespace clang
+
+#endif
Index: clang-tools-extra/clangd/FindTarget.cpp
===================================================================
--- clang-tools-extra/clangd/FindTarget.cpp
+++ clang-tools-extra/clangd/FindTarget.cpp
@@ -285,8 +285,7 @@
         Outer.add(CCE->getConstructor(), Flags);
       }
       void VisitDesignatedInitExpr(const DesignatedInitExpr *DIE) {
-        for (const DesignatedInitExpr::Designator &D :
-             llvm::reverse(DIE->designators()))
+        for (const Designator &D : llvm::reverse(DIE->designators()))
           if (D.isFieldDesignator()) {
             Outer.add(D.getField(), Flags);
             // We don't know which designator was intended, we assume the outer.
@@ -801,7 +800,7 @@
     }
 
     void VisitDesignatedInitExpr(const DesignatedInitExpr *DIE) {
-      for (const DesignatedInitExpr::Designator &D : DIE->designators()) {
+      for (const Designator &D : DIE->designators()) {
         if (!D.isFieldDesignator())
           continue;
 
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to