Add semantic checking for template arguments that correspond to
non-type template parameters that are references to functions or
pointers to member functions. Did a little bit of refactoring so that
these two cases, along with the handling of non-type template
parameters that are pointers to functions, are handled by the same
path. 

Also, tweaked FixOverloadedFunctionReference to cope with member
function pointers. This is a necessary step for getting all of the fun
member pointer conversions working outside of template arguments, too.




git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@64277 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Sema/SemaOverload.cpp b/lib/Sema/SemaOverload.cpp
index 64c61e1..e40455b 100644
--- a/lib/Sema/SemaOverload.cpp
+++ b/lib/Sema/SemaOverload.cpp
@@ -3952,6 +3952,25 @@
   } else if (UnaryOperator *UnOp = dyn_cast<UnaryOperator>(E)) {
     assert(UnOp->getOpcode() == UnaryOperator::AddrOf && 
            "Can only take the address of an overloaded function");
+    if (CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(Fn)) {
+      if (Method->isStatic()) {
+        // Do nothing: static member functions aren't any different
+        // from non-member functions.
+      }
+      else if (QualifiedDeclRefExpr *DRE 
+                 = dyn_cast<QualifiedDeclRefExpr>(UnOp->getSubExpr())) {
+        // We have taken the address of a pointer to member
+        // function. Perform the computation here so that we get the
+        // appropriate pointer to member type.
+        DRE->setDecl(Fn);
+        DRE->setType(Fn->getType());
+        QualType ClassType
+          = Context.getTypeDeclType(cast<RecordDecl>(Method->getDeclContext()));
+        E->setType(Context.getMemberPointerType(Fn->getType(), 
+                                                ClassType.getTypePtr()));
+        return;
+      }
+    }
     FixOverloadedFunctionReference(UnOp->getSubExpr(), Fn);
     E->setType(Context.getPointerType(UnOp->getSubExpr()->getType()));
   } else if (DeclRefExpr *DR = dyn_cast<DeclRefExpr>(E)) {