Complete code gen for '.*' binary expression for
both scalar and aggregates.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@84910 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp
index 0b56fa9..bfbd6f7 100644
--- a/lib/CodeGen/CGExpr.cpp
+++ b/lib/CodeGen/CGExpr.cpp
@@ -1379,6 +1379,9 @@
return EmitLValue(E->getRHS());
}
+ if (E->getOpcode() == BinaryOperator::PtrMemD)
+ return EmitPointerToDataMemberBinaryExpr(E);
+
// Can only get l-value for binary operator expressions which are a
// simple assignment of aggregate type.
if (E->getOpcode() != BinaryOperator::Assign)
@@ -1560,3 +1563,25 @@
CallingConvention),
Callee, Args, TargetDecl);
}
+
+LValue CodeGenFunction::EmitPointerToDataMemberBinaryExpr(
+ const BinaryOperator *E) {
+ llvm::Value *BaseV = EmitLValue(E->getLHS()).getAddress();
+ const llvm::Type *i8Ty = llvm::Type::getInt8PtrTy(getLLVMContext());
+ BaseV = Builder.CreateBitCast(BaseV, i8Ty);
+ LValue RHSLV = EmitLValue(E->getRHS());
+ llvm::Value *OffsetV =
+ EmitLoadOfLValue(RHSLV, E->getRHS()->getType()).getScalarVal();
+ const llvm::Type* ResultType = ConvertType(getContext().getPointerDiffType());
+ OffsetV = Builder.CreateBitCast(OffsetV, ResultType);
+ llvm::Value *AddV = Builder.CreateInBoundsGEP(BaseV, OffsetV, "add.ptr");
+ QualType Ty = E->getRHS()->getType();
+ const MemberPointerType *MemPtrType = Ty->getAs<MemberPointerType>();
+ Ty = MemPtrType->getPointeeType();
+ const llvm::Type* PType =
+ ConvertType(getContext().getPointerType(Ty));
+ AddV = Builder.CreateBitCast(AddV, PType);
+ LValue LV = LValue::MakeAddr(AddV, MakeQualifiers(Ty));
+ return LV;
+}
+