Unifies the name-lookup mechanisms used in various parts of the AST
and separates lexical name lookup from qualified name lookup. In
particular:
  * Make DeclContext the central data structure for storing and
    looking up declarations within existing declarations, e.g., members
    of structs/unions/classes, enumerators in C++0x enums, members of
    C++ namespaces, and (later) members of Objective-C
    interfaces/implementations. DeclContext uses a lazily-constructed
    data structure optimized for fast lookup (array for small contexts,
    hash table for larger contexts). 

  * Implement C++ qualified name lookup in terms of lookup into
    DeclContext.

  * Implement C++ unqualified name lookup in terms of
    qualified+unqualified name lookup (since unqualified lookup is not
    purely lexical in C++!)

  * Limit the use of the chains of declarations stored in
    IdentifierInfo to those names declared lexically.

  * Eliminate CXXFieldDecl, collapsing its behavior into
    FieldDecl. (FieldDecl is now a ScopedDecl).

  * Make RecordDecl into a DeclContext and eliminates its
    Members/NumMembers fields (since one can just iterate through the
    DeclContext to get the fields).



git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@60878 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/AST/Decl.cpp b/lib/AST/Decl.cpp
index 194f47f..7643e4e 100644
--- a/lib/AST/Decl.cpp
+++ b/lib/AST/Decl.cpp
@@ -81,10 +81,11 @@
   return new (Mem) BlockDecl(DC, L);
 }
 
-FieldDecl *FieldDecl::Create(ASTContext &C, SourceLocation L,
-                             IdentifierInfo *Id, QualType T, Expr *BW) {
+FieldDecl *FieldDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L,
+                             IdentifierInfo *Id, QualType T, Expr *BW,
+                             bool Mutable, ScopedDecl *PrevDecl) {
   void *Mem = C.getAllocator().Allocate<FieldDecl>();
-  return new (Mem) FieldDecl(L, Id, T, BW);
+  return new (Mem) FieldDecl(Decl::Field, DC, L, Id, T, BW, Mutable, PrevDecl);
 }
 
 
@@ -118,10 +119,21 @@
 }
 
 void EnumDecl::Destroy(ASTContext& C) {
-  if (getEnumConstantList()) getEnumConstantList()->Destroy(C);
+  DeclContext::DestroyDecls(C);
   Decl::Destroy(C);
 }
 
+void EnumDecl::completeDefinition(ASTContext &C, QualType NewType) {
+  assert(!isDefinition() && "Cannot redefine enums!");
+  setDefinition(true);
+
+  IntegerType = NewType;
+
+  // Let ASTContext know that this is the defining EnumDecl for this
+  // type.
+  C.setTagDefinition(this);
+}
+
 FileScopeAsmDecl *FileScopeAsmDecl::Create(ASTContext &C,
                                            SourceLocation L,
                                            StringLiteral *Str) {
@@ -248,12 +260,10 @@
 
 RecordDecl::RecordDecl(Kind DK, TagKind TK, DeclContext *DC, SourceLocation L,
                        IdentifierInfo *Id)
-: TagDecl(DK, TK, DC, L, Id, 0) {
+  : TagDecl(DK, TK, DC, L, Id, 0), DeclContext(DK) {
   
   HasFlexibleArrayMember = false;
   assert(classof(static_cast<Decl*>(this)) && "Invalid Kind!");
-  Members = 0;
-  NumMembers = -1;  
 }
 
 RecordDecl *RecordDecl::Create(ASTContext &C, TagKind TK, DeclContext *DC,
@@ -267,46 +277,25 @@
 }
 
 RecordDecl::~RecordDecl() {
-  delete[] Members;
 }
 
 void RecordDecl::Destroy(ASTContext& C) {
-  if (isDefinition())
-    for (field_iterator I=field_begin(), E=field_end(); I!=E; ++I)
-      (*I)->Destroy(C);
-
+  DeclContext::DestroyDecls(C);
   TagDecl::Destroy(C);
 }
 
-/// defineBody - When created, RecordDecl's correspond to a forward declared
-/// record.  This method is used to mark the decl as being defined, with the
-/// specified contents.
-void RecordDecl::defineBody(ASTContext& C, FieldDecl **members,
-                            unsigned numMembers) {
+/// completeDefinition - Notes that the definition of this type is now
+/// complete.
+void RecordDecl::completeDefinition(ASTContext& C) {
   assert(!isDefinition() && "Cannot redefine record!");
+
   setDefinition(true);
-  NumMembers = numMembers;
-  if (numMembers) {
-    Members = new FieldDecl*[numMembers];
-    memcpy(Members, members, numMembers*sizeof(Decl*));
-  }
   
-  // Let ASTContext know that this is the defining RecordDecl this type.
+  // Let ASTContext know that this is the defining RecordDecl for this
+  // type.
   C.setTagDefinition(this);
 }
 
-
-FieldDecl *RecordDecl::getMember(IdentifierInfo *II) {
-  if (Members == 0 || NumMembers < 0)
-    return 0;
-  
-  // Linear search.  When C++ classes come along, will likely need to revisit.
-  for (int i = 0; i != NumMembers; ++i)
-    if (Members[i]->getIdentifier() == II)
-      return Members[i];
-  return 0;
-}
-
 //===----------------------------------------------------------------------===//
 // BlockDecl Implementation
 //===----------------------------------------------------------------------===//