diff options
author | John McCall <rjmccall@apple.com> | 2010-08-22 08:30:07 +0000 |
---|---|---|
committer | John McCall <rjmccall@apple.com> | 2010-08-22 08:30:07 +0000 |
commit | 131d97d80923ab4a068ee8a5fc3dbed5c97bd15e (patch) | |
tree | 08df0959e02fb7a55a482106c11d0425603d7cf7 /clang/lib/CodeGen/CGExprScalar.cpp | |
parent | 6f33bd9345dd9610676450b86ac5758704628ede (diff) | |
download | bcm5719-llvm-131d97d80923ab4a068ee8a5fc3dbed5c97bd15e.tar.gz bcm5719-llvm-131d97d80923ab4a068ee8a5fc3dbed5c97bd15e.zip |
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.
llvm-svn: 111774
Diffstat (limited to 'clang/lib/CodeGen/CGExprScalar.cpp')
-rw-r--r-- | clang/lib/CodeGen/CGExprScalar.cpp | 29 |
1 files changed, 5 insertions, 24 deletions
diff --git a/clang/lib/CodeGen/CGExprScalar.cpp b/clang/lib/CodeGen/CGExprScalar.cpp index ef4577435cf..d65c22a723a 100644 --- a/clang/lib/CodeGen/CGExprScalar.cpp +++ b/clang/lib/CodeGen/CGExprScalar.cpp @@ -1802,32 +1802,13 @@ Value *ScalarExprEmitter::EmitCompare(const BinaryOperator *E,unsigned UICmpOpc, 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()); |