RecordLayout.cpp 3.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091
  1. //===- RecordLayout.cpp - Layout information for a struct/union -----------===//
  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 file defines the RecordLayout interface.
  10. //
  11. //===----------------------------------------------------------------------===//
  12. #include "clang/AST/RecordLayout.h"
  13. #include "clang/AST/ASTContext.h"
  14. #include "clang/Basic/TargetCXXABI.h"
  15. #include "clang/Basic/TargetInfo.h"
  16. #include <cassert>
  17. using namespace clang;
  18. void ASTRecordLayout::Destroy(ASTContext &Ctx) {
  19. if (CXXInfo) {
  20. CXXInfo->~CXXRecordLayoutInfo();
  21. Ctx.Deallocate(CXXInfo);
  22. }
  23. this->~ASTRecordLayout();
  24. Ctx.Deallocate(this);
  25. }
  26. ASTRecordLayout::ASTRecordLayout(const ASTContext &Ctx, CharUnits size,
  27. CharUnits alignment,
  28. CharUnits preferredAlignment,
  29. CharUnits unadjustedAlignment,
  30. CharUnits requiredAlignment,
  31. CharUnits datasize,
  32. ArrayRef<uint64_t> fieldoffsets)
  33. : Size(size), DataSize(datasize), Alignment(alignment),
  34. PreferredAlignment(preferredAlignment),
  35. UnadjustedAlignment(unadjustedAlignment),
  36. RequiredAlignment(requiredAlignment) {
  37. FieldOffsets.append(Ctx, fieldoffsets.begin(), fieldoffsets.end());
  38. }
  39. // Constructor for C++ records.
  40. ASTRecordLayout::ASTRecordLayout(
  41. const ASTContext &Ctx, CharUnits size, CharUnits alignment,
  42. CharUnits preferredAlignment, CharUnits unadjustedAlignment,
  43. CharUnits requiredAlignment, bool hasOwnVFPtr, bool hasExtendableVFPtr,
  44. CharUnits vbptroffset, CharUnits datasize, ArrayRef<uint64_t> fieldoffsets,
  45. CharUnits nonvirtualsize, CharUnits nonvirtualalignment,
  46. CharUnits preferrednvalignment, CharUnits SizeOfLargestEmptySubobject,
  47. const CXXRecordDecl *PrimaryBase, bool IsPrimaryBaseVirtual,
  48. const CXXRecordDecl *BaseSharingVBPtr, bool EndsWithZeroSizedObject,
  49. bool LeadsWithZeroSizedBase, const BaseOffsetsMapTy &BaseOffsets,
  50. const VBaseOffsetsMapTy &VBaseOffsets)
  51. : Size(size), DataSize(datasize), Alignment(alignment),
  52. PreferredAlignment(preferredAlignment),
  53. UnadjustedAlignment(unadjustedAlignment),
  54. RequiredAlignment(requiredAlignment),
  55. CXXInfo(new (Ctx) CXXRecordLayoutInfo) {
  56. FieldOffsets.append(Ctx, fieldoffsets.begin(), fieldoffsets.end());
  57. CXXInfo->PrimaryBase.setPointer(PrimaryBase);
  58. CXXInfo->PrimaryBase.setInt(IsPrimaryBaseVirtual);
  59. CXXInfo->NonVirtualSize = nonvirtualsize;
  60. CXXInfo->NonVirtualAlignment = nonvirtualalignment;
  61. CXXInfo->PreferredNVAlignment = preferrednvalignment;
  62. CXXInfo->SizeOfLargestEmptySubobject = SizeOfLargestEmptySubobject;
  63. CXXInfo->BaseOffsets = BaseOffsets;
  64. CXXInfo->VBaseOffsets = VBaseOffsets;
  65. CXXInfo->HasOwnVFPtr = hasOwnVFPtr;
  66. CXXInfo->VBPtrOffset = vbptroffset;
  67. CXXInfo->HasExtendableVFPtr = hasExtendableVFPtr;
  68. CXXInfo->BaseSharingVBPtr = BaseSharingVBPtr;
  69. CXXInfo->EndsWithZeroSizedObject = EndsWithZeroSizedObject;
  70. CXXInfo->LeadsWithZeroSizedBase = LeadsWithZeroSizedBase;
  71. #ifndef NDEBUG
  72. if (const CXXRecordDecl *PrimaryBase = getPrimaryBase()) {
  73. if (isPrimaryBaseVirtual()) {
  74. if (Ctx.getTargetInfo().getCXXABI().hasPrimaryVBases()) {
  75. assert(getVBaseClassOffset(PrimaryBase).isZero() &&
  76. "Primary virtual base must be at offset 0!");
  77. }
  78. } else {
  79. assert(getBaseClassOffset(PrimaryBase).isZero() &&
  80. "Primary base must be at offset 0!");
  81. }
  82. }
  83. #endif
  84. }