[cfe-commits] r102434 - in /cfe/trunk: lib/Sema/TreeTransform.h test/SemaTemplate/instantiate-method.cpp

Douglas Gregor dgregor at apple.com
Tue Apr 27 09:10:10 PDT 2010


Author: dgregor
Date: Tue Apr 27 11:10:10 2010
New Revision: 102434

URL: http://llvm.org/viewvc/llvm-project?rev=102434&view=rev
Log:
When instantiating UnresolvedLookupExpr and UnresolvedMemberExpr
expressions, be sure to set the naming class of the LookupResult
structure. Fixes PR6947.


Modified:
    cfe/trunk/lib/Sema/TreeTransform.h
    cfe/trunk/test/SemaTemplate/instantiate-method.cpp

Modified: cfe/trunk/lib/Sema/TreeTransform.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/TreeTransform.h?rev=102434&r1=102433&r2=102434&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/TreeTransform.h (original)
+++ cfe/trunk/lib/Sema/TreeTransform.h Tue Apr 27 11:10:10 2010
@@ -5336,6 +5336,20 @@
     
     SS.setScopeRep(Qualifier);
     SS.setRange(Old->getQualifierRange());
+    
+    // If this nested-name-specifier refers to a class type, that is the
+    // naming class.
+    if (const Type *NamedType = Qualifier->getAsType())
+      if (const RecordType *NamedRecord = NamedType->getAs<RecordType>())
+        R.setNamingClass(cast<CXXRecordDecl>(NamedRecord->getDecl()));
+  } else if (Old->getNamingClass()) {
+    CXXRecordDecl *NamingClass
+      = cast_or_null<CXXRecordDecl>(getDerived().TransformDecl(
+                                                            Old->getNameLoc(),
+                                                        Old->getNamingClass()));
+    if (!NamingClass)
+      return SemaRef.ExprError();
+    R.setNamingClass(NamingClass);
   }
 
   // If we have no template arguments, it's a normal declaration name.
@@ -5721,6 +5735,7 @@
     BaseType = getDerived().TransformType(Old->getBaseType());
   }
 
+  CXXRecordDecl *NamingClass = 0;
   NestedNameSpecifier *Qualifier = 0;
   if (Old->getQualifier()) {
     Qualifier
@@ -5728,6 +5743,12 @@
                                                   Old->getQualifierRange());
     if (Qualifier == 0)
       return SemaRef.ExprError();
+    
+    // If this nested-name-specifier refers to a class type, that is the
+    // naming class.
+    if (const Type *NamedType = Qualifier->getAsType())
+      if (const RecordType *NamedRecord = NamedType->getAs<RecordType>())
+        NamingClass = cast<CXXRecordDecl>(NamedRecord->getDecl());
   }
 
   LookupResult R(SemaRef, Old->getMemberName(), Old->getMemberLoc(),
@@ -5762,6 +5783,25 @@
 
   R.resolveKind();
 
+  // Determine the naming class, if we haven't already.
+  if (!NamingClass) {
+    QualType T = BaseType;
+    if (const PointerType *PointerTy = T->getAs<PointerType>())
+      T = PointerTy->getPointeeType();
+    if (const RecordType *NamedRecord = T->getAs<RecordType>())
+      NamingClass = cast<CXXRecordDecl>(NamedRecord->getDecl());    
+  }
+  
+  if (!NamingClass && Old->getNamingClass()) {
+    NamingClass = cast_or_null<CXXRecordDecl>(getDerived().TransformDecl(
+                                                          Old->getMemberLoc(),
+                                                        Old->getNamingClass()));
+    if (!NamingClass)
+      return SemaRef.ExprError();
+  }
+  if (NamingClass)
+    R.setNamingClass(NamingClass);
+  
   TemplateArgumentListInfo TransArgs;
   if (Old->hasExplicitTemplateArgs()) {
     TransArgs.setLAngleLoc(Old->getLAngleLoc());

Modified: cfe/trunk/test/SemaTemplate/instantiate-method.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaTemplate/instantiate-method.cpp?rev=102434&r1=102433&r2=102434&view=diff
==============================================================================
--- cfe/trunk/test/SemaTemplate/instantiate-method.cpp (original)
+++ cfe/trunk/test/SemaTemplate/instantiate-method.cpp Tue Apr 27 11:10:10 2010
@@ -127,3 +127,28 @@
   };
   template class B<int>;
 }
+
+namespace PR6947 {
+  template< class T > 
+  struct X {
+    int f0( )      
+    {
+      typedef void ( X::*impl_fun_ptr )( );
+      impl_fun_ptr pImpl = &X::template
+        f0_impl1<int>;
+    }
+  private:                  
+    int f1() {
+    }
+    template< class Processor>                  
+    void f0_impl1( )                 
+    {
+    }
+  };
+
+  char g0() {
+    X<int> pc;
+    pc.f0();
+  }
+
+}





More information about the cfe-commits mailing list