зеркало из https://github.com/microsoft/clang-1.git
Amusingly, I missed this point of abstraction in all my earlier
member-pointer refactoring: dereferencing a member data pointer. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@112640 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Родитель
410c4f2eb5
Коммит
6c2ab1d578
|
@ -359,6 +359,15 @@ llvm::Value *CGCXXABI::EmitLoadOfMemberFunctionPointer(CodeGenFunction &CGF,
|
|||
return llvm::Constant::getNullValue(FTy->getPointerTo());
|
||||
}
|
||||
|
||||
llvm::Value *CGCXXABI::EmitMemberDataPointerAddress(CodeGenFunction &CGF,
|
||||
llvm::Value *Base,
|
||||
llvm::Value *MemPtr,
|
||||
const MemberPointerType *MPT) {
|
||||
ErrorUnsupportedABI(CGF, "loads of member pointers");
|
||||
const llvm::Type *Ty = CGF.ConvertType(MPT->getPointeeType())->getPointerTo();
|
||||
return llvm::Constant::getNullValue(Ty);
|
||||
}
|
||||
|
||||
llvm::Value *CGCXXABI::EmitMemberPointerConversion(CodeGenFunction &CGF,
|
||||
const CastExpr *E,
|
||||
llvm::Value *Src) {
|
||||
|
|
|
@ -88,6 +88,12 @@ public:
|
|||
llvm::Value *MemPtr,
|
||||
const MemberPointerType *MPT);
|
||||
|
||||
/// Calculate an l-value from an object and a data member pointer.
|
||||
virtual llvm::Value *EmitMemberDataPointerAddress(CodeGenFunction &CGF,
|
||||
llvm::Value *Base,
|
||||
llvm::Value *MemPtr,
|
||||
const MemberPointerType *MPT);
|
||||
|
||||
/// Perform a derived-to-base or base-to-derived member pointer
|
||||
/// conversion.
|
||||
virtual llvm::Value *EmitMemberPointerConversion(CodeGenFunction &CGF,
|
||||
|
|
|
@ -2090,16 +2090,15 @@ EmitPointerToDataMemberBinaryExpr(const BinaryOperator *E) {
|
|||
BaseV = EmitScalarExpr(E->getLHS());
|
||||
else
|
||||
BaseV = EmitLValue(E->getLHS()).getAddress();
|
||||
const llvm::Type *i8Ty = llvm::Type::getInt8PtrTy(getLLVMContext());
|
||||
BaseV = Builder.CreateBitCast(BaseV, i8Ty);
|
||||
llvm::Value *OffsetV = EmitScalarExpr(E->getRHS());
|
||||
llvm::Value *AddV = Builder.CreateInBoundsGEP(BaseV, OffsetV, "add.ptr");
|
||||
|
||||
QualType Ty = E->getRHS()->getType();
|
||||
Ty = Ty->getAs<MemberPointerType>()->getPointeeType();
|
||||
|
||||
const llvm::Type *PType = ConvertType(getContext().getPointerType(Ty));
|
||||
AddV = Builder.CreateBitCast(AddV, PType);
|
||||
return MakeAddrLValue(AddV, Ty);
|
||||
llvm::Value *OffsetV = EmitScalarExpr(E->getRHS());
|
||||
|
||||
const MemberPointerType *MPT
|
||||
= E->getRHS()->getType()->getAs<MemberPointerType>();
|
||||
|
||||
llvm::Value *AddV =
|
||||
CGM.getCXXABI().EmitMemberDataPointerAddress(*this, BaseV, OffsetV, MPT);
|
||||
|
||||
return MakeAddrLValue(AddV, MPT->getPointeeType());
|
||||
}
|
||||
|
||||
|
|
|
@ -66,6 +66,11 @@ public:
|
|||
llvm::Value *MemFnPtr,
|
||||
const MemberPointerType *MPT);
|
||||
|
||||
llvm::Value *EmitMemberDataPointerAddress(CodeGenFunction &CGF,
|
||||
llvm::Value *Base,
|
||||
llvm::Value *MemPtr,
|
||||
const MemberPointerType *MPT);
|
||||
|
||||
llvm::Value *EmitMemberPointerConversion(CodeGenFunction &CGF,
|
||||
const CastExpr *E,
|
||||
llvm::Value *Src);
|
||||
|
@ -261,6 +266,31 @@ ItaniumCXXABI::EmitLoadOfMemberFunctionPointer(CodeGenFunction &CGF,
|
|||
return Callee;
|
||||
}
|
||||
|
||||
/// Compute an l-value by applying the given pointer-to-member to a
|
||||
/// base object.
|
||||
llvm::Value *ItaniumCXXABI::EmitMemberDataPointerAddress(CodeGenFunction &CGF,
|
||||
llvm::Value *Base,
|
||||
llvm::Value *MemPtr,
|
||||
const MemberPointerType *MPT) {
|
||||
assert(MemPtr->getType() == getPtrDiffTy());
|
||||
|
||||
CGBuilderTy &Builder = CGF.Builder;
|
||||
|
||||
unsigned AS = cast<llvm::PointerType>(Base->getType())->getAddressSpace();
|
||||
|
||||
// Cast to char*.
|
||||
Base = Builder.CreateBitCast(Base, Builder.getInt8Ty()->getPointerTo(AS));
|
||||
|
||||
// Apply the offset, which we assume is non-null.
|
||||
llvm::Value *Addr = Builder.CreateInBoundsGEP(Base, MemPtr, "memptr.offset");
|
||||
|
||||
// Cast the address to the appropriate pointer type, adopting the
|
||||
// address space of the base pointer.
|
||||
const llvm::Type *PType
|
||||
= CGF.ConvertType(MPT->getPointeeType())->getPointerTo(AS);
|
||||
return Builder.CreateBitCast(Addr, PType);
|
||||
}
|
||||
|
||||
/// Perform a derived-to-base or base-to-derived member pointer conversion.
|
||||
///
|
||||
/// Obligatory offset/adjustment diagram:
|
||||
|
|
Загрузка…
Ссылка в новой задаче