]> granicus.if.org Git - clang/commitdiff
Keep track of when DependentNameTypes have no associated keyword
authorDouglas Gregor <dgregor@apple.com>
Sat, 24 Apr 2010 15:35:55 +0000 (15:35 +0000)
committerDouglas Gregor <dgregor@apple.com>
Sat, 24 Apr 2010 15:35:55 +0000 (15:35 +0000)
(e.g., no typename, enum, class, etc.), e.g., because the context is
one that is known to refer to a type. Patch from Enea Zaffanella!

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@102243 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Sema/Sema.h
lib/Sema/SemaDecl.cpp
lib/Sema/SemaDeclCXX.cpp
lib/Sema/SemaExprCXX.cpp
lib/Sema/SemaTemplate.cpp
lib/Sema/TreeTransform.h

index 64afd56a40f17589720c6581ad2e405bfa0cafaf..dffc7126ed36a8e28703669015fbf064cfe2d888 100644 (file)
@@ -3017,7 +3017,8 @@ public:
   ActOnTypenameType(SourceLocation TypenameLoc, const CXXScopeSpec &SS,
                     SourceLocation TemplateLoc, TypeTy *Ty);
 
-  QualType CheckTypenameType(NestedNameSpecifier *NNS,
+  QualType CheckTypenameType(ElaboratedTypeKeyword Keyword,
+                             NestedNameSpecifier *NNS,
                              const IdentifierInfo &II,
                              SourceRange Range);
 
index cdfd0553f2af5e04d9814ffc021ccdc967cdc072..b8ff182be087fe4cf48d138544bb3965d2196a60 100644 (file)
@@ -89,9 +89,8 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
         
         // We know from the grammar that this name refers to a type, so build a
         // DependentNameType node to describe the type.
-        // FIXME: Record somewhere that this DependentNameType node has no "typename"
-        // keyword associated with it.
-        return CheckTypenameType((NestedNameSpecifier *)SS->getScopeRep(),
+        return CheckTypenameType(ETK_None,
+                                 (NestedNameSpecifier *)SS->getScopeRep(),
                                  II, SS->getRange()).getAsOpaquePtr();
       }
       
index 9038a2508226a44211d33575c2f76ec6eb1ae804..f1b1244b9e36a964c878b4b1a71c2d8483a4a8ff 100644 (file)
@@ -1088,7 +1088,8 @@ Sema::ActOnMemInitializer(DeclPtrTy ConstructorD,
         if (!NotUnknownSpecialization) {
           // When the scope specifier can refer to a member of an unknown
           // specialization, we take it as a type name.
-          BaseType = CheckTypenameType((NestedNameSpecifier *)SS.getScopeRep(),
+          BaseType = CheckTypenameType(ETK_None,
+                                       (NestedNameSpecifier *)SS.getScopeRep(),
                                        *MemberOrBase, SS.getRange());
           if (BaseType.isNull())
             return true;
index 6983a1e0d8cf04da2acc5d70ad5da713d9762952..042f2c14abefd82224e6acc923588b9e25d346c7 100644 (file)
@@ -261,7 +261,7 @@ Action::TypeTy *Sema::getDestructorName(SourceLocation TildeLoc,
       Range = SourceRange(NameLoc);
     }
 
-    return CheckTypenameType(NNS, II, Range).getAsOpaquePtr();
+    return CheckTypenameType(ETK_None, NNS, II, Range).getAsOpaquePtr();
   }
 
   if (ObjectTypePtr)
index 7a3e83a4979f7dc19e82c317ab089e1580e878f6..1075f41399840d98e59a05533cc4effb95b49d40 100644 (file)
@@ -5128,7 +5128,8 @@ Sema::ActOnTypenameType(SourceLocation TypenameLoc, const CXXScopeSpec &SS,
   if (!NNS)
     return true;
 
-  QualType T = CheckTypenameType(NNS, II, SourceRange(TypenameLoc, IdLoc));
+  QualType T = CheckTypenameType(ETK_Typename, NNS, II,
+                                 SourceRange(TypenameLoc, IdLoc));
   if (T.isNull())
     return true;
   return T.getAsOpaquePtr();
@@ -5160,7 +5161,8 @@ Sema::ActOnTypenameType(SourceLocation TypenameLoc, const CXXScopeSpec &SS,
 /// \brief Build the type that describes a C++ typename specifier,
 /// e.g., "typename T::type".
 QualType
-Sema::CheckTypenameType(NestedNameSpecifier *NNS, const IdentifierInfo &II,
+Sema::CheckTypenameType(ElaboratedTypeKeyword Keyword,
+                        NestedNameSpecifier *NNS, const IdentifierInfo &II,
                         SourceRange Range) {
   CXXRecordDecl *CurrentInstantiation = 0;
   if (NNS->isDependent()) {
@@ -5169,7 +5171,7 @@ Sema::CheckTypenameType(NestedNameSpecifier *NNS, const IdentifierInfo &II,
     // If the nested-name-specifier does not refer to the current
     // instantiation, then build a typename type.
     if (!CurrentInstantiation)
-      return Context.getDependentNameType(ETK_Typename, NNS, &II);
+      return Context.getDependentNameType(Keyword, NNS, &II);
 
     // The nested-name-specifier refers to the current instantiation, so the
     // "typename" keyword itself is superfluous. In C++03, the program is
@@ -5205,7 +5207,7 @@ Sema::CheckTypenameType(NestedNameSpecifier *NNS, const IdentifierInfo &II,
       
   case LookupResult::NotFoundInCurrentInstantiation:
     // Okay, it's a member of an unknown instantiation.
-    return Context.getDependentNameType(ETK_Typename, NNS, &II);
+    return Context.getDependentNameType(Keyword, NNS, &II);
 
   case LookupResult::Found:
     if (TypeDecl *Type = dyn_cast<TypeDecl>(Result.getFoundDecl())) {
index 8b2aa4e308820fb93d60d94cc45a24be4177532b..302d405b7f9c1bd8808bd1fee17041675f958a20 100644 (file)
@@ -574,10 +574,9 @@ public:
     TagDecl::TagKind Kind = TagDecl::TK_enum;
     switch (Keyword) {
       case ETK_None:
-        // FIXME: Note the lack of the "typename" specifier!
-        // Fall through
+        // Fall through.
       case ETK_Typename:
-        return SemaRef.CheckTypenameType(NNS, *Id, SR);
+        return SemaRef.CheckTypenameType(Keyword, NNS, *Id, SR);
         
       case ETK_Class: Kind = TagDecl::TK_class; break;
       case ETK_Struct: Kind = TagDecl::TK_struct; break;