]> granicus.if.org Git - clang/commitdiff
If filtering a lookup result leaves it ambiguous, keep the ambiguity
authorJohn McCall <rjmccall@apple.com>
Sat, 28 Aug 2010 20:17:00 +0000 (20:17 +0000)
committerJohn McCall <rjmccall@apple.com>
Sat, 28 Aug 2010 20:17:00 +0000 (20:17 +0000)
kind.  Fixes PR7252.

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

include/clang/Sema/Lookup.h
lib/Sema/SemaTemplate.cpp
test/SemaTemplate/temp.cpp

index c9b090ae228cb3d0b12cf0bf9418e73a8557ac8e..1c7720abb1e11fad0d2fd4f8c50a762b61c5136e 100644 (file)
@@ -366,10 +366,15 @@ public:
       if (ResultKind != NotFoundInCurrentInstantiation)
         ResultKind = NotFound;
     } else {
+      AmbiguityKind SavedAK = Ambiguity;
       ResultKind = Found;
       resolveKind();
-      
-      if (Paths && (ResultKind != Ambiguous)) {
+
+      // If we didn't make the lookup unambiguous, restore the old
+      // ambiguity kind.
+      if (ResultKind == Ambiguous) {
+        Ambiguity = SavedAK;
+      } else if (Paths) {
         deletePaths(Paths);
         Paths = 0;
       }
index 09656bcd915452d5d948ddb5ed90cee0db0df718..2cbf3073a4679e920c6faab52f9c90055856b285 100644 (file)
@@ -141,8 +141,13 @@ TemplateNameKind Sema::isTemplateName(Scope *S,
                  LookupOrdinaryName);
   LookupTemplateName(R, S, SS, ObjectType, EnteringContext,
                      MemberOfUnknownSpecialization);
-  if (R.empty() || R.isAmbiguous()) {
+  if (R.empty()) return TNK_Non_template;
+  if (R.isAmbiguous()) {
+    // Suppress diagnostics;  we'll redo this lookup later.
     R.suppressDiagnostics();
+
+    // FIXME: we might have ambiguous templates, in which case we
+    // should at least parse them properly!
     return TNK_Non_template;
   }
 
index 961b9c873ab8b22175afe9f0a0f26e6bef6ba5dd..e037f0f0713aebd270499cdd600476803d168e2c 100644 (file)
@@ -1,5 +1,19 @@
 // RUN: %clang_cc1 -fsyntax-only -verify %s
 
 
-// p3
-template<typename T> int foo(T), bar(T, T); // expected-error{{single entity}}
+namespace test0 {
+  // p3
+  template<typename T> int foo(T), bar(T, T); // expected-error{{single entity}}
+}
+
+// PR7252
+namespace test1 {
+  namespace A { template<typename T> struct Base { typedef T t; }; } // expected-note {{member found}}
+  namespace B { template<typename T> struct Base { typedef T t; }; } // expected-note {{member found}}
+
+  template<typename T> struct Derived : A::Base<char>, B::Base<int> {
+    // FIXME: the syntax error here is unfortunate
+    typename Derived::Base<float>::t x; // expected-error {{found in multiple base classes of different types}} \
+                                        // expected-error {{expected member name or ';'}}
+  };
+}