[cfe-commits] r60093 - in /cfe/trunk/lib/Sema: Sema.h SemaExpr.cpp SemaOverload.cpp

Douglas Gregor doug.gregor at gmail.com
Tue Nov 25 21:54:24 PST 2008


Author: dgregor
Date: Tue Nov 25 23:54:23 2008
New Revision: 60093

URL: http://llvm.org/viewvc/llvm-project?rev=60093&view=rev
Log:
Move the overloading logic of Sema::ActOnCallExpr to a separate function

Modified:
    cfe/trunk/lib/Sema/Sema.h
    cfe/trunk/lib/Sema/SemaExpr.cpp
    cfe/trunk/lib/Sema/SemaOverload.cpp

Modified: cfe/trunk/lib/Sema/Sema.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/Sema.h?rev=60093&r1=60092&r2=60093&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/Sema.h (original)
+++ cfe/trunk/lib/Sema/Sema.h Tue Nov 25 23:54:23 2008
@@ -447,6 +447,12 @@
                                                    bool Complain);
   void FixOverloadedFunctionReference(Expr *E, FunctionDecl *Fn);
 
+  Expr *ResolveOverloadedCallFn(Expr *Fn, OverloadedFunctionDecl *Ovl,
+                                SourceLocation LParenLoc,
+                                Expr **Args, unsigned NumArgs,
+                                SourceLocation *CommaLocs, 
+                                SourceLocation RParenLoc);
+
   ExprResult 
   BuildCallToObjectOfClassType(Expr *Object, SourceLocation LParenLoc,
                                Expr **Args, unsigned NumArgs,

Modified: cfe/trunk/lib/Sema/SemaExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=60093&r1=60092&r2=60093&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Tue Nov 25 23:54:23 2008
@@ -1294,39 +1294,13 @@
     }
   }
 
-  // If we have a set of overloaded functions, perform overload
-  // resolution to pick the function.
   if (Ovl) {
-    OverloadCandidateSet CandidateSet;
-    AddOverloadCandidates(Ovl, Args, NumArgs, CandidateSet);
-    OverloadCandidateSet::iterator Best;
-    switch (BestViableFunction(CandidateSet, Best)) {
-    case OR_Success: 
-      {
-        // Success! Let the remainder of this function build a call to
-        // the function selected by overload resolution.
-        FDecl = Best->Function;
-        Expr *NewFn = new DeclRefExpr(FDecl, FDecl->getType(), 
-                                      Fn->getSourceRange().getBegin());
-        delete Fn;
-        Fn = NewFn;
-      }
-      break;
-
-    case OR_No_Viable_Function:
-      Diag(Fn->getSourceRange().getBegin(), 
-           diag::err_ovl_no_viable_function_in_call)
-        << Ovl->getDeclName() << (unsigned)CandidateSet.size()
-        << Fn->getSourceRange();
-      PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+    Fn = ResolveOverloadedCallFn(Fn, Ovl, LParenLoc, Args, NumArgs, CommaLocs,
+                                 RParenLoc);
+    if (!Fn)
       return true;
 
-    case OR_Ambiguous:
-      Diag(Fn->getSourceRange().getBegin(), diag::err_ovl_ambiguous_call)
-        << Ovl->getDeclName() << Fn->getSourceRange();
-      PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
-      return true;
-    }
+    // Fall through and build the call to Fn.
   }
 
   if (getLangOptions().CPlusPlus && Fn->getType()->isRecordType())

Modified: cfe/trunk/lib/Sema/SemaOverload.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaOverload.cpp?rev=60093&r1=60092&r2=60093&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/SemaOverload.cpp (original)
+++ cfe/trunk/lib/Sema/SemaOverload.cpp Tue Nov 25 23:54:23 2008
@@ -2963,6 +2963,52 @@
   return 0;
 }
 
+/// ResolveOverloadedCallFn - Given the call expression that calls Fn
+/// (which eventually refers to the set of overloaded functions in
+/// Ovl) and the call arguments Args/NumArgs, attempt to resolve the
+/// function call down to a specific function. If overload resolution
+/// succeeds, returns an expression that refers to a specific function
+/// and deletes Fn. Otherwise, emits diagnostics, deletes all of the
+/// arguments and Fn, and returns NULL.
+Expr *Sema::ResolveOverloadedCallFn(Expr *Fn, OverloadedFunctionDecl *Ovl,
+                                    SourceLocation LParenLoc,
+                                    Expr **Args, unsigned NumArgs,
+                                    SourceLocation *CommaLocs, 
+                                    SourceLocation RParenLoc) {
+  OverloadCandidateSet CandidateSet;
+  AddOverloadCandidates(Ovl, Args, NumArgs, CandidateSet);
+  OverloadCandidateSet::iterator Best;
+  switch (BestViableFunction(CandidateSet, Best)) {
+  case OR_Success: {
+    Expr *NewFn = new DeclRefExpr(Best->Function, Best->Function->getType(), 
+                                  Fn->getSourceRange().getBegin());
+    Fn->Destroy(Context);
+    return NewFn;
+  }
+
+  case OR_No_Viable_Function:
+    Diag(Fn->getSourceRange().getBegin(), 
+         diag::err_ovl_no_viable_function_in_call)
+      << Ovl->getDeclName() << (unsigned)CandidateSet.size()
+      << Fn->getSourceRange();
+    PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+    break;
+
+  case OR_Ambiguous:
+    Diag(Fn->getSourceRange().getBegin(), diag::err_ovl_ambiguous_call)
+      << Ovl->getDeclName() << Fn->getSourceRange();
+    PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+    break;
+  }
+
+  // Overload resolution failed. Destroy all of the subexpressions and
+  // return NULL.
+  Fn->Destroy(Context);
+  for (unsigned Arg = 0; Arg < NumArgs; ++Arg)
+    Args[Arg]->Destroy(Context);
+  return 0;
+}
+
 /// BuildCallToObjectOfClassType - Build a call to an object of class
 /// type (C++ [over.call.object]), which can end up invoking an
 /// overloaded function call operator (@c operator()) or performing a





More information about the cfe-commits mailing list