CGVTT.cpp revision 206084
1235368Sgnn//===--- CGVTT.cpp - Emit LLVM Code for C++ VTTs --------------------------===// 2235368Sgnn// 3235368Sgnn// The LLVM Compiler Infrastructure 4235368Sgnn// 5235368Sgnn// This file is distributed under the University of Illinois Open Source 6235368Sgnn// License. See LICENSE.TXT for details. 7235368Sgnn// 8235368Sgnn//===----------------------------------------------------------------------===// 9235368Sgnn// 10235368Sgnn// This contains code dealing with C++ code generation of VTTs (vtable tables). 11235368Sgnn// 12235368Sgnn//===----------------------------------------------------------------------===// 13235368Sgnn 14235368Sgnn#include "CodeGenModule.h" 15235368Sgnn#include "clang/AST/RecordLayout.h" 16235368Sgnnusing namespace clang; 17235368Sgnnusing namespace CodeGen; 18235368Sgnn 19235368Sgnn#define D1(x) 20235368Sgnn 21235368Sgnnnamespace { 22235368Sgnn 23235368Sgnn/// VTT builder - Class for building VTT layout information. 24235368Sgnnclass VTTBuilder { 25235368Sgnn 26235368Sgnn CodeGenModule &CGM; 27235368Sgnn 28235368Sgnn /// MostDerivedClass - The most derived class for which we're building this 29235368Sgnn /// vtable. 30235368Sgnn const CXXRecordDecl *MostDerivedClass; 31235368Sgnn 32235368Sgnn typedef llvm::SmallVector<llvm::Constant *, 64> VTTComponentsVectorTy; 33235368Sgnn 34235368Sgnn /// VTTComponents - The VTT components. 35235368Sgnn VTTComponentsVectorTy VTTComponents; 36235368Sgnn 37235368Sgnn /// MostDerivedClassLayout - the AST record layout of the most derived class. 38235368Sgnn const ASTRecordLayout &MostDerivedClassLayout; 39235368Sgnn 40235368Sgnn typedef llvm::SmallPtrSet<const CXXRecordDecl *, 4> VisitedVirtualBasesSetTy; 41235368Sgnn 42235368Sgnn typedef llvm::DenseMap<BaseSubobject, uint64_t> AddressPointsMapTy; 43235368Sgnn 44235368Sgnn /// SubVTTIndicies - The sub-VTT indices for the bases of the most derived 45235368Sgnn /// class. 46235368Sgnn llvm::DenseMap<const CXXRecordDecl *, uint64_t> SubVTTIndicies; 47235368Sgnn 48235368Sgnn /// SecondaryVirtualPointerIndices - The secondary virtual pointer indices of 49235368Sgnn /// all subobjects of the most derived class. 50235368Sgnn llvm::DenseMap<BaseSubobject, uint64_t> SecondaryVirtualPointerIndices; 51235368Sgnn 52235368Sgnn /// GenerateDefinition - Whether the VTT builder should generate LLVM IR for 53235368Sgnn /// the VTT. 54235368Sgnn bool GenerateDefinition; 55235368Sgnn 56235368Sgnn /// GetAddrOfVTable - Returns the address of the vtable for the base class in 57235368Sgnn /// the given vtable class. 58235368Sgnn /// 59235368Sgnn /// \param AddressPoints - If the returned vtable is a construction vtable, 60235368Sgnn /// this will hold the address points for it. 61235368Sgnn llvm::Constant *GetAddrOfVTable(BaseSubobject Base, bool BaseIsVirtual, 62235368Sgnn AddressPointsMapTy& AddressPoints); 63235368Sgnn 64235368Sgnn /// AddVTablePointer - Add a vtable pointer to the VTT currently being built. 65235368Sgnn /// 66235368Sgnn /// \param AddressPoints - If the vtable is a construction vtable, this has 67235368Sgnn /// the address points for it. 68235368Sgnn void AddVTablePointer(BaseSubobject Base, llvm::Constant *VTable, 69235368Sgnn const CXXRecordDecl *VTableClass, 70235368Sgnn const AddressPointsMapTy& AddressPoints); 71235368Sgnn 72235368Sgnn /// LayoutSecondaryVTTs - Lay out the secondary VTTs of the given base 73235368Sgnn /// subobject. 74235368Sgnn void LayoutSecondaryVTTs(BaseSubobject Base); 75235368Sgnn 76235368Sgnn /// LayoutSecondaryVirtualPointers - Lay out the secondary virtual pointers 77235368Sgnn /// for the given base subobject. 78235368Sgnn /// 79235368Sgnn /// \param BaseIsMorallyVirtual whether the base subobject is a virtual base 80235368Sgnn /// or a direct or indirect base of a virtual base. 81235368Sgnn /// 82235368Sgnn /// \param AddressPoints - If the vtable is a construction vtable, this has 83235368Sgnn /// the address points for it. 84235368Sgnn void LayoutSecondaryVirtualPointers(BaseSubobject Base, 85235368Sgnn bool BaseIsMorallyVirtual, 86235368Sgnn llvm::Constant *VTable, 87235368Sgnn const CXXRecordDecl *VTableClass, 88235368Sgnn const AddressPointsMapTy& AddressPoints, 89235368Sgnn VisitedVirtualBasesSetTy &VBases); 90235368Sgnn 91235368Sgnn /// LayoutSecondaryVirtualPointers - Lay out the secondary virtual pointers 92235368Sgnn /// for the given base subobject. 93235368Sgnn /// 94235368Sgnn /// \param AddressPoints - If the vtable is a construction vtable, this has 95235368Sgnn /// the address points for it. 96235368Sgnn void LayoutSecondaryVirtualPointers(BaseSubobject Base, 97235368Sgnn llvm::Constant *VTable, 98235368Sgnn const AddressPointsMapTy& AddressPoints); 99235368Sgnn 100235368Sgnn /// LayoutVirtualVTTs - Lay out the VTTs for the virtual base classes of the 101235368Sgnn /// given record decl. 102235368Sgnn void LayoutVirtualVTTs(const CXXRecordDecl *RD, 103235368Sgnn VisitedVirtualBasesSetTy &VBases); 104235368Sgnn 105235368Sgnn /// LayoutVTT - Will lay out the VTT for the given subobject, including any 106235368Sgnn /// secondary VTTs, secondary virtual pointers and virtual VTTs. 107235368Sgnn void LayoutVTT(BaseSubobject Base, bool BaseIsVirtual); 108235368Sgnn 109235368Sgnnpublic: 110235368Sgnn VTTBuilder(CodeGenModule &CGM, const CXXRecordDecl *MostDerivedClass, 111235368Sgnn bool GenerateDefinition); 112235368Sgnn 113235368Sgnn // getVTTComponents - Returns a reference to the VTT components. 114235368Sgnn const VTTComponentsVectorTy &getVTTComponents() const { 115235368Sgnn return VTTComponents; 116235368Sgnn } 117235368Sgnn 118235368Sgnn /// getSubVTTIndicies - Returns a reference to the sub-VTT indices. 119235368Sgnn const llvm::DenseMap<const CXXRecordDecl *, uint64_t> & 120235368Sgnn getSubVTTIndicies() const { 121235368Sgnn return SubVTTIndicies; 122235368Sgnn } 123235368Sgnn 124235368Sgnn /// getSecondaryVirtualPointerIndices - Returns a reference to the secondary 125235368Sgnn /// virtual pointer indices. 126235368Sgnn const llvm::DenseMap<BaseSubobject, uint64_t> & 127235368Sgnn getSecondaryVirtualPointerIndices() const { 128235368Sgnn return SecondaryVirtualPointerIndices; 129235368Sgnn } 130235368Sgnn 131235368Sgnn}; 132235368Sgnn 133235368SgnnVTTBuilder::VTTBuilder(CodeGenModule &CGM, 134235368Sgnn const CXXRecordDecl *MostDerivedClass, 135235368Sgnn bool GenerateDefinition) 136235368Sgnn : CGM(CGM), MostDerivedClass(MostDerivedClass), 137235368Sgnn MostDerivedClassLayout(CGM.getContext().getASTRecordLayout(MostDerivedClass)), 138235368Sgnn GenerateDefinition(GenerateDefinition) { 139235368Sgnn 140235368Sgnn // Lay out this VTT. 141235368Sgnn LayoutVTT(BaseSubobject(MostDerivedClass, 0), /*BaseIsVirtual=*/false); 142235368Sgnn} 143235368Sgnn 144235368Sgnnllvm::Constant * 145235368SgnnVTTBuilder::GetAddrOfVTable(BaseSubobject Base, bool BaseIsVirtual, 146235368Sgnn AddressPointsMapTy& AddressPoints) { 147235368Sgnn if (!GenerateDefinition) 148235368Sgnn return 0; 149235368Sgnn 150235368Sgnn if (Base.getBase() == MostDerivedClass) { 151235368Sgnn assert(Base.getBaseOffset() == 0 && 152235368Sgnn "Most derived class vtable must have a zero offset!"); 153235368Sgnn // This is a regular vtable. 154235368Sgnn return CGM.getVTables().GetAddrOfVTable(MostDerivedClass); 155235368Sgnn } 156235368Sgnn 157235368Sgnn return CGM.getVTables().GenerateConstructionVTable(MostDerivedClass, 158235368Sgnn Base, BaseIsVirtual, 159235368Sgnn AddressPoints); 160235368Sgnn} 161235368Sgnn 162235368Sgnnvoid VTTBuilder::AddVTablePointer(BaseSubobject Base, llvm::Constant *VTable, 163235368Sgnn const CXXRecordDecl *VTableClass, 164235368Sgnn const AddressPointsMapTy& AddressPoints) { 165235368Sgnn // Store the vtable pointer index if we're generating the primary VTT. 166235368Sgnn if (VTableClass == MostDerivedClass) { 167235368Sgnn assert(!SecondaryVirtualPointerIndices.count(Base) && 168235368Sgnn "A virtual pointer index already exists for this base subobject!"); 169235368Sgnn SecondaryVirtualPointerIndices[Base] = VTTComponents.size(); 170235368Sgnn } 171235368Sgnn 172235368Sgnn if (!GenerateDefinition) { 173235368Sgnn VTTComponents.push_back(0); 174235368Sgnn return; 175235368Sgnn } 176235368Sgnn 177235368Sgnn uint64_t AddressPoint; 178235368Sgnn if (VTableClass != MostDerivedClass) { 179235368Sgnn // The vtable is a construction vtable, look in the construction vtable 180235368Sgnn // address points. 181235368Sgnn AddressPoint = AddressPoints.lookup(Base); 182235368Sgnn } else { 183235368Sgnn // Just get the address point for the regular vtable. 184235368Sgnn AddressPoint = CGM.getVTables().getAddressPoint(Base, VTableClass); 185235368Sgnn } 186235368Sgnn 187235368Sgnn if (!AddressPoint) AddressPoint = 0; 188235368Sgnn assert(AddressPoint != 0 && "Did not find an address point!"); 189235368Sgnn 190235368Sgnn llvm::Value *Idxs[] = { 191235368Sgnn llvm::ConstantInt::get(llvm::Type::getInt64Ty(CGM.getLLVMContext()), 0), 192235368Sgnn llvm::ConstantInt::get(llvm::Type::getInt64Ty(CGM.getLLVMContext()), 193235368Sgnn AddressPoint) 194235368Sgnn }; 195235368Sgnn 196235368Sgnn llvm::Constant *Init = 197235368Sgnn llvm::ConstantExpr::getInBoundsGetElementPtr(VTable, Idxs, 2); 198235368Sgnn 199235368Sgnn const llvm::Type *Int8PtrTy = llvm::Type::getInt8PtrTy(CGM.getLLVMContext()); 200235368Sgnn Init = llvm::ConstantExpr::getBitCast(Init, Int8PtrTy); 201235368Sgnn 202235368Sgnn VTTComponents.push_back(Init); 203235368Sgnn} 204235368Sgnn 205235368Sgnnvoid VTTBuilder::LayoutSecondaryVTTs(BaseSubobject Base) { 206235368Sgnn const CXXRecordDecl *RD = Base.getBase(); 207235368Sgnn 208235368Sgnn for (CXXRecordDecl::base_class_const_iterator I = RD->bases_begin(), 209235368Sgnn E = RD->bases_end(); I != E; ++I) { 210235368Sgnn 211235368Sgnn // Don't layout virtual bases. 212235368Sgnn if (I->isVirtual()) 213235368Sgnn continue; 214235368Sgnn 215235368Sgnn const CXXRecordDecl *BaseDecl = 216235368Sgnn cast<CXXRecordDecl>(I->getType()->getAs<RecordType>()->getDecl()); 217235368Sgnn 218235368Sgnn const ASTRecordLayout &Layout = CGM.getContext().getASTRecordLayout(RD); 219235368Sgnn uint64_t BaseOffset = Base.getBaseOffset() + 220235368Sgnn Layout.getBaseClassOffset(BaseDecl); 221235368Sgnn 222235368Sgnn // Layout the VTT for this base. 223235368Sgnn LayoutVTT(BaseSubobject(BaseDecl, BaseOffset), /*BaseIsVirtual=*/false); 224235368Sgnn } 225235368Sgnn} 226235368Sgnn 227235368Sgnnvoid 228235368SgnnVTTBuilder::LayoutSecondaryVirtualPointers(BaseSubobject Base, 229235368Sgnn bool BaseIsMorallyVirtual, 230235368Sgnn llvm::Constant *VTable, 231235368Sgnn const CXXRecordDecl *VTableClass, 232235368Sgnn const AddressPointsMapTy& AddressPoints, 233235368Sgnn VisitedVirtualBasesSetTy &VBases) { 234235368Sgnn const CXXRecordDecl *RD = Base.getBase(); 235235368Sgnn 236235368Sgnn // We're not interested in bases that don't have virtual bases, and not 237235368Sgnn // morally virtual bases. 238235368Sgnn if (!RD->getNumVBases() && !BaseIsMorallyVirtual) 239235368Sgnn return; 240235368Sgnn 241235368Sgnn for (CXXRecordDecl::base_class_const_iterator I = RD->bases_begin(), 242235368Sgnn E = RD->bases_end(); I != E; ++I) { 243235368Sgnn const CXXRecordDecl *BaseDecl = 244235368Sgnn cast<CXXRecordDecl>(I->getType()->getAs<RecordType>()->getDecl()); 245235368Sgnn 246235368Sgnn // Itanium C++ ABI 2.6.2: 247235368Sgnn // Secondary virtual pointers are present for all bases with either 248235368Sgnn // virtual bases or virtual function declarations overridden along a 249235368Sgnn // virtual path. 250235368Sgnn // 251235368Sgnn // If the base class is not dynamic, we don't want to add it, nor any 252235368Sgnn // of its base classes. 253235368Sgnn if (!BaseDecl->isDynamicClass()) 254235368Sgnn continue; 255235368Sgnn 256235368Sgnn bool BaseDeclIsMorallyVirtual = BaseIsMorallyVirtual; 257235368Sgnn bool BaseDeclIsNonVirtualPrimaryBase = false; 258235368Sgnn uint64_t BaseOffset; 259235368Sgnn if (I->isVirtual()) { 260235368Sgnn // Ignore virtual bases that we've already visited. 261235368Sgnn if (!VBases.insert(BaseDecl)) 262235368Sgnn continue; 263235368Sgnn 264235368Sgnn BaseOffset = MostDerivedClassLayout.getVBaseClassOffset(BaseDecl); 265235368Sgnn BaseDeclIsMorallyVirtual = true; 266235368Sgnn } else { 267235368Sgnn const ASTRecordLayout &Layout = CGM.getContext().getASTRecordLayout(RD); 268235368Sgnn 269 BaseOffset = Base.getBaseOffset() + Layout.getBaseClassOffset(BaseDecl); 270 271 if (!Layout.getPrimaryBaseWasVirtual() && 272 Layout.getPrimaryBase() == BaseDecl) 273 BaseDeclIsNonVirtualPrimaryBase = true; 274 } 275 276 // Itanium C++ ABI 2.6.2: 277 // Secondary virtual pointers: for each base class X which (a) has virtual 278 // bases or is reachable along a virtual path from D, and (b) is not a 279 // non-virtual primary base, the address of the virtual table for X-in-D 280 // or an appropriate construction virtual table. 281 if (!BaseDeclIsNonVirtualPrimaryBase && 282 (BaseDecl->getNumVBases() || BaseDeclIsMorallyVirtual)) { 283 // Add the vtable pointer. 284 AddVTablePointer(BaseSubobject(BaseDecl, BaseOffset), VTable, VTableClass, 285 AddressPoints); 286 } 287 288 // And lay out the secondary virtual pointers for the base class. 289 LayoutSecondaryVirtualPointers(BaseSubobject(BaseDecl, BaseOffset), 290 BaseDeclIsMorallyVirtual, VTable, 291 VTableClass, AddressPoints, VBases); 292 } 293} 294 295void 296VTTBuilder::LayoutSecondaryVirtualPointers(BaseSubobject Base, 297 llvm::Constant *VTable, 298 const AddressPointsMapTy& AddressPoints) { 299 VisitedVirtualBasesSetTy VBases; 300 LayoutSecondaryVirtualPointers(Base, /*BaseIsMorallyVirtual=*/false, 301 VTable, Base.getBase(), AddressPoints, VBases); 302} 303 304void VTTBuilder::LayoutVirtualVTTs(const CXXRecordDecl *RD, 305 VisitedVirtualBasesSetTy &VBases) { 306 for (CXXRecordDecl::base_class_const_iterator I = RD->bases_begin(), 307 E = RD->bases_end(); I != E; ++I) { 308 const CXXRecordDecl *BaseDecl = 309 cast<CXXRecordDecl>(I->getType()->getAs<RecordType>()->getDecl()); 310 311 // Check if this is a virtual base. 312 if (I->isVirtual()) { 313 // Check if we've seen this base before. 314 if (!VBases.insert(BaseDecl)) 315 continue; 316 317 uint64_t BaseOffset = 318 MostDerivedClassLayout.getVBaseClassOffset(BaseDecl); 319 320 LayoutVTT(BaseSubobject(BaseDecl, BaseOffset), /*BaseIsVirtual=*/true); 321 } 322 323 // We only need to layout virtual VTTs for this base if it actually has 324 // virtual bases. 325 if (BaseDecl->getNumVBases()) 326 LayoutVirtualVTTs(BaseDecl, VBases); 327 } 328} 329 330void VTTBuilder::LayoutVTT(BaseSubobject Base, bool BaseIsVirtual) { 331 const CXXRecordDecl *RD = Base.getBase(); 332 333 // Itanium C++ ABI 2.6.2: 334 // An array of virtual table addresses, called the VTT, is declared for 335 // each class type that has indirect or direct virtual base classes. 336 if (RD->getNumVBases() == 0) 337 return; 338 339 bool IsPrimaryVTT = Base.getBase() == MostDerivedClass; 340 341 if (!IsPrimaryVTT) { 342 // Remember the sub-VTT index. 343 SubVTTIndicies[RD] = VTTComponents.size(); 344 } 345 346 AddressPointsMapTy AddressPoints; 347 llvm::Constant *VTable = GetAddrOfVTable(Base, BaseIsVirtual, AddressPoints); 348 349 // Add the primary vtable pointer. 350 AddVTablePointer(Base, VTable, RD, AddressPoints); 351 352 // Add the secondary VTTs. 353 LayoutSecondaryVTTs(Base); 354 355 // Add the secondary virtual pointers. 356 LayoutSecondaryVirtualPointers(Base, VTable, AddressPoints); 357 358 // If this is the primary VTT, we want to lay out virtual VTTs as well. 359 if (IsPrimaryVTT) { 360 VisitedVirtualBasesSetTy VBases; 361 LayoutVirtualVTTs(Base.getBase(), VBases); 362 } 363} 364 365} 366 367llvm::GlobalVariable * 368CodeGenVTables::GenerateVTT(llvm::GlobalVariable::LinkageTypes Linkage, 369 bool GenerateDefinition, 370 const CXXRecordDecl *RD) { 371 // Only classes that have virtual bases need a VTT. 372 if (RD->getNumVBases() == 0) 373 return 0; 374 375 llvm::SmallString<256> OutName; 376 CGM.getMangleContext().mangleCXXVTT(RD, OutName); 377 llvm::StringRef Name = OutName.str(); 378 379 D1(printf("vtt %s\n", RD->getNameAsCString())); 380 381 llvm::GlobalVariable *GV = CGM.getModule().getGlobalVariable(Name); 382 if (GV == 0 || GV->isDeclaration()) { 383 const llvm::Type *Int8PtrTy = 384 llvm::Type::getInt8PtrTy(CGM.getLLVMContext()); 385 386 VTTBuilder Builder(CGM, RD, GenerateDefinition); 387 388 const llvm::ArrayType *Type = 389 llvm::ArrayType::get(Int8PtrTy, Builder.getVTTComponents().size()); 390 391 llvm::Constant *Init = 0; 392 if (GenerateDefinition) 393 Init = llvm::ConstantArray::get(Type, Builder.getVTTComponents().data(), 394 Builder.getVTTComponents().size()); 395 396 llvm::GlobalVariable *OldGV = GV; 397 GV = new llvm::GlobalVariable(CGM.getModule(), Type, /*isConstant=*/true, 398 Linkage, Init, Name); 399 CGM.setGlobalVisibility(GV, RD); 400 401 if (OldGV) { 402 GV->takeName(OldGV); 403 llvm::Constant *NewPtr = 404 llvm::ConstantExpr::getBitCast(GV, OldGV->getType()); 405 OldGV->replaceAllUsesWith(NewPtr); 406 OldGV->eraseFromParent(); 407 } 408 } 409 410 return GV; 411} 412 413llvm::GlobalVariable *CodeGenVTables::getVTT(const CXXRecordDecl *RD) { 414 return GenerateVTT(llvm::GlobalValue::ExternalLinkage, 415 /*GenerateDefinition=*/false, RD); 416} 417 418bool CodeGenVTables::needsVTTParameter(GlobalDecl GD) { 419 const CXXMethodDecl *MD = cast<CXXMethodDecl>(GD.getDecl()); 420 421 // We don't have any virtual bases, just return early. 422 if (!MD->getParent()->getNumVBases()) 423 return false; 424 425 // Check if we have a base constructor. 426 if (isa<CXXConstructorDecl>(MD) && GD.getCtorType() == Ctor_Base) 427 return true; 428 429 // Check if we have a base destructor. 430 if (isa<CXXDestructorDecl>(MD) && GD.getDtorType() == Dtor_Base) 431 return true; 432 433 return false; 434} 435 436uint64_t CodeGenVTables::getSubVTTIndex(const CXXRecordDecl *RD, 437 const CXXRecordDecl *Base) { 438 ClassPairTy ClassPair(RD, Base); 439 440 SubVTTIndiciesMapTy::iterator I = SubVTTIndicies.find(ClassPair); 441 if (I != SubVTTIndicies.end()) 442 return I->second; 443 444 VTTBuilder Builder(CGM, RD, /*GenerateDefinition=*/false); 445 446 for (llvm::DenseMap<const CXXRecordDecl *, uint64_t>::const_iterator I = 447 Builder.getSubVTTIndicies().begin(), 448 E = Builder.getSubVTTIndicies().end(); I != E; ++I) { 449 // Insert all indices. 450 ClassPairTy ClassPair(RD, I->first); 451 452 SubVTTIndicies.insert(std::make_pair(ClassPair, I->second)); 453 } 454 455 I = SubVTTIndicies.find(ClassPair); 456 assert(I != SubVTTIndicies.end() && "Did not find index!"); 457 458 return I->second; 459} 460 461uint64_t 462CodeGenVTables::getSecondaryVirtualPointerIndex(const CXXRecordDecl *RD, 463 BaseSubobject Base) { 464 SecondaryVirtualPointerIndicesMapTy::iterator I = 465 SecondaryVirtualPointerIndices.find(std::make_pair(RD, Base)); 466 467 if (I != SecondaryVirtualPointerIndices.end()) 468 return I->second; 469 470 VTTBuilder Builder(CGM, RD, /*GenerateDefinition=*/false); 471 472 // Insert all secondary vpointer indices. 473 for (llvm::DenseMap<BaseSubobject, uint64_t>::const_iterator I = 474 Builder.getSecondaryVirtualPointerIndices().begin(), 475 E = Builder.getSecondaryVirtualPointerIndices().end(); I != E; ++I) { 476 std::pair<const CXXRecordDecl *, BaseSubobject> Pair = 477 std::make_pair(RD, I->first); 478 479 SecondaryVirtualPointerIndices.insert(std::make_pair(Pair, I->second)); 480 } 481 482 I = SecondaryVirtualPointerIndices.find(std::make_pair(RD, Base)); 483 assert(I != SecondaryVirtualPointerIndices.end() && "Did not find index!"); 484 485 return I->second; 486} 487 488