Extract member function pointer comparison and null comparison into
the ABI code.  Implement correct semantics for these on ARM.

I believe this completes the implementation of member function pointers
on ARM.

I think I'm going to switch member function pointers over to be
non-aggregates while I have all this in mind.



git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@111774 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/CGExprScalar.cpp b/lib/CodeGen/CGExprScalar.cpp
index ef45774..d65c22a 100644
--- a/lib/CodeGen/CGExprScalar.cpp
+++ b/lib/CodeGen/CGExprScalar.cpp
@@ -1802,32 +1802,13 @@
   Value *Result;
   QualType LHSTy = E->getLHS()->getType();
   if (LHSTy->isMemberFunctionPointerType()) {
+    assert(E->getOpcode() == BinaryOperator::EQ ||
+           E->getOpcode() == BinaryOperator::NE);
     Value *LHSPtr = CGF.EmitAnyExprToTemp(E->getLHS()).getAggregateAddr();
     Value *RHSPtr = CGF.EmitAnyExprToTemp(E->getRHS()).getAggregateAddr();
-    llvm::Value *LHSFunc = Builder.CreateStructGEP(LHSPtr, 0);
-    LHSFunc = Builder.CreateLoad(LHSFunc);
-    llvm::Value *RHSFunc = Builder.CreateStructGEP(RHSPtr, 0);
-    RHSFunc = Builder.CreateLoad(RHSFunc);
-    Value *ResultF = Builder.CreateICmp((llvm::ICmpInst::Predicate)UICmpOpc,
-                                        LHSFunc, RHSFunc, "cmp.func");
-    Value *NullPtr = llvm::Constant::getNullValue(LHSFunc->getType());
-    Value *ResultNull = Builder.CreateICmp((llvm::ICmpInst::Predicate)UICmpOpc,
-                                           LHSFunc, NullPtr, "cmp.null");
-    llvm::Value *LHSAdj = Builder.CreateStructGEP(LHSPtr, 1);
-    LHSAdj = Builder.CreateLoad(LHSAdj);
-    llvm::Value *RHSAdj = Builder.CreateStructGEP(RHSPtr, 1);
-    RHSAdj = Builder.CreateLoad(RHSAdj);
-    Value *ResultA = Builder.CreateICmp((llvm::ICmpInst::Predicate)UICmpOpc,
-                                        LHSAdj, RHSAdj, "cmp.adj");
-    if (E->getOpcode() == BinaryOperator::EQ) {
-      Result = Builder.CreateOr(ResultNull, ResultA, "or.na");
-      Result = Builder.CreateAnd(Result, ResultF, "and.f");
-    } else {
-      assert(E->getOpcode() == BinaryOperator::NE &&
-             "Member pointer comparison other than == or != ?");
-      Result = Builder.CreateAnd(ResultNull, ResultA, "and.na");
-      Result = Builder.CreateOr(Result, ResultF, "or.f");
-    }
+    Result = CGF.CGM.getCXXABI().EmitMemberFunctionPointerComparison(
+                     CGF, LHSPtr, RHSPtr, LHSTy->getAs<MemberPointerType>(),
+                                    E->getOpcode() == BinaryOperator::NE);
   } else if (!LHSTy->isAnyComplexType()) {
     Value *LHS = Visit(E->getLHS());
     Value *RHS = Visit(E->getRHS());