6
6
//
7
7
// ===----------------------------------------------------------------------===//
8
8
9
- // Tests for ItaniumDemangle live in llvm/unittests/Demangle
9
+ // This test is too big for most embedded devices.
10
+ // XFAIL: LIBCXX-PICOLIBC-FIXME
10
11
11
12
// This test exercises support for char array initializer lists added in
12
13
// dd8b266ef.
13
14
// UNSUPPORTED: using-built-library-before-llvm-20
14
15
16
+ // XFAIL: win32-broken-printf-a-precision
17
+
15
18
#include " support/timer.h"
16
19
#include < algorithm>
17
20
#include < cassert>
21
24
#include < cxxabi.h>
22
25
#include < string>
23
26
27
+ // Is long double fp80? (Only x87 extended double has 64-bit mantissa)
28
+ #define LDBL_FP80 (__LDBL_MANT_DIG__ == 64 )
29
+ // Is long double fp128?
30
+ #define LDBL_FP128 (__LDBL_MANT_DIG__ == 113 )
31
+
32
+ const char * cases[][2 ] = {
33
+ #include " DemangleTestCases.inc"
34
+ };
35
+
36
+ const unsigned N = sizeof (cases) / sizeof (cases[0 ]);
37
+
38
+ struct FPLiteralCase {
39
+ const char *mangled;
40
+ // There are four possible demanglings of a given float.
41
+ std::string expecting[4 ];
42
+ } fp_literal_cases[] = {
43
+ // clang-format off
44
+ {" _ZN5test01gIfEEvRAszplcvT__ELf40a00000E_c" ,
45
+ {
46
+ " void test0::g<float>(char (&) [sizeof ((float)() + 0x1.4p+2f)])" ,
47
+ " void test0::g<float>(char (&) [sizeof ((float)() + 0x2.8p+1f)])" ,
48
+ " void test0::g<float>(char (&) [sizeof ((float)() + 0x5p+0f)])" ,
49
+ " void test0::g<float>(char (&) [sizeof ((float)() + 0xap-1f)])" ,
50
+ }},
51
+ {" _ZN5test01hIfEEvRAszplcvT__ELd4014000000000000E_c" ,
52
+ {
53
+ " void test0::h<float>(char (&) [sizeof ((float)() + 0x1.4p+2)])" ,
54
+ " void test0::h<float>(char (&) [sizeof ((float)() + 0x2.8p+1)])" ,
55
+ " void test0::h<float>(char (&) [sizeof ((float)() + 0x5p+0)])" ,
56
+ " void test0::h<float>(char (&) [sizeof ((float)() + 0xap-1)])" ,
57
+ }},
58
+ #if LDBL_FP80
59
+ {" _ZN5test01hIfEEvRAcvjplstT_Le4001a000000000000000E_c" ,
60
+ {
61
+ " void test0::h<float>(char (&) [(unsigned int)(sizeof (float) + 0x1.4p+2L)])" ,
62
+ " void test0::h<float>(char (&) [(unsigned int)(sizeof (float) + 0x2.8p+1L)])" ,
63
+ " void test0::h<float>(char (&) [(unsigned int)(sizeof (float) + 0x5p+0L)])" ,
64
+ " void test0::h<float>(char (&) [(unsigned int)(sizeof (float) + 0xap-1L)])" ,
65
+ }},
66
+ #endif
67
+ #if LDBL_FP128
68
+ // A 32-character FP literal of long double type
69
+ {" 3FooILeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeEE" ,
70
+ {" Foo<-0x1.eeeeeeeeeeeeeeeeeeeeeeeeeeeep+12015L>" }},
71
+ #endif
72
+ // clang-format on
73
+ };
74
+ const unsigned NF = sizeof (fp_literal_cases) / sizeof (fp_literal_cases[0 ]);
75
+ const unsigned NEF = sizeof (fp_literal_cases[0 ].expecting) /
76
+ sizeof (fp_literal_cases[0 ].expecting[0 ]);
77
+
78
+ const char *invalid_cases[] = {
79
+ // clang-format off
80
+ " _ZIPPreEncode" ,
81
+ " Agentt" ,
82
+ " NSoERj5E=Y1[uM:ga" ,
83
+ " Aon_PmKVPDk7?fg4XP5smMUL6;<WsI_mgbf23cCgsHbT<l8EE\0 uVRkNOoXDrgdA4[8IU>Vl<>IL8ayHpiVDDDXTY;^o9;i" ,
84
+ " _ZNSt16allocator_traitsISaIN4llvm3sys2fs18directory_iteratorEEE9constructIS3_IS3_EEEDTcl12_S_constructfp_fp0_spcl7forwardIT0_Efp1_EEERS4_PT_DpOS7_" ,
85
+ " 3FooILdaaaaaaaaaaAAAAaaEE" ,
86
+ " 3FooILdaaaaaaaaaaaaaaEE" ,
87
+ #if !LDBL_FP80
88
+ " _ZN5test01hIfEEvRAcvjplstT_Le4001a000000000000000E_c" ,
89
+ #endif
90
+ // The following test cases were found by libFuzzer+ASAN
91
+ " \x44\x74\x70\x74\x71\x75\x34\x43\x41\x72\x4D\x6E\x65\x34\x9F\xC1\x43\x41\x72\x4D\x6E\x77\x38\x9A\x8E\x44\x6F\x64\x6C\x53\xF9\x5F\x70\x74\x70\x69\x45\x34\xD3\x73\x9E\x2A\x37 " ,
92
+ " \x4D\x41\x72\x63\x4E\x39\x44\x76\x72\x4D\x34\x44\x53\x4B\x6F\x44\x54\x6E\x61\x37\x47\x77\x78\x38\x43\x27\x41\x5F\x73\x70\x69\x45 *" ,
93
+ " \x41\x64\x6E\x32 *" ,
94
+ " \x43\x46\x41\x67\x73 *" ,
95
+ " \x72\x3A\x4E\x53\x64\x45\x39\x4F\x52\x4E\x1F\x43\x34\x64\x54\x5F\x49\x31\x41\x63\x6C\x37\x2A\x4D\x41\x67\x73\x76\x43\x54\x35\x5F\x49\x4B\x4C\x55\x6C\x73\x4C\x38\x64\x43\x41\x47\x4C\x5A\x28\x4F\x41\x6E\x77\x5F\x53\x6F\x70\x69\x45\x5F\x63\x47\x61\x4C\x31\x4F\x4C\x33\x3E\x41\x4C\x4B\x4C\x55\x6C\x73\x4C\x38\x64\x43\x66\x41\x47\x4C\x5A\x28\x4F\x41\x6E\x77\x5F\x53\x6F\x70\x69\x45\x5F\x37\x41 *" ,
96
+ " \x2D\x5F\x63\x47\x4F\x63\xD3 " ,
97
+ " \x44\x74\x70\x74\x71\x75\x32\x43\x41\x38\x65\x6E\x9B\x72\x4D\xC1\x43\x41\x72\x4D\x6E\x77\x38\x9A\x8E\x44\x6F\x64\xC3\x53\xF9\x5F\x70\x74\x70\x69\x45\x38\xD3\x73\x9E\x2A\x37 " ,
98
+ " \x4C\x5A\x4C\x55\x6C\x4D\x41\x5F\x41\x67\x74\x71\x75\x34\x4D\x41\x64\x73\x4C\x44\x76\x72\x4D\x34\x44\x4B\x44\x54\x6E\x61\x37\x47\x77\x78\x38\x43\x27\x41\x5F\x73\x70\x69\x45\x6D\x73\x72\x53\x41\x6F\x41\x7B " ,
99
+ " \x44\x74\x70\x74\x71\x75\x32\x43\x41\x38\x65\x6E\x9B\x72\x4D\xC1\x43\x41\x72\x4D\x6E\x77\x38\x9A\x8E\x44\x6F\x64\x2C\x53\xF9\x5F\x70\x74\x70\x69\x45\xB4\xD3\x73\x9F\x2A\x37 " ,
100
+ " \x4C\x5A\x4C\x55\x6C\x69\x4D\x73\x72\x53\x6F\x7A\x41\x5F\x41\x67\x74\x71\x75\x32\x4D\x41\x64\x73\x39\x28\x76\x72\x4D\x34\x44\x4B\x45\x54\x6E\x61\x37\x47\x77\x78\x38\x43\x27\x41\x5F\x73\x70\x69\x45\x6F\x45\x49\x6D\x1A\x4C\x53\x38\x6A\x7A\x5A " ,
101
+ " \x44\x74\x63 *" ,
102
+ " \x44\x74\x71\x75\x35\x2A\xDF\x74\x44\x61\x73\x63\x35\x2A\x3B\x41\x72\x4D\x6E\x65\x34\x9F\xC1\x63\x41\x72\x4D\x6E\x77\x38\x9A\x8E\x44\x6F\x64\x6C\x53\xF9\x5F\x70\x74\x70\x69\x45\x33\x44\x76\x35 " ,
103
+ " \x44\x74\x70\x74\x71\x75\x32\x43\x41\x38\x65\x6E\x9B\x72\x4D\xC1\x43\x41\x72\x4D\x6E\x77\x38\x9A\x8E\x44\x6F\x64\x6C\x53\xF9\x5F\x70\x74\x70\x69\x45\x38\xD3\x73\x9E\x2A\x37 " ,
104
+ " \x46\x44\x74\x70\x74\x71\x75\x32\x43\x41\x72\x4D\x6E\x65\x34\x9F\xC1\x43\x41\x72\x4D\x6E\x77\x38\x9A\x8E\x44\x6F\x64\x6C\x53\xF9\x5F\x70\x74\x70\x69\x45\x34\xD3\x73\x9E\x2A\x37\x72\x33\x8E\x3A\x29\x8E\x44\x35 " ,
105
+ " _ZcvCiIJEEDvT__FFFFT_vT_v" ,
106
+ " Z1JIJ1_T_EE3o00EUlT_E0" ,
107
+ " ___Z2i_D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D1D" ,
108
+ " ZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIDv_ZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIDv_ZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIDv_Dv_Dv_Dv_Dv_dZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIDv_ZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIDv_ZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIZcvSdIDv_Dv_Dv_Dv_Dv_d" ,
109
+ " Z1 Z1 IJEEAcvZcvT_EcvT_T_" ,
110
+ " T_IZaaIJEEAnaaaT_T__" ,
111
+ " PT_IJPNT_IJEET_T_T_T_)J)JKE" ,
112
+ " 1 IJEVNT_T_T_EE" ,
113
+ " AT__ZSiIJEEAnwscT_T__" ,
114
+ " FSiIJEENT_IoE " ,
115
+ " ZTVSiIZTVSiIZTVSiIZTVSiINIJEET_T_T_T_T_ " ,
116
+ " Ana_T_E_T_IJEffffffffffffffersfffffrsrsffffffbgE" ,
117
+
118
+ " _ZN3TPLS_E" ,
119
+ " _ZN3CLSIiEIiEE" ,
120
+ " _ZN3CLSDtLi0EEE" ,
121
+ " _ZN3CLSIiEEvNS_T_Ev" ,
122
+
123
+ " _ZN1fIiEEvNTUt_E" ,
124
+ " _ZNDTUt_Ev" ,
125
+
126
+ " _Z1fIXfLpt1x1yEEvv" ,
127
+ " _Z1fIXfLdt1x1yEEvv" ,
128
+
129
+ " _ZN1fIXawLi0EEEEvv" ,
130
+
131
+ " _ZNWUt_3FOOEv" ,
132
+ " _ZWDC3FOOEv" ,
133
+ " _ZGI3Foo" ,
134
+ " _ZGIW3Foov" ,
135
+ " W1x" ,
136
+ // clang-format on
137
+ };
138
+
139
+ const unsigned NI = sizeof (invalid_cases) / sizeof (invalid_cases[0 ]);
140
+
24
141
void test () {
25
142
std::size_t len = 0 ;
26
143
char *buf = nullptr ;
27
144
bool failed = false ;
28
- const char * mangled = " _ZN5test71XIiEC1IdEEPT_PNS_5int_cIXplL_ZNS_4metaIiE5valueEEsrNS6_IS3_EE5valueEE4typeE" ;
29
- const char * expected =
30
- " test7::X<int>::X<double>(double*, test7::int_c<test7::meta<int>::value + test7::meta<double>::value>::type*)" ;
31
-
32
- int status;
33
- char * demang = __cxxabiv1::__cxa_demangle (mangled, buf, &len, &status);
34
- if (!demang || std::strcmp (demang, expected) != 0 || status != 0 ) {
35
- std::fprintf (stderr,
36
- " ERROR demangling %s\n "
37
- " expected: %s\n "
38
- " got: %d, %s\n " ,
39
- mangled, expected, status, demang ? demang : " (null)" );
40
- failed = true ;
145
+ for (unsigned i = 0 ; i < N; ++i) {
146
+ int status;
147
+ char *demang = __cxxabiv1::__cxa_demangle (cases[i][0 ], buf, &len, &status);
148
+ if (!demang || std::strcmp (demang, cases[i][1 ]) != 0 ) {
149
+ std::fprintf (stderr,
150
+ " ERROR demangling %s\n "
151
+ " expected: %s\n "
152
+ " got: %d, %s\n " ,
153
+ cases[i][0 ], cases[i][1 ], status,
154
+ demang ? demang : " (null)" );
155
+ failed = true ;
156
+ }
157
+ if (demang)
158
+ buf = demang;
41
159
}
42
- if (demang)
43
- buf = demang;
44
-
45
160
free (buf);
46
161
assert (!failed && " demangle failed" );
47
162
}
@@ -50,48 +165,116 @@ void test_invalid_cases() {
50
165
std::size_t len = 0 ;
51
166
char *buf = nullptr ;
52
167
bool passed = false ;
53
- const char * invalid =
54
- " Aon_PmKVPDk7?fg4XP5smMUL6;<WsI_mgbf23cCgsHbT<l8EE\0 uVRkNOoXDrgdA4[8IU>Vl<>IL8ayHpiVDDDXTY;^o9;i" ;
55
-
56
- int status;
57
- char * demang = __cxxabiv1::__cxa_demangle (invalid, buf, &len, &status);
58
- if (status != -2 ) {
59
- std::printf (" %s should be invalid but is not\n " , invalid);
60
- std::printf (" Got: %d, %s\n " , status, demang ? demang : " (null)" );
61
- passed = true ;
168
+ for (unsigned i = 0 ; i < NI; ++i) {
169
+ int status;
170
+ char *demang =
171
+ __cxxabiv1::__cxa_demangle (invalid_cases[i], buf, &len, &status);
172
+ if (status != -2 ) {
173
+ std::printf (" %s should be invalid but is not\n " , invalid_cases[i]);
174
+ std::printf (" Got: %d, %s\n " , status, demang ? demang : " (null)" );
175
+ passed = true ;
176
+ }
177
+ if (demang)
178
+ buf = demang;
62
179
}
63
- if (demang)
64
- buf = demang;
65
-
66
180
free (buf);
67
181
assert (!passed && " demangle did not fail" );
68
182
}
69
183
70
- void test_invalid_args () {
71
- std::size_t len = 16 ;
72
- char buf[16 ];
73
- {
74
- // NULL mangled name should fail.
184
+ const char *const xfail_cases[] = {
185
+ // Sentinel value
186
+ nullptr ,
187
+ };
188
+
189
+ void test_xfail_cases () {
190
+ std::size_t len = 0 ;
191
+ char *buf = nullptr ;
192
+ for (const char *c_str : xfail_cases) {
193
+ if (!c_str)
194
+ break ;
75
195
int status;
76
- char * demang = __cxxabiv1::__cxa_demangle (nullptr , buf, &len, &status);
77
- assert (status == -3 );
78
- assert (!demang);
196
+ char *demang = __cxxabiv1::__cxa_demangle (c_str, buf, &len, &status);
197
+ if (status != -2 ) {
198
+ std::printf (" %s was documented as xfail but passed\n " , c_str);
199
+ std::printf (" Got status = %d\n " , status);
200
+ assert (status == -2 );
201
+ } else {
202
+ buf = demang;
203
+ }
79
204
}
205
+ free (buf);
206
+ }
80
207
81
- {
82
- // Buffer without specifying length should fail.
208
+ void testFPLiterals () {
209
+ std::size_t len = 0 ;
210
+ char *buf = nullptr ;
211
+ for (unsigned i = 0 ; i < NF; ++i) {
212
+ FPLiteralCase *fpCase = fp_literal_cases + i;
83
213
int status;
84
- char * demang = __cxxabiv1::__cxa_demangle (" _Z1fv" , buf, nullptr , &status);
85
- assert (status == -3 );
86
- assert (!demang);
214
+ char *demang =
215
+ __cxxabiv1::__cxa_demangle (fpCase->mangled , buf, &len, &status);
216
+ if (demang == 0 ) {
217
+ std::printf (" %s -> %s\n " , fpCase->mangled , fpCase->expecting [0 ].c_str ());
218
+ std::printf (" Got instead: NULL, %d\n " , status);
219
+ assert (false );
220
+ continue ;
221
+ }
222
+ std::string *e_beg = fpCase->expecting ;
223
+ std::string *e_end = fpCase->expecting + NEF;
224
+ if (std::find (e_beg, e_end, demang) == e_end) {
225
+ std::printf (" %s -> %s\n " , fpCase->mangled , fpCase->expecting [0 ].c_str ());
226
+ std::printf (" Got instead: %s\n " , demang);
227
+ assert (false );
228
+ continue ;
229
+ }
230
+ buf = demang;
87
231
}
232
+ free (buf);
88
233
}
89
234
90
- int main (int , char **) {
91
- timer t;
92
- test ();
93
- test_invalid_cases ();
94
- test_invalid_args ();
235
+ int main (int , char **) {
236
+ std::printf (" Testing %d symbols.\n " , N);
237
+ {
238
+ timer t;
239
+ test ();
240
+ test_invalid_cases ();
241
+ test_xfail_cases ();
242
+ testFPLiterals ();
243
+ }
244
+ #if 0
245
+ std::string input;
246
+ while (std::cin)
247
+ {
248
+ std::getline(std::cin, input);
249
+ if (std::cin.fail())
250
+ break;
251
+ std::size_t len = 0;
252
+ int status;
253
+ len = 0;
254
+ char* demang = abi::__cxa_demangle(input.c_str(), 0, &len, &status);
255
+ switch (status)
256
+ {
257
+ case -3:
258
+ std::cout << "Invalid arguments\n";
259
+ break;
260
+ case -2:
261
+ std::cout << "Invalid mangled name\n";
262
+ break;
263
+ case -1:
264
+ std::cout << "memory allocation failure\n";
265
+ break;
266
+ case 0:
267
+ std::cout << "len = " << len << '\n';
268
+ std::cout << demang << '\n';
269
+ std::free(demang);
270
+ break;
271
+ case 1:
272
+ std::cout << "not implemented\n";
273
+ break;
274
+ }
275
+ std::cout << '\n';
276
+ }
277
+ #endif
95
278
96
279
return 0 ;
97
280
}
0 commit comments