clang  19.0.0git
VTableBuilder.h
Go to the documentation of this file.
1 //===--- VTableBuilder.h - C++ vtable layout builder --------------*- C++ -*-=//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This contains code dealing with generation of the layout of virtual tables.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #ifndef LLVM_CLANG_AST_VTABLEBUILDER_H
14 #define LLVM_CLANG_AST_VTABLEBUILDER_H
15 
18 #include "clang/AST/GlobalDecl.h"
19 #include "clang/AST/RecordLayout.h"
20 #include "clang/Basic/ABI.h"
21 #include "clang/Basic/Thunk.h"
22 #include "llvm/ADT/DenseMap.h"
23 #include <memory>
24 #include <utility>
25 
26 namespace clang {
27  class CXXRecordDecl;
28 
29 /// Represents a single component in a vtable.
31 public:
32  enum Kind {
38 
39  /// A pointer to the complete destructor.
41 
42  /// A pointer to the deleting destructor.
44 
45  /// An entry that is never used.
46  ///
47  /// In some cases, a vtable function pointer will end up never being
48  /// called. Such vtable function pointers are represented as a
49  /// CK_UnusedFunctionPointer.
51  };
52 
53  VTableComponent() = default;
54 
57  }
58 
61  }
62 
65  }
66 
68  return VTableComponent(CK_RTTI, reinterpret_cast<uintptr_t>(RD));
69  }
70 
72  assert(!isa<CXXDestructorDecl>(MD) &&
73  "Don't use MakeFunction with destructors!");
74 
76  reinterpret_cast<uintptr_t>(MD));
77  }
78 
81  reinterpret_cast<uintptr_t>(DD));
82  }
83 
86  reinterpret_cast<uintptr_t>(DD));
87  }
88 
90  assert(!isa<CXXDestructorDecl>(MD) &&
91  "Don't use MakeUnusedFunction with destructors!");
93  reinterpret_cast<uintptr_t>(MD));
94  }
95 
96  /// Get the kind of this vtable component.
97  Kind getKind() const {
98  return (Kind)(Value & 0x7);
99  }
100 
102  assert(getKind() == CK_VCallOffset && "Invalid component kind!");
103 
104  return getOffset();
105  }
106 
108  assert(getKind() == CK_VBaseOffset && "Invalid component kind!");
109 
110  return getOffset();
111  }
112 
114  assert(getKind() == CK_OffsetToTop && "Invalid component kind!");
115 
116  return getOffset();
117  }
118 
119  const CXXRecordDecl *getRTTIDecl() const {
120  assert(isRTTIKind() && "Invalid component kind!");
121  return reinterpret_cast<CXXRecordDecl *>(getPointer());
122  }
123 
125  assert(isFunctionPointerKind() && "Invalid component kind!");
126  if (isDestructorKind())
127  return getDestructorDecl();
128  return reinterpret_cast<CXXMethodDecl *>(getPointer());
129  }
130 
132  assert(isDestructorKind() && "Invalid component kind!");
133  return reinterpret_cast<CXXDestructorDecl *>(getPointer());
134  }
135 
137  assert(getKind() == CK_UnusedFunctionPointer && "Invalid component kind!");
138  return reinterpret_cast<CXXMethodDecl *>(getPointer());
139  }
140 
141  bool isDestructorKind() const { return isDestructorKind(getKind()); }
142 
145  }
146 
147  bool isFunctionPointerKind() const {
148  return isFunctionPointerKind(getKind());
149  }
150 
151  bool isRTTIKind() const { return isRTTIKind(getKind()); }
152 
154  assert(isUsedFunctionPointerKind() &&
155  "GlobalDecl can be created only from virtual function");
156 
157  auto *DtorDecl = dyn_cast<CXXDestructorDecl>(getFunctionDecl());
158  switch (getKind()) {
159  case CK_FunctionPointer:
160  return GlobalDecl(getFunctionDecl());
162  return GlobalDecl(DtorDecl, CXXDtorType::Dtor_Complete);
164  return GlobalDecl(DtorDecl, CXXDtorType::Dtor_Deleting);
165  case CK_VCallOffset:
166  case CK_VBaseOffset:
167  case CK_OffsetToTop:
168  case CK_RTTI:
170  llvm_unreachable("Only function pointers kinds");
171  }
172  llvm_unreachable("Should already return");
173  }
174 
175 private:
176  static bool isFunctionPointerKind(Kind ComponentKind) {
177  return isUsedFunctionPointerKind(ComponentKind) ||
178  ComponentKind == CK_UnusedFunctionPointer;
179  }
180  static bool isUsedFunctionPointerKind(Kind ComponentKind) {
181  return ComponentKind == CK_FunctionPointer ||
182  isDestructorKind(ComponentKind);
183  }
184  static bool isDestructorKind(Kind ComponentKind) {
185  return ComponentKind == CK_CompleteDtorPointer ||
186  ComponentKind == CK_DeletingDtorPointer;
187  }
188  static bool isRTTIKind(Kind ComponentKind) {
189  return ComponentKind == CK_RTTI;
190  }
191 
192  VTableComponent(Kind ComponentKind, CharUnits Offset) {
193  assert((ComponentKind == CK_VCallOffset ||
194  ComponentKind == CK_VBaseOffset ||
195  ComponentKind == CK_OffsetToTop) && "Invalid component kind!");
196  assert(Offset.getQuantity() < (1LL << 56) && "Offset is too big!");
197  assert(Offset.getQuantity() >= -(1LL << 56) && "Offset is too small!");
198 
199  Value = (uint64_t(Offset.getQuantity()) << 3) | ComponentKind;
200  }
201 
202  VTableComponent(Kind ComponentKind, uintptr_t Ptr) {
203  assert((isRTTIKind(ComponentKind) || isFunctionPointerKind(ComponentKind)) &&
204  "Invalid component kind!");
205 
206  assert((Ptr & 7) == 0 && "Pointer not sufficiently aligned!");
207 
208  Value = Ptr | ComponentKind;
209  }
210 
211  CharUnits getOffset() const {
212  assert((getKind() == CK_VCallOffset || getKind() == CK_VBaseOffset ||
213  getKind() == CK_OffsetToTop) && "Invalid component kind!");
214 
215  return CharUnits::fromQuantity(Value >> 3);
216  }
217 
218  uintptr_t getPointer() const {
219  assert((getKind() == CK_RTTI || isFunctionPointerKind()) &&
220  "Invalid component kind!");
221 
222  return static_cast<uintptr_t>(Value & ~7ULL);
223  }
224 
225  /// The kind is stored in the lower 3 bits of the value. For offsets, we
226  /// make use of the facts that classes can't be larger than 2^55 bytes,
227  /// so we store the offset in the lower part of the 61 bits that remain.
228  /// (The reason that we're not simply using a PointerIntPair here is that we
229  /// need the offsets to be 64-bit, even when on a 32-bit machine).
230  int64_t Value;
231 };
232 
234 public:
235  typedef std::pair<uint64_t, ThunkInfo> VTableThunkTy;
238  };
239  typedef llvm::DenseMap<BaseSubobject, AddressPointLocation>
241 
242  // Mapping between the VTable index and address point index. This is useful
243  // when you don't care about the base subobjects and only want the address
244  // point for a given vtable index.
246 
247 private:
248  // Stores the component indices of the first component of each virtual table in
249  // the virtual table group. To save a little memory in the common case where
250  // the vtable group contains a single vtable, an empty vector here represents
251  // the vector {0}.
252  OwningArrayRef<size_t> VTableIndices;
253 
254  OwningArrayRef<VTableComponent> VTableComponents;
255 
256  /// Contains thunks needed by vtables, sorted by indices.
257  OwningArrayRef<VTableThunkTy> VTableThunks;
258 
259  /// Address points for all vtables.
260  AddressPointsMapTy AddressPoints;
261 
262  /// Address points for all vtable indices.
263  AddressPointsIndexMapTy AddressPointIndices;
264 
265 public:
266  VTableLayout(ArrayRef<size_t> VTableIndices,
267  ArrayRef<VTableComponent> VTableComponents,
268  ArrayRef<VTableThunkTy> VTableThunks,
269  const AddressPointsMapTy &AddressPoints);
270  ~VTableLayout();
271 
273  return VTableComponents;
274  }
275 
277  return VTableThunks;
278  }
279 
281  assert(AddressPoints.count(Base) && "Did not find address point!");
282  return AddressPoints.lookup(Base);
283  }
284 
286  return AddressPoints;
287  }
288 
290  return AddressPointIndices;
291  }
292 
293  size_t getNumVTables() const {
294  if (VTableIndices.empty())
295  return 1;
296  return VTableIndices.size();
297  }
298 
299  size_t getVTableOffset(size_t i) const {
300  if (VTableIndices.empty()) {
301  assert(i == 0);
302  return 0;
303  }
304  return VTableIndices[i];
305  }
306 
307  size_t getVTableSize(size_t i) const {
308  if (VTableIndices.empty()) {
309  assert(i == 0);
310  return vtable_components().size();
311  }
312 
313  size_t thisIndex = VTableIndices[i];
314  size_t nextIndex = (i + 1 == VTableIndices.size())
315  ? vtable_components().size()
316  : VTableIndices[i + 1];
317  return nextIndex - thisIndex;
318  }
319 };
320 
322 public:
324 
325  bool isMicrosoft() const { return IsMicrosoftABI; }
326 
327  virtual ~VTableContextBase() {}
328 
329 protected:
330  typedef llvm::DenseMap<const CXXMethodDecl *, ThunkInfoVectorTy> ThunksMapTy;
331 
332  /// Contains all thunks that a given method decl will need.
334 
335  /// Compute and store all vtable related information (vtable layout, vbase
336  /// offset offsets, thunks etc) for the given record decl.
337  virtual void computeVTableRelatedInformation(const CXXRecordDecl *RD) = 0;
338 
340 
341 public:
343  const CXXMethodDecl *MD = cast<CXXMethodDecl>(GD.getDecl()->getCanonicalDecl());
345 
346  // This assumes that all the destructors present in the vtable
347  // use exactly the same set of thunks.
348  ThunksMapTy::const_iterator I = Thunks.find(MD);
349  if (I == Thunks.end()) {
350  // We did not find a thunk for this method.
351  return nullptr;
352  }
353 
354  return &I->second;
355  }
356 
358 
359  /// Determine whether this function should be assigned a vtable slot.
360  static bool hasVtableSlot(const CXXMethodDecl *MD);
361 };
362 
364 private:
365 
366  /// Contains the index (relative to the vtable address point)
367  /// where the function pointer for a virtual function is stored.
368  typedef llvm::DenseMap<GlobalDecl, int64_t> MethodVTableIndicesTy;
369  MethodVTableIndicesTy MethodVTableIndices;
370 
371  typedef llvm::DenseMap<const CXXRecordDecl *,
372  std::unique_ptr<const VTableLayout>>
373  VTableLayoutMapTy;
374  VTableLayoutMapTy VTableLayouts;
375 
376  typedef std::pair<const CXXRecordDecl *,
377  const CXXRecordDecl *> ClassPairTy;
378 
379  /// vtable offsets for offsets of virtual bases of a class.
380  ///
381  /// Contains the vtable offset (relative to the address point) in chars
382  /// where the offsets for virtual bases of a class are stored.
383  typedef llvm::DenseMap<ClassPairTy, CharUnits>
384  VirtualBaseClassOffsetOffsetsMapTy;
385  VirtualBaseClassOffsetOffsetsMapTy VirtualBaseClassOffsetOffsets;
386 
387  void computeVTableRelatedInformation(const CXXRecordDecl *RD) override;
388 
389 public:
391  /// Components in the vtable are pointers to other structs/functions.
393 
394  /// Components in the vtable are relative offsets between the vtable and the
395  /// other structs/functions.
397  };
398 
400  VTableComponentLayout ComponentLayout = Pointer);
401  ~ItaniumVTableContext() override;
402 
404  computeVTableRelatedInformation(RD);
405  assert(VTableLayouts.count(RD) && "No layout for this record decl!");
406 
407  return *VTableLayouts[RD];
408  }
409 
410  std::unique_ptr<VTableLayout> createConstructionVTableLayout(
411  const CXXRecordDecl *MostDerivedClass, CharUnits MostDerivedClassOffset,
412  bool MostDerivedClassIsVirtual, const CXXRecordDecl *LayoutClass);
413 
414  /// Locate a virtual function in the vtable.
415  ///
416  /// Return the index (relative to the vtable address point) where the
417  /// function pointer for the given virtual function is stored.
419 
420  /// Return the offset in chars (relative to the vtable address point) where
421  /// the offset of the virtual base that contains the given base is stored,
422  /// otherwise, if no virtual base contains the given class, return 0.
423  ///
424  /// Base must be a virtual base class or an unambiguous base.
426  const CXXRecordDecl *VBase);
427 
428  static bool classof(const VTableContextBase *VT) {
429  return !VT->isMicrosoft();
430  }
431 
433  return ComponentLayout;
434  }
435 
436  bool isPointerLayout() const { return ComponentLayout == Pointer; }
437  bool isRelativeLayout() const { return ComponentLayout == Relative; }
438 
439 private:
440  VTableComponentLayout ComponentLayout;
441 };
442 
443 /// Holds information about the inheritance path to a virtual base or function
444 /// table pointer. A record may contain as many vfptrs or vbptrs as there are
445 /// base subobjects.
446 struct VPtrInfo {
448 
451 
452  /// This is the most derived class that has this vptr at offset zero. When
453  /// single inheritance is used, this is always the most derived class. If
454  /// multiple inheritance is used, it may be any direct or indirect base.
456 
457  /// This is the class that introduced the vptr by declaring new virtual
458  /// methods or virtual bases.
460 
461  /// IntroducingObject is at this offset from its containing complete object or
462  /// virtual base.
464 
465  /// The bases from the inheritance path that got used to mangle the vbtable
466  /// name. This is not really a full path like a CXXBasePath. It holds the
467  /// subset of records that need to be mangled into the vbtable symbol name in
468  /// order to get a unique name.
470 
471  /// The next base to push onto the mangled path if this path is ambiguous in a
472  /// derived class. If it's null, then it's already been pushed onto the path.
474 
475  /// The set of possibly indirect vbases that contain this vbtable. When a
476  /// derived class indirectly inherits from the same vbase twice, we only keep
477  /// vtables and their paths from the first instance.
479 
480  /// This holds the base classes path from the complete type to the first base
481  /// with the given vfptr offset, in the base-to-derived order. Only used for
482  /// vftables.
484 
485  /// Static offset from the top of the most derived class to this vfptr,
486  /// including any virtual base offset. Only used for vftables.
488 
489  /// The vptr is stored inside the non-virtual component of this virtual base.
491  return ContainingVBases.empty() ? nullptr : ContainingVBases.front();
492  }
493 };
494 
496 
497 /// All virtual base related information about a given record decl. Includes
498 /// information on all virtual base tables and the path components that are used
499 /// to mangle them.
501  /// A map from virtual base to vbtable index for doing a conversion from the
502  /// the derived class to the a base.
503  llvm::DenseMap<const CXXRecordDecl *, unsigned> VBTableIndices;
504 
505  /// Information on all virtual base tables used when this record is the most
506  /// derived class.
508 };
509 
511  /// If nonzero, holds the vbtable index of the virtual base with the vfptr.
513 
514  /// If nonnull, holds the last vbase which contains the vfptr that the
515  /// method definition is adjusted to.
517 
518  /// This is the offset of the vfptr from the start of the last vbase, or the
519  /// complete type if there are no virtual bases.
521 
522  /// Method's index in the vftable.
524 
526  : VBTableIndex(0), VBase(nullptr), VFPtrOffset(CharUnits::Zero()),
527  Index(0) {}
528 
532  Index(Index) {}
533 
534  bool operator<(const MethodVFTableLocation &other) const {
535  if (VBTableIndex != other.VBTableIndex) {
536  assert(VBase != other.VBase);
537  return VBTableIndex < other.VBTableIndex;
538  }
539  return std::tie(VFPtrOffset, Index) <
540  std::tie(other.VFPtrOffset, other.Index);
541  }
542 };
543 
545 public:
546 
547 private:
548  ASTContext &Context;
549 
550  typedef llvm::DenseMap<GlobalDecl, MethodVFTableLocation>
551  MethodVFTableLocationsTy;
552  MethodVFTableLocationsTy MethodVFTableLocations;
553 
554  typedef llvm::DenseMap<const CXXRecordDecl *, std::unique_ptr<VPtrInfoVector>>
555  VFPtrLocationsMapTy;
556  VFPtrLocationsMapTy VFPtrLocations;
557 
558  typedef std::pair<const CXXRecordDecl *, CharUnits> VFTableIdTy;
559  typedef llvm::DenseMap<VFTableIdTy, std::unique_ptr<const VTableLayout>>
560  VFTableLayoutMapTy;
561  VFTableLayoutMapTy VFTableLayouts;
562 
563  llvm::DenseMap<const CXXRecordDecl *, std::unique_ptr<VirtualBaseInfo>>
564  VBaseInfo;
565 
566  void computeVTableRelatedInformation(const CXXRecordDecl *RD) override;
567 
568  void dumpMethodLocations(const CXXRecordDecl *RD,
569  const MethodVFTableLocationsTy &NewMethods,
570  raw_ostream &);
571 
572  const VirtualBaseInfo &
573  computeVBTableRelatedInformation(const CXXRecordDecl *RD);
574 
575  void computeVTablePaths(bool ForVBTables, const CXXRecordDecl *RD,
576  VPtrInfoVector &Paths);
577 
578 public:
580  : VTableContextBase(/*MS=*/true), Context(Context) {}
581 
582  ~MicrosoftVTableContext() override;
583 
584  const VPtrInfoVector &getVFPtrOffsets(const CXXRecordDecl *RD);
585 
587  CharUnits VFPtrOffset);
588 
590 
592  // Complete destructors don't have a slot in a vftable, so no thunks needed.
593  if (isa<CXXDestructorDecl>(GD.getDecl()) &&
594  GD.getDtorType() == Dtor_Complete)
595  return nullptr;
597  }
598 
599  /// Returns the index of VBase in the vbtable of Derived.
600  /// VBase must be a morally virtual base of Derived.
601  /// The vbtable is an array of i32 offsets. The first entry is a self entry,
602  /// and the rest are offsets from the vbptr to virtual bases.
603  unsigned getVBTableIndex(const CXXRecordDecl *Derived,
604  const CXXRecordDecl *VBase);
605 
607 
608  static bool classof(const VTableContextBase *VT) { return VT->isMicrosoft(); }
609 };
610 
611 } // namespace clang
612 
613 #endif
Enums/classes describing ABI related information about constructors, destructors and thunks.
unsigned Offset
Definition: Format.cpp:2978
Enums/classes describing THUNK related information about constructors, destructors and thunks.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:185
Represents a C++ destructor within a class.
Definition: DeclCXX.h:2799
Represents a static or instance method of a struct/union/class.
Definition: DeclCXX.h:2060
const CXXRecordDecl * getParent() const
Return the parent of this method declaration, which is the class in which this method is defined.
Definition: DeclCXX.h:2186
Represents a C++ struct/union/class.
Definition: DeclCXX.h:258
CharUnits - This is an opaque type for sizes expressed in character units.
Definition: CharUnits.h:38
static CharUnits fromQuantity(QuantityType Quantity)
fromQuantity - Construct a CharUnits quantity from a raw integer type.
Definition: CharUnits.h:63
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
Definition: DeclBase.h:968
GlobalDecl - represents a global declaration.
Definition: GlobalDecl.h:56
const Decl * getDecl() const
Definition: GlobalDecl.h:103
CXXDtorType getDtorType() const
Definition: GlobalDecl.h:110
@ Relative
Components in the vtable are relative offsets between the vtable and the other structs/functions.
@ Pointer
Components in the vtable are pointers to other structs/functions.
VTableComponentLayout getVTableComponentLayout() const
uint64_t getMethodVTableIndex(GlobalDecl GD)
Locate a virtual function in the vtable.
std::unique_ptr< VTableLayout > createConstructionVTableLayout(const CXXRecordDecl *MostDerivedClass, CharUnits MostDerivedClassOffset, bool MostDerivedClassIsVirtual, const CXXRecordDecl *LayoutClass)
CharUnits getVirtualBaseOffsetOffset(const CXXRecordDecl *RD, const CXXRecordDecl *VBase)
Return the offset in chars (relative to the vtable address point) where the offset of the virtual bas...
ItaniumVTableContext(ASTContext &Context, VTableComponentLayout ComponentLayout=Pointer)
const VTableLayout & getVTableLayout(const CXXRecordDecl *RD)
static bool classof(const VTableContextBase *VT)
static bool classof(const VTableContextBase *VT)
MicrosoftVTableContext(ASTContext &Context)
unsigned getVBTableIndex(const CXXRecordDecl *Derived, const CXXRecordDecl *VBase)
Returns the index of VBase in the vbtable of Derived.
const VPtrInfoVector & enumerateVBTables(const CXXRecordDecl *RD)
MethodVFTableLocation getMethodVFTableLocation(GlobalDecl GD)
const VPtrInfoVector & getVFPtrOffsets(const CXXRecordDecl *RD)
const VTableLayout & getVFTableLayout(const CXXRecordDecl *RD, CharUnits VFPtrOffset)
const ThunkInfoVectorTy * getThunkInfo(GlobalDecl GD) override
Represents a single component in a vtable.
Definition: VTableBuilder.h:30
static VTableComponent MakeCompleteDtor(const CXXDestructorDecl *DD)
Definition: VTableBuilder.h:79
static VTableComponent MakeRTTI(const CXXRecordDecl *RD)
Definition: VTableBuilder.h:67
GlobalDecl getGlobalDecl() const
static VTableComponent MakeOffsetToTop(CharUnits Offset)
Definition: VTableBuilder.h:63
bool isUsedFunctionPointerKind() const
bool isDestructorKind() const
CharUnits getVBaseOffset() const
static VTableComponent MakeUnusedFunction(const CXXMethodDecl *MD)
Definition: VTableBuilder.h:89
Kind getKind() const
Get the kind of this vtable component.
Definition: VTableBuilder.h:97
static VTableComponent MakeFunction(const CXXMethodDecl *MD)
Definition: VTableBuilder.h:71
@ CK_DeletingDtorPointer
A pointer to the deleting destructor.
Definition: VTableBuilder.h:43
@ CK_UnusedFunctionPointer
An entry that is never used.
Definition: VTableBuilder.h:50
@ CK_CompleteDtorPointer
A pointer to the complete destructor.
Definition: VTableBuilder.h:40
static VTableComponent MakeVBaseOffset(CharUnits Offset)
Definition: VTableBuilder.h:59
static VTableComponent MakeDeletingDtor(const CXXDestructorDecl *DD)
Definition: VTableBuilder.h:84
const CXXRecordDecl * getRTTIDecl() const
const CXXMethodDecl * getFunctionDecl() const
bool isFunctionPointerKind() const
const CXXDestructorDecl * getDestructorDecl() const
CharUnits getOffsetToTop() const
static VTableComponent MakeVCallOffset(CharUnits Offset)
Definition: VTableBuilder.h:55
CharUnits getVCallOffset() const
const CXXMethodDecl * getUnusedFunctionDecl() const
static bool hasVtableSlot(const CXXMethodDecl *MD)
Determine whether this function should be assigned a vtable slot.
virtual void computeVTableRelatedInformation(const CXXRecordDecl *RD)=0
Compute and store all vtable related information (vtable layout, vbase offset offsets,...
virtual const ThunkInfoVectorTy * getThunkInfo(GlobalDecl GD)
SmallVector< ThunkInfo, 1 > ThunkInfoVectorTy
llvm::DenseMap< const CXXMethodDecl *, ThunkInfoVectorTy > ThunksMapTy
ThunksMapTy Thunks
Contains all thunks that a given method decl will need.
size_t getVTableOffset(size_t i) const
llvm::SmallVector< unsigned, 4 > AddressPointsIndexMapTy
ArrayRef< VTableThunkTy > vtable_thunks() const
ArrayRef< VTableComponent > vtable_components() const
VTableLayout(ArrayRef< size_t > VTableIndices, ArrayRef< VTableComponent > VTableComponents, ArrayRef< VTableThunkTy > VTableThunks, const AddressPointsMapTy &AddressPoints)
const AddressPointsIndexMapTy & getAddressPointIndices() const
llvm::DenseMap< BaseSubobject, AddressPointLocation > AddressPointsMapTy
const AddressPointsMapTy & getAddressPoints() const
AddressPointLocation getAddressPoint(BaseSubobject Base) const
std::pair< uint64_t, ThunkInfo > VTableThunkTy
size_t getNumVTables() const
size_t getVTableSize(size_t i) const
The JSON file list parser is used to communicate input to InstallAPI.
SmallVector< std::unique_ptr< VPtrInfo >, 2 > VPtrInfoVector
@ Dtor_Complete
Complete object dtor.
Definition: ABI.h:35
@ Dtor_Deleting
Deleting dtor.
Definition: ABI.h:34
unsigned long uint64_t
long int64_t
__UINTPTR_TYPE__ uintptr_t
An unsigned integer type with the property that any valid pointer to void can be converted to this ty...
#define true
Definition: stdbool.h:25
bool operator<(const MethodVFTableLocation &other) const
const CXXRecordDecl * VBase
If nonnull, holds the last vbase which contains the vfptr that the method definition is adjusted to.
MethodVFTableLocation(uint64_t VBTableIndex, const CXXRecordDecl *VBase, CharUnits VFPtrOffset, uint64_t Index)
CharUnits VFPtrOffset
This is the offset of the vfptr from the start of the last vbase, or the complete type if there are n...
uint64_t VBTableIndex
If nonzero, holds the vbtable index of the virtual base with the vfptr.
uint64_t Index
Method's index in the vftable.
Holds information about the inheritance path to a virtual base or function table pointer.
CharUnits NonVirtualOffset
IntroducingObject is at this offset from its containing complete object or virtual base.
CharUnits FullOffsetInMDC
Static offset from the top of the most derived class to this vfptr, including any virtual base offset...
SmallVector< const CXXRecordDecl *, 1 > BasePath
VPtrInfo(const CXXRecordDecl *RD)
const CXXRecordDecl * getVBaseWithVPtr() const
The vptr is stored inside the non-virtual component of this virtual base.
BasePath ContainingVBases
The set of possibly indirect vbases that contain this vbtable.
const CXXRecordDecl * IntroducingObject
This is the class that introduced the vptr by declaring new virtual methods or virtual bases.
BasePath MangledPath
The bases from the inheritance path that got used to mangle the vbtable name.
const CXXRecordDecl * NextBaseToMangle
The next base to push onto the mangled path if this path is ambiguous in a derived class.
BasePath PathToIntroducingObject
This holds the base classes path from the complete type to the first base with the given vfptr offset...
const CXXRecordDecl * ObjectWithVPtr
This is the most derived class that has this vptr at offset zero.
All virtual base related information about a given record decl.
VPtrInfoVector VBPtrPaths
Information on all virtual base tables used when this record is the most derived class.
llvm::DenseMap< const CXXRecordDecl *, unsigned > VBTableIndices
A map from virtual base to vbtable index for doing a conversion from the the derived class to the a b...