1 //===--- CGVTT.cpp - Emit LLVM Code for C++ VTTs --------------------------===// 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 C++ code generation of VTTs (vtable tables). 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "CodeGenModule.h" 15 #include "CGCXXABI.h" 16 #include "clang/AST/RecordLayout.h" 17 using namespace clang; 18 using namespace CodeGen; 19 20 #define D1(x) 21 22 namespace { 23 24 /// VTT builder - Class for building VTT layout information. 25 class VTTBuilder { 26 27 CodeGenModule &CGM; 28 29 /// MostDerivedClass - The most derived class for which we're building this 30 /// vtable. 31 const CXXRecordDecl *MostDerivedClass; 32 33 typedef llvm::SmallVector<llvm::Constant *, 64> VTTComponentsVectorTy; 34 35 /// VTTComponents - The VTT components. 36 VTTComponentsVectorTy VTTComponents; 37 38 /// MostDerivedClassLayout - the AST record layout of the most derived class. 39 const ASTRecordLayout &MostDerivedClassLayout; 40 41 typedef llvm::SmallPtrSet<const CXXRecordDecl *, 4> VisitedVirtualBasesSetTy; 42 43 typedef llvm::DenseMap<BaseSubobject, uint64_t> AddressPointsMapTy; 44 45 /// SubVTTIndicies - The sub-VTT indices for the bases of the most derived 46 /// class. 47 llvm::DenseMap<BaseSubobject, uint64_t> SubVTTIndicies; 48 49 /// SecondaryVirtualPointerIndices - The secondary virtual pointer indices of 50 /// all subobjects of the most derived class. 51 llvm::DenseMap<BaseSubobject, uint64_t> SecondaryVirtualPointerIndices; 52 53 /// GenerateDefinition - Whether the VTT builder should generate LLVM IR for 54 /// the VTT. 55 bool GenerateDefinition; 56 57 /// GetAddrOfVTable - Returns the address of the vtable for the base class in 58 /// the given vtable class. 59 /// 60 /// \param AddressPoints - If the returned vtable is a construction vtable, 61 /// this will hold the address points for it. 62 llvm::Constant *GetAddrOfVTable(BaseSubobject Base, bool BaseIsVirtual, 63 AddressPointsMapTy& AddressPoints); 64 65 /// AddVTablePointer - Add a vtable pointer to the VTT currently being built. 66 /// 67 /// \param AddressPoints - If the vtable is a construction vtable, this has 68 /// the address points for it. 69 void AddVTablePointer(BaseSubobject Base, llvm::Constant *VTable, 70 const CXXRecordDecl *VTableClass, 71 const AddressPointsMapTy& AddressPoints); 72 73 /// LayoutSecondaryVTTs - Lay out the secondary VTTs of the given base 74 /// subobject. 75 void LayoutSecondaryVTTs(BaseSubobject Base); 76 77 /// LayoutSecondaryVirtualPointers - Lay out the secondary virtual pointers 78 /// for the given base subobject. 79 /// 80 /// \param BaseIsMorallyVirtual whether the base subobject is a virtual base 81 /// or a direct or indirect base of a virtual base. 82 /// 83 /// \param AddressPoints - If the vtable is a construction vtable, this has 84 /// the address points for it. 85 void LayoutSecondaryVirtualPointers(BaseSubobject Base, 86 bool BaseIsMorallyVirtual, 87 llvm::Constant *VTable, 88 const CXXRecordDecl *VTableClass, 89 const AddressPointsMapTy& AddressPoints, 90 VisitedVirtualBasesSetTy &VBases); 91 92 /// LayoutSecondaryVirtualPointers - Lay out the secondary virtual pointers 93 /// for the given base subobject. 94 /// 95 /// \param AddressPoints - If the vtable is a construction vtable, this has 96 /// the address points for it. 97 void LayoutSecondaryVirtualPointers(BaseSubobject Base, 98 llvm::Constant *VTable, 99 const AddressPointsMapTy& AddressPoints); 100 101 /// LayoutVirtualVTTs - Lay out the VTTs for the virtual base classes of the 102 /// given record decl. 103 void LayoutVirtualVTTs(const CXXRecordDecl *RD, 104 VisitedVirtualBasesSetTy &VBases); 105 106 /// LayoutVTT - Will lay out the VTT for the given subobject, including any 107 /// secondary VTTs, secondary virtual pointers and virtual VTTs. 108 void LayoutVTT(BaseSubobject Base, bool BaseIsVirtual); 109 110 public: 111 VTTBuilder(CodeGenModule &CGM, const CXXRecordDecl *MostDerivedClass, 112 bool GenerateDefinition); 113 114 // getVTTComponents - Returns a reference to the VTT components. 115 const VTTComponentsVectorTy &getVTTComponents() const { 116 return VTTComponents; 117 } 118 119 /// getSubVTTIndicies - Returns a reference to the sub-VTT indices. 120 const llvm::DenseMap<BaseSubobject, uint64_t> &getSubVTTIndicies() const { 121 return SubVTTIndicies; 122 } 123 124 /// getSecondaryVirtualPointerIndices - Returns a reference to the secondary 125 /// virtual pointer indices. 126 const llvm::DenseMap<BaseSubobject, uint64_t> & 127 getSecondaryVirtualPointerIndices() const { 128 return SecondaryVirtualPointerIndices; 129 } 130 131 }; 132 133 VTTBuilder::VTTBuilder(CodeGenModule &CGM, 134 const CXXRecordDecl *MostDerivedClass, 135 bool GenerateDefinition) 136 : CGM(CGM), MostDerivedClass(MostDerivedClass), 137 MostDerivedClassLayout(CGM.getContext().getASTRecordLayout(MostDerivedClass)), 138 GenerateDefinition(GenerateDefinition) { 139 140 // Lay out this VTT. 141 LayoutVTT(BaseSubobject(MostDerivedClass, 0), /*BaseIsVirtual=*/false); 142 } 143 144 llvm::Constant * 145 VTTBuilder::GetAddrOfVTable(BaseSubobject Base, bool BaseIsVirtual, 146 AddressPointsMapTy& AddressPoints) { 147 if (!GenerateDefinition) 148 return 0; 149 150 if (Base.getBase() == MostDerivedClass) { 151 assert(Base.getBaseOffset() == 0 && 152 "Most derived class vtable must have a zero offset!"); 153 // This is a regular vtable. 154 return CGM.getVTables().GetAddrOfVTable(MostDerivedClass); 155 } 156 157 return CGM.getVTables().GenerateConstructionVTable(MostDerivedClass, 158 Base, BaseIsVirtual, 159 AddressPoints); 160 } 161 162 void VTTBuilder::AddVTablePointer(BaseSubobject Base, llvm::Constant *VTable, 163 const CXXRecordDecl *VTableClass, 164 const AddressPointsMapTy& AddressPoints) { 165 // Store the vtable pointer index if we're generating the primary VTT. 166 if (VTableClass == MostDerivedClass) { 167 assert(!SecondaryVirtualPointerIndices.count(Base) && 168 "A virtual pointer index already exists for this base subobject!"); 169 SecondaryVirtualPointerIndices[Base] = VTTComponents.size(); 170 } 171 172 if (!GenerateDefinition) { 173 VTTComponents.push_back(0); 174 return; 175 } 176 177 uint64_t AddressPoint; 178 if (VTableClass != MostDerivedClass) { 179 // The vtable is a construction vtable, look in the construction vtable 180 // address points. 181 AddressPoint = AddressPoints.lookup(Base); 182 assert(AddressPoint != 0 && "Did not find ctor vtable address point!"); 183 } else { 184 // Just get the address point for the regular vtable. 185 AddressPoint = CGM.getVTables().getAddressPoint(Base, VTableClass); 186 assert(AddressPoint != 0 && "Did not find vtable address point!"); 187 } 188 189 if (!AddressPoint) AddressPoint = 0; 190 191 llvm::Value *Idxs[] = { 192 llvm::ConstantInt::get(llvm::Type::getInt64Ty(CGM.getLLVMContext()), 0), 193 llvm::ConstantInt::get(llvm::Type::getInt64Ty(CGM.getLLVMContext()), 194 AddressPoint) 195 }; 196 197 llvm::Constant *Init = 198 llvm::ConstantExpr::getInBoundsGetElementPtr(VTable, Idxs, 2); 199 200 const llvm::Type *Int8PtrTy = llvm::Type::getInt8PtrTy(CGM.getLLVMContext()); 201 Init = llvm::ConstantExpr::getBitCast(Init, Int8PtrTy); 202 203 VTTComponents.push_back(Init); 204 } 205 206 void VTTBuilder::LayoutSecondaryVTTs(BaseSubobject Base) { 207 const CXXRecordDecl *RD = Base.getBase(); 208 209 for (CXXRecordDecl::base_class_const_iterator I = RD->bases_begin(), 210 E = RD->bases_end(); I != E; ++I) { 211 212 // Don't layout virtual bases. 213 if (I->isVirtual()) 214 continue; 215 216 const CXXRecordDecl *BaseDecl = 217 cast<CXXRecordDecl>(I->getType()->getAs<RecordType>()->getDecl()); 218 219 const ASTRecordLayout &Layout = CGM.getContext().getASTRecordLayout(RD); 220 uint64_t BaseOffset = Base.getBaseOffset() + 221 Layout.getBaseClassOffsetInBits(BaseDecl); 222 223 // Layout the VTT for this base. 224 LayoutVTT(BaseSubobject(BaseDecl, BaseOffset), /*BaseIsVirtual=*/false); 225 } 226 } 227 228 void 229 VTTBuilder::LayoutSecondaryVirtualPointers(BaseSubobject Base, 230 bool BaseIsMorallyVirtual, 231 llvm::Constant *VTable, 232 const CXXRecordDecl *VTableClass, 233 const AddressPointsMapTy& AddressPoints, 234 VisitedVirtualBasesSetTy &VBases) { 235 const CXXRecordDecl *RD = Base.getBase(); 236 237 // We're not interested in bases that don't have virtual bases, and not 238 // morally virtual bases. 239 if (!RD->getNumVBases() && !BaseIsMorallyVirtual) 240 return; 241 242 for (CXXRecordDecl::base_class_const_iterator I = RD->bases_begin(), 243 E = RD->bases_end(); I != E; ++I) { 244 const CXXRecordDecl *BaseDecl = 245 cast<CXXRecordDecl>(I->getType()->getAs<RecordType>()->getDecl()); 246 247 // Itanium C++ ABI 2.6.2: 248 // Secondary virtual pointers are present for all bases with either 249 // virtual bases or virtual function declarations overridden along a 250 // virtual path. 251 // 252 // If the base class is not dynamic, we don't want to add it, nor any 253 // of its base classes. 254 if (!BaseDecl->isDynamicClass()) 255 continue; 256 257 bool BaseDeclIsMorallyVirtual = BaseIsMorallyVirtual; 258 bool BaseDeclIsNonVirtualPrimaryBase = false; 259 uint64_t BaseOffset; 260 if (I->isVirtual()) { 261 // Ignore virtual bases that we've already visited. 262 if (!VBases.insert(BaseDecl)) 263 continue; 264 265 BaseOffset = MostDerivedClassLayout.getVBaseClassOffsetInBits(BaseDecl); 266 BaseDeclIsMorallyVirtual = true; 267 } else { 268 const ASTRecordLayout &Layout = CGM.getContext().getASTRecordLayout(RD); 269 270 BaseOffset = 271 Base.getBaseOffset() + Layout.getBaseClassOffsetInBits(BaseDecl); 272 273 if (!Layout.isPrimaryBaseVirtual() && 274 Layout.getPrimaryBase() == BaseDecl) 275 BaseDeclIsNonVirtualPrimaryBase = true; 276 } 277 278 // Itanium C++ ABI 2.6.2: 279 // Secondary virtual pointers: for each base class X which (a) has virtual 280 // bases or is reachable along a virtual path from D, and (b) is not a 281 // non-virtual primary base, the address of the virtual table for X-in-D 282 // or an appropriate construction virtual table. 283 if (!BaseDeclIsNonVirtualPrimaryBase && 284 (BaseDecl->getNumVBases() || BaseDeclIsMorallyVirtual)) { 285 // Add the vtable pointer. 286 AddVTablePointer(BaseSubobject(BaseDecl, BaseOffset), VTable, VTableClass, 287 AddressPoints); 288 } 289 290 // And lay out the secondary virtual pointers for the base class. 291 LayoutSecondaryVirtualPointers(BaseSubobject(BaseDecl, BaseOffset), 292 BaseDeclIsMorallyVirtual, VTable, 293 VTableClass, AddressPoints, VBases); 294 } 295 } 296 297 void 298 VTTBuilder::LayoutSecondaryVirtualPointers(BaseSubobject Base, 299 llvm::Constant *VTable, 300 const AddressPointsMapTy& AddressPoints) { 301 VisitedVirtualBasesSetTy VBases; 302 LayoutSecondaryVirtualPointers(Base, /*BaseIsMorallyVirtual=*/false, 303 VTable, Base.getBase(), AddressPoints, VBases); 304 } 305 306 void VTTBuilder::LayoutVirtualVTTs(const CXXRecordDecl *RD, 307 VisitedVirtualBasesSetTy &VBases) { 308 for (CXXRecordDecl::base_class_const_iterator I = RD->bases_begin(), 309 E = RD->bases_end(); I != E; ++I) { 310 const CXXRecordDecl *BaseDecl = 311 cast<CXXRecordDecl>(I->getType()->getAs<RecordType>()->getDecl()); 312 313 // Check if this is a virtual base. 314 if (I->isVirtual()) { 315 // Check if we've seen this base before. 316 if (!VBases.insert(BaseDecl)) 317 continue; 318 319 uint64_t BaseOffset = 320 MostDerivedClassLayout.getVBaseClassOffsetInBits(BaseDecl); 321 322 LayoutVTT(BaseSubobject(BaseDecl, BaseOffset), /*BaseIsVirtual=*/true); 323 } 324 325 // We only need to layout virtual VTTs for this base if it actually has 326 // virtual bases. 327 if (BaseDecl->getNumVBases()) 328 LayoutVirtualVTTs(BaseDecl, VBases); 329 } 330 } 331 332 void VTTBuilder::LayoutVTT(BaseSubobject Base, bool BaseIsVirtual) { 333 const CXXRecordDecl *RD = Base.getBase(); 334 335 // Itanium C++ ABI 2.6.2: 336 // An array of virtual table addresses, called the VTT, is declared for 337 // each class type that has indirect or direct virtual base classes. 338 if (RD->getNumVBases() == 0) 339 return; 340 341 bool IsPrimaryVTT = Base.getBase() == MostDerivedClass; 342 343 if (!IsPrimaryVTT) { 344 // Remember the sub-VTT index. 345 SubVTTIndicies[Base] = VTTComponents.size(); 346 } 347 348 AddressPointsMapTy AddressPoints; 349 llvm::Constant *VTable = GetAddrOfVTable(Base, BaseIsVirtual, AddressPoints); 350 351 // Add the primary vtable pointer. 352 AddVTablePointer(Base, VTable, RD, AddressPoints); 353 354 // Add the secondary VTTs. 355 LayoutSecondaryVTTs(Base); 356 357 // Add the secondary virtual pointers. 358 LayoutSecondaryVirtualPointers(Base, VTable, AddressPoints); 359 360 // If this is the primary VTT, we want to lay out virtual VTTs as well. 361 if (IsPrimaryVTT) { 362 VisitedVirtualBasesSetTy VBases; 363 LayoutVirtualVTTs(Base.getBase(), VBases); 364 } 365 } 366 367 } 368 369 llvm::GlobalVariable * 370 CodeGenVTables::GenerateVTT(llvm::GlobalVariable::LinkageTypes Linkage, 371 bool GenerateDefinition, 372 const CXXRecordDecl *RD) { 373 // Only classes that have virtual bases need a VTT. 374 if (RD->getNumVBases() == 0) 375 return 0; 376 377 llvm::SmallString<256> OutName; 378 CGM.getCXXABI().getMangleContext().mangleCXXVTT(RD, OutName); 379 llvm::StringRef Name = OutName.str(); 380 381 D1(printf("vtt %s\n", RD->getNameAsCString())); 382 383 llvm::GlobalVariable *GV = CGM.getModule().getGlobalVariable(Name, true); 384 if (GV == 0 || GV->isDeclaration()) { 385 const llvm::Type *Int8PtrTy = 386 llvm::Type::getInt8PtrTy(CGM.getLLVMContext()); 387 388 VTTBuilder Builder(CGM, RD, GenerateDefinition); 389 390 const llvm::ArrayType *Type = 391 llvm::ArrayType::get(Int8PtrTy, Builder.getVTTComponents().size()); 392 393 llvm::Constant *Init = 0; 394 if (GenerateDefinition) 395 Init = llvm::ConstantArray::get(Type, Builder.getVTTComponents().data(), 396 Builder.getVTTComponents().size()); 397 398 llvm::GlobalVariable *OldGV = GV; 399 GV = new llvm::GlobalVariable(CGM.getModule(), Type, /*isConstant=*/true, 400 Linkage, Init, Name); 401 CGM.setGlobalVisibility(GV, RD, /*ForDefinition*/ GenerateDefinition); 402 403 if (OldGV) { 404 GV->takeName(OldGV); 405 llvm::Constant *NewPtr = 406 llvm::ConstantExpr::getBitCast(GV, OldGV->getType()); 407 OldGV->replaceAllUsesWith(NewPtr); 408 OldGV->eraseFromParent(); 409 } 410 } 411 412 return GV; 413 } 414 415 llvm::GlobalVariable *CodeGenVTables::getVTT(const CXXRecordDecl *RD) { 416 return GenerateVTT(llvm::GlobalValue::ExternalLinkage, 417 /*GenerateDefinition=*/false, RD); 418 } 419 420 bool CodeGenVTables::needsVTTParameter(GlobalDecl GD) { 421 const CXXMethodDecl *MD = cast<CXXMethodDecl>(GD.getDecl()); 422 423 // We don't have any virtual bases, just return early. 424 if (!MD->getParent()->getNumVBases()) 425 return false; 426 427 // Check if we have a base constructor. 428 if (isa<CXXConstructorDecl>(MD) && GD.getCtorType() == Ctor_Base) 429 return true; 430 431 // Check if we have a base destructor. 432 if (isa<CXXDestructorDecl>(MD) && GD.getDtorType() == Dtor_Base) 433 return true; 434 435 return false; 436 } 437 438 uint64_t CodeGenVTables::getSubVTTIndex(const CXXRecordDecl *RD, 439 BaseSubobject Base) { 440 BaseSubobjectPairTy ClassSubobjectPair(RD, Base); 441 442 SubVTTIndiciesMapTy::iterator I = SubVTTIndicies.find(ClassSubobjectPair); 443 if (I != SubVTTIndicies.end()) 444 return I->second; 445 446 VTTBuilder Builder(CGM, RD, /*GenerateDefinition=*/false); 447 448 for (llvm::DenseMap<BaseSubobject, uint64_t>::const_iterator I = 449 Builder.getSubVTTIndicies().begin(), 450 E = Builder.getSubVTTIndicies().end(); I != E; ++I) { 451 // Insert all indices. 452 BaseSubobjectPairTy ClassSubobjectPair(RD, I->first); 453 454 SubVTTIndicies.insert(std::make_pair(ClassSubobjectPair, I->second)); 455 } 456 457 I = SubVTTIndicies.find(ClassSubobjectPair); 458 assert(I != SubVTTIndicies.end() && "Did not find index!"); 459 460 return I->second; 461 } 462 463 uint64_t 464 CodeGenVTables::getSecondaryVirtualPointerIndex(const CXXRecordDecl *RD, 465 BaseSubobject Base) { 466 SecondaryVirtualPointerIndicesMapTy::iterator I = 467 SecondaryVirtualPointerIndices.find(std::make_pair(RD, Base)); 468 469 if (I != SecondaryVirtualPointerIndices.end()) 470 return I->second; 471 472 VTTBuilder Builder(CGM, RD, /*GenerateDefinition=*/false); 473 474 // Insert all secondary vpointer indices. 475 for (llvm::DenseMap<BaseSubobject, uint64_t>::const_iterator I = 476 Builder.getSecondaryVirtualPointerIndices().begin(), 477 E = Builder.getSecondaryVirtualPointerIndices().end(); I != E; ++I) { 478 std::pair<const CXXRecordDecl *, BaseSubobject> Pair = 479 std::make_pair(RD, I->first); 480 481 SecondaryVirtualPointerIndices.insert(std::make_pair(Pair, I->second)); 482 } 483 484 I = SecondaryVirtualPointerIndices.find(std::make_pair(RD, Base)); 485 assert(I != SecondaryVirtualPointerIndices.end() && "Did not find index!"); 486 487 return I->second; 488 } 489 490