blob: 9cea06187e2f61f7f58d42e431f5b11d25fbd7b5 [file] [log] [blame]
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001//===--- MicrosoftMangle.cpp - Microsoft Visual C++ Name Mangling ---------===//
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// This provides C++ name mangling targeting the Microsoft Visual C++ ABI.
11//
12//===----------------------------------------------------------------------===//
13
14#include "clang/AST/Mangle.h"
15#include "clang/AST/ASTContext.h"
16#include "clang/AST/Attr.h"
17#include "clang/AST/CharUnits.h"
18#include "clang/AST/Decl.h"
19#include "clang/AST/DeclCXX.h"
20#include "clang/AST/DeclObjC.h"
21#include "clang/AST/DeclTemplate.h"
22#include "clang/AST/ExprCXX.h"
23#include "clang/Basic/ABI.h"
24#include "clang/Basic/DiagnosticOptions.h"
Reid Klecknerd6a08d12013-05-14 20:30:42 +000025#include "clang/Basic/TargetInfo.h"
Reid Klecknerf0219cd2013-05-22 17:16:39 +000026#include "llvm/ADT/StringMap.h"
David Majnemer978c5e02013-09-13 09:40:55 +000027#include "llvm/ADT/StringSwitch.h"
Guy Benyei7f92f2d2012-12-18 14:30:41 +000028
29using namespace clang;
30
31namespace {
32
David Majnemercab7dad2013-09-13 09:03:14 +000033/// \brief Retrieve the declaration context that should be used when mangling
34/// the given declaration.
35static const DeclContext *getEffectiveDeclContext(const Decl *D) {
36 // The ABI assumes that lambda closure types that occur within
37 // default arguments live in the context of the function. However, due to
38 // the way in which Clang parses and creates function declarations, this is
39 // not the case: the lambda closure type ends up living in the context
40 // where the function itself resides, because the function declaration itself
41 // had not yet been created. Fix the context here.
42 if (const CXXRecordDecl *RD = dyn_cast<CXXRecordDecl>(D)) {
43 if (RD->isLambda())
44 if (ParmVarDecl *ContextParam =
45 dyn_cast_or_null<ParmVarDecl>(RD->getLambdaContextDecl()))
46 return ContextParam->getDeclContext();
47 }
48
49 // Perform the same check for block literals.
50 if (const BlockDecl *BD = dyn_cast<BlockDecl>(D)) {
51 if (ParmVarDecl *ContextParam =
52 dyn_cast_or_null<ParmVarDecl>(BD->getBlockManglingContextDecl()))
53 return ContextParam->getDeclContext();
54 }
55
56 const DeclContext *DC = D->getDeclContext();
57 if (const CapturedDecl *CD = dyn_cast<CapturedDecl>(DC))
58 return getEffectiveDeclContext(CD);
59
60 return DC;
61}
62
63static const DeclContext *getEffectiveParentContext(const DeclContext *DC) {
64 return getEffectiveDeclContext(cast<Decl>(DC));
65}
66
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +000067static const FunctionDecl *getStructor(const FunctionDecl *fn) {
68 if (const FunctionTemplateDecl *ftd = fn->getPrimaryTemplate())
69 return ftd->getTemplatedDecl();
70
71 return fn;
72}
73
David Majnemer978c5e02013-09-13 09:40:55 +000074// The ABI expects that we would never mangle "typical" user-defined entry
75// points regardless of visibility or freestanding-ness.
76//
77// N.B. This is distinct from asking about "main". "main" has a lot of special
78// rules associated with it in the standard while these user-defined entry
79// points are outside of the purview of the standard. For example, there can be
80// only one definition for "main" in a standards compliant program; however
81// nothing forbids the existence of wmain and WinMain in the same translation
82// unit.
83static bool isUserDefinedEntryPoint(const FunctionDecl *FD) {
84 if (!FD->getIdentifier())
85 return false;
86
87 return llvm::StringSwitch<bool>(FD->getName())
88 .Cases("main", // An ANSI console app
89 "wmain", // A Unicode console App
90 "WinMain", // An ANSI GUI app
91 "wWinMain", // A Unicode GUI app
92 "DllMain", // A DLL
93 true)
94 .Default(false);
95}
96
Guy Benyei7f92f2d2012-12-18 14:30:41 +000097/// MicrosoftCXXNameMangler - Manage the mangling of a single name for the
98/// Microsoft Visual C++ ABI.
99class MicrosoftCXXNameMangler {
100 MangleContext &Context;
101 raw_ostream &Out;
102
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000103 /// The "structor" is the top-level declaration being mangled, if
104 /// that's not a template specialization; otherwise it's the pattern
105 /// for that specialization.
106 const NamedDecl *Structor;
107 unsigned StructorType;
108
Reid Klecknerf0219cd2013-05-22 17:16:39 +0000109 typedef llvm::StringMap<unsigned> BackRefMap;
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000110 BackRefMap NameBackReferences;
111 bool UseNameBackReferences;
112
113 typedef llvm::DenseMap<void*, unsigned> ArgBackRefMap;
114 ArgBackRefMap TypeBackReferences;
115
116 ASTContext &getASTContext() const { return Context.getASTContext(); }
117
Reid Klecknerd6a08d12013-05-14 20:30:42 +0000118 // FIXME: If we add support for __ptr32/64 qualifiers, then we should push
119 // this check into mangleQualifiers().
120 const bool PointersAre64Bit;
121
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000122public:
Peter Collingbourneb70d1c32013-04-25 04:25:40 +0000123 enum QualifierMangleMode { QMM_Drop, QMM_Mangle, QMM_Escape, QMM_Result };
124
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000125 MicrosoftCXXNameMangler(MangleContext &C, raw_ostream &Out_)
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000126 : Context(C), Out(Out_),
127 Structor(0), StructorType(-1),
David Blaikiee7e94c92013-05-14 21:31:46 +0000128 UseNameBackReferences(true),
Reid Klecknerd6a08d12013-05-14 20:30:42 +0000129 PointersAre64Bit(C.getASTContext().getTargetInfo().getPointerWidth(0) ==
David Blaikiee7e94c92013-05-14 21:31:46 +0000130 64) { }
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000131
132 MicrosoftCXXNameMangler(MangleContext &C, raw_ostream &Out_,
133 const CXXDestructorDecl *D, CXXDtorType Type)
134 : Context(C), Out(Out_),
135 Structor(getStructor(D)), StructorType(Type),
David Blaikiee7e94c92013-05-14 21:31:46 +0000136 UseNameBackReferences(true),
Reid Klecknerd6a08d12013-05-14 20:30:42 +0000137 PointersAre64Bit(C.getASTContext().getTargetInfo().getPointerWidth(0) ==
David Blaikiee7e94c92013-05-14 21:31:46 +0000138 64) { }
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000139
140 raw_ostream &getStream() const { return Out; }
141
142 void mangle(const NamedDecl *D, StringRef Prefix = "\01?");
143 void mangleName(const NamedDecl *ND);
David Majnemerc80eb462013-08-13 06:32:20 +0000144 void mangleDeclaration(const NamedDecl *ND);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000145 void mangleFunctionEncoding(const FunctionDecl *FD);
146 void mangleVariableEncoding(const VarDecl *VD);
147 void mangleNumber(int64_t Number);
148 void mangleNumber(const llvm::APSInt &Value);
Peter Collingbourneb70d1c32013-04-25 04:25:40 +0000149 void mangleType(QualType T, SourceRange Range,
150 QualifierMangleMode QMM = QMM_Mangle);
Timur Iskhodzhanov635de282013-07-30 09:46:19 +0000151 void mangleFunctionType(const FunctionType *T, const FunctionDecl *D,
152 bool IsStructor, bool IsInstMethod);
Reid Kleckner942f9fe2013-09-10 20:14:30 +0000153 void manglePostfix(const DeclContext *DC, bool NoFunction = false);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000154
155private:
156 void disableBackReferences() { UseNameBackReferences = false; }
157 void mangleUnqualifiedName(const NamedDecl *ND) {
158 mangleUnqualifiedName(ND, ND->getDeclName());
159 }
160 void mangleUnqualifiedName(const NamedDecl *ND, DeclarationName Name);
161 void mangleSourceName(const IdentifierInfo *II);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000162 void mangleOperatorName(OverloadedOperatorKind OO, SourceLocation Loc);
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000163 void mangleCXXDtorType(CXXDtorType T);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000164 void mangleQualifiers(Qualifiers Quals, bool IsMember);
165 void manglePointerQualifiers(Qualifiers Quals);
166
167 void mangleUnscopedTemplateName(const TemplateDecl *ND);
168 void mangleTemplateInstantiationName(const TemplateDecl *TD,
Reid Klecknerf16216c2013-03-20 01:40:23 +0000169 const TemplateArgumentList &TemplateArgs);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000170 void mangleObjCMethodName(const ObjCMethodDecl *MD);
171 void mangleLocalName(const FunctionDecl *FD);
172
173 void mangleArgumentType(QualType T, SourceRange Range);
174
175 // Declare manglers for every type class.
176#define ABSTRACT_TYPE(CLASS, PARENT)
177#define NON_CANONICAL_TYPE(CLASS, PARENT)
178#define TYPE(CLASS, PARENT) void mangleType(const CLASS##Type *T, \
179 SourceRange Range);
180#include "clang/AST/TypeNodes.def"
181#undef ABSTRACT_TYPE
182#undef NON_CANONICAL_TYPE
183#undef TYPE
184
David Majnemer02c44f02013-08-05 22:26:46 +0000185 void mangleType(const TagDecl *TD);
David Majnemer58e4cd02013-09-11 04:44:30 +0000186 void mangleDecayedArrayType(const ArrayType *T);
Reid Klecknerf21818d2013-06-24 19:21:52 +0000187 void mangleArrayType(const ArrayType *T);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000188 void mangleFunctionClass(const FunctionDecl *FD);
189 void mangleCallingConvention(const FunctionType *T, bool IsInstMethod = false);
190 void mangleIntegerLiteral(const llvm::APSInt &Number, bool IsBoolean);
191 void mangleExpression(const Expr *E);
192 void mangleThrowSpecification(const FunctionProtoType *T);
193
Reid Klecknerf16216c2013-03-20 01:40:23 +0000194 void mangleTemplateArgs(const TemplateDecl *TD,
195 const TemplateArgumentList &TemplateArgs);
David Majnemer309f6452013-08-27 08:21:25 +0000196 void mangleTemplateArg(const TemplateDecl *TD, const TemplateArgument &TA);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000197};
198
199/// MicrosoftMangleContext - Overrides the default MangleContext for the
200/// Microsoft Visual C++ ABI.
201class MicrosoftMangleContext : public MangleContext {
202public:
203 MicrosoftMangleContext(ASTContext &Context,
204 DiagnosticsEngine &Diags) : MangleContext(Context, Diags) { }
205 virtual bool shouldMangleDeclName(const NamedDecl *D);
206 virtual void mangleName(const NamedDecl *D, raw_ostream &Out);
207 virtual void mangleThunk(const CXXMethodDecl *MD,
208 const ThunkInfo &Thunk,
209 raw_ostream &);
210 virtual void mangleCXXDtorThunk(const CXXDestructorDecl *DD, CXXDtorType Type,
211 const ThisAdjustment &ThisAdjustment,
212 raw_ostream &);
213 virtual void mangleCXXVTable(const CXXRecordDecl *RD,
214 raw_ostream &);
215 virtual void mangleCXXVTT(const CXXRecordDecl *RD,
216 raw_ostream &);
Reid Kleckner90633022013-06-19 15:20:38 +0000217 virtual void mangleCXXVBTable(const CXXRecordDecl *Derived,
218 ArrayRef<const CXXRecordDecl *> BasePath,
219 raw_ostream &Out);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000220 virtual void mangleCXXCtorVTable(const CXXRecordDecl *RD, int64_t Offset,
221 const CXXRecordDecl *Type,
222 raw_ostream &);
223 virtual void mangleCXXRTTI(QualType T, raw_ostream &);
224 virtual void mangleCXXRTTIName(QualType T, raw_ostream &);
225 virtual void mangleCXXCtor(const CXXConstructorDecl *D, CXXCtorType Type,
226 raw_ostream &);
227 virtual void mangleCXXDtor(const CXXDestructorDecl *D, CXXDtorType Type,
228 raw_ostream &);
Reid Kleckner942f9fe2013-09-10 20:14:30 +0000229 virtual void mangleReferenceTemporary(const VarDecl *, raw_ostream &);
230 virtual void mangleStaticGuardVariable(const VarDecl *D, raw_ostream &Out);
Reid Klecknerc5c6fa72013-09-10 20:43:12 +0000231 virtual void mangleDynamicInitializer(const VarDecl *D, raw_ostream &Out);
Reid Kleckner942f9fe2013-09-10 20:14:30 +0000232 virtual void mangleDynamicAtExitDestructor(const VarDecl *D,
233 raw_ostream &Out);
Reid Klecknerc5c6fa72013-09-10 20:43:12 +0000234
235private:
236 void mangleInitFiniStub(const VarDecl *D, raw_ostream &Out, char CharCode);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000237};
238
239}
240
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000241bool MicrosoftMangleContext::shouldMangleDeclName(const NamedDecl *D) {
242 // In C, functions with no attributes never need to be mangled. Fastpath them.
243 if (!getASTContext().getLangOpts().CPlusPlus && !D->hasAttrs())
244 return false;
245
246 // Any decl can be declared with __asm("foo") on it, and this takes precedence
247 // over all other naming in the .o file.
248 if (D->hasAttr<AsmLabelAttr>())
249 return true;
250
David Majnemercab7dad2013-09-13 09:03:14 +0000251 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) {
252 LanguageLinkage L = FD->getLanguageLinkage();
253 // Overloadable functions need mangling.
254 if (FD->hasAttr<OverloadableAttr>())
255 return true;
256
David Majnemer978c5e02013-09-13 09:40:55 +0000257 if (isUserDefinedEntryPoint(FD))
David Majnemercab7dad2013-09-13 09:03:14 +0000258 return false;
259
260 // C++ functions and those whose names are not a simple identifier need
261 // mangling.
262 if (!FD->getDeclName().isIdentifier() || L == CXXLanguageLinkage)
263 return true;
264
265 // C functions are not mangled.
266 if (L == CLanguageLinkage)
267 return false;
268 }
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000269
270 // Otherwise, no mangling is done outside C++ mode.
271 if (!getASTContext().getLangOpts().CPlusPlus)
272 return false;
273
David Majnemercab7dad2013-09-13 09:03:14 +0000274 if (const VarDecl *VD = dyn_cast<VarDecl>(D)) {
275 // C variables are not mangled.
276 if (VD->isExternC())
277 return false;
278
279 // Variables at global scope with non-internal linkage are not mangled.
280 const DeclContext *DC = getEffectiveDeclContext(D);
281 // Check for extern variable declared locally.
282 if (DC->isFunctionOrMethod() && D->hasLinkage())
283 while (!DC->isNamespace() && !DC->isTranslationUnit())
284 DC = getEffectiveParentContext(DC);
285
286 if (DC->isTranslationUnit() && D->getFormalLinkage() == InternalLinkage &&
287 !isa<VarTemplateSpecializationDecl>(D))
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000288 return false;
289 }
290
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000291 return true;
292}
293
294void MicrosoftCXXNameMangler::mangle(const NamedDecl *D,
295 StringRef Prefix) {
296 // MSVC doesn't mangle C++ names the same way it mangles extern "C" names.
297 // Therefore it's really important that we don't decorate the
298 // name with leading underscores or leading/trailing at signs. So, by
299 // default, we emit an asm marker at the start so we get the name right.
300 // Callers can override this with a custom prefix.
301
302 // Any decl can be declared with __asm("foo") on it, and this takes precedence
303 // over all other naming in the .o file.
304 if (const AsmLabelAttr *ALA = D->getAttr<AsmLabelAttr>()) {
305 // If we have an asm name, then we use it as the mangling.
306 Out << '\01' << ALA->getLabel();
307 return;
308 }
309
310 // <mangled-name> ::= ? <name> <type-encoding>
311 Out << Prefix;
312 mangleName(D);
313 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D))
314 mangleFunctionEncoding(FD);
315 else if (const VarDecl *VD = dyn_cast<VarDecl>(D))
316 mangleVariableEncoding(VD);
317 else {
318 // TODO: Fields? Can MSVC even mangle them?
319 // Issue a diagnostic for now.
320 DiagnosticsEngine &Diags = Context.getDiags();
321 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
322 "cannot mangle this declaration yet");
323 Diags.Report(D->getLocation(), DiagID)
324 << D->getSourceRange();
325 }
326}
327
328void MicrosoftCXXNameMangler::mangleFunctionEncoding(const FunctionDecl *FD) {
329 // <type-encoding> ::= <function-class> <function-type>
330
Reid Klecknerf21818d2013-06-24 19:21:52 +0000331 // Since MSVC operates on the type as written and not the canonical type, it
332 // actually matters which decl we have here. MSVC appears to choose the
333 // first, since it is most likely to be the declaration in a header file.
334 FD = FD->getFirstDeclaration();
335
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000336 // We should never ever see a FunctionNoProtoType at this point.
337 // We don't even know how to mangle their types anyway :).
Reid Klecknerf21818d2013-06-24 19:21:52 +0000338 TypeSourceInfo *TSI = FD->getTypeSourceInfo();
339 QualType T = TSI ? TSI->getType() : FD->getType();
340 const FunctionProtoType *FT = T->castAs<FunctionProtoType>();
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000341
342 bool InStructor = false, InInstMethod = false;
343 const CXXMethodDecl *MD = dyn_cast<CXXMethodDecl>(FD);
344 if (MD) {
345 if (MD->isInstance())
346 InInstMethod = true;
347 if (isa<CXXConstructorDecl>(MD) || isa<CXXDestructorDecl>(MD))
348 InStructor = true;
349 }
350
David Majnemercab7dad2013-09-13 09:03:14 +0000351 // extern "C" functions can hold entities that must be mangled.
352 // As it stands, these functions still need to get expressed in the full
353 // external name. They have their class and type omitted, replaced with '9'.
354 if (Context.shouldMangleDeclName(FD)) {
355 // First, the function class.
356 mangleFunctionClass(FD);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000357
David Majnemercab7dad2013-09-13 09:03:14 +0000358 mangleFunctionType(FT, FD, InStructor, InInstMethod);
359 } else
360 Out << '9';
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000361}
362
363void MicrosoftCXXNameMangler::mangleVariableEncoding(const VarDecl *VD) {
364 // <type-encoding> ::= <storage-class> <variable-type>
365 // <storage-class> ::= 0 # private static member
366 // ::= 1 # protected static member
367 // ::= 2 # public static member
368 // ::= 3 # global
369 // ::= 4 # static local
370
371 // The first character in the encoding (after the name) is the storage class.
372 if (VD->isStaticDataMember()) {
373 // If it's a static member, it also encodes the access level.
374 switch (VD->getAccess()) {
375 default:
376 case AS_private: Out << '0'; break;
377 case AS_protected: Out << '1'; break;
378 case AS_public: Out << '2'; break;
379 }
380 }
381 else if (!VD->isStaticLocal())
382 Out << '3';
383 else
384 Out << '4';
385 // Now mangle the type.
386 // <variable-type> ::= <type> <cvr-qualifiers>
387 // ::= <type> <pointee-cvr-qualifiers> # pointers, references
388 // Pointers and references are odd. The type of 'int * const foo;' gets
389 // mangled as 'QAHA' instead of 'PAHB', for example.
390 TypeLoc TL = VD->getTypeSourceInfo()->getTypeLoc();
391 QualType Ty = TL.getType();
David Majnemer1c7a4092013-08-15 08:13:23 +0000392 if (Ty->isPointerType() || Ty->isReferenceType() ||
393 Ty->isMemberPointerType()) {
David Majnemer17ffbd02013-08-09 05:56:24 +0000394 mangleType(Ty, TL.getSourceRange(), QMM_Drop);
David Majnemer1c7a4092013-08-15 08:13:23 +0000395 if (PointersAre64Bit)
396 Out << 'E';
397 if (const MemberPointerType *MPT = Ty->getAs<MemberPointerType>()) {
398 mangleQualifiers(MPT->getPointeeType().getQualifiers(), true);
399 // Member pointers are suffixed with a back reference to the member
400 // pointer's class name.
401 mangleName(MPT->getClass()->getAsCXXRecordDecl());
402 } else
403 mangleQualifiers(Ty->getPointeeType().getQualifiers(), false);
David Majnemer17ffbd02013-08-09 05:56:24 +0000404 } else if (const ArrayType *AT = getASTContext().getAsArrayType(Ty)) {
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000405 // Global arrays are funny, too.
David Majnemer58e4cd02013-09-11 04:44:30 +0000406 mangleDecayedArrayType(AT);
Peter Collingbourneb70d1c32013-04-25 04:25:40 +0000407 if (AT->getElementType()->isArrayType())
408 Out << 'A';
409 else
410 mangleQualifiers(Ty.getQualifiers(), false);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000411 } else {
Peter Collingbourneb70d1c32013-04-25 04:25:40 +0000412 mangleType(Ty, TL.getSourceRange(), QMM_Drop);
David Majnemer1c7a4092013-08-15 08:13:23 +0000413 mangleQualifiers(Ty.getLocalQualifiers(), false);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000414 }
415}
416
417void MicrosoftCXXNameMangler::mangleName(const NamedDecl *ND) {
418 // <name> ::= <unscoped-name> {[<named-scope>]+ | [<nested-name>]}? @
419 const DeclContext *DC = ND->getDeclContext();
420
421 // Always start with the unqualified name.
422 mangleUnqualifiedName(ND);
423
424 // If this is an extern variable declared locally, the relevant DeclContext
425 // is that of the containing namespace, or the translation unit.
426 if (isa<FunctionDecl>(DC) && ND->hasLinkage())
427 while (!DC->isNamespace() && !DC->isTranslationUnit())
428 DC = DC->getParent();
429
430 manglePostfix(DC);
431
432 // Terminate the whole name with an '@'.
433 Out << '@';
434}
435
436void MicrosoftCXXNameMangler::mangleNumber(int64_t Number) {
437 llvm::APSInt APSNumber(/*BitWidth=*/64, /*isUnsigned=*/false);
438 APSNumber = Number;
439 mangleNumber(APSNumber);
440}
441
442void MicrosoftCXXNameMangler::mangleNumber(const llvm::APSInt &Value) {
443 // <number> ::= [?] <decimal digit> # 1 <= Number <= 10
444 // ::= [?] <hex digit>+ @ # 0 or > 9; A = 0, B = 1, etc...
445 // ::= [?] @ # 0 (alternate mangling, not emitted by VC)
446 if (Value.isSigned() && Value.isNegative()) {
447 Out << '?';
448 mangleNumber(llvm::APSInt(Value.abs()));
449 return;
450 }
451 llvm::APSInt Temp(Value);
452 // There's a special shorter mangling for 0, but Microsoft
453 // chose not to use it. Instead, 0 gets mangled as "A@". Oh well...
454 if (Value.uge(1) && Value.ule(10)) {
455 --Temp;
456 Temp.print(Out, false);
457 } else {
458 // We have to build up the encoding in reverse order, so it will come
459 // out right when we write it out.
460 char Encoding[64];
461 char *EndPtr = Encoding+sizeof(Encoding);
462 char *CurPtr = EndPtr;
463 llvm::APSInt NibbleMask(Value.getBitWidth(), Value.isUnsigned());
464 NibbleMask = 0xf;
465 do {
466 *--CurPtr = 'A' + Temp.And(NibbleMask).getLimitedValue(0xf);
467 Temp = Temp.lshr(4);
468 } while (Temp != 0);
469 Out.write(CurPtr, EndPtr-CurPtr);
470 Out << '@';
471 }
472}
473
474static const TemplateDecl *
Reid Klecknerf16216c2013-03-20 01:40:23 +0000475isTemplate(const NamedDecl *ND, const TemplateArgumentList *&TemplateArgs) {
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000476 // Check if we have a function template.
477 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(ND)){
478 if (const TemplateDecl *TD = FD->getPrimaryTemplate()) {
Reid Klecknerf16216c2013-03-20 01:40:23 +0000479 TemplateArgs = FD->getTemplateSpecializationArgs();
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000480 return TD;
481 }
482 }
483
484 // Check if we have a class template.
485 if (const ClassTemplateSpecializationDecl *Spec =
Reid Klecknerf16216c2013-03-20 01:40:23 +0000486 dyn_cast<ClassTemplateSpecializationDecl>(ND)) {
487 TemplateArgs = &Spec->getTemplateArgs();
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000488 return Spec->getSpecializedTemplate();
489 }
490
491 return 0;
492}
493
494void
495MicrosoftCXXNameMangler::mangleUnqualifiedName(const NamedDecl *ND,
496 DeclarationName Name) {
497 // <unqualified-name> ::= <operator-name>
498 // ::= <ctor-dtor-name>
499 // ::= <source-name>
500 // ::= <template-name>
Reid Klecknerf16216c2013-03-20 01:40:23 +0000501
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000502 // Check if we have a template.
Reid Klecknerf16216c2013-03-20 01:40:23 +0000503 const TemplateArgumentList *TemplateArgs = 0;
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000504 if (const TemplateDecl *TD = isTemplate(ND, TemplateArgs)) {
Reid Kleckner3be37d12013-07-13 00:43:39 +0000505 // Function templates aren't considered for name back referencing. This
506 // makes sense since function templates aren't likely to occur multiple
507 // times in a symbol.
508 // FIXME: Test alias template mangling with MSVC 2013.
509 if (!isa<ClassTemplateDecl>(TD)) {
510 mangleTemplateInstantiationName(TD, *TemplateArgs);
511 return;
512 }
513
514 // We have a class template.
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000515 // Here comes the tricky thing: if we need to mangle something like
516 // void foo(A::X<Y>, B::X<Y>),
517 // the X<Y> part is aliased. However, if you need to mangle
518 // void foo(A::X<A::Y>, A::X<B::Y>),
519 // the A::X<> part is not aliased.
520 // That said, from the mangler's perspective we have a structure like this:
521 // namespace[s] -> type[ -> template-parameters]
522 // but from the Clang perspective we have
523 // type [ -> template-parameters]
524 // \-> namespace[s]
525 // What we do is we create a new mangler, mangle the same type (without
526 // a namespace suffix) using the extra mangler with back references
527 // disabled (to avoid infinite recursion) and then use the mangled type
528 // name as a key to check the mangling of different types for aliasing.
529
530 std::string BackReferenceKey;
531 BackRefMap::iterator Found;
532 if (UseNameBackReferences) {
533 llvm::raw_string_ostream Stream(BackReferenceKey);
534 MicrosoftCXXNameMangler Extra(Context, Stream);
535 Extra.disableBackReferences();
536 Extra.mangleUnqualifiedName(ND, Name);
537 Stream.flush();
538
539 Found = NameBackReferences.find(BackReferenceKey);
540 }
541 if (!UseNameBackReferences || Found == NameBackReferences.end()) {
Reid Klecknerf16216c2013-03-20 01:40:23 +0000542 mangleTemplateInstantiationName(TD, *TemplateArgs);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000543 if (UseNameBackReferences && NameBackReferences.size() < 10) {
544 size_t Size = NameBackReferences.size();
545 NameBackReferences[BackReferenceKey] = Size;
546 }
547 } else {
548 Out << Found->second;
549 }
550 return;
551 }
552
553 switch (Name.getNameKind()) {
554 case DeclarationName::Identifier: {
555 if (const IdentifierInfo *II = Name.getAsIdentifierInfo()) {
556 mangleSourceName(II);
557 break;
558 }
559
560 // Otherwise, an anonymous entity. We must have a declaration.
561 assert(ND && "mangling empty name without declaration");
562
563 if (const NamespaceDecl *NS = dyn_cast<NamespaceDecl>(ND)) {
564 if (NS->isAnonymousNamespace()) {
565 Out << "?A@";
566 break;
567 }
568 }
569
570 // We must have an anonymous struct.
571 const TagDecl *TD = cast<TagDecl>(ND);
572 if (const TypedefNameDecl *D = TD->getTypedefNameForAnonDecl()) {
573 assert(TD->getDeclContext() == D->getDeclContext() &&
574 "Typedef should not be in another decl context!");
575 assert(D->getDeclName().getAsIdentifierInfo() &&
576 "Typedef was not named!");
577 mangleSourceName(D->getDeclName().getAsIdentifierInfo());
578 break;
579 }
580
581 // When VC encounters an anonymous type with no tag and no typedef,
David Majnemerec0258a2013-08-26 02:35:51 +0000582 // it literally emits '<unnamed-tag>@'.
583 Out << "<unnamed-tag>@";
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000584 break;
585 }
586
587 case DeclarationName::ObjCZeroArgSelector:
588 case DeclarationName::ObjCOneArgSelector:
589 case DeclarationName::ObjCMultiArgSelector:
590 llvm_unreachable("Can't mangle Objective-C selector names here!");
591
592 case DeclarationName::CXXConstructorName:
Timur Iskhodzhanov1d4fff52013-02-27 13:46:31 +0000593 if (ND == Structor) {
594 assert(StructorType == Ctor_Complete &&
595 "Should never be asked to mangle a ctor other than complete");
596 }
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000597 Out << "?0";
598 break;
599
600 case DeclarationName::CXXDestructorName:
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000601 if (ND == Structor)
602 // If the named decl is the C++ destructor we're mangling,
603 // use the type we were given.
604 mangleCXXDtorType(static_cast<CXXDtorType>(StructorType));
605 else
Reid Klecknera4130ba2013-07-22 13:51:44 +0000606 // Otherwise, use the base destructor name. This is relevant if a
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000607 // class with a destructor is declared within a destructor.
Reid Klecknera4130ba2013-07-22 13:51:44 +0000608 mangleCXXDtorType(Dtor_Base);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000609 break;
610
611 case DeclarationName::CXXConversionFunctionName:
612 // <operator-name> ::= ?B # (cast)
613 // The target type is encoded as the return type.
614 Out << "?B";
615 break;
616
617 case DeclarationName::CXXOperatorName:
618 mangleOperatorName(Name.getCXXOverloadedOperator(), ND->getLocation());
619 break;
620
621 case DeclarationName::CXXLiteralOperatorName: {
622 // FIXME: Was this added in VS2010? Does MS even know how to mangle this?
623 DiagnosticsEngine Diags = Context.getDiags();
624 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
625 "cannot mangle this literal operator yet");
626 Diags.Report(ND->getLocation(), DiagID);
627 break;
628 }
629
630 case DeclarationName::CXXUsingDirective:
631 llvm_unreachable("Can't mangle a using directive name!");
632 }
633}
634
635void MicrosoftCXXNameMangler::manglePostfix(const DeclContext *DC,
636 bool NoFunction) {
637 // <postfix> ::= <unqualified-name> [<postfix>]
638 // ::= <substitution> [<postfix>]
639
640 if (!DC) return;
641
642 while (isa<LinkageSpecDecl>(DC))
643 DC = DC->getParent();
644
645 if (DC->isTranslationUnit())
646 return;
647
648 if (const BlockDecl *BD = dyn_cast<BlockDecl>(DC)) {
Eli Friedmane5798892013-07-10 01:13:27 +0000649 DiagnosticsEngine Diags = Context.getDiags();
650 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
651 "cannot mangle a local inside this block yet");
652 Diags.Report(BD->getLocation(), DiagID);
653
654 // FIXME: This is completely, utterly, wrong; see ItaniumMangle
655 // for how this should be done.
656 Out << "__block_invoke" << Context.getBlockId(BD, false);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000657 Out << '@';
658 return manglePostfix(DC->getParent(), NoFunction);
Ben Langmuir524387a2013-05-09 19:17:11 +0000659 } else if (isa<CapturedDecl>(DC)) {
660 // Skip CapturedDecl context.
661 manglePostfix(DC->getParent(), NoFunction);
662 return;
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000663 }
664
665 if (NoFunction && (isa<FunctionDecl>(DC) || isa<ObjCMethodDecl>(DC)))
666 return;
667 else if (const ObjCMethodDecl *Method = dyn_cast<ObjCMethodDecl>(DC))
668 mangleObjCMethodName(Method);
669 else if (const FunctionDecl *Func = dyn_cast<FunctionDecl>(DC))
670 mangleLocalName(Func);
671 else {
672 mangleUnqualifiedName(cast<NamedDecl>(DC));
673 manglePostfix(DC->getParent(), NoFunction);
674 }
675}
676
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000677void MicrosoftCXXNameMangler::mangleCXXDtorType(CXXDtorType T) {
Reid Klecknera4130ba2013-07-22 13:51:44 +0000678 // Microsoft uses the names on the case labels for these dtor variants. Clang
679 // uses the Itanium terminology internally. Everything in this ABI delegates
680 // towards the base dtor.
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000681 switch (T) {
Reid Klecknera4130ba2013-07-22 13:51:44 +0000682 // <operator-name> ::= ?1 # destructor
683 case Dtor_Base: Out << "?1"; return;
684 // <operator-name> ::= ?_D # vbase destructor
685 case Dtor_Complete: Out << "?_D"; return;
686 // <operator-name> ::= ?_G # scalar deleting destructor
687 case Dtor_Deleting: Out << "?_G"; return;
688 // <operator-name> ::= ?_E # vector deleting destructor
689 // FIXME: Add a vector deleting dtor type. It goes in the vtable, so we need
690 // it.
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +0000691 }
692 llvm_unreachable("Unsupported dtor type?");
693}
694
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000695void MicrosoftCXXNameMangler::mangleOperatorName(OverloadedOperatorKind OO,
696 SourceLocation Loc) {
697 switch (OO) {
698 // ?0 # constructor
699 // ?1 # destructor
700 // <operator-name> ::= ?2 # new
701 case OO_New: Out << "?2"; break;
702 // <operator-name> ::= ?3 # delete
703 case OO_Delete: Out << "?3"; break;
704 // <operator-name> ::= ?4 # =
705 case OO_Equal: Out << "?4"; break;
706 // <operator-name> ::= ?5 # >>
707 case OO_GreaterGreater: Out << "?5"; break;
708 // <operator-name> ::= ?6 # <<
709 case OO_LessLess: Out << "?6"; break;
710 // <operator-name> ::= ?7 # !
711 case OO_Exclaim: Out << "?7"; break;
712 // <operator-name> ::= ?8 # ==
713 case OO_EqualEqual: Out << "?8"; break;
714 // <operator-name> ::= ?9 # !=
715 case OO_ExclaimEqual: Out << "?9"; break;
716 // <operator-name> ::= ?A # []
717 case OO_Subscript: Out << "?A"; break;
718 // ?B # conversion
719 // <operator-name> ::= ?C # ->
720 case OO_Arrow: Out << "?C"; break;
721 // <operator-name> ::= ?D # *
722 case OO_Star: Out << "?D"; break;
723 // <operator-name> ::= ?E # ++
724 case OO_PlusPlus: Out << "?E"; break;
725 // <operator-name> ::= ?F # --
726 case OO_MinusMinus: Out << "?F"; break;
727 // <operator-name> ::= ?G # -
728 case OO_Minus: Out << "?G"; break;
729 // <operator-name> ::= ?H # +
730 case OO_Plus: Out << "?H"; break;
731 // <operator-name> ::= ?I # &
732 case OO_Amp: Out << "?I"; break;
733 // <operator-name> ::= ?J # ->*
734 case OO_ArrowStar: Out << "?J"; break;
735 // <operator-name> ::= ?K # /
736 case OO_Slash: Out << "?K"; break;
737 // <operator-name> ::= ?L # %
738 case OO_Percent: Out << "?L"; break;
739 // <operator-name> ::= ?M # <
740 case OO_Less: Out << "?M"; break;
741 // <operator-name> ::= ?N # <=
742 case OO_LessEqual: Out << "?N"; break;
743 // <operator-name> ::= ?O # >
744 case OO_Greater: Out << "?O"; break;
745 // <operator-name> ::= ?P # >=
746 case OO_GreaterEqual: Out << "?P"; break;
747 // <operator-name> ::= ?Q # ,
748 case OO_Comma: Out << "?Q"; break;
749 // <operator-name> ::= ?R # ()
750 case OO_Call: Out << "?R"; break;
751 // <operator-name> ::= ?S # ~
752 case OO_Tilde: Out << "?S"; break;
753 // <operator-name> ::= ?T # ^
754 case OO_Caret: Out << "?T"; break;
755 // <operator-name> ::= ?U # |
756 case OO_Pipe: Out << "?U"; break;
757 // <operator-name> ::= ?V # &&
758 case OO_AmpAmp: Out << "?V"; break;
759 // <operator-name> ::= ?W # ||
760 case OO_PipePipe: Out << "?W"; break;
761 // <operator-name> ::= ?X # *=
762 case OO_StarEqual: Out << "?X"; break;
763 // <operator-name> ::= ?Y # +=
764 case OO_PlusEqual: Out << "?Y"; break;
765 // <operator-name> ::= ?Z # -=
766 case OO_MinusEqual: Out << "?Z"; break;
767 // <operator-name> ::= ?_0 # /=
768 case OO_SlashEqual: Out << "?_0"; break;
769 // <operator-name> ::= ?_1 # %=
770 case OO_PercentEqual: Out << "?_1"; break;
771 // <operator-name> ::= ?_2 # >>=
772 case OO_GreaterGreaterEqual: Out << "?_2"; break;
773 // <operator-name> ::= ?_3 # <<=
774 case OO_LessLessEqual: Out << "?_3"; break;
775 // <operator-name> ::= ?_4 # &=
776 case OO_AmpEqual: Out << "?_4"; break;
777 // <operator-name> ::= ?_5 # |=
778 case OO_PipeEqual: Out << "?_5"; break;
779 // <operator-name> ::= ?_6 # ^=
780 case OO_CaretEqual: Out << "?_6"; break;
781 // ?_7 # vftable
782 // ?_8 # vbtable
783 // ?_9 # vcall
784 // ?_A # typeof
785 // ?_B # local static guard
786 // ?_C # string
787 // ?_D # vbase destructor
788 // ?_E # vector deleting destructor
789 // ?_F # default constructor closure
790 // ?_G # scalar deleting destructor
791 // ?_H # vector constructor iterator
792 // ?_I # vector destructor iterator
793 // ?_J # vector vbase constructor iterator
794 // ?_K # virtual displacement map
795 // ?_L # eh vector constructor iterator
796 // ?_M # eh vector destructor iterator
797 // ?_N # eh vector vbase constructor iterator
798 // ?_O # copy constructor closure
799 // ?_P<name> # udt returning <name>
800 // ?_Q # <unknown>
801 // ?_R0 # RTTI Type Descriptor
802 // ?_R1 # RTTI Base Class Descriptor at (a,b,c,d)
803 // ?_R2 # RTTI Base Class Array
804 // ?_R3 # RTTI Class Hierarchy Descriptor
805 // ?_R4 # RTTI Complete Object Locator
806 // ?_S # local vftable
807 // ?_T # local vftable constructor closure
808 // <operator-name> ::= ?_U # new[]
809 case OO_Array_New: Out << "?_U"; break;
810 // <operator-name> ::= ?_V # delete[]
811 case OO_Array_Delete: Out << "?_V"; break;
812
813 case OO_Conditional: {
814 DiagnosticsEngine &Diags = Context.getDiags();
815 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
816 "cannot mangle this conditional operator yet");
817 Diags.Report(Loc, DiagID);
818 break;
819 }
820
821 case OO_None:
822 case NUM_OVERLOADED_OPERATORS:
823 llvm_unreachable("Not an overloaded operator");
824 }
825}
826
827void MicrosoftCXXNameMangler::mangleSourceName(const IdentifierInfo *II) {
828 // <source name> ::= <identifier> @
829 std::string key = II->getNameStart();
830 BackRefMap::iterator Found;
831 if (UseNameBackReferences)
832 Found = NameBackReferences.find(key);
833 if (!UseNameBackReferences || Found == NameBackReferences.end()) {
834 Out << II->getName() << '@';
835 if (UseNameBackReferences && NameBackReferences.size() < 10) {
836 size_t Size = NameBackReferences.size();
837 NameBackReferences[key] = Size;
838 }
839 } else {
840 Out << Found->second;
841 }
842}
843
844void MicrosoftCXXNameMangler::mangleObjCMethodName(const ObjCMethodDecl *MD) {
845 Context.mangleObjCMethodName(MD, Out);
846}
847
848// Find out how many function decls live above this one and return an integer
849// suitable for use as the number in a numbered anonymous scope.
850// TODO: Memoize.
851static unsigned getLocalNestingLevel(const FunctionDecl *FD) {
852 const DeclContext *DC = FD->getParent();
853 int level = 1;
854
855 while (DC && !DC->isTranslationUnit()) {
856 if (isa<FunctionDecl>(DC) || isa<ObjCMethodDecl>(DC)) level++;
857 DC = DC->getParent();
858 }
859
860 return 2*level;
861}
862
863void MicrosoftCXXNameMangler::mangleLocalName(const FunctionDecl *FD) {
864 // <nested-name> ::= <numbered-anonymous-scope> ? <mangled-name>
865 // <numbered-anonymous-scope> ::= ? <number>
866 // Even though the name is rendered in reverse order (e.g.
867 // A::B::C is rendered as C@B@A), VC numbers the scopes from outermost to
868 // innermost. So a method bar in class C local to function foo gets mangled
869 // as something like:
870 // ?bar@C@?1??foo@@YAXXZ@QAEXXZ
871 // This is more apparent when you have a type nested inside a method of a
872 // type nested inside a function. A method baz in class D local to method
873 // bar of class C local to function foo gets mangled as:
874 // ?baz@D@?3??bar@C@?1??foo@@YAXXZ@QAEXXZ@QAEXXZ
875 // This scheme is general enough to support GCC-style nested
876 // functions. You could have a method baz of class C inside a function bar
877 // inside a function foo, like so:
878 // ?baz@C@?3??bar@?1??foo@@YAXXZ@YAXXZ@QAEXXZ
879 int NestLevel = getLocalNestingLevel(FD);
880 Out << '?';
881 mangleNumber(NestLevel);
882 Out << '?';
883 mangle(FD, "?");
884}
885
886void MicrosoftCXXNameMangler::mangleTemplateInstantiationName(
887 const TemplateDecl *TD,
Reid Klecknerf16216c2013-03-20 01:40:23 +0000888 const TemplateArgumentList &TemplateArgs) {
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000889 // <template-name> ::= <unscoped-template-name> <template-args>
890 // ::= <substitution>
891 // Always start with the unqualified name.
892
893 // Templates have their own context for back references.
894 ArgBackRefMap OuterArgsContext;
895 BackRefMap OuterTemplateContext;
896 NameBackReferences.swap(OuterTemplateContext);
897 TypeBackReferences.swap(OuterArgsContext);
898
899 mangleUnscopedTemplateName(TD);
Reid Klecknerf16216c2013-03-20 01:40:23 +0000900 mangleTemplateArgs(TD, TemplateArgs);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000901
902 // Restore the previous back reference contexts.
903 NameBackReferences.swap(OuterTemplateContext);
904 TypeBackReferences.swap(OuterArgsContext);
905}
906
907void
908MicrosoftCXXNameMangler::mangleUnscopedTemplateName(const TemplateDecl *TD) {
909 // <unscoped-template-name> ::= ?$ <unqualified-name>
910 Out << "?$";
911 mangleUnqualifiedName(TD);
912}
913
914void
915MicrosoftCXXNameMangler::mangleIntegerLiteral(const llvm::APSInt &Value,
916 bool IsBoolean) {
917 // <integer-literal> ::= $0 <number>
918 Out << "$0";
919 // Make sure booleans are encoded as 0/1.
920 if (IsBoolean && Value.getBoolValue())
921 mangleNumber(1);
922 else
923 mangleNumber(Value);
924}
925
926void
927MicrosoftCXXNameMangler::mangleExpression(const Expr *E) {
928 // See if this is a constant expression.
929 llvm::APSInt Value;
930 if (E->isIntegerConstantExpr(Value, Context.getASTContext())) {
931 mangleIntegerLiteral(Value, E->getType()->isBooleanType());
932 return;
933 }
934
David Majnemerc80eb462013-08-13 06:32:20 +0000935 const CXXUuidofExpr *UE = 0;
936 if (const UnaryOperator *UO = dyn_cast<UnaryOperator>(E)) {
937 if (UO->getOpcode() == UO_AddrOf)
938 UE = dyn_cast<CXXUuidofExpr>(UO->getSubExpr());
939 } else
940 UE = dyn_cast<CXXUuidofExpr>(E);
941
942 if (UE) {
943 // This CXXUuidofExpr is mangled as-if it were actually a VarDecl from
944 // const __s_GUID _GUID_{lower case UUID with underscores}
945 StringRef Uuid = UE->getUuidAsStringRef(Context.getASTContext());
946 std::string Name = "_GUID_" + Uuid.lower();
947 std::replace(Name.begin(), Name.end(), '-', '_');
948
David Majnemer26314e12013-08-13 09:17:25 +0000949 // If we had to peek through an address-of operator, treat this like we are
David Majnemerc80eb462013-08-13 06:32:20 +0000950 // dealing with a pointer type. Otherwise, treat it like a const reference.
951 //
952 // N.B. This matches up with the handling of TemplateArgument::Declaration
953 // in mangleTemplateArg
954 if (UE == E)
955 Out << "$E?";
956 else
957 Out << "$1?";
958 Out << Name << "@@3U__s_GUID@@B";
959 return;
960 }
961
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000962 // As bad as this diagnostic is, it's better than crashing.
963 DiagnosticsEngine &Diags = Context.getDiags();
964 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
965 "cannot yet mangle expression type %0");
966 Diags.Report(E->getExprLoc(), DiagID)
967 << E->getStmtClassName() << E->getSourceRange();
968}
969
970void
Reid Klecknerf16216c2013-03-20 01:40:23 +0000971MicrosoftCXXNameMangler::mangleTemplateArgs(const TemplateDecl *TD,
972 const TemplateArgumentList &TemplateArgs) {
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000973 // <template-args> ::= {<type> | <integer-literal>}+ @
974 unsigned NumTemplateArgs = TemplateArgs.size();
975 for (unsigned i = 0; i < NumTemplateArgs; ++i) {
Reid Klecknerf16216c2013-03-20 01:40:23 +0000976 const TemplateArgument &TA = TemplateArgs[i];
David Majnemer309f6452013-08-27 08:21:25 +0000977 mangleTemplateArg(TD, TA);
Guy Benyei7f92f2d2012-12-18 14:30:41 +0000978 }
979 Out << '@';
980}
981
Reid Kleckner5d90d182013-07-02 18:10:07 +0000982void MicrosoftCXXNameMangler::mangleTemplateArg(const TemplateDecl *TD,
David Majnemer309f6452013-08-27 08:21:25 +0000983 const TemplateArgument &TA) {
Reid Kleckner5d90d182013-07-02 18:10:07 +0000984 switch (TA.getKind()) {
985 case TemplateArgument::Null:
986 llvm_unreachable("Can't mangle null template arguments!");
David Majnemer309f6452013-08-27 08:21:25 +0000987 case TemplateArgument::TemplateExpansion:
988 llvm_unreachable("Can't mangle template expansion arguments!");
Reid Kleckner5d90d182013-07-02 18:10:07 +0000989 case TemplateArgument::Type: {
990 QualType T = TA.getAsType();
991 mangleType(T, SourceRange(), QMM_Escape);
992 break;
993 }
David Majnemerf2081f62013-08-13 01:25:35 +0000994 case TemplateArgument::Declaration: {
995 const NamedDecl *ND = cast<NamedDecl>(TA.getAsDecl());
996 mangle(ND, TA.isDeclForReferenceParam() ? "$E?" : "$1?");
Reid Kleckner5d90d182013-07-02 18:10:07 +0000997 break;
David Majnemerf2081f62013-08-13 01:25:35 +0000998 }
Reid Kleckner5d90d182013-07-02 18:10:07 +0000999 case TemplateArgument::Integral:
1000 mangleIntegerLiteral(TA.getAsIntegral(),
1001 TA.getIntegralType()->isBooleanType());
1002 break;
David Majnemer7802fc92013-08-05 21:33:59 +00001003 case TemplateArgument::NullPtr:
1004 Out << "$0A@";
1005 break;
Reid Kleckner5d90d182013-07-02 18:10:07 +00001006 case TemplateArgument::Expression:
1007 mangleExpression(TA.getAsExpr());
1008 break;
1009 case TemplateArgument::Pack:
1010 // Unlike Itanium, there is no character code to indicate an argument pack.
Reid Kleckner5d90d182013-07-02 18:10:07 +00001011 for (TemplateArgument::pack_iterator I = TA.pack_begin(), E = TA.pack_end();
1012 I != E; ++I)
David Majnemer309f6452013-08-27 08:21:25 +00001013 mangleTemplateArg(TD, *I);
Reid Kleckner5d90d182013-07-02 18:10:07 +00001014 break;
1015 case TemplateArgument::Template:
David Majnemer02c44f02013-08-05 22:26:46 +00001016 mangleType(cast<TagDecl>(
1017 TA.getAsTemplate().getAsTemplateDecl()->getTemplatedDecl()));
1018 break;
Reid Kleckner5d90d182013-07-02 18:10:07 +00001019 }
1020}
1021
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001022void MicrosoftCXXNameMangler::mangleQualifiers(Qualifiers Quals,
1023 bool IsMember) {
1024 // <cvr-qualifiers> ::= [E] [F] [I] <base-cvr-qualifiers>
1025 // 'E' means __ptr64 (32-bit only); 'F' means __unaligned (32/64-bit only);
1026 // 'I' means __restrict (32/64-bit).
1027 // Note that the MSVC __restrict keyword isn't the same as the C99 restrict
1028 // keyword!
1029 // <base-cvr-qualifiers> ::= A # near
1030 // ::= B # near const
1031 // ::= C # near volatile
1032 // ::= D # near const volatile
1033 // ::= E # far (16-bit)
1034 // ::= F # far const (16-bit)
1035 // ::= G # far volatile (16-bit)
1036 // ::= H # far const volatile (16-bit)
1037 // ::= I # huge (16-bit)
1038 // ::= J # huge const (16-bit)
1039 // ::= K # huge volatile (16-bit)
1040 // ::= L # huge const volatile (16-bit)
1041 // ::= M <basis> # based
1042 // ::= N <basis> # based const
1043 // ::= O <basis> # based volatile
1044 // ::= P <basis> # based const volatile
1045 // ::= Q # near member
1046 // ::= R # near const member
1047 // ::= S # near volatile member
1048 // ::= T # near const volatile member
1049 // ::= U # far member (16-bit)
1050 // ::= V # far const member (16-bit)
1051 // ::= W # far volatile member (16-bit)
1052 // ::= X # far const volatile member (16-bit)
1053 // ::= Y # huge member (16-bit)
1054 // ::= Z # huge const member (16-bit)
1055 // ::= 0 # huge volatile member (16-bit)
1056 // ::= 1 # huge const volatile member (16-bit)
1057 // ::= 2 <basis> # based member
1058 // ::= 3 <basis> # based const member
1059 // ::= 4 <basis> # based volatile member
1060 // ::= 5 <basis> # based const volatile member
1061 // ::= 6 # near function (pointers only)
1062 // ::= 7 # far function (pointers only)
1063 // ::= 8 # near method (pointers only)
1064 // ::= 9 # far method (pointers only)
1065 // ::= _A <basis> # based function (pointers only)
1066 // ::= _B <basis> # based function (far?) (pointers only)
1067 // ::= _C <basis> # based method (pointers only)
1068 // ::= _D <basis> # based method (far?) (pointers only)
1069 // ::= _E # block (Clang)
1070 // <basis> ::= 0 # __based(void)
1071 // ::= 1 # __based(segment)?
1072 // ::= 2 <name> # __based(name)
1073 // ::= 3 # ?
1074 // ::= 4 # ?
1075 // ::= 5 # not really based
1076 bool HasConst = Quals.hasConst(),
1077 HasVolatile = Quals.hasVolatile();
David Majnemerc0e64f32013-08-05 22:43:06 +00001078
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001079 if (!IsMember) {
1080 if (HasConst && HasVolatile) {
1081 Out << 'D';
1082 } else if (HasVolatile) {
1083 Out << 'C';
1084 } else if (HasConst) {
1085 Out << 'B';
1086 } else {
1087 Out << 'A';
1088 }
1089 } else {
1090 if (HasConst && HasVolatile) {
1091 Out << 'T';
1092 } else if (HasVolatile) {
1093 Out << 'S';
1094 } else if (HasConst) {
1095 Out << 'R';
1096 } else {
1097 Out << 'Q';
1098 }
1099 }
1100
1101 // FIXME: For now, just drop all extension qualifiers on the floor.
1102}
1103
1104void MicrosoftCXXNameMangler::manglePointerQualifiers(Qualifiers Quals) {
1105 // <pointer-cvr-qualifiers> ::= P # no qualifiers
1106 // ::= Q # const
1107 // ::= R # volatile
1108 // ::= S # const volatile
1109 bool HasConst = Quals.hasConst(),
1110 HasVolatile = Quals.hasVolatile();
1111 if (HasConst && HasVolatile) {
1112 Out << 'S';
1113 } else if (HasVolatile) {
1114 Out << 'R';
1115 } else if (HasConst) {
1116 Out << 'Q';
1117 } else {
1118 Out << 'P';
1119 }
1120}
1121
1122void MicrosoftCXXNameMangler::mangleArgumentType(QualType T,
1123 SourceRange Range) {
Reid Klecknerf21818d2013-06-24 19:21:52 +00001124 // MSVC will backreference two canonically equivalent types that have slightly
1125 // different manglings when mangled alone.
David Majnemer58e4cd02013-09-11 04:44:30 +00001126
1127 // Decayed types do not match up with non-decayed versions of the same type.
1128 //
1129 // e.g.
1130 // void (*x)(void) will not form a backreference with void x(void)
1131 void *TypePtr;
1132 if (const DecayedType *DT = T->getAs<DecayedType>()) {
1133 TypePtr = DT->getOriginalType().getCanonicalType().getAsOpaquePtr();
1134 // If the original parameter was textually written as an array,
1135 // instead treat the decayed parameter like it's const.
1136 //
1137 // e.g.
1138 // int [] -> int * const
1139 if (DT->getOriginalType()->isArrayType())
1140 T = T.withConst();
1141 } else
1142 TypePtr = T.getCanonicalType().getAsOpaquePtr();
1143
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001144 ArgBackRefMap::iterator Found = TypeBackReferences.find(TypePtr);
1145
1146 if (Found == TypeBackReferences.end()) {
1147 size_t OutSizeBefore = Out.GetNumBytesInBuffer();
1148
David Majnemer58e4cd02013-09-11 04:44:30 +00001149 mangleType(T, Range, QMM_Drop);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001150
1151 // See if it's worth creating a back reference.
1152 // Only types longer than 1 character are considered
1153 // and only 10 back references slots are available:
1154 bool LongerThanOneChar = (Out.GetNumBytesInBuffer() - OutSizeBefore > 1);
1155 if (LongerThanOneChar && TypeBackReferences.size() < 10) {
1156 size_t Size = TypeBackReferences.size();
1157 TypeBackReferences[TypePtr] = Size;
1158 }
1159 } else {
1160 Out << Found->second;
1161 }
1162}
1163
1164void MicrosoftCXXNameMangler::mangleType(QualType T, SourceRange Range,
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001165 QualifierMangleMode QMM) {
Reid Klecknerf21818d2013-06-24 19:21:52 +00001166 // Don't use the canonical types. MSVC includes things like 'const' on
1167 // pointer arguments to function pointers that canonicalization strips away.
1168 T = T.getDesugaredType(getASTContext());
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001169 Qualifiers Quals = T.getLocalQualifiers();
Reid Klecknerf21818d2013-06-24 19:21:52 +00001170 if (const ArrayType *AT = getASTContext().getAsArrayType(T)) {
1171 // If there were any Quals, getAsArrayType() pushed them onto the array
1172 // element type.
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001173 if (QMM == QMM_Mangle)
1174 Out << 'A';
1175 else if (QMM == QMM_Escape || QMM == QMM_Result)
1176 Out << "$$B";
Reid Klecknerf21818d2013-06-24 19:21:52 +00001177 mangleArrayType(AT);
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001178 return;
1179 }
1180
1181 bool IsPointer = T->isAnyPointerType() || T->isMemberPointerType() ||
1182 T->isBlockPointerType();
1183
1184 switch (QMM) {
1185 case QMM_Drop:
1186 break;
1187 case QMM_Mangle:
1188 if (const FunctionType *FT = dyn_cast<FunctionType>(T)) {
1189 Out << '6';
1190 mangleFunctionType(FT, 0, false, false);
1191 return;
1192 }
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001193 mangleQualifiers(Quals, false);
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001194 break;
1195 case QMM_Escape:
1196 if (!IsPointer && Quals) {
1197 Out << "$$C";
1198 mangleQualifiers(Quals, false);
1199 }
1200 break;
1201 case QMM_Result:
1202 if ((!IsPointer && Quals) || isa<TagType>(T)) {
1203 Out << '?';
1204 mangleQualifiers(Quals, false);
1205 }
1206 break;
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001207 }
1208
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001209 // We have to mangle these now, while we still have enough information.
1210 if (IsPointer)
1211 manglePointerQualifiers(Quals);
1212 const Type *ty = T.getTypePtr();
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001213
1214 switch (ty->getTypeClass()) {
1215#define ABSTRACT_TYPE(CLASS, PARENT)
1216#define NON_CANONICAL_TYPE(CLASS, PARENT) \
1217 case Type::CLASS: \
1218 llvm_unreachable("can't mangle non-canonical type " #CLASS "Type"); \
1219 return;
1220#define TYPE(CLASS, PARENT) \
1221 case Type::CLASS: \
1222 mangleType(cast<CLASS##Type>(ty), Range); \
1223 break;
1224#include "clang/AST/TypeNodes.def"
1225#undef ABSTRACT_TYPE
1226#undef NON_CANONICAL_TYPE
1227#undef TYPE
1228 }
1229}
1230
1231void MicrosoftCXXNameMangler::mangleType(const BuiltinType *T,
1232 SourceRange Range) {
1233 // <type> ::= <builtin-type>
1234 // <builtin-type> ::= X # void
1235 // ::= C # signed char
1236 // ::= D # char
1237 // ::= E # unsigned char
1238 // ::= F # short
1239 // ::= G # unsigned short (or wchar_t if it's not a builtin)
1240 // ::= H # int
1241 // ::= I # unsigned int
1242 // ::= J # long
1243 // ::= K # unsigned long
1244 // L # <none>
1245 // ::= M # float
1246 // ::= N # double
1247 // ::= O # long double (__float80 is mangled differently)
1248 // ::= _J # long long, __int64
1249 // ::= _K # unsigned long long, __int64
1250 // ::= _L # __int128
1251 // ::= _M # unsigned __int128
1252 // ::= _N # bool
1253 // _O # <array in parameter>
1254 // ::= _T # __float80 (Intel)
1255 // ::= _W # wchar_t
1256 // ::= _Z # __float80 (Digital Mars)
1257 switch (T->getKind()) {
1258 case BuiltinType::Void: Out << 'X'; break;
1259 case BuiltinType::SChar: Out << 'C'; break;
1260 case BuiltinType::Char_U: case BuiltinType::Char_S: Out << 'D'; break;
1261 case BuiltinType::UChar: Out << 'E'; break;
1262 case BuiltinType::Short: Out << 'F'; break;
1263 case BuiltinType::UShort: Out << 'G'; break;
1264 case BuiltinType::Int: Out << 'H'; break;
1265 case BuiltinType::UInt: Out << 'I'; break;
1266 case BuiltinType::Long: Out << 'J'; break;
1267 case BuiltinType::ULong: Out << 'K'; break;
1268 case BuiltinType::Float: Out << 'M'; break;
1269 case BuiltinType::Double: Out << 'N'; break;
1270 // TODO: Determine size and mangle accordingly
1271 case BuiltinType::LongDouble: Out << 'O'; break;
1272 case BuiltinType::LongLong: Out << "_J"; break;
1273 case BuiltinType::ULongLong: Out << "_K"; break;
1274 case BuiltinType::Int128: Out << "_L"; break;
1275 case BuiltinType::UInt128: Out << "_M"; break;
1276 case BuiltinType::Bool: Out << "_N"; break;
1277 case BuiltinType::WChar_S:
1278 case BuiltinType::WChar_U: Out << "_W"; break;
1279
1280#define BUILTIN_TYPE(Id, SingletonId)
1281#define PLACEHOLDER_TYPE(Id, SingletonId) \
1282 case BuiltinType::Id:
1283#include "clang/AST/BuiltinTypes.def"
1284 case BuiltinType::Dependent:
1285 llvm_unreachable("placeholder types shouldn't get to name mangling");
1286
1287 case BuiltinType::ObjCId: Out << "PAUobjc_object@@"; break;
1288 case BuiltinType::ObjCClass: Out << "PAUobjc_class@@"; break;
1289 case BuiltinType::ObjCSel: Out << "PAUobjc_selector@@"; break;
Guy Benyeib13621d2012-12-18 14:38:23 +00001290
1291 case BuiltinType::OCLImage1d: Out << "PAUocl_image1d@@"; break;
1292 case BuiltinType::OCLImage1dArray: Out << "PAUocl_image1darray@@"; break;
1293 case BuiltinType::OCLImage1dBuffer: Out << "PAUocl_image1dbuffer@@"; break;
1294 case BuiltinType::OCLImage2d: Out << "PAUocl_image2d@@"; break;
1295 case BuiltinType::OCLImage2dArray: Out << "PAUocl_image2darray@@"; break;
1296 case BuiltinType::OCLImage3d: Out << "PAUocl_image3d@@"; break;
Guy Benyei21f18c42013-02-07 10:55:47 +00001297 case BuiltinType::OCLSampler: Out << "PAUocl_sampler@@"; break;
Guy Benyeie6b9d802013-01-20 12:31:11 +00001298 case BuiltinType::OCLEvent: Out << "PAUocl_event@@"; break;
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001299
1300 case BuiltinType::NullPtr: Out << "$$T"; break;
1301
1302 case BuiltinType::Char16:
1303 case BuiltinType::Char32:
1304 case BuiltinType::Half: {
1305 DiagnosticsEngine &Diags = Context.getDiags();
1306 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1307 "cannot mangle this built-in %0 type yet");
1308 Diags.Report(Range.getBegin(), DiagID)
1309 << T->getName(Context.getASTContext().getPrintingPolicy())
1310 << Range;
1311 break;
1312 }
1313 }
1314}
1315
1316// <type> ::= <function-type>
1317void MicrosoftCXXNameMangler::mangleType(const FunctionProtoType *T,
1318 SourceRange) {
1319 // Structors only appear in decls, so at this point we know it's not a
1320 // structor type.
1321 // FIXME: This may not be lambda-friendly.
1322 Out << "$$A6";
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001323 mangleFunctionType(T, NULL, false, false);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001324}
1325void MicrosoftCXXNameMangler::mangleType(const FunctionNoProtoType *T,
1326 SourceRange) {
1327 llvm_unreachable("Can't mangle K&R function prototypes");
1328}
1329
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001330void MicrosoftCXXNameMangler::mangleFunctionType(const FunctionType *T,
1331 const FunctionDecl *D,
1332 bool IsStructor,
1333 bool IsInstMethod) {
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001334 // <function-type> ::= <this-cvr-qualifiers> <calling-convention>
1335 // <return-type> <argument-list> <throw-spec>
1336 const FunctionProtoType *Proto = cast<FunctionProtoType>(T);
1337
Reid Klecknerf21818d2013-06-24 19:21:52 +00001338 SourceRange Range;
1339 if (D) Range = D->getSourceRange();
1340
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001341 // If this is a C++ instance method, mangle the CVR qualifiers for the
1342 // this pointer.
David Majnemer1c7a4092013-08-15 08:13:23 +00001343 if (IsInstMethod) {
1344 if (PointersAre64Bit)
1345 Out << 'E';
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001346 mangleQualifiers(Qualifiers::fromCVRMask(Proto->getTypeQuals()), false);
David Majnemer1c7a4092013-08-15 08:13:23 +00001347 }
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001348
1349 mangleCallingConvention(T, IsInstMethod);
1350
1351 // <return-type> ::= <type>
1352 // ::= @ # structors (they have no declared return type)
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +00001353 if (IsStructor) {
1354 if (isa<CXXDestructorDecl>(D) && D == Structor &&
1355 StructorType == Dtor_Deleting) {
1356 // The scalar deleting destructor takes an extra int argument.
1357 // However, the FunctionType generated has 0 arguments.
1358 // FIXME: This is a temporary hack.
1359 // Maybe should fix the FunctionType creation instead?
Timur Iskhodzhanov4b104062013-08-26 10:32:04 +00001360 Out << (PointersAre64Bit ? "PEAXI@Z" : "PAXI@Z");
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +00001361 return;
1362 }
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001363 Out << '@';
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +00001364 } else {
David Majnemer1c7a4092013-08-15 08:13:23 +00001365 QualType ResultType = Proto->getResultType();
1366 if (ResultType->isVoidType())
1367 ResultType = ResultType.getUnqualifiedType();
1368 mangleType(ResultType, Range, QMM_Result);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001369 }
1370
1371 // <argument-list> ::= X # void
1372 // ::= <type>+ @
1373 // ::= <type>* Z # varargs
1374 if (Proto->getNumArgs() == 0 && !Proto->isVariadic()) {
1375 Out << 'X';
1376 } else {
Reid Klecknerf21818d2013-06-24 19:21:52 +00001377 // Happens for function pointer type arguments for example.
1378 for (FunctionProtoType::arg_type_iterator Arg = Proto->arg_type_begin(),
1379 ArgEnd = Proto->arg_type_end();
1380 Arg != ArgEnd; ++Arg)
1381 mangleArgumentType(*Arg, Range);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001382 // <builtin-type> ::= Z # ellipsis
1383 if (Proto->isVariadic())
1384 Out << 'Z';
1385 else
1386 Out << '@';
1387 }
1388
1389 mangleThrowSpecification(Proto);
1390}
1391
1392void MicrosoftCXXNameMangler::mangleFunctionClass(const FunctionDecl *FD) {
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001393 // <function-class> ::= <member-function> E? # E designates a 64-bit 'this'
1394 // # pointer. in 64-bit mode *all*
1395 // # 'this' pointers are 64-bit.
1396 // ::= <global-function>
1397 // <member-function> ::= A # private: near
1398 // ::= B # private: far
1399 // ::= C # private: static near
1400 // ::= D # private: static far
1401 // ::= E # private: virtual near
1402 // ::= F # private: virtual far
1403 // ::= G # private: thunk near
1404 // ::= H # private: thunk far
1405 // ::= I # protected: near
1406 // ::= J # protected: far
1407 // ::= K # protected: static near
1408 // ::= L # protected: static far
1409 // ::= M # protected: virtual near
1410 // ::= N # protected: virtual far
1411 // ::= O # protected: thunk near
1412 // ::= P # protected: thunk far
1413 // ::= Q # public: near
1414 // ::= R # public: far
1415 // ::= S # public: static near
1416 // ::= T # public: static far
1417 // ::= U # public: virtual near
1418 // ::= V # public: virtual far
1419 // ::= W # public: thunk near
1420 // ::= X # public: thunk far
1421 // <global-function> ::= Y # global near
1422 // ::= Z # global far
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001423 if (const CXXMethodDecl *MD = dyn_cast<CXXMethodDecl>(FD)) {
1424 switch (MD->getAccess()) {
1425 default:
1426 case AS_private:
1427 if (MD->isStatic())
1428 Out << 'C';
1429 else if (MD->isVirtual())
1430 Out << 'E';
1431 else
1432 Out << 'A';
1433 break;
1434 case AS_protected:
1435 if (MD->isStatic())
1436 Out << 'K';
1437 else if (MD->isVirtual())
1438 Out << 'M';
1439 else
1440 Out << 'I';
1441 break;
1442 case AS_public:
1443 if (MD->isStatic())
1444 Out << 'S';
1445 else if (MD->isVirtual())
1446 Out << 'U';
1447 else
1448 Out << 'Q';
1449 }
1450 } else
1451 Out << 'Y';
1452}
1453void MicrosoftCXXNameMangler::mangleCallingConvention(const FunctionType *T,
1454 bool IsInstMethod) {
1455 // <calling-convention> ::= A # __cdecl
1456 // ::= B # __export __cdecl
1457 // ::= C # __pascal
1458 // ::= D # __export __pascal
1459 // ::= E # __thiscall
1460 // ::= F # __export __thiscall
1461 // ::= G # __stdcall
1462 // ::= H # __export __stdcall
1463 // ::= I # __fastcall
1464 // ::= J # __export __fastcall
1465 // The 'export' calling conventions are from a bygone era
1466 // (*cough*Win16*cough*) when functions were declared for export with
1467 // that keyword. (It didn't actually export them, it just made them so
1468 // that they could be in a DLL and somebody from another module could call
1469 // them.)
1470 CallingConv CC = T->getCallConv();
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001471 switch (CC) {
1472 default:
1473 llvm_unreachable("Unsupported CC for mangling");
Charles Davise8519c32013-08-30 04:39:01 +00001474 case CC_X86_64Win64:
1475 case CC_X86_64SysV:
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001476 case CC_C: Out << 'A'; break;
1477 case CC_X86Pascal: Out << 'C'; break;
1478 case CC_X86ThisCall: Out << 'E'; break;
1479 case CC_X86StdCall: Out << 'G'; break;
1480 case CC_X86FastCall: Out << 'I'; break;
1481 }
1482}
1483void MicrosoftCXXNameMangler::mangleThrowSpecification(
1484 const FunctionProtoType *FT) {
1485 // <throw-spec> ::= Z # throw(...) (default)
1486 // ::= @ # throw() or __declspec/__attribute__((nothrow))
1487 // ::= <type>+
1488 // NOTE: Since the Microsoft compiler ignores throw specifications, they are
1489 // all actually mangled as 'Z'. (They're ignored because their associated
1490 // functionality isn't implemented, and probably never will be.)
1491 Out << 'Z';
1492}
1493
1494void MicrosoftCXXNameMangler::mangleType(const UnresolvedUsingType *T,
1495 SourceRange Range) {
1496 // Probably should be mangled as a template instantiation; need to see what
1497 // VC does first.
1498 DiagnosticsEngine &Diags = Context.getDiags();
1499 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1500 "cannot mangle this unresolved dependent type yet");
1501 Diags.Report(Range.getBegin(), DiagID)
1502 << Range;
1503}
1504
1505// <type> ::= <union-type> | <struct-type> | <class-type> | <enum-type>
1506// <union-type> ::= T <name>
1507// <struct-type> ::= U <name>
1508// <class-type> ::= V <name>
1509// <enum-type> ::= W <size> <name>
1510void MicrosoftCXXNameMangler::mangleType(const EnumType *T, SourceRange) {
David Majnemer02c44f02013-08-05 22:26:46 +00001511 mangleType(cast<TagType>(T)->getDecl());
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001512}
1513void MicrosoftCXXNameMangler::mangleType(const RecordType *T, SourceRange) {
David Majnemer02c44f02013-08-05 22:26:46 +00001514 mangleType(cast<TagType>(T)->getDecl());
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001515}
David Majnemer02c44f02013-08-05 22:26:46 +00001516void MicrosoftCXXNameMangler::mangleType(const TagDecl *TD) {
1517 switch (TD->getTagKind()) {
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001518 case TTK_Union:
1519 Out << 'T';
1520 break;
1521 case TTK_Struct:
1522 case TTK_Interface:
1523 Out << 'U';
1524 break;
1525 case TTK_Class:
1526 Out << 'V';
1527 break;
1528 case TTK_Enum:
1529 Out << 'W';
1530 Out << getASTContext().getTypeSizeInChars(
David Majnemer02c44f02013-08-05 22:26:46 +00001531 cast<EnumDecl>(TD)->getIntegerType()).getQuantity();
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001532 break;
1533 }
David Majnemer02c44f02013-08-05 22:26:46 +00001534 mangleName(TD);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001535}
1536
1537// <type> ::= <array-type>
1538// <array-type> ::= <pointer-cvr-qualifiers> <cvr-qualifiers>
1539// [Y <dimension-count> <dimension>+]
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001540// <element-type> # as global, E is never required
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001541// It's supposed to be the other way around, but for some strange reason, it
1542// isn't. Today this behavior is retained for the sole purpose of backwards
1543// compatibility.
David Majnemer58e4cd02013-09-11 04:44:30 +00001544void MicrosoftCXXNameMangler::mangleDecayedArrayType(const ArrayType *T) {
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001545 // This isn't a recursive mangling, so now we have to do it all in this
1546 // one call.
David Majnemer58e4cd02013-09-11 04:44:30 +00001547 manglePointerQualifiers(T->getElementType().getQualifiers());
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001548 mangleType(T->getElementType(), SourceRange());
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001549}
1550void MicrosoftCXXNameMangler::mangleType(const ConstantArrayType *T,
1551 SourceRange) {
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001552 llvm_unreachable("Should have been special cased");
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001553}
1554void MicrosoftCXXNameMangler::mangleType(const VariableArrayType *T,
1555 SourceRange) {
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001556 llvm_unreachable("Should have been special cased");
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001557}
1558void MicrosoftCXXNameMangler::mangleType(const DependentSizedArrayType *T,
1559 SourceRange) {
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001560 llvm_unreachable("Should have been special cased");
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001561}
1562void MicrosoftCXXNameMangler::mangleType(const IncompleteArrayType *T,
1563 SourceRange) {
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001564 llvm_unreachable("Should have been special cased");
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001565}
Reid Klecknerf21818d2013-06-24 19:21:52 +00001566void MicrosoftCXXNameMangler::mangleArrayType(const ArrayType *T) {
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001567 QualType ElementTy(T, 0);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001568 SmallVector<llvm::APInt, 3> Dimensions;
1569 for (;;) {
1570 if (const ConstantArrayType *CAT =
1571 getASTContext().getAsConstantArrayType(ElementTy)) {
1572 Dimensions.push_back(CAT->getSize());
1573 ElementTy = CAT->getElementType();
1574 } else if (ElementTy->isVariableArrayType()) {
1575 const VariableArrayType *VAT =
1576 getASTContext().getAsVariableArrayType(ElementTy);
1577 DiagnosticsEngine &Diags = Context.getDiags();
1578 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1579 "cannot mangle this variable-length array yet");
1580 Diags.Report(VAT->getSizeExpr()->getExprLoc(), DiagID)
1581 << VAT->getBracketsRange();
1582 return;
1583 } else if (ElementTy->isDependentSizedArrayType()) {
1584 // The dependent expression has to be folded into a constant (TODO).
1585 const DependentSizedArrayType *DSAT =
1586 getASTContext().getAsDependentSizedArrayType(ElementTy);
1587 DiagnosticsEngine &Diags = Context.getDiags();
1588 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1589 "cannot mangle this dependent-length array yet");
1590 Diags.Report(DSAT->getSizeExpr()->getExprLoc(), DiagID)
1591 << DSAT->getBracketsRange();
1592 return;
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001593 } else if (const IncompleteArrayType *IAT =
1594 getASTContext().getAsIncompleteArrayType(ElementTy)) {
1595 Dimensions.push_back(llvm::APInt(32, 0));
1596 ElementTy = IAT->getElementType();
1597 }
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001598 else break;
1599 }
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001600 Out << 'Y';
1601 // <dimension-count> ::= <number> # number of extra dimensions
1602 mangleNumber(Dimensions.size());
1603 for (unsigned Dim = 0; Dim < Dimensions.size(); ++Dim)
1604 mangleNumber(Dimensions[Dim].getLimitedValue());
Reid Klecknerf21818d2013-06-24 19:21:52 +00001605 mangleType(ElementTy, SourceRange(), QMM_Escape);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001606}
1607
1608// <type> ::= <pointer-to-member-type>
1609// <pointer-to-member-type> ::= <pointer-cvr-qualifiers> <cvr-qualifiers>
1610// <class name> <type>
1611void MicrosoftCXXNameMangler::mangleType(const MemberPointerType *T,
1612 SourceRange Range) {
1613 QualType PointeeType = T->getPointeeType();
1614 if (const FunctionProtoType *FPT = PointeeType->getAs<FunctionProtoType>()) {
1615 Out << '8';
1616 mangleName(T->getClass()->castAs<RecordType>()->getDecl());
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001617 mangleFunctionType(FPT, NULL, false, true);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001618 } else {
David Majnemer1c7a4092013-08-15 08:13:23 +00001619 if (PointersAre64Bit && !T->getPointeeType()->isFunctionType())
1620 Out << 'E';
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001621 mangleQualifiers(PointeeType.getQualifiers(), true);
1622 mangleName(T->getClass()->castAs<RecordType>()->getDecl());
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001623 mangleType(PointeeType, Range, QMM_Drop);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001624 }
1625}
1626
1627void MicrosoftCXXNameMangler::mangleType(const TemplateTypeParmType *T,
1628 SourceRange Range) {
1629 DiagnosticsEngine &Diags = Context.getDiags();
1630 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1631 "cannot mangle this template type parameter type yet");
1632 Diags.Report(Range.getBegin(), DiagID)
1633 << Range;
1634}
1635
1636void MicrosoftCXXNameMangler::mangleType(
1637 const SubstTemplateTypeParmPackType *T,
1638 SourceRange Range) {
1639 DiagnosticsEngine &Diags = Context.getDiags();
1640 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1641 "cannot mangle this substituted parameter pack yet");
1642 Diags.Report(Range.getBegin(), DiagID)
1643 << Range;
1644}
1645
1646// <type> ::= <pointer-type>
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001647// <pointer-type> ::= E? <pointer-cvr-qualifiers> <cvr-qualifiers> <type>
1648// # the E is required for 64-bit non static pointers
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001649void MicrosoftCXXNameMangler::mangleType(const PointerType *T,
1650 SourceRange Range) {
1651 QualType PointeeTy = T->getPointeeType();
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001652 if (PointersAre64Bit && !T->getPointeeType()->isFunctionType())
1653 Out << 'E';
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001654 mangleType(PointeeTy, Range);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001655}
1656void MicrosoftCXXNameMangler::mangleType(const ObjCObjectPointerType *T,
1657 SourceRange Range) {
1658 // Object pointers never have qualifiers.
1659 Out << 'A';
David Majnemer1c7a4092013-08-15 08:13:23 +00001660 if (PointersAre64Bit && !T->getPointeeType()->isFunctionType())
1661 Out << 'E';
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001662 mangleType(T->getPointeeType(), Range);
1663}
1664
1665// <type> ::= <reference-type>
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001666// <reference-type> ::= A E? <cvr-qualifiers> <type>
1667// # the E is required for 64-bit non static lvalue references
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001668void MicrosoftCXXNameMangler::mangleType(const LValueReferenceType *T,
1669 SourceRange Range) {
1670 Out << 'A';
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001671 if (PointersAre64Bit && !T->getPointeeType()->isFunctionType())
1672 Out << 'E';
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001673 mangleType(T->getPointeeType(), Range);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001674}
1675
1676// <type> ::= <r-value-reference-type>
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001677// <r-value-reference-type> ::= $$Q E? <cvr-qualifiers> <type>
1678// # the E is required for 64-bit non static rvalue references
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001679void MicrosoftCXXNameMangler::mangleType(const RValueReferenceType *T,
1680 SourceRange Range) {
1681 Out << "$$Q";
Reid Klecknerd6a08d12013-05-14 20:30:42 +00001682 if (PointersAre64Bit && !T->getPointeeType()->isFunctionType())
1683 Out << 'E';
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001684 mangleType(T->getPointeeType(), Range);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001685}
1686
1687void MicrosoftCXXNameMangler::mangleType(const ComplexType *T,
1688 SourceRange Range) {
1689 DiagnosticsEngine &Diags = Context.getDiags();
1690 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1691 "cannot mangle this complex number type yet");
1692 Diags.Report(Range.getBegin(), DiagID)
1693 << Range;
1694}
1695
1696void MicrosoftCXXNameMangler::mangleType(const VectorType *T,
1697 SourceRange Range) {
Reid Kleckner1232e272013-03-26 16:56:59 +00001698 const BuiltinType *ET = T->getElementType()->getAs<BuiltinType>();
1699 assert(ET && "vectors with non-builtin elements are unsupported");
1700 uint64_t Width = getASTContext().getTypeSize(T);
1701 // Pattern match exactly the typedefs in our intrinsic headers. Anything that
1702 // doesn't match the Intel types uses a custom mangling below.
1703 bool IntelVector = true;
1704 if (Width == 64 && ET->getKind() == BuiltinType::LongLong) {
1705 Out << "T__m64";
1706 } else if (Width == 128 || Width == 256) {
1707 if (ET->getKind() == BuiltinType::Float)
1708 Out << "T__m" << Width;
1709 else if (ET->getKind() == BuiltinType::LongLong)
1710 Out << "T__m" << Width << 'i';
1711 else if (ET->getKind() == BuiltinType::Double)
1712 Out << "U__m" << Width << 'd';
1713 else
1714 IntelVector = false;
1715 } else {
1716 IntelVector = false;
1717 }
1718
1719 if (!IntelVector) {
1720 // The MS ABI doesn't have a special mangling for vector types, so we define
1721 // our own mangling to handle uses of __vector_size__ on user-specified
1722 // types, and for extensions like __v4sf.
1723 Out << "T__clang_vec" << T->getNumElements() << '_';
1724 mangleType(ET, Range);
1725 }
1726
1727 Out << "@@";
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001728}
Reid Kleckner1232e272013-03-26 16:56:59 +00001729
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001730void MicrosoftCXXNameMangler::mangleType(const ExtVectorType *T,
1731 SourceRange Range) {
1732 DiagnosticsEngine &Diags = Context.getDiags();
1733 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1734 "cannot mangle this extended vector type yet");
1735 Diags.Report(Range.getBegin(), DiagID)
1736 << Range;
1737}
1738void MicrosoftCXXNameMangler::mangleType(const DependentSizedExtVectorType *T,
1739 SourceRange Range) {
1740 DiagnosticsEngine &Diags = Context.getDiags();
1741 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1742 "cannot mangle this dependent-sized extended vector type yet");
1743 Diags.Report(Range.getBegin(), DiagID)
1744 << Range;
1745}
1746
1747void MicrosoftCXXNameMangler::mangleType(const ObjCInterfaceType *T,
1748 SourceRange) {
1749 // ObjC interfaces have structs underlying them.
1750 Out << 'U';
1751 mangleName(T->getDecl());
1752}
1753
1754void MicrosoftCXXNameMangler::mangleType(const ObjCObjectType *T,
1755 SourceRange Range) {
1756 // We don't allow overloading by different protocol qualification,
1757 // so mangling them isn't necessary.
1758 mangleType(T->getBaseType(), Range);
1759}
1760
1761void MicrosoftCXXNameMangler::mangleType(const BlockPointerType *T,
1762 SourceRange Range) {
1763 Out << "_E";
1764
1765 QualType pointee = T->getPointeeType();
Peter Collingbourneb70d1c32013-04-25 04:25:40 +00001766 mangleFunctionType(pointee->castAs<FunctionProtoType>(), NULL, false, false);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001767}
1768
David Majnemer360d23e2013-08-16 08:29:13 +00001769void MicrosoftCXXNameMangler::mangleType(const InjectedClassNameType *,
1770 SourceRange) {
1771 llvm_unreachable("Cannot mangle injected class name type.");
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001772}
1773
1774void MicrosoftCXXNameMangler::mangleType(const TemplateSpecializationType *T,
1775 SourceRange Range) {
1776 DiagnosticsEngine &Diags = Context.getDiags();
1777 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1778 "cannot mangle this template specialization type yet");
1779 Diags.Report(Range.getBegin(), DiagID)
1780 << Range;
1781}
1782
1783void MicrosoftCXXNameMangler::mangleType(const DependentNameType *T,
1784 SourceRange Range) {
1785 DiagnosticsEngine &Diags = Context.getDiags();
1786 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1787 "cannot mangle this dependent name type yet");
1788 Diags.Report(Range.getBegin(), DiagID)
1789 << Range;
1790}
1791
1792void MicrosoftCXXNameMangler::mangleType(
1793 const DependentTemplateSpecializationType *T,
1794 SourceRange Range) {
1795 DiagnosticsEngine &Diags = Context.getDiags();
1796 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1797 "cannot mangle this dependent template specialization type yet");
1798 Diags.Report(Range.getBegin(), DiagID)
1799 << Range;
1800}
1801
1802void MicrosoftCXXNameMangler::mangleType(const PackExpansionType *T,
1803 SourceRange Range) {
1804 DiagnosticsEngine &Diags = Context.getDiags();
1805 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1806 "cannot mangle this pack expansion yet");
1807 Diags.Report(Range.getBegin(), DiagID)
1808 << Range;
1809}
1810
1811void MicrosoftCXXNameMangler::mangleType(const TypeOfType *T,
1812 SourceRange Range) {
1813 DiagnosticsEngine &Diags = Context.getDiags();
1814 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1815 "cannot mangle this typeof(type) yet");
1816 Diags.Report(Range.getBegin(), DiagID)
1817 << Range;
1818}
1819
1820void MicrosoftCXXNameMangler::mangleType(const TypeOfExprType *T,
1821 SourceRange Range) {
1822 DiagnosticsEngine &Diags = Context.getDiags();
1823 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1824 "cannot mangle this typeof(expression) yet");
1825 Diags.Report(Range.getBegin(), DiagID)
1826 << Range;
1827}
1828
1829void MicrosoftCXXNameMangler::mangleType(const DecltypeType *T,
1830 SourceRange Range) {
1831 DiagnosticsEngine &Diags = Context.getDiags();
1832 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1833 "cannot mangle this decltype() yet");
1834 Diags.Report(Range.getBegin(), DiagID)
1835 << Range;
1836}
1837
1838void MicrosoftCXXNameMangler::mangleType(const UnaryTransformType *T,
1839 SourceRange Range) {
1840 DiagnosticsEngine &Diags = Context.getDiags();
1841 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1842 "cannot mangle this unary transform type yet");
1843 Diags.Report(Range.getBegin(), DiagID)
1844 << Range;
1845}
1846
1847void MicrosoftCXXNameMangler::mangleType(const AutoType *T, SourceRange Range) {
1848 DiagnosticsEngine &Diags = Context.getDiags();
1849 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1850 "cannot mangle this 'auto' type yet");
1851 Diags.Report(Range.getBegin(), DiagID)
1852 << Range;
1853}
1854
1855void MicrosoftCXXNameMangler::mangleType(const AtomicType *T,
1856 SourceRange Range) {
1857 DiagnosticsEngine &Diags = Context.getDiags();
1858 unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error,
1859 "cannot mangle this C11 atomic type yet");
1860 Diags.Report(Range.getBegin(), DiagID)
1861 << Range;
1862}
1863
1864void MicrosoftMangleContext::mangleName(const NamedDecl *D,
1865 raw_ostream &Out) {
1866 assert((isa<FunctionDecl>(D) || isa<VarDecl>(D)) &&
1867 "Invalid mangleName() call, argument is not a variable or function!");
1868 assert(!isa<CXXConstructorDecl>(D) && !isa<CXXDestructorDecl>(D) &&
1869 "Invalid mangleName() call on 'structor decl!");
1870
1871 PrettyStackTraceDecl CrashInfo(D, SourceLocation(),
1872 getASTContext().getSourceManager(),
1873 "Mangling declaration");
1874
1875 MicrosoftCXXNameMangler Mangler(*this, Out);
1876 return Mangler.mangle(D);
1877}
Timur Iskhodzhanov635de282013-07-30 09:46:19 +00001878
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001879void MicrosoftMangleContext::mangleThunk(const CXXMethodDecl *MD,
1880 const ThunkInfo &Thunk,
Timur Iskhodzhanov635de282013-07-30 09:46:19 +00001881 raw_ostream &Out) {
1882 // FIXME: this is not yet a complete implementation, but merely a
1883 // reasonably-working stub to avoid crashing when required to emit a thunk.
1884 MicrosoftCXXNameMangler Mangler(*this, Out);
1885 Out << "\01?";
1886 Mangler.mangleName(MD);
1887 if (Thunk.This.NonVirtual != 0) {
1888 // FIXME: add support for protected/private or use mangleFunctionClass.
1889 Out << "W";
1890 llvm::APSInt APSNumber(/*BitWidth=*/32 /*FIXME: check on x64*/,
1891 /*isUnsigned=*/true);
1892 APSNumber = -Thunk.This.NonVirtual;
1893 Mangler.mangleNumber(APSNumber);
1894 } else {
1895 // FIXME: add support for protected/private or use mangleFunctionClass.
1896 Out << "Q";
1897 }
1898 // FIXME: mangle return adjustment? Most likely includes using an overridee FPT?
1899 Mangler.mangleFunctionType(MD->getType()->castAs<FunctionProtoType>(), MD, false, true);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001900}
Timur Iskhodzhanov635de282013-07-30 09:46:19 +00001901
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001902void MicrosoftMangleContext::mangleCXXDtorThunk(const CXXDestructorDecl *DD,
1903 CXXDtorType Type,
1904 const ThisAdjustment &,
1905 raw_ostream &) {
1906 unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
1907 "cannot mangle thunk for this destructor yet");
1908 getDiags().Report(DD->getLocation(), DiagID);
1909}
Reid Kleckner90633022013-06-19 15:20:38 +00001910
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001911void MicrosoftMangleContext::mangleCXXVTable(const CXXRecordDecl *RD,
1912 raw_ostream &Out) {
Reid Kleckner90633022013-06-19 15:20:38 +00001913 // <mangled-name> ::= ?_7 <class-name> <storage-class>
1914 // <cvr-qualifiers> [<name>] @
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001915 // NOTE: <cvr-qualifiers> here is always 'B' (const). <storage-class>
Reid Kleckner90633022013-06-19 15:20:38 +00001916 // is always '6' for vftables.
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001917 MicrosoftCXXNameMangler Mangler(*this, Out);
1918 Mangler.getStream() << "\01??_7";
1919 Mangler.mangleName(RD);
Reid Kleckner90633022013-06-19 15:20:38 +00001920 Mangler.getStream() << "6B"; // '6' for vftable, 'B' for const.
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001921 // TODO: If the class has more than one vtable, mangle in the class it came
1922 // from.
1923 Mangler.getStream() << '@';
1924}
Reid Kleckner90633022013-06-19 15:20:38 +00001925
1926void MicrosoftMangleContext::mangleCXXVBTable(
1927 const CXXRecordDecl *Derived, ArrayRef<const CXXRecordDecl *> BasePath,
1928 raw_ostream &Out) {
1929 // <mangled-name> ::= ?_8 <class-name> <storage-class>
1930 // <cvr-qualifiers> [<name>] @
1931 // NOTE: <cvr-qualifiers> here is always 'B' (const). <storage-class>
1932 // is always '7' for vbtables.
1933 MicrosoftCXXNameMangler Mangler(*this, Out);
1934 Mangler.getStream() << "\01??_8";
1935 Mangler.mangleName(Derived);
1936 Mangler.getStream() << "7B"; // '7' for vbtable, 'B' for const.
1937 for (ArrayRef<const CXXRecordDecl *>::iterator I = BasePath.begin(),
1938 E = BasePath.end();
1939 I != E; ++I) {
1940 Mangler.mangleName(*I);
1941 }
1942 Mangler.getStream() << '@';
1943}
1944
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001945void MicrosoftMangleContext::mangleCXXVTT(const CXXRecordDecl *RD,
1946 raw_ostream &) {
1947 llvm_unreachable("The MS C++ ABI does not have virtual table tables!");
1948}
1949void MicrosoftMangleContext::mangleCXXCtorVTable(const CXXRecordDecl *RD,
1950 int64_t Offset,
1951 const CXXRecordDecl *Type,
1952 raw_ostream &) {
1953 llvm_unreachable("The MS C++ ABI does not have constructor vtables!");
1954}
1955void MicrosoftMangleContext::mangleCXXRTTI(QualType T,
1956 raw_ostream &) {
1957 // FIXME: Give a location...
1958 unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
1959 "cannot mangle RTTI descriptors for type %0 yet");
1960 getDiags().Report(DiagID)
1961 << T.getBaseTypeIdentifier();
1962}
1963void MicrosoftMangleContext::mangleCXXRTTIName(QualType T,
1964 raw_ostream &) {
1965 // FIXME: Give a location...
1966 unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
1967 "cannot mangle the name of type %0 into RTTI descriptors yet");
1968 getDiags().Report(DiagID)
1969 << T.getBaseTypeIdentifier();
1970}
1971void MicrosoftMangleContext::mangleCXXCtor(const CXXConstructorDecl *D,
1972 CXXCtorType Type,
1973 raw_ostream & Out) {
1974 MicrosoftCXXNameMangler mangler(*this, Out);
1975 mangler.mangle(D);
1976}
1977void MicrosoftMangleContext::mangleCXXDtor(const CXXDestructorDecl *D,
1978 CXXDtorType Type,
1979 raw_ostream & Out) {
Timur Iskhodzhanov59660c22013-02-13 08:37:51 +00001980 MicrosoftCXXNameMangler mangler(*this, Out, D, Type);
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001981 mangler.mangle(D);
1982}
Reid Kleckner942f9fe2013-09-10 20:14:30 +00001983void MicrosoftMangleContext::mangleReferenceTemporary(const VarDecl *VD,
Guy Benyei7f92f2d2012-12-18 14:30:41 +00001984 raw_ostream &) {
1985 unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
1986 "cannot mangle this reference temporary yet");
1987 getDiags().Report(VD->getLocation(), DiagID);
1988}
1989
Reid Kleckner942f9fe2013-09-10 20:14:30 +00001990void MicrosoftMangleContext::mangleStaticGuardVariable(const VarDecl *VD,
1991 raw_ostream &Out) {
1992 // <guard-name> ::= ?_B <postfix> @51
1993 // ::= ?$S <guard-num> @ <postfix> @4IA
1994
1995 // The first mangling is what MSVC uses to guard static locals in inline
1996 // functions. It uses a different mangling in external functions to support
1997 // guarding more than 32 variables. MSVC rejects inline functions with more
1998 // than 32 static locals. We don't fully implement the second mangling
1999 // because those guards are not externally visible, and instead use LLVM's
2000 // default renaming when creating a new guard variable.
2001 MicrosoftCXXNameMangler Mangler(*this, Out);
2002
2003 bool Visible = VD->isExternallyVisible();
2004 // <operator-name> ::= ?_B # local static guard
2005 Mangler.getStream() << (Visible ? "\01??_B" : "\01?$S1@");
2006 Mangler.manglePostfix(VD->getDeclContext());
2007 Mangler.getStream() << (Visible ? "@51" : "@4IA");
2008}
2009
Reid Klecknerc5c6fa72013-09-10 20:43:12 +00002010void MicrosoftMangleContext::mangleInitFiniStub(const VarDecl *D,
2011 raw_ostream &Out,
2012 char CharCode) {
2013 MicrosoftCXXNameMangler Mangler(*this, Out);
2014 Mangler.getStream() << "\01??__" << CharCode;
2015 Mangler.mangleName(D);
2016 // This is the function class mangling. These stubs are global, non-variadic,
2017 // cdecl functions that return void and take no args.
2018 Mangler.getStream() << "YAXXZ";
2019}
2020
2021void MicrosoftMangleContext::mangleDynamicInitializer(const VarDecl *D,
2022 raw_ostream &Out) {
2023 // <initializer-name> ::= ?__E <name> YAXXZ
2024 mangleInitFiniStub(D, Out, 'E');
2025}
2026
Reid Kleckner942f9fe2013-09-10 20:14:30 +00002027void MicrosoftMangleContext::mangleDynamicAtExitDestructor(const VarDecl *D,
2028 raw_ostream &Out) {
Reid Klecknerc5c6fa72013-09-10 20:43:12 +00002029 // <destructor-name> ::= ?__F <name> YAXXZ
2030 mangleInitFiniStub(D, Out, 'F');
Reid Kleckner942f9fe2013-09-10 20:14:30 +00002031}
2032
Guy Benyei7f92f2d2012-12-18 14:30:41 +00002033MangleContext *clang::createMicrosoftMangleContext(ASTContext &Context,
2034 DiagnosticsEngine &Diags) {
2035 return new MicrosoftMangleContext(Context, Diags);
2036}