]> granicus.if.org Git - clang/commitdiff
Issue good ambiguity diagnostic when convesion fails.
authorFariborz Jahanian <fjahanian@apple.com>
Tue, 22 Sep 2009 19:53:15 +0000 (19:53 +0000)
committerFariborz Jahanian <fjahanian@apple.com>
Tue, 22 Sep 2009 19:53:15 +0000 (19:53 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@82565 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/Basic/DiagnosticSemaKinds.td
lib/Sema/SemaOverload.cpp
test/SemaCXX/ambig-user-defined-convesions.cpp [new file with mode: 0644]

index 1ca9a1fb1b6b77d2c641ee692a4a81418205c225..a3d15fedc3c83b8e50bf2ff194c33892de747704 100644 (file)
@@ -1634,8 +1634,8 @@ def err_type_defined_in_condition : Error<
   "types may not be defined in conditions">;
 def err_typecheck_bool_condition : Error<
   "value of type %0 is not contextually convertible to 'bool'">;
-def err_typecheck_ambiguous_bool_condition : Error<
-  "conversion from %0 to 'bool' is ambiguous">;
+def err_typecheck_ambiguous_condition : Error<
+  "conversion from %0 to %1 is ambiguous">;
 def err_expected_class_or_namespace : Error<"expected a class or namespace">;
 def err_invalid_declarator_scope : Error<
   "definition or redeclaration of %0 not in a namespace enclosing %1">;
index 063b387fba961a23fcc41bc487a66e37d728c8ca..f7a5cb9b1b6184b44e043ac752c8bb59ad1f3349 100644 (file)
@@ -1983,10 +1983,19 @@ bool Sema::PerformCopyInitialization(Expr *&From, QualType ToType,
   if (!PerformImplicitConversion(From, ToType, Flavor,
                                  /*AllowExplicit=*/false, Elidable))
     return false;
-
-  return Diag(From->getSourceRange().getBegin(),
-              diag::err_typecheck_convert_incompatible)
-    << ToType << From->getType() << Flavor << From->getSourceRange();
+  ImplicitConversionSequence ICS;
+  OverloadCandidateSet CandidateSet;
+  if (IsUserDefinedConversion(From, ToType, ICS.UserDefined,
+                              CandidateSet,
+                              true, false, false) != OR_Ambiguous)
+    return Diag(From->getSourceRange().getBegin(),
+                diag::err_typecheck_convert_incompatible)
+      << ToType << From->getType() << Flavor << From->getSourceRange();
+  Diag(From->getSourceRange().getBegin(),
+       diag::err_typecheck_ambiguous_condition)
+  << From->getType() << ToType << From->getSourceRange();
+  PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+  return true;
 }
 
 /// TryObjectArgumentInitialization - Try to initialize the object
@@ -2104,13 +2113,13 @@ bool Sema::PerformContextuallyConvertToBool(Expr *&From) {
     OverloadCandidateSet CandidateSet;
     if (IsUserDefinedConversion(From, Context.BoolTy, ICS.UserDefined,
                             CandidateSet,
-                            true, true, false) != OR_Ambiguous)
+                            true, false, false) != OR_Ambiguous)
       return  Diag(From->getSourceRange().getBegin(),
                    diag::err_typecheck_bool_condition)
                     << From->getType() << From->getSourceRange();
     Diag(From->getSourceRange().getBegin(),
-         diag::err_typecheck_ambiguous_bool_condition)
-          << From->getType() << From->getSourceRange();
+         diag::err_typecheck_ambiguous_condition)
+          << From->getType() << Context.BoolTy << From->getSourceRange();
     PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
     return true;
 }
diff --git a/test/SemaCXX/ambig-user-defined-convesions.cpp b/test/SemaCXX/ambig-user-defined-convesions.cpp
new file mode 100644 (file)
index 0000000..d391a04
--- /dev/null
@@ -0,0 +1,19 @@
+// RUN: clang-cc -fsyntax-only -verify %s
+
+struct BASE { 
+  operator int &(); // expected-note {{candidate function}}
+}; 
+struct BASE1 { 
+  operator int &(); // expected-note {{candidate function}}
+}; 
+
+struct B : public BASE, BASE1 { 
+
+}; 
+
+extern B f(); 
+
+const int main() {
+  return f(); // expected-error {{conversion from 'struct B' to 'int const' is ambiguous}}
+}
+