@@ -31,6 +31,9 @@ class MicrosoftCXXNameMangler {
31
31
MangleContext &Context;
32
32
raw_ostream &Out;
33
33
34
+ typedef llvm::DenseMap<const IdentifierInfo*, unsigned > BackRefMap;
35
+ BackRefMap BackReferences;
36
+
34
37
ASTContext &getASTContext () const { return Context.getASTContext (); }
35
38
36
39
public:
@@ -641,7 +644,16 @@ void MicrosoftCXXNameMangler::mangleOperatorName(OverloadedOperatorKind OO,
641
644
642
645
void MicrosoftCXXNameMangler::mangleSourceName (const IdentifierInfo *II) {
643
646
// <source name> ::= <identifier> @
644
- Out << II->getName () << ' @' ;
647
+ BackRefMap::iterator Found = BackReferences.find (II);
648
+ if (Found == BackReferences.end ()) {
649
+ Out << II->getName () << ' @' ;
650
+ if (BackReferences.size () < 10 ) {
651
+ size_t Size = BackReferences.size ();
652
+ BackReferences[II] = Size;
653
+ }
654
+ } else {
655
+ Out << Found->second ;
656
+ }
645
657
}
646
658
647
659
void MicrosoftCXXNameMangler::mangleObjCMethodName (const ObjCMethodDecl *MD) {
@@ -938,17 +950,19 @@ void MicrosoftCXXNameMangler::mangleType(const BuiltinType *T,
938
950
case BuiltinType::ObjCId: Out << " PAUobjc_object@@" ; break ;
939
951
case BuiltinType::ObjCClass: Out << " PAUobjc_class@@" ; break ;
940
952
case BuiltinType::ObjCSel: Out << " PAUobjc_selector@@" ; break ;
953
+
954
+ case BuiltinType::NullPtr: Out << " $$T" ; break ;
941
955
942
956
case BuiltinType::Char16:
943
957
case BuiltinType::Char32:
944
- case BuiltinType::Half:
945
- case BuiltinType::NullPtr: {
958
+ case BuiltinType::Half: {
946
959
DiagnosticsEngine &Diags = Context.getDiags ();
947
960
unsigned DiagID = Diags.getCustomDiagID (DiagnosticsEngine::Error,
948
961
" cannot mangle this built-in %0 type yet" );
949
962
Diags.Report (Range.getBegin (), DiagID)
950
963
<< T->getName (Context.getASTContext ().getPrintingPolicy ())
951
964
<< Range;
965
+ break ;
952
966
}
953
967
}
954
968
}
@@ -986,29 +1000,45 @@ void MicrosoftCXXNameMangler::mangleType(const FunctionType *T,
986
1000
// ::= @ # structors (they have no declared return type)
987
1001
if (IsStructor)
988
1002
Out << ' @' ;
989
- else
1003
+ else {
1004
+ QualType Result = Proto->getResultType ();
1005
+ const Type* RT = Result.getTypePtr ();
1006
+ if (isa<TagType>(RT) && !RT->isAnyPointerType () && !RT->isReferenceType ())
1007
+ Out << " ?A" ;
990
1008
// FIXME: Get the source range for the result type. Or, better yet,
991
1009
// implement the unimplemented stuff so we don't need accurate source
992
1010
// location info anymore :).
993
- mangleType (Proto->getResultType (), SourceRange ());
1011
+ mangleType (Result, SourceRange ());
1012
+ }
994
1013
995
1014
// <argument-list> ::= X # void
996
1015
// ::= <type>+ @
997
1016
// ::= <type>* Z # varargs
998
1017
if (Proto->getNumArgs () == 0 && !Proto->isVariadic ()) {
999
1018
Out << ' X' ;
1000
1019
} else {
1020
+ typedef llvm::DenseMap<void *, unsigned > BackRef;
1021
+ BackRef BackReferences;
1001
1022
if (D) {
1002
1023
// If we got a decl, use the type-as-written to make sure arrays
1003
1024
// get mangled right. Note that we can't rely on the TSI
1004
1025
// existing if (for example) the parameter was synthesized.
1005
1026
for (FunctionDecl::param_const_iterator Parm = D->param_begin (),
1006
1027
ParmEnd = D->param_end (); Parm != ParmEnd; ++Parm) {
1007
- if (TypeSourceInfo *typeAsWritten = (*Parm)->getTypeSourceInfo ())
1008
- mangleType (typeAsWritten->getType (),
1009
- typeAsWritten->getTypeLoc ().getSourceRange ());
1010
- else
1011
- mangleType ((*Parm)->getType (), SourceRange ());
1028
+ TypeSourceInfo *TSI = (*Parm)->getTypeSourceInfo ();
1029
+ QualType Type = TSI ? TSI->getType () : (*Parm)->getType ();
1030
+ CanQualType Canonical = getASTContext ().getCanonicalType (Type);
1031
+ void *TypePtr = Canonical.getAsOpaquePtr ();
1032
+ BackRef::iterator Found = BackReferences.find (TypePtr);
1033
+ if (Found == BackReferences.end ()) {
1034
+ mangleType (Type, (*Parm)->getSourceRange ());
1035
+ if (BackReferences.size () < 10 && (Canonical->getTypeClass () != Type::Builtin)) {
1036
+ size_t Size = BackReferences.size ();
1037
+ BackReferences[TypePtr] = Size;
1038
+ }
1039
+ } else {
1040
+ Out << Found->second ;
1041
+ }
1012
1042
}
1013
1043
} else {
1014
1044
for (FunctionProtoType::arg_type_iterator Arg = Proto->arg_type_begin (),
@@ -1316,13 +1346,16 @@ void MicrosoftCXXNameMangler::mangleType(const LValueReferenceType *T,
1316
1346
mangleType (PointeeTy, Range);
1317
1347
}
1318
1348
1349
+ // <type> ::= <r-value-reference-type>
1350
+ // <r-value-reference-type> ::= $$Q <cvr-qualifiers> <type>
1319
1351
void MicrosoftCXXNameMangler::mangleType (const RValueReferenceType *T,
1320
1352
SourceRange Range) {
1321
- DiagnosticsEngine &Diags = Context.getDiags ();
1322
- unsigned DiagID = Diags.getCustomDiagID (DiagnosticsEngine::Error,
1323
- " cannot mangle this r-value reference type yet" );
1324
- Diags.Report (Range.getBegin (), DiagID)
1325
- << Range;
1353
+ Out << " $$Q" ;
1354
+ QualType PointeeTy = T->getPointeeType ();
1355
+ if (!PointeeTy.hasQualifiers ())
1356
+ // Lack of qualifiers is mangled as 'A'.
1357
+ Out << ' A' ;
1358
+ mangleType (PointeeTy, Range);
1326
1359
}
1327
1360
1328
1361
void MicrosoftCXXNameMangler::mangleType (const ComplexType *T,
0 commit comments