VTTBuilder.h revision 341825
1//===- VTTBuilder.h - C++ VTT layout builder --------------------*- C++ -*-===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This contains code dealing with generation of the layout of virtual table 11// tables (VTT). 12// 13//===----------------------------------------------------------------------===// 14 15#ifndef LLVM_CLANG_AST_VTTBUILDER_H 16#define LLVM_CLANG_AST_VTTBUILDER_H 17 18#include "clang/AST/BaseSubobject.h" 19#include "clang/AST/CharUnits.h" 20#include "clang/Basic/LLVM.h" 21#include "llvm/ADT/DenseMap.h" 22#include "llvm/ADT/PointerIntPair.h" 23#include "llvm/ADT/SmallPtrSet.h" 24#include "llvm/ADT/SmallVector.h" 25#include <cstdint> 26 27namespace clang { 28 29class ASTContext; 30class ASTRecordLayout; 31class CXXRecordDecl; 32 33class VTTVTable { 34 llvm::PointerIntPair<const CXXRecordDecl *, 1, bool> BaseAndIsVirtual; 35 CharUnits BaseOffset; 36 37public: 38 VTTVTable() = default; 39 VTTVTable(const CXXRecordDecl *Base, CharUnits BaseOffset, bool BaseIsVirtual) 40 : BaseAndIsVirtual(Base, BaseIsVirtual), BaseOffset(BaseOffset) {} 41 VTTVTable(BaseSubobject Base, bool BaseIsVirtual) 42 : BaseAndIsVirtual(Base.getBase(), BaseIsVirtual), 43 BaseOffset(Base.getBaseOffset()) {} 44 45 const CXXRecordDecl *getBase() const { 46 return BaseAndIsVirtual.getPointer(); 47 } 48 49 CharUnits getBaseOffset() const { 50 return BaseOffset; 51 } 52 53 bool isVirtual() const { 54 return BaseAndIsVirtual.getInt(); 55 } 56 57 BaseSubobject getBaseSubobject() const { 58 return BaseSubobject(getBase(), getBaseOffset()); 59 } 60}; 61 62struct VTTComponent { 63 uint64_t VTableIndex; 64 BaseSubobject VTableBase; 65 66 VTTComponent() = default; 67 VTTComponent(uint64_t VTableIndex, BaseSubobject VTableBase) 68 : VTableIndex(VTableIndex), VTableBase(VTableBase) {} 69}; 70 71/// Class for building VTT layout information. 72class VTTBuilder { 73 ASTContext &Ctx; 74 75 /// The most derived class for which we're building this vtable. 76 const CXXRecordDecl *MostDerivedClass; 77 78 using VTTVTablesVectorTy = SmallVector<VTTVTable, 64>; 79 80 /// The VTT vtables. 81 VTTVTablesVectorTy VTTVTables; 82 83 using VTTComponentsVectorTy = SmallVector<VTTComponent, 64>; 84 85 /// The VTT components. 86 VTTComponentsVectorTy VTTComponents; 87 88 /// The AST record layout of the most derived class. 89 const ASTRecordLayout &MostDerivedClassLayout; 90 91 using VisitedVirtualBasesSetTy = llvm::SmallPtrSet<const CXXRecordDecl *, 4>; 92 93 using AddressPointsMapTy = llvm::DenseMap<BaseSubobject, uint64_t>; 94 95 /// The sub-VTT indices for the bases of the most derived class. 96 llvm::DenseMap<BaseSubobject, uint64_t> SubVTTIndicies; 97 98 /// The secondary virtual pointer indices of all subobjects of 99 /// the most derived class. 100 llvm::DenseMap<BaseSubobject, uint64_t> SecondaryVirtualPointerIndices; 101 102 /// Whether the VTT builder should generate LLVM IR for the VTT. 103 bool GenerateDefinition; 104 105 /// Add a vtable pointer to the VTT currently being built. 106 void AddVTablePointer(BaseSubobject Base, uint64_t VTableIndex, 107 const CXXRecordDecl *VTableClass); 108 109 /// Lay out the secondary VTTs of the given base subobject. 110 void LayoutSecondaryVTTs(BaseSubobject Base); 111 112 /// Lay out the secondary virtual pointers for the given base 113 /// subobject. 114 /// 115 /// \param BaseIsMorallyVirtual whether the base subobject is a virtual base 116 /// or a direct or indirect base of a virtual base. 117 void LayoutSecondaryVirtualPointers(BaseSubobject Base, 118 bool BaseIsMorallyVirtual, 119 uint64_t VTableIndex, 120 const CXXRecordDecl *VTableClass, 121 VisitedVirtualBasesSetTy &VBases); 122 123 /// Lay out the secondary virtual pointers for the given base 124 /// subobject. 125 void LayoutSecondaryVirtualPointers(BaseSubobject Base, 126 uint64_t VTableIndex); 127 128 /// Lay out the VTTs for the virtual base classes of the given 129 /// record declaration. 130 void LayoutVirtualVTTs(const CXXRecordDecl *RD, 131 VisitedVirtualBasesSetTy &VBases); 132 133 /// Lay out the VTT for the given subobject, including any 134 /// secondary VTTs, secondary virtual pointers and virtual VTTs. 135 void LayoutVTT(BaseSubobject Base, bool BaseIsVirtual); 136 137public: 138 VTTBuilder(ASTContext &Ctx, const CXXRecordDecl *MostDerivedClass, 139 bool GenerateDefinition); 140 141 // Returns a reference to the VTT components. 142 const VTTComponentsVectorTy &getVTTComponents() const { 143 return VTTComponents; 144 } 145 146 // Returns a reference to the VTT vtables. 147 const VTTVTablesVectorTy &getVTTVTables() const { 148 return VTTVTables; 149 } 150 151 /// Returns a reference to the sub-VTT indices. 152 const llvm::DenseMap<BaseSubobject, uint64_t> &getSubVTTIndicies() const { 153 return SubVTTIndicies; 154 } 155 156 /// Returns a reference to the secondary virtual pointer indices. 157 const llvm::DenseMap<BaseSubobject, uint64_t> & 158 getSecondaryVirtualPointerIndices() const { 159 return SecondaryVirtualPointerIndices; 160 } 161}; 162 163} // namespace clang 164 165#endif // LLVM_CLANG_AST_VTTBUILDER_H 166