clang  10.0.0svn
MicrosoftCXXABI.cpp
Go to the documentation of this file.
1 //===------- MicrosoftCXXABI.cpp - AST support for the Microsoft C++ ABI --===//
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 provides C++ AST support targeting the Microsoft Visual C++
10 // ABI.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #include "CXXABI.h"
15 #include "clang/AST/ASTContext.h"
16 #include "clang/AST/Attr.h"
17 #include "clang/AST/DeclCXX.h"
19 #include "clang/AST/RecordLayout.h"
20 #include "clang/AST/Type.h"
21 #include "clang/Basic/TargetInfo.h"
22 
23 using namespace clang;
24 
25 namespace {
26 
27 /// Numbers things which need to correspond across multiple TUs.
28 /// Typically these are things like static locals, lambdas, or blocks.
29 class MicrosoftNumberingContext : public MangleNumberingContext {
30  llvm::DenseMap<const Type *, unsigned> ManglingNumbers;
31  unsigned LambdaManglingNumber;
32  unsigned StaticLocalNumber;
33  unsigned StaticThreadlocalNumber;
34 
35 public:
36  MicrosoftNumberingContext()
37  : MangleNumberingContext(), LambdaManglingNumber(0),
38  StaticLocalNumber(0), StaticThreadlocalNumber(0) {}
39 
40  unsigned getManglingNumber(const CXXMethodDecl *CallOperator) override {
41  return ++LambdaManglingNumber;
42  }
43 
44  unsigned getManglingNumber(const BlockDecl *BD) override {
45  const Type *Ty = nullptr;
46  return ++ManglingNumbers[Ty];
47  }
48 
49  unsigned getStaticLocalNumber(const VarDecl *VD) override {
50  if (VD->getTLSKind())
51  return ++StaticThreadlocalNumber;
52  return ++StaticLocalNumber;
53  }
54 
55  unsigned getManglingNumber(const VarDecl *VD,
56  unsigned MSLocalManglingNumber) override {
57  return MSLocalManglingNumber;
58  }
59 
60  unsigned getManglingNumber(const TagDecl *TD,
61  unsigned MSLocalManglingNumber) override {
62  return MSLocalManglingNumber;
63  }
64 };
65 
66 class MicrosoftCXXABI : public CXXABI {
67  ASTContext &Context;
68  llvm::SmallDenseMap<CXXRecordDecl *, CXXConstructorDecl *> RecordToCopyCtor;
69 
70  llvm::SmallDenseMap<TagDecl *, DeclaratorDecl *>
71  UnnamedTagDeclToDeclaratorDecl;
72  llvm::SmallDenseMap<TagDecl *, TypedefNameDecl *>
73  UnnamedTagDeclToTypedefNameDecl;
74 
75 public:
76  MicrosoftCXXABI(ASTContext &Ctx) : Context(Ctx) { }
77 
78  MemberPointerInfo
79  getMemberPointerInfo(const MemberPointerType *MPT) const override;
80 
81  CallingConv getDefaultMethodCallConv(bool isVariadic) const override {
82  if (!isVariadic &&
83  Context.getTargetInfo().getTriple().getArch() == llvm::Triple::x86)
84  return CC_X86ThisCall;
85  return Context.getTargetInfo().getDefaultCallingConv();
86  }
87 
88  bool isNearlyEmpty(const CXXRecordDecl *RD) const override {
89  llvm_unreachable("unapplicable to the MS ABI");
90  }
91 
92  const CXXConstructorDecl *
93  getCopyConstructorForExceptionObject(CXXRecordDecl *RD) override {
94  return RecordToCopyCtor[RD];
95  }
96 
97  void
98  addCopyConstructorForExceptionObject(CXXRecordDecl *RD,
99  CXXConstructorDecl *CD) override {
100  assert(CD != nullptr);
101  assert(RecordToCopyCtor[RD] == nullptr || RecordToCopyCtor[RD] == CD);
102  RecordToCopyCtor[RD] = CD;
103  }
104 
105  void addTypedefNameForUnnamedTagDecl(TagDecl *TD,
106  TypedefNameDecl *DD) override {
107  TD = TD->getCanonicalDecl();
108  DD = DD->getCanonicalDecl();
109  TypedefNameDecl *&I = UnnamedTagDeclToTypedefNameDecl[TD];
110  if (!I)
111  I = DD;
112  }
113 
114  TypedefNameDecl *getTypedefNameForUnnamedTagDecl(const TagDecl *TD) override {
115  return UnnamedTagDeclToTypedefNameDecl.lookup(
116  const_cast<TagDecl *>(TD->getCanonicalDecl()));
117  }
118 
119  void addDeclaratorForUnnamedTagDecl(TagDecl *TD,
120  DeclaratorDecl *DD) override {
121  TD = TD->getCanonicalDecl();
122  DD = cast<DeclaratorDecl>(DD->getCanonicalDecl());
123  DeclaratorDecl *&I = UnnamedTagDeclToDeclaratorDecl[TD];
124  if (!I)
125  I = DD;
126  }
127 
128  DeclaratorDecl *getDeclaratorForUnnamedTagDecl(const TagDecl *TD) override {
129  return UnnamedTagDeclToDeclaratorDecl.lookup(
130  const_cast<TagDecl *>(TD->getCanonicalDecl()));
131  }
132 
133  std::unique_ptr<MangleNumberingContext>
134  createMangleNumberingContext() const override {
135  return std::make_unique<MicrosoftNumberingContext>();
136  }
137 };
138 }
139 
140 // getNumBases() seems to only give us the number of direct bases, and not the
141 // total. This function tells us if we inherit from anybody that uses MI, or if
142 // we have a non-primary base class, which uses the multiple inheritance model.
144  while (RD->getNumBases() > 0) {
145  if (RD->getNumBases() > 1)
146  return true;
147  assert(RD->getNumBases() == 1);
148  const CXXRecordDecl *Base =
150  if (RD->isPolymorphic() && !Base->isPolymorphic())
151  return true;
152  RD = Base;
153  }
154  return false;
155 }
156 
157 MSInheritanceAttr::Spelling CXXRecordDecl::calculateInheritanceModel() const {
158  if (!hasDefinition() || isParsingBaseSpecifiers())
159  return MSInheritanceAttr::Keyword_unspecified_inheritance;
160  if (getNumVBases() > 0)
161  return MSInheritanceAttr::Keyword_virtual_inheritance;
163  return MSInheritanceAttr::Keyword_multiple_inheritance;
164  return MSInheritanceAttr::Keyword_single_inheritance;
165 }
166 
167 MSInheritanceAttr::Spelling
169  MSInheritanceAttr *IA = getAttr<MSInheritanceAttr>();
170  assert(IA && "Expected MSInheritanceAttr on the CXXRecordDecl!");
171  return IA->getSemanticSpelling();
172 }
173 
174 MSVtorDispAttr::Mode CXXRecordDecl::getMSVtorDispMode() const {
175  if (MSVtorDispAttr *VDA = getAttr<MSVtorDispAttr>())
176  return VDA->getVtorDispMode();
177  return MSVtorDispAttr::Mode(getASTContext().getLangOpts().VtorDispMode);
178 }
179 
180 // Returns the number of pointer and integer slots used to represent a member
181 // pointer in the MS C++ ABI.
182 //
183 // Member function pointers have the following general form; however, fields
184 // are dropped as permitted (under the MSVC interpretation) by the inheritance
185 // model of the actual class.
186 //
187 // struct {
188 // // A pointer to the member function to call. If the member function is
189 // // virtual, this will be a thunk that forwards to the appropriate vftable
190 // // slot.
191 // void *FunctionPointerOrVirtualThunk;
192 //
193 // // An offset to add to the address of the vbtable pointer after
194 // // (possibly) selecting the virtual base but before resolving and calling
195 // // the function.
196 // // Only needed if the class has any virtual bases or bases at a non-zero
197 // // offset.
198 // int NonVirtualBaseAdjustment;
199 //
200 // // The offset of the vb-table pointer within the object. Only needed for
201 // // incomplete types.
202 // int VBPtrOffset;
203 //
204 // // An offset within the vb-table that selects the virtual base containing
205 // // the member. Loading from this offset produces a new offset that is
206 // // added to the address of the vb-table pointer to produce the base.
207 // int VirtualBaseAdjustmentOffset;
208 // };
209 static std::pair<unsigned, unsigned>
211  const CXXRecordDecl *RD = MPT->getMostRecentCXXRecordDecl();
212  MSInheritanceAttr::Spelling Inheritance = RD->getMSInheritanceModel();
213  unsigned Ptrs = 0;
214  unsigned Ints = 0;
215  if (MPT->isMemberFunctionPointer())
216  Ptrs = 1;
217  else
218  Ints = 1;
219  if (MSInheritanceAttr::hasNVOffsetField(MPT->isMemberFunctionPointer(),
220  Inheritance))
221  Ints++;
222  if (MSInheritanceAttr::hasVBPtrOffsetField(Inheritance))
223  Ints++;
224  if (MSInheritanceAttr::hasVBTableOffsetField(Inheritance))
225  Ints++;
226  return std::make_pair(Ptrs, Ints);
227 }
228 
229 CXXABI::MemberPointerInfo MicrosoftCXXABI::getMemberPointerInfo(
230  const MemberPointerType *MPT) const {
231  // The nominal struct is laid out with pointers followed by ints and aligned
232  // to a pointer width if any are present and an int width otherwise.
233  const TargetInfo &Target = Context.getTargetInfo();
234  unsigned PtrSize = Target.getPointerWidth(0);
235  unsigned IntSize = Target.getIntWidth();
236 
237  unsigned Ptrs, Ints;
238  std::tie(Ptrs, Ints) = getMSMemberPointerSlots(MPT);
239  MemberPointerInfo MPI;
240  MPI.HasPadding = false;
241  MPI.Width = Ptrs * PtrSize + Ints * IntSize;
242 
243  // When MSVC does x86_32 record layout, it aligns aggregate member pointers to
244  // 8 bytes. However, __alignof usually returns 4 for data memptrs and 8 for
245  // function memptrs.
246  if (Ptrs + Ints > 1 && Target.getTriple().isArch32Bit())
247  MPI.Align = 64;
248  else if (Ptrs)
249  MPI.Align = Target.getPointerAlign(0);
250  else
251  MPI.Align = Target.getIntAlign();
252 
253  if (Target.getTriple().isArch64Bit()) {
254  MPI.Width = llvm::alignTo(MPI.Width, MPI.Align);
255  MPI.HasPadding = MPI.Width != (Ptrs * PtrSize + Ints * IntSize);
256  }
257  return MPI;
258 }
259 
261  return new MicrosoftCXXABI(Ctx);
262 }
263 
Defines the clang::ASTContext interface.
CXXABI * CreateMicrosoftCXXABI(ASTContext &Ctx)
if(T->getSizeExpr()) TRY_TO(TraverseStmt(T -> getSizeExpr()))
unsigned getNumBases() const
Retrieves the number of base classes of this class.
Definition: DeclCXX.h:583
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
Definition: TargetInfo.h:991
C Language Family Type Representation.
The base class of the type hierarchy.
Definition: Type.h:1436
const TargetInfo & getTargetInfo() const
Definition: ASTContext.h:706
Represents a C++ constructor within a class.
Definition: DeclCXX.h:2365
MSInheritanceAttr::Spelling getMSInheritanceModel() const
Returns the inheritance model used for this record.
Represents a variable declaration or definition.
Definition: Decl.h:827
MSInheritanceAttr::Spelling calculateInheritanceModel() const
Calculate what the inheritance model would be for this class.
uint64_t getPointerWidth(unsigned AddrSpace) const
Return the width of pointers on this target, for the specified address space.
Definition: TargetInfo.h:360
unsigned getIntAlign() const
Definition: TargetInfo.h:396
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:160
TypedefNameDecl * getCanonicalDecl() override
Retrieves the canonical declaration of this typedef-name.
Definition: Decl.h:3057
Keeps track of the mangled names of lambda expressions and block literals within a particular context...
base_class_iterator bases_begin()
Definition: DeclCXX.h:596
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
Definition: DeclBase.h:877
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
Definition: Type.cpp:1692
Represents a ValueDecl that came out of a declarator.
Definition: Decl.h:696
Exposes information about the current target.
Definition: TargetInfo.h:163
Represents a block literal declaration, which is like an unnamed FunctionDecl.
Definition: Decl.h:3951
unsigned getIntWidth() const
getIntWidth/Align - Return the size of &#39;signed int&#39; and &#39;unsigned int&#39; for this target, in bits.
Definition: TargetInfo.h:395
virtual CallingConv getDefaultCallingConv() const
Gets the default calling convention for the given target and declaration context. ...
Definition: TargetInfo.h:1260
TLSKind getTLSKind() const
Definition: Decl.cpp:1983
bool isPolymorphic() const
Whether this class is polymorphic (C++ [class.virtual]), which means that the class contains or inher...
Definition: DeclCXX.h:1118
static bool hasDefinition(const ObjCObjectPointerType *ObjPtr)
Implements C++ ABI-specific semantic analysis functions.
Definition: CXXABI.h:29
CallingConv
CallingConv - Specifies the calling convention that a function uses.
Definition: Specifiers.h:265
static bool usesMultipleInheritanceModel(const CXXRecordDecl *RD)
Represents the declaration of a struct/union/class/enum.
Definition: Decl.h:3133
TagDecl * getCanonicalDecl() override
Retrieves the "canonical" declaration of the given declaration.
Definition: Decl.cpp:4061
Represents a static or instance method of a struct/union/class.
Definition: DeclCXX.h:1905
MSVtorDispAttr::Mode getMSVtorDispMode() const
Controls when vtordisps will be emitted if this record is used as a virtual base. ...
Base class for declarations which introduce a typedef-name.
Definition: Decl.h:2985
CXXRecordDecl * getMostRecentCXXRecordDecl() const
Definition: Type.cpp:4149
Dataflow Directional Tag Classes.
A pointer to member type per C++ 8.3.3 - Pointers to members.
Definition: Type.h:2804
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate.h) and friends (in DeclFriend.h).
Represents a C++ struct/union/class.
Definition: DeclCXX.h:255
bool isMemberFunctionPointer() const
Returns true if the member type (i.e.
Definition: Type.h:2828
uint64_t getPointerAlign(unsigned AddrSpace) const
Definition: TargetInfo.h:363
Defines the clang::TargetInfo interface.
static std::pair< unsigned, unsigned > getMSMemberPointerSlots(const MemberPointerType *MPT)
QualType getType() const
Retrieves the type of the base class.
Definition: DeclCXX.h:246