diff --git a/lib/CodeGen/CGVTT.cpp b/lib/CodeGen/CGVTT.cpp index e179ecbce4..f2b2945290 100644 --- a/lib/CodeGen/CGVTT.cpp +++ b/lib/CodeGen/CGVTT.cpp @@ -44,9 +44,13 @@ class VTTBuilder { typedef llvm::DenseMap AddressPointsMapTy; /// SubVTTIndicies - The sub-VTT indices for the bases of the most derived - /// class whose VTT is being built. + /// class. llvm::DenseMap SubVTTIndicies; - + + /// SecondaryVirtualPointerIndices - The secondary virtual pointer indices of + /// all subobjects of the most derived class. + llvm::DenseMap SecondaryVirtualPointerIndices; + /// GenerateDefinition - Whether the VTT builder should generate LLVM IR for /// the VTT. bool GenerateDefinition; @@ -107,15 +111,25 @@ class VTTBuilder { public: VTTBuilder(CodeGenModule &CGM, const CXXRecordDecl *MostDerivedClass, bool GenerateDefinition); - - llvm::DenseMap &getSubVTTIndicies() { - return SubVTTIndicies; - } - + // getVTTComponents - Returns a reference to the VTT components. const VTTComponentsVectorTy &getVTTComponents() const { return VTTComponents; } + + /// getSubVTTIndicies - Returns a reference to the sub-VTT indices. + const llvm::DenseMap & + getSubVTTIndicies() const { + return SubVTTIndicies; + } + + /// getSecondaryVirtualPointerIndices - Returns a reference to the secondary + /// virtual pointer indices. + const llvm::DenseMap & + getSecondaryVirtualPointerIndices() const { + return SecondaryVirtualPointerIndices; + } + }; VTTBuilder::VTTBuilder(CodeGenModule &CGM, @@ -420,14 +434,13 @@ uint64_t CodeGenVTables::getSubVTTIndex(const CXXRecordDecl *RD, const CXXRecordDecl *Base) { ClassPairTy ClassPair(RD, Base); - SubVTTIndiciesTy::iterator I = - SubVTTIndicies.find(ClassPair); + SubVTTIndiciesMapTy::iterator I = SubVTTIndicies.find(ClassPair); if (I != SubVTTIndicies.end()) return I->second; VTTBuilder Builder(CGM, RD, /*GenerateDefinition=*/false); - for (llvm::DenseMap::iterator I = + for (llvm::DenseMap::const_iterator I = Builder.getSubVTTIndicies().begin(), E = Builder.getSubVTTIndicies().end(); I != E; ++I) { // Insert all indices. @@ -441,3 +454,31 @@ uint64_t CodeGenVTables::getSubVTTIndex(const CXXRecordDecl *RD, return I->second; } + +uint64_t +CodeGenVTables::getSecondaryVirtualPointerIndex(const CXXRecordDecl *RD, + BaseSubobject Base) { + SecondaryVirtualPointerIndicesMapTy::iterator I = + SecondaryVirtualPointerIndices.find(std::make_pair(RD, Base)); + + if (I != SecondaryVirtualPointerIndices.end()) + return I->second; + + VTTBuilder Builder(CGM, RD, /*GenerateDefinition=*/false); + + // Insert all secondary vpointer indices. + for (llvm::DenseMap::const_iterator I = + Builder.getSecondaryVirtualPointerIndices().begin(), + E = Builder.getSecondaryVirtualPointerIndices().end(); I != E; ++I) { + std::pair Pair = + std::make_pair(RD, I->first); + + SecondaryVirtualPointerIndices.insert(std::make_pair(Pair, I->second)); + } + + I = SecondaryVirtualPointerIndices.find(std::make_pair(RD, Base)); + assert(I != SecondaryVirtualPointerIndices.end() && "Did not find index!"); + + return I->second; +} + diff --git a/lib/CodeGen/CGVtable.h b/lib/CodeGen/CGVtable.h index 216fd059a8..e07017bef6 100644 --- a/lib/CodeGen/CGVtable.h +++ b/lib/CodeGen/CGVtable.h @@ -292,8 +292,19 @@ private: return VTableLayoutMap.lookup(RD)[0]; } - typedef llvm::DenseMap SubVTTIndiciesTy; - SubVTTIndiciesTy SubVTTIndicies; + typedef llvm::DenseMap SubVTTIndiciesMapTy; + + /// SubVTTIndicies - Contains indices into the various sub-VTTs. + SubVTTIndiciesMapTy SubVTTIndicies; + + + typedef llvm::DenseMap, uint64_t> + SecondaryVirtualPointerIndicesMapTy; + + /// SecondaryVirtualPointerIndices - Contains the secondary virtual pointer + /// indices. + SecondaryVirtualPointerIndicesMapTy SecondaryVirtualPointerIndices; /// getNumVirtualFunctionPointers - Return the number of virtual function /// pointers in the vtable for a given record decl. @@ -344,6 +355,11 @@ public: /// given record decl. uint64_t getSubVTTIndex(const CXXRecordDecl *RD, const CXXRecordDecl *Base); + /// getSecondaryVirtualPointerIndex - Return the index in the VTT where the + /// virtual pointer for the given subobject is located. + uint64_t getSecondaryVirtualPointerIndex(const CXXRecordDecl *RD, + BaseSubobject Base); + /// getMethodVtableIndex - Return the index (relative to the vtable address /// point) where the function pointer for the given virtual function is /// stored.