forked from OSchip/llvm-project
More work toward data member access ir-gen.
llvm-svn: 77332
This commit is contained in:
parent
bca2105c57
commit
5142fbd02e
|
@ -155,6 +155,42 @@ llvm::Value *CodeGenFunction::LoadCXXThis() {
|
|||
return Builder.CreateLoad(LocalDeclMap[CXXThisDecl], "this");
|
||||
}
|
||||
|
||||
llvm::Value *CodeGenFunction::AddressCXXOfBaseClass(llvm::Value *BaseValue,
|
||||
CXXRecordDecl *ClassDecl,
|
||||
CXXRecordDecl *BaseClassDecl) {
|
||||
if (ClassDecl == BaseClassDecl)
|
||||
return BaseValue;
|
||||
|
||||
// Accessing a member of the base class. Must add delata to
|
||||
// the load of 'this'.
|
||||
// FIXME. Once type layout is complete, this will probably change.
|
||||
const ASTRecordLayout &Layout =
|
||||
getContext().getASTRecordLayout(ClassDecl);
|
||||
llvm::Type *I8Ptr = VMContext.getPointerTypeUnqual(llvm::Type::Int8Ty);
|
||||
unsigned Idx = 0;
|
||||
for (CXXRecordDecl::base_class_const_iterator i =
|
||||
ClassDecl->bases_begin(),
|
||||
e = ClassDecl->bases_end(); i != e; ++i, ++Idx) {
|
||||
if (!i->isVirtual()) {
|
||||
const CXXRecordDecl *Base =
|
||||
cast<CXXRecordDecl>(i->getType()->getAsRecordType()->getDecl());
|
||||
if (Base == BaseClassDecl)
|
||||
break;
|
||||
}
|
||||
}
|
||||
uint64_t Offset = Layout.getFieldOffset(Idx) / 8;
|
||||
llvm::Value *OffsetVal = llvm::ConstantInt::get(llvm::Type::Int32Ty, Offset);
|
||||
BaseValue = Builder.CreateBitCast(BaseValue, I8Ptr);
|
||||
BaseValue = Builder.CreateGEP(BaseValue, OffsetVal, "add.ptr");
|
||||
QualType BTy =
|
||||
getContext().getCanonicalType(
|
||||
getContext().getTypeDeclType(BaseClassDecl));
|
||||
const llvm::Type *BasePtr = ConvertType(BTy);
|
||||
BasePtr = VMContext.getPointerTypeUnqual(BasePtr);
|
||||
BaseValue = Builder.CreateBitCast(BaseValue, BasePtr);
|
||||
return BaseValue;
|
||||
}
|
||||
|
||||
void
|
||||
CodeGenFunction::EmitCXXConstructorCall(const CXXConstructorDecl *D,
|
||||
CXXCtorType Type,
|
||||
|
|
|
@ -993,6 +993,16 @@ LValue CodeGenFunction::EmitMemberExpr(const MemberExpr *E) {
|
|||
if (PTy->getPointeeType()->isUnionType())
|
||||
isUnion = true;
|
||||
CVRQualifiers = PTy->getPointeeType().getCVRQualifiers();
|
||||
if (CXXThisExpr *ThisExpr = dyn_cast<CXXThisExpr>(BaseExpr)) {
|
||||
QualType ClassTy = ThisExpr->getType();
|
||||
ClassTy = ClassTy->getPointeeType();
|
||||
CXXRecordDecl *ClassDecl =
|
||||
cast<CXXRecordDecl>(ClassTy->getAsRecordType()->getDecl());
|
||||
FieldDecl *Field = dyn_cast<FieldDecl>(E->getMemberDecl());
|
||||
CXXRecordDecl *BaseClassDecl =
|
||||
cast<CXXRecordDecl>(Field->getDeclContext());
|
||||
BaseValue = AddressCXXOfBaseClass(BaseValue, ClassDecl, BaseClassDecl);
|
||||
}
|
||||
} else if (isa<ObjCPropertyRefExpr>(BaseExpr) ||
|
||||
isa<ObjCKVCRefExpr>(BaseExpr)) {
|
||||
RValue RV = EmitObjCPropertyGet(BaseExpr);
|
||||
|
|
|
@ -528,6 +528,14 @@ public:
|
|||
/// generating code for an C++ member function.
|
||||
llvm::Value *LoadCXXThis();
|
||||
|
||||
/// AddressCXXOfBaseClass - This function will add the necessary delta
|
||||
/// to the load of 'this' and returns address of the base class.
|
||||
// FIXME. This currently only does a derived to non-virtual base conversion.
|
||||
// Other kinds of conversions will come later.
|
||||
llvm::Value *AddressCXXOfBaseClass(llvm::Value *ThisValue,
|
||||
CXXRecordDecl *ClassDecl,
|
||||
CXXRecordDecl *BaseClassDecl);
|
||||
|
||||
void EmitCXXConstructorCall(const CXXConstructorDecl *D, CXXCtorType Type,
|
||||
llvm::Value *This,
|
||||
CallExpr::const_arg_iterator ArgBeg,
|
||||
|
|
|
@ -35,6 +35,9 @@ struct N : M , P, Q {
|
|||
MPR();
|
||||
PPR();
|
||||
QPR();
|
||||
printf("iQ = %d\n", iQ);
|
||||
printf("iP = %d\n", iP);
|
||||
printf("iM = %d\n", iM);
|
||||
}
|
||||
float ld;
|
||||
float ff;
|
||||
|
|
Loading…
Reference in New Issue