More work towards zero-initializing structs that contain member pointers in constant expressions.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@79805 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/CGExprConstant.cpp b/lib/CodeGen/CGExprConstant.cpp
index b3e0fef..2770527 100644
--- a/lib/CodeGen/CGExprConstant.cpp
+++ b/lib/CodeGen/CGExprConstant.cpp
@@ -800,6 +800,14 @@
return llvm::ConstantArray::get(ATy, Array);
}
}
+
+ if (const RecordType *RT = T->getAs<RecordType>()) {
+ const CGRecordLayout *Layout = Types.getCGRecordLayout(RT->getDecl());
+ if (Layout->containsMemberPointer()) {
+ assert(0 && "FIXME: No support for structs with member pointers yet!");
+ }
+
+ }
// FIXME: Handle structs that contain member pointers.
if (T->isMemberPointerType())
diff --git a/lib/CodeGen/CGRecordLayoutBuilder.cpp b/lib/CodeGen/CGRecordLayoutBuilder.cpp
index 0dc64f0..ea5de5f 100644
--- a/lib/CodeGen/CGRecordLayoutBuilder.cpp
+++ b/lib/CodeGen/CGRecordLayoutBuilder.cpp
@@ -301,6 +301,25 @@
return Types.getTargetData().getTypeAllocSize(Ty);
}
+void CGRecordLayoutBuilder::CheckForMemberPointer(const FieldDecl *FD) {
+ // This record already contains a member pointer.
+ if (ContainsMemberPointer)
+ return;
+
+ // Can only have member pointers if we're compiling C++.
+ if (!Types.getContext().getLangOptions().CPlusPlus)
+ return;
+
+ QualType Ty = FD->getType();
+
+ if (Ty->isMemberPointerType()) {
+ // We have a member pointer!
+ ContainsMemberPointer = true;
+ return;
+ }
+
+}
+
CGRecordLayout *
CGRecordLayoutBuilder::ComputeLayout(CodeGenTypes &Types,
const RecordDecl *D) {
@@ -330,5 +349,5 @@
Types.addBitFieldInfo(Info.FD, Info.FieldNo, Info.Start, Info.Size);
}
- return new CGRecordLayout(Ty);
+ return new CGRecordLayout(Ty, Builder.ContainsMemberPointer);
}
diff --git a/lib/CodeGen/CGRecordLayoutBuilder.h b/lib/CodeGen/CGRecordLayoutBuilder.h
index ff551a4..63ddc10 100644
--- a/lib/CodeGen/CGRecordLayoutBuilder.h
+++ b/lib/CodeGen/CGRecordLayoutBuilder.h
@@ -36,6 +36,10 @@
/// Packed - Whether the resulting LLVM struct will be packed or not.
bool Packed;
+ /// ContainsMemberPointer - Whether one of the fields is a member pointer
+ /// or is a struct that contains a member pointer.
+ bool ContainsMemberPointer;
+
/// Alignment - Contains the alignment of the RecordDecl.
unsigned Alignment;
@@ -72,7 +76,8 @@
llvm::SmallVector<LLVMBitFieldInfo, 16> LLVMBitFields;
CGRecordLayoutBuilder(CodeGenTypes &Types)
- : Types(Types), Packed(false), Alignment(0), AlignmentAsLLVMStruct(1)
+ : Types(Types), Packed(false), ContainsMemberPointer(false)
+ , Alignment(0), AlignmentAsLLVMStruct(1)
, BitsAvailableInLastField(0), NextFieldOffsetInBytes(0) { }
/// Layout - Will layout a RecordDecl.
@@ -113,6 +118,9 @@
unsigned getTypeAlignment(const llvm::Type *Ty) const;
uint64_t getTypeSizeInBytes(const llvm::Type *Ty) const;
+ /// CheckForMemberPointer - Check if the field contains a member pointer.
+ void CheckForMemberPointer(const FieldDecl *FD);
+
public:
/// ComputeLayout - Return the right record layout for a given record decl.
static CGRecordLayout *ComputeLayout(CodeGenTypes &Types,
diff --git a/lib/CodeGen/CodeGenTypes.h b/lib/CodeGen/CodeGenTypes.h
index 530946b..22ebbf1 100644
--- a/lib/CodeGen/CodeGenTypes.h
+++ b/lib/CodeGen/CodeGenTypes.h
@@ -53,17 +53,27 @@
/// lowering AST types to LLVM types.
class CGRecordLayout {
CGRecordLayout(); // DO NOT IMPLEMENT
+
+ /// LLVMType - The LLVMType corresponding to this record layout.
+ const llvm::Type *LLVMType;
+
+ /// ContainsMemberPointer - Whether one of the fields in this record layout
+ /// is a member pointer, or a struct that contains a member pointer.
+ bool ContainsMemberPointer;
+
public:
- CGRecordLayout(const llvm::Type *T)
- : STy(T) { }
+ CGRecordLayout(const llvm::Type *T, bool ContainsMemberPointer)
+ : LLVMType(T), ContainsMemberPointer(ContainsMemberPointer) { }
/// getLLVMType - Return llvm type associated with this record.
const llvm::Type *getLLVMType() const {
- return STy;
+ return LLVMType;
}
- private:
- const llvm::Type *STy;
+ bool containsMemberPointer() const {
+ return ContainsMemberPointer;
+ }
+
};
/// CodeGenTypes - This class organizes the cross-module state that is used