@@ -115,8 +115,10 @@ class ItaniumMangleContextImpl : public ItaniumMangleContext {
115
115
void mangleCXXCtorVTable (const CXXRecordDecl *RD, int64_t Offset,
116
116
const CXXRecordDecl *Type, raw_ostream &) override ;
117
117
void mangleCXXRTTI (QualType T, raw_ostream &) override ;
118
- void mangleCXXRTTIName (QualType T, raw_ostream &) override ;
119
- void mangleTypeName (QualType T, raw_ostream &) override ;
118
+ void mangleCXXRTTIName (QualType T, raw_ostream &,
119
+ bool NormalizeIntegers) override ;
120
+ void mangleTypeName (QualType T, raw_ostream &,
121
+ bool NormalizeIntegers) override ;
120
122
121
123
void mangleCXXCtorComdat (const CXXConstructorDecl *D, raw_ostream &) override ;
122
124
void mangleCXXDtorComdat (const CXXDestructorDecl *D, raw_ostream &) override ;
@@ -221,6 +223,10 @@ class ItaniumMangleContextImpl : public ItaniumMangleContext {
221
223
class CXXNameMangler {
222
224
ItaniumMangleContextImpl &Context;
223
225
raw_ostream &Out;
226
+ // / Normalize integer types for cross-language CFI support with other
227
+ // / languages that can't represent and encode C/C++ integer types.
228
+ bool NormalizeIntegers = false ;
229
+
224
230
bool NullOut = false ;
225
231
// / In the "DisableDerivedAbiTags" mode derived ABI tags are not calculated.
226
232
// / This mode is used when mangler creates another mangler recursively to
@@ -419,6 +425,10 @@ class CXXNameMangler {
419
425
: Context(C), Out(Out_), Structor(getStructor(D)), StructorType(Type),
420
426
AbiTagsRoot(AbiTags) {}
421
427
428
+ CXXNameMangler (ItaniumMangleContextImpl &C, raw_ostream &Out_,
429
+ bool NormalizeIntegers_)
430
+ : Context(C), Out(Out_), NormalizeIntegers(NormalizeIntegers_),
431
+ NullOut(false ), AbiTagsRoot(AbiTags) {}
422
432
CXXNameMangler (CXXNameMangler &Outer, raw_ostream &Out_)
423
433
: Context(Outer.Context), Out(Out_), Structor(Outer.Structor),
424
434
StructorType(Outer.StructorType), SeqID(Outer.SeqID),
@@ -2944,6 +2954,85 @@ void CXXNameMangler::mangleType(const BuiltinType *T) {
2944
2954
// ::= Dn # std::nullptr_t (i.e., decltype(nullptr))
2945
2955
// ::= u <source-name> # vendor extended type
2946
2956
std::string type_name;
2957
+ // Normalize integer types as vendor extended types:
2958
+ // u<length>i<type size>
2959
+ // u<length>u<type size>
2960
+ if (NormalizeIntegers && T->isInteger ()) {
2961
+ if (T->isSignedInteger ()) {
2962
+ switch (getASTContext ().getTypeSize (T)) {
2963
+ case 8 :
2964
+ // Pick a representative for each integer size in the substitution
2965
+ // dictionary. (Its actual defined size is not relevant.)
2966
+ if (mangleSubstitution (BuiltinType::SChar))
2967
+ break ;
2968
+ Out << " u2i8" ;
2969
+ addSubstitution (BuiltinType::SChar);
2970
+ break ;
2971
+ case 16 :
2972
+ if (mangleSubstitution (BuiltinType::Short))
2973
+ break ;
2974
+ Out << " u3i16" ;
2975
+ addSubstitution (BuiltinType::Short);
2976
+ break ;
2977
+ case 32 :
2978
+ if (mangleSubstitution (BuiltinType::Int))
2979
+ break ;
2980
+ Out << " u3i32" ;
2981
+ addSubstitution (BuiltinType::Int);
2982
+ break ;
2983
+ case 64 :
2984
+ if (mangleSubstitution (BuiltinType::Long))
2985
+ break ;
2986
+ Out << " u3i64" ;
2987
+ addSubstitution (BuiltinType::Long);
2988
+ break ;
2989
+ case 128 :
2990
+ if (mangleSubstitution (BuiltinType::Int128))
2991
+ break ;
2992
+ Out << " u4i128" ;
2993
+ addSubstitution (BuiltinType::Int128);
2994
+ break ;
2995
+ default :
2996
+ llvm_unreachable (" Unknown integer size for normalization" );
2997
+ }
2998
+ } else {
2999
+ switch (getASTContext ().getTypeSize (T)) {
3000
+ case 8 :
3001
+ if (mangleSubstitution (BuiltinType::UChar))
3002
+ break ;
3003
+ Out << " u2u8" ;
3004
+ addSubstitution (BuiltinType::UChar);
3005
+ break ;
3006
+ case 16 :
3007
+ if (mangleSubstitution (BuiltinType::UShort))
3008
+ break ;
3009
+ Out << " u3u16" ;
3010
+ addSubstitution (BuiltinType::UShort);
3011
+ break ;
3012
+ case 32 :
3013
+ if (mangleSubstitution (BuiltinType::UInt))
3014
+ break ;
3015
+ Out << " u3u32" ;
3016
+ addSubstitution (BuiltinType::UInt);
3017
+ break ;
3018
+ case 64 :
3019
+ if (mangleSubstitution (BuiltinType::ULong))
3020
+ break ;
3021
+ Out << " u3u64" ;
3022
+ addSubstitution (BuiltinType::ULong);
3023
+ break ;
3024
+ case 128 :
3025
+ if (mangleSubstitution (BuiltinType::UInt128))
3026
+ break ;
3027
+ Out << " u4u128" ;
3028
+ addSubstitution (BuiltinType::UInt128);
3029
+ break ;
3030
+ default :
3031
+ llvm_unreachable (" Unknown integer size for normalization" );
3032
+ }
3033
+ }
3034
+ return ;
3035
+ }
2947
3036
switch (T->getKind ()) {
2948
3037
case BuiltinType::Void:
2949
3038
Out << ' v' ;
@@ -6558,16 +6647,17 @@ void ItaniumMangleContextImpl::mangleCXXRTTI(QualType Ty, raw_ostream &Out) {
6558
6647
Mangler.mangleType (Ty);
6559
6648
}
6560
6649
6561
- void ItaniumMangleContextImpl::mangleCXXRTTIName (QualType Ty,
6562
- raw_ostream &Out ) {
6650
+ void ItaniumMangleContextImpl::mangleCXXRTTIName (
6651
+ QualType Ty, raw_ostream &Out, bool NormalizeIntegers = false ) {
6563
6652
// <special-name> ::= TS <type> # typeinfo name (null terminated byte string)
6564
- CXXNameMangler Mangler (*this , Out);
6653
+ CXXNameMangler Mangler (*this , Out, NormalizeIntegers );
6565
6654
Mangler.getStream () << " _ZTS" ;
6566
6655
Mangler.mangleType (Ty);
6567
6656
}
6568
6657
6569
- void ItaniumMangleContextImpl::mangleTypeName (QualType Ty, raw_ostream &Out) {
6570
- mangleCXXRTTIName (Ty, Out);
6658
+ void ItaniumMangleContextImpl::mangleTypeName (QualType Ty, raw_ostream &Out,
6659
+ bool NormalizeIntegers = false ) {
6660
+ mangleCXXRTTIName (Ty, Out, NormalizeIntegers);
6571
6661
}
6572
6662
6573
6663
void ItaniumMangleContextImpl::mangleStringLiteral (const StringLiteral *, raw_ostream &) {
0 commit comments