]> CyberLeo.Net >> Repos - FreeBSD/releng/10.2.git/blob - contrib/llvm/tools/clang/include/clang/AST/Mangle.h
- Copy stable/10@285827 to releng/10.2 in preparation for 10.2-RC1
[FreeBSD/releng/10.2.git] / contrib / llvm / tools / clang / include / clang / AST / Mangle.h
1 //===--- Mangle.h - Mangle C++ Names ----------------------------*- C++ -*-===//
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 // Defines the C++ name mangling interface.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #ifndef LLVM_CLANG_AST_MANGLE_H
15 #define LLVM_CLANG_AST_MANGLE_H
16
17 #include "clang/AST/Type.h"
18 #include "clang/Basic/ABI.h"
19 #include "llvm/ADT/DenseMap.h"
20 #include "llvm/ADT/SmallString.h"
21 #include "llvm/ADT/StringRef.h"
22 #include "llvm/Support/Casting.h"
23 #include "llvm/Support/raw_ostream.h"
24
25 namespace clang {
26   class ASTContext;
27   class BlockDecl;
28   class CXXConstructorDecl;
29   class CXXDestructorDecl;
30   class CXXMethodDecl;
31   class FunctionDecl;
32   class NamedDecl;
33   class ObjCMethodDecl;
34   class VarDecl;
35   struct ThisAdjustment;
36   struct ThunkInfo;
37
38 /// MangleBuffer - a convenient class for storing a name which is
39 /// either the result of a mangling or is a constant string with
40 /// external memory ownership.
41 class MangleBuffer {
42 public:
43   void setString(StringRef Ref) {
44     String = Ref;
45   }
46
47   SmallVectorImpl<char> &getBuffer() {
48     return Buffer;
49   }
50
51   StringRef getString() const {
52     if (!String.empty()) return String;
53     return Buffer.str();
54   }
55
56   operator StringRef() const {
57     return getString();
58   }
59
60 private:
61   StringRef String;
62   SmallString<256> Buffer;
63 };
64
65 /// MangleContext - Context for tracking state which persists across multiple
66 /// calls to the C++ name mangler.
67 class MangleContext {
68 public:
69   enum ManglerKind {
70     MK_Itanium,
71     MK_Microsoft
72   };
73
74 private:
75   virtual void anchor();
76
77   ASTContext &Context;
78   DiagnosticsEngine &Diags;
79   const ManglerKind Kind;
80
81   llvm::DenseMap<const BlockDecl*, unsigned> GlobalBlockIds;
82   llvm::DenseMap<const BlockDecl*, unsigned> LocalBlockIds;
83
84 public:
85   ManglerKind getKind() const { return Kind; }
86
87   explicit MangleContext(ASTContext &Context,
88                          DiagnosticsEngine &Diags,
89                          ManglerKind Kind)
90       : Context(Context), Diags(Diags), Kind(Kind) {}
91
92   virtual ~MangleContext() { }
93
94   ASTContext &getASTContext() const { return Context; }
95
96   DiagnosticsEngine &getDiags() const { return Diags; }
97
98   virtual void startNewFunction() { LocalBlockIds.clear(); }
99   
100   unsigned getBlockId(const BlockDecl *BD, bool Local) {
101     llvm::DenseMap<const BlockDecl *, unsigned> &BlockIds
102       = Local? LocalBlockIds : GlobalBlockIds;
103     std::pair<llvm::DenseMap<const BlockDecl *, unsigned>::iterator, bool>
104       Result = BlockIds.insert(std::make_pair(BD, BlockIds.size()));
105     return Result.first->second;
106   }
107   
108   /// @name Mangler Entry Points
109   /// @{
110
111   bool shouldMangleDeclName(const NamedDecl *D);
112   virtual bool shouldMangleCXXName(const NamedDecl *D) = 0;
113
114   // FIXME: consider replacing raw_ostream & with something like SmallString &.
115   void mangleName(const NamedDecl *D, raw_ostream &);
116   virtual void mangleCXXName(const NamedDecl *D, raw_ostream &) = 0;
117   virtual void mangleThunk(const CXXMethodDecl *MD,
118                           const ThunkInfo &Thunk,
119                           raw_ostream &) = 0;
120   virtual void mangleCXXDtorThunk(const CXXDestructorDecl *DD, CXXDtorType Type,
121                                   const ThisAdjustment &ThisAdjustment,
122                                   raw_ostream &) = 0;
123   virtual void mangleReferenceTemporary(const VarDecl *D,
124                                         raw_ostream &) = 0;
125   virtual void mangleCXXRTTI(QualType T, raw_ostream &) = 0;
126   virtual void mangleCXXRTTIName(QualType T, raw_ostream &) = 0;
127   virtual void mangleCXXCtor(const CXXConstructorDecl *D, CXXCtorType Type,
128                              raw_ostream &) = 0;
129   virtual void mangleCXXDtor(const CXXDestructorDecl *D, CXXDtorType Type,
130                              raw_ostream &) = 0;
131
132   void mangleGlobalBlock(const BlockDecl *BD,
133                          const NamedDecl *ID,
134                          raw_ostream &Out);
135   void mangleCtorBlock(const CXXConstructorDecl *CD, CXXCtorType CT,
136                        const BlockDecl *BD, raw_ostream &Out);
137   void mangleDtorBlock(const CXXDestructorDecl *CD, CXXDtorType DT,
138                        const BlockDecl *BD, raw_ostream &Out);
139   void mangleBlock(const DeclContext *DC, const BlockDecl *BD,
140                    raw_ostream &Out);
141
142   void mangleObjCMethodName(const ObjCMethodDecl *MD, raw_ostream &);
143
144   virtual void mangleStaticGuardVariable(const VarDecl *D, raw_ostream &) = 0;
145
146   virtual void mangleDynamicInitializer(const VarDecl *D, raw_ostream &) = 0;
147
148   virtual void mangleDynamicAtExitDestructor(const VarDecl *D,
149                                              raw_ostream &) = 0;
150
151   /// Generates a unique string for an externally visible type for use with TBAA
152   /// or type uniquing.
153   /// TODO: Extend this to internal types by generating names that are unique
154   /// across translation units so it can be used with LTO.
155   virtual void mangleTypeName(QualType T, raw_ostream &) = 0;
156
157   /// @}
158 };
159
160 class ItaniumMangleContext : public MangleContext {
161 public:
162   explicit ItaniumMangleContext(ASTContext &C, DiagnosticsEngine &D)
163       : MangleContext(C, D, MK_Itanium) {}
164
165   virtual void mangleCXXVTable(const CXXRecordDecl *RD, raw_ostream &) = 0;
166   virtual void mangleCXXVTT(const CXXRecordDecl *RD, raw_ostream &) = 0;
167   virtual void mangleCXXCtorVTable(const CXXRecordDecl *RD, int64_t Offset,
168                                    const CXXRecordDecl *Type,
169                                    raw_ostream &) = 0;
170   virtual void mangleItaniumThreadLocalInit(const VarDecl *D,
171                                             raw_ostream &) = 0;
172   virtual void mangleItaniumThreadLocalWrapper(const VarDecl *D,
173                                                raw_ostream &) = 0;
174
175   static bool classof(const MangleContext *C) {
176     return C->getKind() == MK_Itanium;
177   }
178
179   static ItaniumMangleContext *create(ASTContext &Context,
180                                       DiagnosticsEngine &Diags);
181 };
182
183 class MicrosoftMangleContext : public MangleContext {
184 public:
185   explicit MicrosoftMangleContext(ASTContext &C, DiagnosticsEngine &D)
186       : MangleContext(C, D, MK_Microsoft) {}
187
188   /// \brief Mangle vftable symbols.  Only a subset of the bases along the path
189   /// to the vftable are included in the name.  It's up to the caller to pick
190   /// them correctly.
191   virtual void mangleCXXVFTable(const CXXRecordDecl *Derived,
192                                 ArrayRef<const CXXRecordDecl *> BasePath,
193                                 raw_ostream &Out) = 0;
194
195   /// \brief Mangle vbtable symbols.  Only a subset of the bases along the path
196   /// to the vbtable are included in the name.  It's up to the caller to pick
197   /// them correctly.
198   virtual void mangleCXXVBTable(const CXXRecordDecl *Derived,
199                                 ArrayRef<const CXXRecordDecl *> BasePath,
200                                 raw_ostream &Out) = 0;
201
202   virtual void mangleVirtualMemPtrThunk(const CXXMethodDecl *MD,
203                                         uint64_t OffsetInVFTable,
204                                         raw_ostream &) = 0;
205
206   static bool classof(const MangleContext *C) {
207     return C->getKind() == MK_Microsoft;
208   }
209
210   static MicrosoftMangleContext *create(ASTContext &Context,
211                                         DiagnosticsEngine &Diags);
212 };
213 }
214
215 #endif