]> git.ipfire.org Git - thirdparty/gcc.git/blame - libiberty/cplus-dem.c
* config.gcc: Update c4x and i370 for C front end-specific
[thirdparty/gcc.git] / libiberty / cplus-dem.c
CommitLineData
0f82222a 1/* Demangler for GNU C++
f0bff53d 2 Copyright 1989, 1991, 1994, 1995, 1996, 1997, 1998, 1999,
1c1033dd 3 2000, 2001 Free Software Foundation, Inc.
28e9041c 4 Written by James Clark (jjc@jclark.uucp)
5 Rewritten by Fred Fish (fnf@cygnus.com) for ARM and Lucid demangling
f75dc4de 6 Modified by Satish Pai (pai@apollo.hp.com) for HP demangling
0f82222a 7
28e9041c 8This file is part of the libiberty library.
9Libiberty is free software; you can redistribute it and/or
10modify it under the terms of the GNU Library General Public
11License as published by the Free Software Foundation; either
12version 2 of the License, or (at your option) any later version.
13
14Libiberty is distributed in the hope that it will be useful,
15but WITHOUT ANY WARRANTY; without even the implied warranty of
16MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17Library General Public License for more details.
18
19You should have received a copy of the GNU Library General Public
20License along with libiberty; see the file COPYING.LIB. If
21not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
22Boston, MA 02111-1307, USA. */
23
24/* This file exports two functions; cplus_mangle_opname and cplus_demangle.
25
26 This file imports xmalloc and xrealloc, which are like malloc and
27 realloc except that they generate a fatal error if there is no
28 available memory. */
29
30/* This file lives in both GCC and libiberty. When making changes, please
31 try not to break either. */
32
00af597b 33#ifdef HAVE_CONFIG_H
34#include "config.h"
35#endif
36
93ce8ce4 37#include "safe-ctype.h"
38
f39af051 39#include <sys/types.h>
28e9041c 40#include <string.h>
41#include <stdio.h>
42
f39af051 43#ifdef HAVE_STDLIB_H
44#include <stdlib.h>
00af597b 45#else
46char * malloc ();
47char * realloc ();
f39af051 48#endif
49
28e9041c 50#include <demangle.h>
51#undef CURRENT_DEMANGLING_STYLE
52#define CURRENT_DEMANGLING_STYLE work->options
53
4ae63959 54#include "libiberty.h"
28e9041c 55
626946fb 56static char *ada_demangle PARAMS ((const char *, int));
d7c1c148 57
41980611 58#define min(X,Y) (((X) < (Y)) ? (X) : (Y))
59
42c870f1 60/* A value at least one greater than the maximum number of characters
61 that will be output when using the `%d' format with `printf'. */
62#define INTBUF_SIZE 32
63
4d84eafd 64extern void fancy_abort PARAMS ((void)) ATTRIBUTE_NORETURN;
65
28e9041c 66static const char *mystrstr PARAMS ((const char *, const char *));
67
68static const char *
69mystrstr (s1, s2)
70 const char *s1, *s2;
71{
72 register const char *p = s1;
73 register int len = strlen (s2);
74
75 for (; (p = strchr (p, *s2)) != 0; p++)
76 {
77 if (strncmp (p, s2, len) == 0)
78 {
79 return (p);
80 }
81 }
82 return (0);
83}
84
85/* In order to allow a single demangler executable to demangle strings
86 using various common values of CPLUS_MARKER, as well as any specific
87 one set at compile time, we maintain a string containing all the
88 commonly used ones, and check to see if the marker we are looking for
89 is in that string. CPLUS_MARKER is usually '$' on systems where the
90 assembler can deal with that. Where the assembler can't, it's usually
91 '.' (but on many systems '.' is used for other things). We put the
92 current defined CPLUS_MARKER first (which defaults to '$'), followed
93 by the next most common value, followed by an explicit '$' in case
94 the value of CPLUS_MARKER is not '$'.
95
96 We could avoid this if we could just get g++ to tell us what the actual
97 cplus marker character is as part of the debug information, perhaps by
98 ensuring that it is the character that terminates the gcc<n>_compiled
99 marker symbol (FIXME). */
100
101#if !defined (CPLUS_MARKER)
102#define CPLUS_MARKER '$'
103#endif
104
bb505139 105enum demangling_styles current_demangling_style = auto_demangling;
28e9041c 106
107static char cplus_markers[] = { CPLUS_MARKER, '.', '$', '\0' };
108
f75dc4de 109static char char_str[2] = { '\000', '\000' };
110
28e9041c 111void
112set_cplus_marker_for_demangling (ch)
113 int ch;
114{
115 cplus_markers[0] = ch;
116}
117
99906878 118typedef struct string /* Beware: these aren't required to be */
119{ /* '\0' terminated. */
120 char *b; /* pointer to start of string */
121 char *p; /* pointer after last character */
122 char *e; /* pointer after end of allocated space */
123} string;
124
28e9041c 125/* Stuff that is shared between sub-routines.
126 Using a shared structure allows cplus_demangle to be reentrant. */
127
128struct work_stuff
129{
130 int options;
131 char **typevec;
fa4f3779 132 char **ktypevec;
133 char **btypevec;
134 int numk;
135 int numb;
136 int ksize;
137 int bsize;
28e9041c 138 int ntypes;
139 int typevec_size;
140 int constructor;
141 int destructor;
142 int static_type; /* A static member function */
0f82222a 143 int temp_start; /* index in demangled to start of template args */
3e04bd45 144 int type_quals; /* The type qualifiers. */
37c9cc60 145 int dllimported; /* Symbol imported from a PE DLL */
402ace4b 146 char **tmpl_argvec; /* Template function arguments. */
147 int ntmpl_args; /* The number of template function arguments. */
99906878 148 int forgetting_types; /* Nonzero if we are not remembering the types
149 we see. */
150 string* previous_argument; /* The last function argument demangled. */
151 int nrepeats; /* The number of times to repeat the previous
152 argument. */
28e9041c 153};
154
155#define PRINT_ANSI_QUALIFIERS (work -> options & DMGL_ANSI)
156#define PRINT_ARG_TYPES (work -> options & DMGL_PARAMS)
157
158static const struct optable
159{
542e9271 160 const char *const in;
161 const char *const out;
162 const int flags;
28e9041c 163} optable[] = {
164 {"nw", " new", DMGL_ANSI}, /* new (1.92, ansi) */
165 {"dl", " delete", DMGL_ANSI}, /* new (1.92, ansi) */
166 {"new", " new", 0}, /* old (1.91, and 1.x) */
167 {"delete", " delete", 0}, /* old (1.91, and 1.x) */
168 {"vn", " new []", DMGL_ANSI}, /* GNU, pending ansi */
169 {"vd", " delete []", DMGL_ANSI}, /* GNU, pending ansi */
170 {"as", "=", DMGL_ANSI}, /* ansi */
171 {"ne", "!=", DMGL_ANSI}, /* old, ansi */
172 {"eq", "==", DMGL_ANSI}, /* old, ansi */
173 {"ge", ">=", DMGL_ANSI}, /* old, ansi */
174 {"gt", ">", DMGL_ANSI}, /* old, ansi */
175 {"le", "<=", DMGL_ANSI}, /* old, ansi */
176 {"lt", "<", DMGL_ANSI}, /* old, ansi */
177 {"plus", "+", 0}, /* old */
178 {"pl", "+", DMGL_ANSI}, /* ansi */
179 {"apl", "+=", DMGL_ANSI}, /* ansi */
180 {"minus", "-", 0}, /* old */
181 {"mi", "-", DMGL_ANSI}, /* ansi */
182 {"ami", "-=", DMGL_ANSI}, /* ansi */
183 {"mult", "*", 0}, /* old */
184 {"ml", "*", DMGL_ANSI}, /* ansi */
185 {"amu", "*=", DMGL_ANSI}, /* ansi (ARM/Lucid) */
186 {"aml", "*=", DMGL_ANSI}, /* ansi (GNU/g++) */
187 {"convert", "+", 0}, /* old (unary +) */
188 {"negate", "-", 0}, /* old (unary -) */
189 {"trunc_mod", "%", 0}, /* old */
190 {"md", "%", DMGL_ANSI}, /* ansi */
191 {"amd", "%=", DMGL_ANSI}, /* ansi */
192 {"trunc_div", "/", 0}, /* old */
193 {"dv", "/", DMGL_ANSI}, /* ansi */
194 {"adv", "/=", DMGL_ANSI}, /* ansi */
195 {"truth_andif", "&&", 0}, /* old */
196 {"aa", "&&", DMGL_ANSI}, /* ansi */
197 {"truth_orif", "||", 0}, /* old */
198 {"oo", "||", DMGL_ANSI}, /* ansi */
199 {"truth_not", "!", 0}, /* old */
200 {"nt", "!", DMGL_ANSI}, /* ansi */
201 {"postincrement","++", 0}, /* old */
202 {"pp", "++", DMGL_ANSI}, /* ansi */
203 {"postdecrement","--", 0}, /* old */
204 {"mm", "--", DMGL_ANSI}, /* ansi */
205 {"bit_ior", "|", 0}, /* old */
206 {"or", "|", DMGL_ANSI}, /* ansi */
207 {"aor", "|=", DMGL_ANSI}, /* ansi */
208 {"bit_xor", "^", 0}, /* old */
209 {"er", "^", DMGL_ANSI}, /* ansi */
210 {"aer", "^=", DMGL_ANSI}, /* ansi */
211 {"bit_and", "&", 0}, /* old */
212 {"ad", "&", DMGL_ANSI}, /* ansi */
213 {"aad", "&=", DMGL_ANSI}, /* ansi */
214 {"bit_not", "~", 0}, /* old */
215 {"co", "~", DMGL_ANSI}, /* ansi */
216 {"call", "()", 0}, /* old */
217 {"cl", "()", DMGL_ANSI}, /* ansi */
218 {"alshift", "<<", 0}, /* old */
219 {"ls", "<<", DMGL_ANSI}, /* ansi */
220 {"als", "<<=", DMGL_ANSI}, /* ansi */
221 {"arshift", ">>", 0}, /* old */
222 {"rs", ">>", DMGL_ANSI}, /* ansi */
223 {"ars", ">>=", DMGL_ANSI}, /* ansi */
224 {"component", "->", 0}, /* old */
225 {"pt", "->", DMGL_ANSI}, /* ansi; Lucid C++ form */
226 {"rf", "->", DMGL_ANSI}, /* ansi; ARM/GNU form */
227 {"indirect", "*", 0}, /* old */
228 {"method_call", "->()", 0}, /* old */
229 {"addr", "&", 0}, /* old (unary &) */
230 {"array", "[]", 0}, /* old */
231 {"vc", "[]", DMGL_ANSI}, /* ansi */
232 {"compound", ", ", 0}, /* old */
233 {"cm", ", ", DMGL_ANSI}, /* ansi */
234 {"cond", "?:", 0}, /* old */
235 {"cn", "?:", DMGL_ANSI}, /* pseudo-ansi */
236 {"max", ">?", 0}, /* old */
237 {"mx", ">?", DMGL_ANSI}, /* pseudo-ansi */
238 {"min", "<?", 0}, /* old */
239 {"mn", "<?", DMGL_ANSI}, /* pseudo-ansi */
240 {"nop", "", 0}, /* old (for operator=) */
80283fb2 241 {"rm", "->*", DMGL_ANSI}, /* ansi */
242 {"sz", "sizeof ", DMGL_ANSI} /* pseudo-ansi */
28e9041c 243};
244
2d53096b 245/* These values are used to indicate the various type varieties.
246 They are all non-zero so that they can be used as `success'
247 values. */
0f82222a 248typedef enum type_kind_t
249{
2d53096b 250 tk_none,
251 tk_pointer,
73bea962 252 tk_reference,
0f82222a 253 tk_integral,
2d53096b 254 tk_bool,
0f82222a 255 tk_char,
2d53096b 256 tk_real
257} type_kind_t;
0f82222a 258
542e9271 259const struct demangler_engine libiberty_demanglers[] =
6f572555 260{
261 {
262 AUTO_DEMANGLING_STYLE_STRING,
263 auto_demangling,
264 "Automatic selection based on executable"
265 }
266 ,
267 {
268 GNU_DEMANGLING_STYLE_STRING,
269 gnu_demangling,
270 "GNU (g++) style demangling"
271 }
272 ,
273 {
274 LUCID_DEMANGLING_STYLE_STRING,
275 lucid_demangling,
276 "Lucid (lcc) style demangling"
277 }
278 ,
279 {
280 ARM_DEMANGLING_STYLE_STRING,
281 arm_demangling,
282 "ARM style demangling"
283 }
284 ,
285 {
286 HP_DEMANGLING_STYLE_STRING,
287 hp_demangling,
288 "HP (aCC) style demangling"
289 }
290 ,
291 {
292 EDG_DEMANGLING_STYLE_STRING,
293 edg_demangling,
294 "EDG style demangling"
295 }
296 ,
168d63e5 297 {
bb505139 298 GNU_V3_DEMANGLING_STYLE_STRING,
299 gnu_v3_demangling,
300 "GNU (g++) V3 ABI-style demangling"
168d63e5 301 }
302 ,
d7c1c148 303 {
304 JAVA_DEMANGLING_STYLE_STRING,
305 java_demangling,
306 "Java style demangling"
307 }
308 ,
309 {
310 GNAT_DEMANGLING_STYLE_STRING,
311 gnat_demangling,
312 "GNAT style demangling"
313 }
314 ,
6f572555 315 {
316 NULL, unknown_demangling, NULL
317 }
318};
319
28e9041c 320#define STRING_EMPTY(str) ((str) -> b == (str) -> p)
321#define PREPEND_BLANK(str) {if (!STRING_EMPTY(str)) \
322 string_prepend(str, " ");}
323#define APPEND_BLANK(str) {if (!STRING_EMPTY(str)) \
324 string_append(str, " ");}
fa4f3779 325#define LEN_STRING(str) ( (STRING_EMPTY(str))?0:((str)->p - (str)->b))
28e9041c 326
99906878 327/* The scope separator appropriate for the language being demangled. */
bdaa26ad 328
329#define SCOPE_STRING(work) ((work->options & DMGL_JAVA) ? "." : "::")
99906878 330
28e9041c 331#define ARM_VTABLE_STRING "__vtbl__" /* Lucid/ARM virtual table prefix */
332#define ARM_VTABLE_STRLEN 8 /* strlen (ARM_VTABLE_STRING) */
333
334/* Prototypes for local functions */
335
f2e5a608 336static void
337delete_work_stuff PARAMS ((struct work_stuff *));
338
339static void
340delete_non_B_K_work_stuff PARAMS ((struct work_stuff *));
341
28e9041c 342static char *
343mop_up PARAMS ((struct work_stuff *, string *, int));
344
cd03a192 345static void
fa4f3779 346squangle_mop_up PARAMS ((struct work_stuff *));
347
f2e5a608 348static void
349work_stuff_copy_to_from PARAMS ((struct work_stuff *, struct work_stuff *));
350
28e9041c 351#if 0
352static int
fa4f3779 353demangle_method_args PARAMS ((struct work_stuff *, const char **, string *));
28e9041c 354#endif
355
fa4f3779 356static char *
cd03a192 357internal_cplus_demangle PARAMS ((struct work_stuff *, const char *));
fa4f3779 358
f39af051 359static int
0f82222a 360demangle_template_template_parm PARAMS ((struct work_stuff *work,
f39af051 361 const char **, string *));
362
28e9041c 363static int
364demangle_template PARAMS ((struct work_stuff *work, const char **, string *,
99906878 365 string *, int, int));
28e9041c 366
367static int
368arm_pt PARAMS ((struct work_stuff *, const char *, int, const char **,
369 const char **));
370
28e9041c 371static int
372demangle_class_name PARAMS ((struct work_stuff *, const char **, string *));
373
374static int
375demangle_qualified PARAMS ((struct work_stuff *, const char **, string *,
376 int, int));
377
378static int
379demangle_class PARAMS ((struct work_stuff *, const char **, string *));
380
381static int
382demangle_fund_type PARAMS ((struct work_stuff *, const char **, string *));
383
384static int
385demangle_signature PARAMS ((struct work_stuff *, const char **, string *));
386
387static int
388demangle_prefix PARAMS ((struct work_stuff *, const char **, string *));
389
390static int
391gnu_special PARAMS ((struct work_stuff *, const char **, string *));
392
393static int
f39af051 394arm_special PARAMS ((const char **, string *));
28e9041c 395
396static void
397string_need PARAMS ((string *, int));
398
399static void
400string_delete PARAMS ((string *));
401
402static void
403string_init PARAMS ((string *));
404
405static void
406string_clear PARAMS ((string *));
407
408#if 0
409static int
410string_empty PARAMS ((string *));
411#endif
412
413static void
414string_append PARAMS ((string *, const char *));
415
416static void
417string_appends PARAMS ((string *, string *));
418
419static void
420string_appendn PARAMS ((string *, const char *, int));
421
422static void
423string_prepend PARAMS ((string *, const char *));
424
425static void
426string_prependn PARAMS ((string *, const char *, int));
427
42c870f1 428static void
429string_append_template_idx PARAMS ((string *, int));
430
28e9041c 431static int
432get_count PARAMS ((const char **, int *));
433
434static int
435consume_count PARAMS ((const char **));
436
0f82222a 437static int
402ace4b 438consume_count_with_underscores PARAMS ((const char**));
439
28e9041c 440static int
441demangle_args PARAMS ((struct work_stuff *, const char **, string *));
442
99906878 443static int
444demangle_nested_args PARAMS ((struct work_stuff*, const char**, string*));
445
28e9041c 446static int
447do_type PARAMS ((struct work_stuff *, const char **, string *));
448
449static int
450do_arg PARAMS ((struct work_stuff *, const char **, string *));
451
452static void
453demangle_function_name PARAMS ((struct work_stuff *, const char **, string *,
454 const char *));
455
f2e5a608 456static int
457iterate_demangle_function PARAMS ((struct work_stuff *,
458 const char **, string *, const char *));
459
28e9041c 460static void
461remember_type PARAMS ((struct work_stuff *, const char *, int));
462
fa4f3779 463static void
464remember_Btype PARAMS ((struct work_stuff *, const char *, int, int));
465
466static int
467register_Btype PARAMS ((struct work_stuff *));
468
469static void
470remember_Ktype PARAMS ((struct work_stuff *, const char *, int));
471
28e9041c 472static void
473forget_types PARAMS ((struct work_stuff *));
474
fa4f3779 475static void
476forget_B_and_K_types PARAMS ((struct work_stuff *));
477
28e9041c 478static void
479string_prepends PARAMS ((string *, string *));
480
0f82222a 481static int
482demangle_template_value_parm PARAMS ((struct work_stuff*, const char**,
2d53096b 483 string*, type_kind_t));
80283fb2 484
0f82222a 485static int
f75dc4de 486do_hpacc_template_const_value PARAMS ((struct work_stuff *, const char **, string *));
487
0f82222a 488static int
f75dc4de 489do_hpacc_template_literal PARAMS ((struct work_stuff *, const char **, string *));
490
0f82222a 491static int
7c8c70e9 492snarf_numeric_literal PARAMS ((const char **, string *));
f75dc4de 493
3e04bd45 494/* There is a TYPE_QUAL value for each type qualifier. They can be
495 combined by bitwise-or to form the complete set of qualifiers for a
496 type. */
497
498#define TYPE_UNQUALIFIED 0x0
499#define TYPE_QUAL_CONST 0x1
500#define TYPE_QUAL_VOLATILE 0x2
501#define TYPE_QUAL_RESTRICT 0x4
502
0f82222a 503static int
7c8c70e9 504code_for_qualifier PARAMS ((int));
3e04bd45 505
506static const char*
507qualifier_string PARAMS ((int));
508
509static const char*
7c8c70e9 510demangle_qualifier PARAMS ((int));
3e04bd45 511
42c870f1 512static int
513demangle_expression PARAMS ((struct work_stuff *, const char **, string *,
514 type_kind_t));
515
4d84eafd 516static int
517demangle_integral_value PARAMS ((struct work_stuff *, const char **,
518 string *));
519
42c870f1 520static int
521demangle_real_value PARAMS ((struct work_stuff *, const char **, string *));
522
4d84eafd 523static void
524demangle_arm_hp_template PARAMS ((struct work_stuff *, const char **, int,
525 string *));
526
527static void
528recursively_demangle PARAMS ((struct work_stuff *, const char **, string *,
529 int));
530
918a89ef 531static void
626946fb 532grow_vect PARAMS ((void **, size_t *, size_t, int));
918a89ef 533
9fec6063 534/* Translate count to integer, consuming tokens in the process.
535 Conversion terminates on the first non-digit character.
536
537 Trying to consume something that isn't a count results in no
538 consumption of input and a return of -1.
539
540 Overflow consumes the rest of the digits, and returns -1. */
28e9041c 541
542static int
543consume_count (type)
544 const char **type;
545{
9fec6063 546 int count = 0;
547
93ce8ce4 548 if (! ISDIGIT ((unsigned char)**type))
9fec6063 549 return -1;
28e9041c 550
93ce8ce4 551 while (ISDIGIT ((unsigned char)**type))
28e9041c 552 {
553 count *= 10;
9fec6063 554
555 /* Check for overflow.
556 We assume that count is represented using two's-complement;
557 no power of two is divisible by ten, so if an overflow occurs
558 when multiplying by ten, the result will not be a multiple of
559 ten. */
560 if ((count % 10) != 0)
6fd618e7 561 {
93ce8ce4 562 while (ISDIGIT ((unsigned char) **type))
9fec6063 563 (*type)++;
564 return -1;
6fd618e7 565 }
9fec6063 566
567 count += **type - '0';
28e9041c 568 (*type)++;
569 }
9fec6063 570
28e9041c 571 return (count);
572}
573
402ace4b 574
f39af051 575/* Like consume_count, but for counts that are preceded and followed
402ace4b 576 by '_' if they are greater than 10. Also, -1 is returned for
577 failure, since 0 can be a valid value. */
578
579static int
580consume_count_with_underscores (mangled)
581 const char **mangled;
582{
583 int idx;
584
585 if (**mangled == '_')
586 {
587 (*mangled)++;
93ce8ce4 588 if (!ISDIGIT ((unsigned char)**mangled))
402ace4b 589 return -1;
590
591 idx = consume_count (mangled);
592 if (**mangled != '_')
593 /* The trailing underscore was missing. */
594 return -1;
0f82222a 595
402ace4b 596 (*mangled)++;
597 }
598 else
599 {
600 if (**mangled < '0' || **mangled > '9')
601 return -1;
0f82222a 602
402ace4b 603 idx = **mangled - '0';
604 (*mangled)++;
605 }
606
607 return idx;
608}
609
3e04bd45 610/* C is the code for a type-qualifier. Return the TYPE_QUAL
611 corresponding to this qualifier. */
612
613static int
614code_for_qualifier (c)
7c8c70e9 615 int c;
3e04bd45 616{
0f82222a 617 switch (c)
3e04bd45 618 {
619 case 'C':
620 return TYPE_QUAL_CONST;
621
622 case 'V':
623 return TYPE_QUAL_VOLATILE;
0f82222a 624
3e04bd45 625 case 'u':
626 return TYPE_QUAL_RESTRICT;
627
628 default:
629 break;
630 }
631
632 /* C was an invalid qualifier. */
633 abort ();
634}
635
636/* Return the string corresponding to the qualifiers given by
637 TYPE_QUALS. */
638
639static const char*
640qualifier_string (type_quals)
641 int type_quals;
642{
643 switch (type_quals)
644 {
645 case TYPE_UNQUALIFIED:
646 return "";
647
648 case TYPE_QUAL_CONST:
649 return "const";
650
651 case TYPE_QUAL_VOLATILE:
652 return "volatile";
653
654 case TYPE_QUAL_RESTRICT:
655 return "__restrict";
656
657 case TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE:
658 return "const volatile";
659
660 case TYPE_QUAL_CONST | TYPE_QUAL_RESTRICT:
661 return "const __restrict";
662
663 case TYPE_QUAL_VOLATILE | TYPE_QUAL_RESTRICT:
664 return "volatile __restrict";
665
666 case TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE | TYPE_QUAL_RESTRICT:
667 return "const volatile __restrict";
668
669 default:
670 break;
671 }
672
673 /* TYPE_QUALS was an invalid qualifier set. */
674 abort ();
675}
676
677/* C is the code for a type-qualifier. Return the string
678 corresponding to this qualifier. This function should only be
679 called with a valid qualifier code. */
680
681static const char*
682demangle_qualifier (c)
7c8c70e9 683 int c;
3e04bd45 684{
685 return qualifier_string (code_for_qualifier (c));
686}
687
28e9041c 688int
689cplus_demangle_opname (opname, result, options)
690 const char *opname;
691 char *result;
692 int options;
693{
cd03a192 694 int len, len1, ret;
28e9041c 695 string type;
696 struct work_stuff work[1];
697 const char *tem;
698
699 len = strlen(opname);
700 result[0] = '\0';
701 ret = 0;
786da241 702 memset ((char *) work, 0, sizeof (work));
28e9041c 703 work->options = options;
0f82222a 704
28e9041c 705 if (opname[0] == '_' && opname[1] == '_'
706 && opname[2] == 'o' && opname[3] == 'p')
707 {
708 /* ANSI. */
709 /* type conversion operator. */
710 tem = opname + 4;
711 if (do_type (work, &tem, &type))
712 {
713 strcat (result, "operator ");
714 strncat (result, type.b, type.p - type.b);
715 string_delete (&type);
716 ret = 1;
717 }
718 }
719 else if (opname[0] == '_' && opname[1] == '_'
93ce8ce4 720 && ISLOWER((unsigned char)opname[2])
721 && ISLOWER((unsigned char)opname[3]))
28e9041c 722 {
723 if (opname[4] == '\0')
724 {
725 /* Operator. */
cd03a192 726 size_t i;
f0bff53d 727 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 728 {
729 if (strlen (optable[i].in) == 2
730 && memcmp (optable[i].in, opname + 2, 2) == 0)
731 {
732 strcat (result, "operator");
733 strcat (result, optable[i].out);
734 ret = 1;
735 break;
736 }
737 }
738 }
739 else
740 {
741 if (opname[2] == 'a' && opname[5] == '\0')
742 {
743 /* Assignment. */
cd03a192 744 size_t i;
f0bff53d 745 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 746 {
747 if (strlen (optable[i].in) == 3
748 && memcmp (optable[i].in, opname + 2, 3) == 0)
749 {
750 strcat (result, "operator");
751 strcat (result, optable[i].out);
752 ret = 1;
753 break;
0f82222a 754 }
28e9041c 755 }
756 }
757 }
758 }
0f82222a 759 else if (len >= 3
28e9041c 760 && opname[0] == 'o'
761 && opname[1] == 'p'
762 && strchr (cplus_markers, opname[2]) != NULL)
763 {
764 /* see if it's an assignment expression */
765 if (len >= 10 /* op$assign_ */
766 && memcmp (opname + 3, "assign_", 7) == 0)
767 {
cd03a192 768 size_t i;
f0bff53d 769 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 770 {
771 len1 = len - 10;
4350e959 772 if ((int) strlen (optable[i].in) == len1
28e9041c 773 && memcmp (optable[i].in, opname + 10, len1) == 0)
774 {
775 strcat (result, "operator");
776 strcat (result, optable[i].out);
777 strcat (result, "=");
778 ret = 1;
779 break;
780 }
781 }
782 }
783 else
784 {
cd03a192 785 size_t i;
f0bff53d 786 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 787 {
788 len1 = len - 3;
0f82222a 789 if ((int) strlen (optable[i].in) == len1
28e9041c 790 && memcmp (optable[i].in, opname + 3, len1) == 0)
791 {
792 strcat (result, "operator");
793 strcat (result, optable[i].out);
794 ret = 1;
795 break;
796 }
797 }
798 }
799 }
800 else if (len >= 5 && memcmp (opname, "type", 4) == 0
801 && strchr (cplus_markers, opname[4]) != NULL)
802 {
803 /* type conversion operator */
804 tem = opname + 5;
805 if (do_type (work, &tem, &type))
806 {
807 strcat (result, "operator ");
808 strncat (result, type.b, type.p - type.b);
809 string_delete (&type);
810 ret = 1;
811 }
812 }
fa4f3779 813 squangle_mop_up (work);
28e9041c 814 return ret;
815
816}
6f572555 817
28e9041c 818/* Takes operator name as e.g. "++" and returns mangled
819 operator name (e.g. "postincrement_expr"), or NULL if not found.
820
821 If OPTIONS & DMGL_ANSI == 1, return the ANSI name;
822 if OPTIONS & DMGL_ANSI == 0, return the old GNU name. */
823
824const char *
825cplus_mangle_opname (opname, options)
826 const char *opname;
827 int options;
828{
cd03a192 829 size_t i;
28e9041c 830 int len;
831
832 len = strlen (opname);
f0bff53d 833 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 834 {
4350e959 835 if ((int) strlen (optable[i].out) == len
28e9041c 836 && (options & DMGL_ANSI) == (optable[i].flags & DMGL_ANSI)
837 && memcmp (optable[i].out, opname, len) == 0)
838 return optable[i].in;
839 }
840 return (0);
841}
842
6f572555 843/* Add a routine to set the demangling style to be sure it is valid and
844 allow for any demangler initialization that maybe necessary. */
845
846enum demangling_styles
847cplus_demangle_set_style (style)
848 enum demangling_styles style;
849{
542e9271 850 const struct demangler_engine *demangler = libiberty_demanglers;
6f572555 851
852 for (; demangler->demangling_style != unknown_demangling; ++demangler)
853 if (style == demangler->demangling_style)
854 {
855 current_demangling_style = style;
856 return current_demangling_style;
857 }
858
859 return unknown_demangling;
860}
861
862/* Do string name to style translation */
863
864enum demangling_styles
865cplus_demangle_name_to_style (name)
866 const char *name;
867{
542e9271 868 const struct demangler_engine *demangler = libiberty_demanglers;
6f572555 869
870 for (; demangler->demangling_style != unknown_demangling; ++demangler)
871 if (strcmp (name, demangler->demangling_style_name) == 0)
872 return demangler->demangling_style;
873
874 return unknown_demangling;
875}
876
28e9041c 877/* char *cplus_demangle (const char *mangled, int options)
878
879 If MANGLED is a mangled function name produced by GNU C++, then
880 a pointer to a malloced string giving a C++ representation
881 of the name will be returned; otherwise NULL will be returned.
882 It is the caller's responsibility to free the string which
883 is returned.
884
885 The OPTIONS arg may contain one or more of the following bits:
886
887 DMGL_ANSI ANSI qualifiers such as `const' and `void' are
888 included.
889 DMGL_PARAMS Function parameters are included.
890
891 For example,
0f82222a 892
28e9041c 893 cplus_demangle ("foo__1Ai", DMGL_PARAMS) => "A::foo(int)"
894 cplus_demangle ("foo__1Ai", DMGL_PARAMS | DMGL_ANSI) => "A::foo(int)"
895 cplus_demangle ("foo__1Ai", 0) => "A::foo"
896
897 cplus_demangle ("foo__1Afe", DMGL_PARAMS) => "A::foo(float,...)"
898 cplus_demangle ("foo__1Afe", DMGL_PARAMS | DMGL_ANSI)=> "A::foo(float,...)"
899 cplus_demangle ("foo__1Afe", 0) => "A::foo"
900
901 Note that any leading underscores, or other such characters prepended by
902 the compilation system, are presumed to have already been stripped from
903 MANGLED. */
904
905char *
906cplus_demangle (mangled, options)
907 const char *mangled;
908 int options;
909{
fa4f3779 910 char *ret;
911 struct work_stuff work[1];
912 memset ((char *) work, 0, sizeof (work));
626946fb 913 work->options = options;
914 if ((work->options & DMGL_STYLE_MASK) == 0)
915 work->options |= (int) current_demangling_style & DMGL_STYLE_MASK;
fa4f3779 916
bb505139 917 /* The V3 ABI demangling is implemented elsewhere. */
918 if (GNU_V3_DEMANGLING || AUTO_DEMANGLING)
919 {
920 ret = cplus_demangle_v3 (mangled);
921 if (ret || GNU_V3_DEMANGLING)
922 return ret;
923 }
168d63e5 924
1c1033dd 925 if (JAVA_DEMANGLING)
926 {
927 ret = java_demangle_v3 (mangled);
928 if (ret)
929 return ret;
930 }
931
d7c1c148 932 if (GNAT_DEMANGLING)
933 return ada_demangle(mangled,options);
934
cd03a192 935 ret = internal_cplus_demangle (work, mangled);
fa4f3779 936 squangle_mop_up (work);
937 return (ret);
938}
fa4f3779 939
0f82222a 940
d7c1c148 941/* Assuming *OLD_VECT points to an array of *SIZE objects of size
942 ELEMENT_SIZE, grow it to contain at least MIN_SIZE objects,
626946fb 943 updating *OLD_VECT and *SIZE as necessary. */
944
d7c1c148 945static void
0d6e3c59 946grow_vect (old_vect, size, min_size, element_size)
626946fb 947 void **old_vect;
948 size_t *size;
0d6e3c59 949 size_t min_size;
950 int element_size;
d7c1c148 951{
626946fb 952 if (*size < min_size)
953 {
954 *size *= 2;
955 if (*size < min_size)
956 *size = min_size;
957 *old_vect = xrealloc (*old_vect, *size * element_size);
958 }
d7c1c148 959}
960
961/* Demangle ada names:
962 1. Discard final __{DIGIT}+ or ${DIGIT}+
963 2. Convert other instances of embedded "__" to `.'.
964 3. Discard leading _ada_.
626946fb 965 4. Remove everything after first ___ if it is followed by 'X'.
d7c1c148 966 5. Put symbols that should be suppressed in <...> brackets.
626946fb 967 The resulting string is valid until the next call of ada_demangle. */
968
d7c1c148 969static char *
0d6e3c59 970ada_demangle (mangled, option)
626946fb 971 const char *mangled;
582f72ad 972 int option ATTRIBUTE_UNUSED;
d7c1c148 973{
974 int i, j;
975 int len0;
976 const char* p;
626946fb 977 char *demangled = NULL;
d7c1c148 978 int at_start_name;
979 int changed;
626946fb 980 char *demangling_buffer = NULL;
d7c1c148 981 size_t demangling_buffer_size = 0;
982
983 changed = 0;
984
985 if (strncmp (mangled, "_ada_", 5) == 0)
986 {
987 mangled += 5;
988 changed = 1;
989 }
990
991 if (mangled[0] == '_' || mangled[0] == '<')
992 goto Suppress;
993
994 p = strstr (mangled, "___");
995 if (p == NULL)
996 len0 = strlen (mangled);
997 else
998 {
999 if (p[3] == 'X')
1000 {
1001 len0 = p - mangled;
1002 changed = 1;
1003 }
1004 else
1005 goto Suppress;
1006 }
1007
626946fb 1008 /* Make demangled big enough for possible expansion by operator name. */
1009 grow_vect ((void **) &(demangling_buffer),
d7c1c148 1010 &demangling_buffer_size, 2 * len0 + 1,
1011 sizeof (char));
1012 demangled = demangling_buffer;
1013
93ce8ce4 1014 if (ISDIGIT ((unsigned char) mangled[len0 - 1])) {
1015 for (i = len0 - 2; i >= 0 && ISDIGIT ((unsigned char) mangled[i]); i -= 1)
d7c1c148 1016 ;
626946fb 1017 if (i > 1 && mangled[i] == '_' && mangled[i - 1] == '_')
d7c1c148 1018 {
1019 len0 = i - 1;
1020 changed = 1;
1021 }
1022 else if (mangled[i] == '$')
1023 {
1024 len0 = i;
1025 changed = 1;
1026 }
1027 }
1028
93ce8ce4 1029 for (i = 0, j = 0; i < len0 && ! ISALPHA ((unsigned char)mangled[i]);
918a89ef 1030 i += 1, j += 1)
d7c1c148 1031 demangled[j] = mangled[i];
1032
1033 at_start_name = 1;
1034 while (i < len0)
1035 {
1036 at_start_name = 0;
1037
626946fb 1038 if (i < len0 - 2 && mangled[i] == '_' && mangled[i + 1] == '_')
d7c1c148 1039 {
1040 demangled[j] = '.';
1041 changed = at_start_name = 1;
1042 i += 2; j += 1;
1043 }
1044 else
1045 {
1046 demangled[j] = mangled[i];
1047 i += 1; j += 1;
1048 }
1049 }
1050 demangled[j] = '\000';
1051
1052 for (i = 0; demangled[i] != '\0'; i += 1)
93ce8ce4 1053 if (ISUPPER ((unsigned char)demangled[i]) || demangled[i] == ' ')
d7c1c148 1054 goto Suppress;
1055
1056 if (! changed)
1057 return NULL;
1058 else
1059 return demangled;
1060
1061 Suppress:
626946fb 1062 grow_vect ((void **) &(demangling_buffer),
d7c1c148 1063 &demangling_buffer_size, strlen (mangled) + 3,
1064 sizeof (char));
1065 demangled = demangling_buffer;
1066 if (mangled[0] == '<')
1067 strcpy (demangled, mangled);
1068 else
1069 sprintf (demangled, "<%s>", mangled);
1070
1071 return demangled;
1072}
1073
0f82222a 1074/* This function performs most of what cplus_demangle use to do, but
fa4f3779 1075 to be able to demangle a name with a B, K or n code, we need to
1076 have a longer term memory of what types have been seen. The original
1077 now intializes and cleans up the squangle code info, while internal
1078 calls go directly to this routine to avoid resetting that info. */
1079
1080static char *
cd03a192 1081internal_cplus_demangle (work, mangled)
fa4f3779 1082 struct work_stuff *work;
1083 const char *mangled;
fa4f3779 1084{
1085
28e9041c 1086 string decl;
1087 int success = 0;
28e9041c 1088 char *demangled = NULL;
626946fb 1089 int s1, s2, s3, s4;
fa4f3779 1090 s1 = work->constructor;
1091 s2 = work->destructor;
1092 s3 = work->static_type;
3e04bd45 1093 s4 = work->type_quals;
fa4f3779 1094 work->constructor = work->destructor = 0;
3e04bd45 1095 work->type_quals = TYPE_UNQUALIFIED;
37c9cc60 1096 work->dllimported = 0;
28e9041c 1097
1098 if ((mangled != NULL) && (*mangled != '\0'))
1099 {
28e9041c 1100 string_init (&decl);
1101
1102 /* First check to see if gnu style demangling is active and if the
1103 string to be demangled contains a CPLUS_MARKER. If so, attempt to
1104 recognize one of the gnu special forms rather than looking for a
1105 standard prefix. In particular, don't worry about whether there
1106 is a "__" string in the mangled string. Consider "_$_5__foo" for
1107 example. */
1108
1109 if ((AUTO_DEMANGLING || GNU_DEMANGLING))
1110 {
1111 success = gnu_special (work, &mangled, &decl);
1112 }
1113 if (!success)
1114 {
1115 success = demangle_prefix (work, &mangled, &decl);
1116 }
1117 if (success && (*mangled != '\0'))
1118 {
1119 success = demangle_signature (work, &mangled, &decl);
1120 }
1121 if (work->constructor == 2)
1122 {
fa4f3779 1123 string_prepend (&decl, "global constructors keyed to ");
28e9041c 1124 work->constructor = 0;
1125 }
1126 else if (work->destructor == 2)
1127 {
fa4f3779 1128 string_prepend (&decl, "global destructors keyed to ");
28e9041c 1129 work->destructor = 0;
1130 }
37c9cc60 1131 else if (work->dllimported == 1)
1132 {
1133 string_prepend (&decl, "import stub for ");
1134 work->dllimported = 0;
1135 }
28e9041c 1136 demangled = mop_up (work, &decl, success);
1137 }
fa4f3779 1138 work->constructor = s1;
1139 work->destructor = s2;
1140 work->static_type = s3;
3e04bd45 1141 work->type_quals = s4;
626946fb 1142 return demangled;
28e9041c 1143}
1144
fa4f3779 1145
1146/* Clear out and squangling related storage */
cd03a192 1147static void
fa4f3779 1148squangle_mop_up (work)
1149 struct work_stuff *work;
1150{
1151 /* clean up the B and K type mangling types. */
1152 forget_B_and_K_types (work);
1153 if (work -> btypevec != NULL)
1154 {
1155 free ((char *) work -> btypevec);
1156 }
1157 if (work -> ktypevec != NULL)
1158 {
1159 free ((char *) work -> ktypevec);
1160 }
1161}
1162
fa4f3779 1163
f2e5a608 1164/* Copy the work state and storage. */
1165
1166static void
1167work_stuff_copy_to_from (to, from)
1168 struct work_stuff *to;
1169 struct work_stuff *from;
28e9041c 1170{
f2e5a608 1171 int i;
1172
1173 delete_work_stuff (to);
1174
1175 /* Shallow-copy scalars. */
1176 memcpy (to, from, sizeof (*to));
1177
1178 /* Deep-copy dynamic storage. */
1179 if (from->typevec_size)
1180 to->typevec
1181 = (char **) xmalloc (from->typevec_size * sizeof (to->typevec[0]));
1182
1183 for (i = 0; i < from->ntypes; i++)
1184 {
1185 int len = strlen (from->typevec[i]) + 1;
1186
1187 to->typevec[i] = xmalloc (len);
1188 memcpy (to->typevec[i], from->typevec[i], len);
1189 }
1190
1191 if (from->ksize)
1192 to->ktypevec
1193 = (char **) xmalloc (from->ksize * sizeof (to->ktypevec[0]));
1194
1195 for (i = 0; i < from->numk; i++)
1196 {
1197 int len = strlen (from->ktypevec[i]) + 1;
1198
1199 to->ktypevec[i] = xmalloc (len);
1200 memcpy (to->ktypevec[i], from->ktypevec[i], len);
1201 }
28e9041c 1202
f2e5a608 1203 if (from->bsize)
1204 to->btypevec
1205 = (char **) xmalloc (from->bsize * sizeof (to->btypevec[0]));
1206
1207 for (i = 0; i < from->numb; i++)
1208 {
1209 int len = strlen (from->btypevec[i]) + 1;
1210
1211 to->btypevec[i] = xmalloc (len);
1212 memcpy (to->btypevec[i], from->btypevec[i], len);
1213 }
1214
1215 if (from->ntmpl_args)
1216 to->tmpl_argvec
1217 = xmalloc (from->ntmpl_args * sizeof (to->tmpl_argvec[0]));
1218
1219 for (i = 0; i < from->ntmpl_args; i++)
1220 {
1221 int len = strlen (from->tmpl_argvec[i]) + 1;
1222
1223 to->tmpl_argvec[i] = xmalloc (len);
1224 memcpy (to->tmpl_argvec[i], from->tmpl_argvec[i], len);
1225 }
1226
1227 if (from->previous_argument)
1228 {
1229 to->previous_argument = (string*) xmalloc (sizeof (string));
1230 string_init (to->previous_argument);
1231 string_appends (to->previous_argument, from->previous_argument);
1232 }
1233}
1234
1235
1236/* Delete dynamic stuff in work_stuff that is not to be re-used. */
1237
1238static void
1239delete_non_B_K_work_stuff (work)
1240 struct work_stuff *work;
1241{
28e9041c 1242 /* Discard the remembered types, if any. */
0f82222a 1243
28e9041c 1244 forget_types (work);
1245 if (work -> typevec != NULL)
1246 {
1247 free ((char *) work -> typevec);
fa4f3779 1248 work -> typevec = NULL;
0f08678d 1249 work -> typevec_size = 0;
28e9041c 1250 }
402ace4b 1251 if (work->tmpl_argvec)
1252 {
1253 int i;
1254
1255 for (i = 0; i < work->ntmpl_args; i++)
1256 if (work->tmpl_argvec[i])
1257 free ((char*) work->tmpl_argvec[i]);
0f82222a 1258
402ace4b 1259 free ((char*) work->tmpl_argvec);
fa4f3779 1260 work->tmpl_argvec = NULL;
402ace4b 1261 }
99906878 1262 if (work->previous_argument)
1263 {
1264 string_delete (work->previous_argument);
1265 free ((char*) work->previous_argument);
0f82222a 1266 work->previous_argument = NULL;
99906878 1267 }
f2e5a608 1268}
1269
1270
1271/* Delete all dynamic storage in work_stuff. */
1272static void
1273delete_work_stuff (work)
1274 struct work_stuff *work;
1275{
1276 delete_non_B_K_work_stuff (work);
1277 squangle_mop_up (work);
1278}
1279
1280
1281/* Clear out any mangled storage */
1282
1283static char *
1284mop_up (work, declp, success)
1285 struct work_stuff *work;
1286 string *declp;
1287 int success;
1288{
1289 char *demangled = NULL;
1290
1291 delete_non_B_K_work_stuff (work);
402ace4b 1292
28e9041c 1293 /* If demangling was successful, ensure that the demangled string is null
1294 terminated and return it. Otherwise, free the demangling decl. */
0f82222a 1295
28e9041c 1296 if (!success)
1297 {
1298 string_delete (declp);
1299 }
1300 else
1301 {
1302 string_appendn (declp, "", 1);
626946fb 1303 demangled = declp->b;
28e9041c 1304 }
1305 return (demangled);
1306}
1307
1308/*
1309
1310LOCAL FUNCTION
1311
1312 demangle_signature -- demangle the signature part of a mangled name
1313
1314SYNOPSIS
1315
1316 static int
1317 demangle_signature (struct work_stuff *work, const char **mangled,
1318 string *declp);
1319
1320DESCRIPTION
1321
1322 Consume and demangle the signature portion of the mangled name.
1323
1324 DECLP is the string where demangled output is being built. At
1325 entry it contains the demangled root name from the mangled name
1326 prefix. I.E. either a demangled operator name or the root function
1327 name. In some special cases, it may contain nothing.
1328
1329 *MANGLED points to the current unconsumed location in the mangled
1330 name. As tokens are consumed and demangling is performed, the
1331 pointer is updated to continuously point at the next token to
1332 be consumed.
1333
1334 Demangling GNU style mangled names is nasty because there is no
1335 explicit token that marks the start of the outermost function
1336 argument list. */
1337
1338static int
1339demangle_signature (work, mangled, declp)
1340 struct work_stuff *work;
1341 const char **mangled;
1342 string *declp;
1343{
1344 int success = 1;
1345 int func_done = 0;
1346 int expect_func = 0;
402ace4b 1347 int expect_return_type = 0;
28e9041c 1348 const char *oldmangled = NULL;
1349 string trawname;
1350 string tname;
1351
1352 while (success && (**mangled != '\0'))
1353 {
1354 switch (**mangled)
1355 {
1356 case 'Q':
1357 oldmangled = *mangled;
1358 success = demangle_qualified (work, mangled, declp, 1, 0);
1359 if (success)
99906878 1360 remember_type (work, oldmangled, *mangled - oldmangled);
28e9041c 1361 if (AUTO_DEMANGLING || GNU_DEMANGLING)
99906878 1362 expect_func = 1;
28e9041c 1363 oldmangled = NULL;
1364 break;
fa4f3779 1365
1366 case 'K':
1367 oldmangled = *mangled;
1368 success = demangle_qualified (work, mangled, declp, 1, 0);
1369 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1370 {
1371 expect_func = 1;
1372 }
1373 oldmangled = NULL;
1374 break;
0f82222a 1375
28e9041c 1376 case 'S':
1377 /* Static member function */
1378 if (oldmangled == NULL)
1379 {
1380 oldmangled = *mangled;
1381 }
1382 (*mangled)++;
1383 work -> static_type = 1;
1384 break;
1385
1386 case 'C':
99906878 1387 case 'V':
3e04bd45 1388 case 'u':
1389 work->type_quals |= code_for_qualifier (**mangled);
99906878 1390
1391 /* a qualified member function */
28e9041c 1392 if (oldmangled == NULL)
99906878 1393 oldmangled = *mangled;
28e9041c 1394 (*mangled)++;
28e9041c 1395 break;
f75dc4de 1396
1397 case 'L':
1398 /* Local class name follows after "Lnnn_" */
1399 if (HP_DEMANGLING)
1400 {
1401 while (**mangled && (**mangled != '_'))
1402 (*mangled)++;
1403 if (!**mangled)
1404 success = 0;
1405 else
1406 (*mangled)++;
1407 }
1408 else
1409 success = 0;
1410 break;
0f82222a 1411
28e9041c 1412 case '0': case '1': case '2': case '3': case '4':
1413 case '5': case '6': case '7': case '8': case '9':
1414 if (oldmangled == NULL)
1415 {
1416 oldmangled = *mangled;
1417 }
0f82222a 1418 work->temp_start = -1; /* uppermost call to demangle_class */
28e9041c 1419 success = demangle_class (work, mangled, declp);
1420 if (success)
1421 {
1422 remember_type (work, oldmangled, *mangled - oldmangled);
1423 }
f75dc4de 1424 if (AUTO_DEMANGLING || GNU_DEMANGLING || EDG_DEMANGLING)
28e9041c 1425 {
0f82222a 1426 /* EDG and others will have the "F", so we let the loop cycle
f75dc4de 1427 if we are looking at one. */
1428 if (**mangled != 'F')
1429 expect_func = 1;
28e9041c 1430 }
1431 oldmangled = NULL;
1432 break;
99906878 1433
1434 case 'B':
1435 {
1436 string s;
1437 success = do_type (work, mangled, &s);
1438 if (success)
1439 {
1440 string_append (&s, SCOPE_STRING (work));
1441 string_prepends (declp, &s);
1442 }
1443 oldmangled = NULL;
1444 expect_func = 1;
1445 }
1446 break;
1447
28e9041c 1448 case 'F':
1449 /* Function */
f75dc4de 1450 /* ARM/HP style demangling includes a specific 'F' character after
28e9041c 1451 the class name. For GNU style, it is just implied. So we can
1452 safely just consume any 'F' at this point and be compatible
1453 with either style. */
1454
1455 oldmangled = NULL;
1456 func_done = 1;
1457 (*mangled)++;
1458
f75dc4de 1459 /* For lucid/ARM/HP style we have to forget any types we might
28e9041c 1460 have remembered up to this point, since they were not argument
1461 types. GNU style considers all types seen as available for
1462 back references. See comment in demangle_args() */
1463
f75dc4de 1464 if (LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
28e9041c 1465 {
1466 forget_types (work);
1467 }
1468 success = demangle_args (work, mangled, declp);
f75dc4de 1469 /* After picking off the function args, we expect to either
1470 find the function return type (preceded by an '_') or the
1471 end of the string. */
1472 if (success && (AUTO_DEMANGLING || EDG_DEMANGLING) && **mangled == '_')
1473 {
1474 ++(*mangled);
1475 /* At this level, we do not care about the return type. */
1476 success = do_type (work, mangled, &tname);
1477 string_delete (&tname);
1478 }
1479
28e9041c 1480 break;
0f82222a 1481
28e9041c 1482 case 't':
1483 /* G++ Template */
0f82222a 1484 string_init(&trawname);
28e9041c 1485 string_init(&tname);
1486 if (oldmangled == NULL)
1487 {
1488 oldmangled = *mangled;
1489 }
99906878 1490 success = demangle_template (work, mangled, &tname,
1491 &trawname, 1, 1);
28e9041c 1492 if (success)
1493 {
1494 remember_type (work, oldmangled, *mangled - oldmangled);
1495 }
89e5545f 1496 string_append (&tname, SCOPE_STRING (work));
1497
28e9041c 1498 string_prepends(declp, &tname);
1499 if (work -> destructor & 1)
1500 {
1501 string_prepend (&trawname, "~");
1502 string_appends (declp, &trawname);
1503 work->destructor -= 1;
1504 }
1505 if ((work->constructor & 1) || (work->destructor & 1))
1506 {
1507 string_appends (declp, &trawname);
1508 work->constructor -= 1;
1509 }
1510 string_delete(&trawname);
1511 string_delete(&tname);
1512 oldmangled = NULL;
1513 expect_func = 1;
1514 break;
1515
1516 case '_':
f2e5a608 1517 if ((AUTO_DEMANGLING || GNU_DEMANGLING) && expect_return_type)
402ace4b 1518 {
1519 /* Read the return type. */
1520 string return_type;
1521 string_init (&return_type);
1522
1523 (*mangled)++;
1524 success = do_type (work, mangled, &return_type);
1525 APPEND_BLANK (&return_type);
1526
1527 string_prepends (declp, &return_type);
1528 string_delete (&return_type);
1529 break;
1530 }
1531 else
1532 /* At the outermost level, we cannot have a return type specified,
1533 so if we run into another '_' at this point we are dealing with
1534 a mangled name that is either bogus, or has been mangled by
1535 some algorithm we don't know how to deal with. So just
1536 reject the entire demangling. */
f75dc4de 1537 /* However, "_nnn" is an expected suffix for alternate entry point
1538 numbered nnn for a function, with HP aCC, so skip over that
1539 without reporting failure. pai/1997-09-04 */
1540 if (HP_DEMANGLING)
1541 {
1542 (*mangled)++;
93ce8ce4 1543 while (**mangled && ISDIGIT ((unsigned char)**mangled))
f75dc4de 1544 (*mangled)++;
1545 }
1546 else
1547 success = 0;
28e9041c 1548 break;
1549
402ace4b 1550 case 'H':
f2e5a608 1551 if (AUTO_DEMANGLING || GNU_DEMANGLING)
402ace4b 1552 {
1553 /* A G++ template function. Read the template arguments. */
99906878 1554 success = demangle_template (work, mangled, declp, 0, 0,
1555 0);
8f71bf1d 1556 if (!(work->constructor & 1))
1557 expect_return_type = 1;
402ace4b 1558 (*mangled)++;
1559 break;
1560 }
1561 else
1562 /* fall through */
f39af051 1563 {;}
402ace4b 1564
28e9041c 1565 default:
1566 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1567 {
1568 /* Assume we have stumbled onto the first outermost function
1569 argument token, and start processing args. */
1570 func_done = 1;
1571 success = demangle_args (work, mangled, declp);
1572 }
1573 else
1574 {
1575 /* Non-GNU demanglers use a specific token to mark the start
1576 of the outermost function argument tokens. Typically 'F',
f75dc4de 1577 for ARM/HP-demangling, for example. So if we find something
28e9041c 1578 we are not prepared for, it must be an error. */
1579 success = 0;
1580 }
1581 break;
1582 }
1583 /*
1584 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1585 */
1586 {
1587 if (success && expect_func)
1588 {
1589 func_done = 1;
f75dc4de 1590 if (LUCID_DEMANGLING || ARM_DEMANGLING || EDG_DEMANGLING)
1591 {
1592 forget_types (work);
1593 }
28e9041c 1594 success = demangle_args (work, mangled, declp);
402ace4b 1595 /* Since template include the mangling of their return types,
1596 we must set expect_func to 0 so that we don't try do
1597 demangle more arguments the next time we get here. */
1598 expect_func = 0;
28e9041c 1599 }
1600 }
1601 }
1602 if (success && !func_done)
1603 {
1604 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1605 {
1606 /* With GNU style demangling, bar__3foo is 'foo::bar(void)', and
1607 bar__3fooi is 'foo::bar(int)'. We get here when we find the
1608 first case, and need to ensure that the '(void)' gets added to
f75dc4de 1609 the current declp. Note that with ARM/HP, the first case
28e9041c 1610 represents the name of a static data member 'foo::bar',
1611 which is in the current declp, so we leave it alone. */
1612 success = demangle_args (work, mangled, declp);
1613 }
1614 }
3e04bd45 1615 if (success && PRINT_ARG_TYPES)
1616 {
1617 if (work->static_type)
1618 string_append (declp, " static");
1619 if (work->type_quals != TYPE_UNQUALIFIED)
1620 {
1621 APPEND_BLANK (declp);
1622 string_append (declp, qualifier_string (work->type_quals));
1623 }
1624 }
99906878 1625
28e9041c 1626 return (success);
1627}
1628
1629#if 0
1630
1631static int
1632demangle_method_args (work, mangled, declp)
1633 struct work_stuff *work;
1634 const char **mangled;
1635 string *declp;
1636{
1637 int success = 0;
1638
1639 if (work -> static_type)
1640 {
1641 string_append (declp, *mangled + 1);
1642 *mangled += strlen (*mangled);
1643 success = 1;
1644 }
1645 else
1646 {
1647 success = demangle_args (work, mangled, declp);
1648 }
1649 return (success);
1650}
1651
1652#endif
1653
f39af051 1654static int
1655demangle_template_template_parm (work, mangled, tname)
1656 struct work_stuff *work;
1657 const char **mangled;
1658 string *tname;
1659{
1660 int i;
1661 int r;
1662 int need_comma = 0;
1663 int success = 1;
1664 string temp;
1665
1666 string_append (tname, "template <");
1667 /* get size of template parameter list */
1668 if (get_count (mangled, &r))
1669 {
1670 for (i = 0; i < r; i++)
1671 {
1672 if (need_comma)
1673 {
1674 string_append (tname, ", ");
1675 }
1676
1677 /* Z for type parameters */
1678 if (**mangled == 'Z')
1679 {
1680 (*mangled)++;
1681 string_append (tname, "class");
1682 }
1683 /* z for template parameters */
1684 else if (**mangled == 'z')
1685 {
1686 (*mangled)++;
0f82222a 1687 success =
f39af051 1688 demangle_template_template_parm (work, mangled, tname);
1689 if (!success)
1690 {
1691 break;
1692 }
1693 }
1694 else
1695 {
1696 /* temp is initialized in do_type */
1697 success = do_type (work, mangled, &temp);
1698 if (success)
1699 {
1700 string_appends (tname, &temp);
1701 }
1702 string_delete(&temp);
1703 if (!success)
1704 {
1705 break;
1706 }
1707 }
1708 need_comma = 1;
1709 }
1710
1711 }
1712 if (tname->p[-1] == '>')
1713 string_append (tname, " ");
1714 string_append (tname, "> class");
1715 return (success);
1716}
1717
80283fb2 1718static int
42c870f1 1719demangle_expression (work, mangled, s, tk)
80283fb2 1720 struct work_stuff *work;
1721 const char** mangled;
1722 string* s;
42c870f1 1723 type_kind_t tk;
80283fb2 1724{
42c870f1 1725 int need_operator = 0;
80283fb2 1726 int success;
1727
42c870f1 1728 success = 1;
1729 string_appendn (s, "(", 1);
1730 (*mangled)++;
1731 while (success && **mangled != 'W' && **mangled != '\0')
80283fb2 1732 {
42c870f1 1733 if (need_operator)
80283fb2 1734 {
42c870f1 1735 size_t i;
1736 size_t len;
80283fb2 1737
42c870f1 1738 success = 0;
80283fb2 1739
42c870f1 1740 len = strlen (*mangled);
80283fb2 1741
f0bff53d 1742 for (i = 0; i < ARRAY_SIZE (optable); ++i)
42c870f1 1743 {
1744 size_t l = strlen (optable[i].in);
80283fb2 1745
42c870f1 1746 if (l <= len
1747 && memcmp (optable[i].in, *mangled, l) == 0)
1748 {
1749 string_appendn (s, " ", 1);
1750 string_append (s, optable[i].out);
1751 string_appendn (s, " ", 1);
1752 success = 1;
1753 (*mangled) += l;
1754 break;
80283fb2 1755 }
80283fb2 1756 }
80283fb2 1757
42c870f1 1758 if (!success)
1759 break;
80283fb2 1760 }
0f82222a 1761 else
42c870f1 1762 need_operator = 1;
1763
1764 success = demangle_template_value_parm (work, mangled, s, tk);
1765 }
1766
1767 if (**mangled != 'W')
1768 success = 0;
1769 else
1770 {
1771 string_appendn (s, ")", 1);
1772 (*mangled)++;
80283fb2 1773 }
42c870f1 1774
1775 return success;
1776}
1777
1778static int
1779demangle_integral_value (work, mangled, s)
1780 struct work_stuff *work;
1781 const char** mangled;
1782 string* s;
1783{
1784 int success;
1785
1786 if (**mangled == 'E')
1787 success = demangle_expression (work, mangled, s, tk_integral);
fa4f3779 1788 else if (**mangled == 'Q' || **mangled == 'K')
80283fb2 1789 success = demangle_qualified (work, mangled, s, 0, 1);
1790 else
1791 {
42c870f1 1792 int value;
1793
f2e5a608 1794 /* By default, we let the number decide whether we shall consume an
1795 underscore. */
1796 int consume_following_underscore = 0;
1797 int leave_following_underscore = 0;
1798
80283fb2 1799 success = 0;
1800
42c870f1 1801 /* Negative numbers are indicated with a leading `m'. */
80283fb2 1802 if (**mangled == 'm')
1803 {
1804 string_appendn (s, "-", 1);
1805 (*mangled)++;
1806 }
f2e5a608 1807 else if (mangled[0][0] == '_' && mangled[0][1] == 'm')
1808 {
1809 /* Since consume_count_with_underscores does not handle the
1810 `m'-prefix we must do it here, using consume_count and
1811 adjusting underscores: we have to consume the underscore
1812 matching the prepended one. */
1813 consume_following_underscore = 1;
1814 string_appendn (s, "-", 1);
1815 (*mangled) += 2;
1816 }
1817 else if (**mangled == '_')
1818 {
1819 /* Do not consume a following underscore;
1820 consume_following_underscore will consume what should be
1821 consumed. */
1822 leave_following_underscore = 1;
1823 }
1824
1825 /* We must call consume_count if we expect to remove a trailing
1826 underscore, since consume_count_with_underscores expects
1827 the leading underscore (that we consumed) if it is to handle
1828 multi-digit numbers. */
1829 if (consume_following_underscore)
1830 value = consume_count (mangled);
1831 else
1832 value = consume_count_with_underscores (mangled);
42c870f1 1833
42c870f1 1834 if (value != -1)
1835 {
1836 char buf[INTBUF_SIZE];
1837 sprintf (buf, "%d", value);
1838 string_append (s, buf);
1839
f2e5a608 1840 /* Numbers not otherwise delimited, might have an underscore
1841 appended as a delimeter, which we should skip.
1842
1843 ??? This used to always remove a following underscore, which
1844 is wrong. If other (arbitrary) cases are followed by an
1845 underscore, we need to do something more radical. */
1846
1847 if ((value > 9 || consume_following_underscore)
1848 && ! leave_following_underscore
1849 && **mangled == '_')
42c870f1 1850 (*mangled)++;
1851
1852 /* All is well. */
1853 success = 1;
1854 }
1855 }
1856
1857 return success;
1858}
1859
1860/* Demangle the real value in MANGLED. */
1861
1862static int
1863demangle_real_value (work, mangled, s)
1864 struct work_stuff *work;
1865 const char **mangled;
1866 string* s;
1867{
1868 if (**mangled == 'E')
1869 return demangle_expression (work, mangled, s, tk_real);
1870
1871 if (**mangled == 'm')
1872 {
1873 string_appendn (s, "-", 1);
1874 (*mangled)++;
1875 }
93ce8ce4 1876 while (ISDIGIT ((unsigned char)**mangled))
42c870f1 1877 {
1878 string_appendn (s, *mangled, 1);
1879 (*mangled)++;
1880 }
1881 if (**mangled == '.') /* fraction */
1882 {
1883 string_appendn (s, ".", 1);
1884 (*mangled)++;
93ce8ce4 1885 while (ISDIGIT ((unsigned char)**mangled))
42c870f1 1886 {
1887 string_appendn (s, *mangled, 1);
1888 (*mangled)++;
1889 }
1890 }
1891 if (**mangled == 'e') /* exponent */
1892 {
1893 string_appendn (s, "e", 1);
1894 (*mangled)++;
93ce8ce4 1895 while (ISDIGIT ((unsigned char)**mangled))
80283fb2 1896 {
1897 string_appendn (s, *mangled, 1);
1898 (*mangled)++;
80283fb2 1899 }
1900 }
0f82222a 1901
42c870f1 1902 return 1;
80283fb2 1903}
1904
0f82222a 1905static int
2d53096b 1906demangle_template_value_parm (work, mangled, s, tk)
80283fb2 1907 struct work_stuff *work;
1908 const char **mangled;
1909 string* s;
2d53096b 1910 type_kind_t tk;
80283fb2 1911{
80283fb2 1912 int success = 1;
1913
80283fb2 1914 if (**mangled == 'Y')
1915 {
1916 /* The next argument is a template parameter. */
1917 int idx;
1918
1919 (*mangled)++;
1920 idx = consume_count_with_underscores (mangled);
0f82222a 1921 if (idx == -1
80283fb2 1922 || (work->tmpl_argvec && idx >= work->ntmpl_args)
1923 || consume_count_with_underscores (mangled) == -1)
1924 return -1;
1925 if (work->tmpl_argvec)
1926 string_append (s, work->tmpl_argvec[idx]);
1927 else
42c870f1 1928 string_append_template_idx (s, idx);
80283fb2 1929 }
2d53096b 1930 else if (tk == tk_integral)
80283fb2 1931 success = demangle_integral_value (work, mangled, s);
2d53096b 1932 else if (tk == tk_char)
80283fb2 1933 {
1934 char tmp[2];
1935 int val;
1936 if (**mangled == 'm')
1937 {
1938 string_appendn (s, "-", 1);
1939 (*mangled)++;
1940 }
1941 string_appendn (s, "'", 1);
1942 val = consume_count(mangled);
9fec6063 1943 if (val <= 0)
1944 success = 0;
1945 else
1946 {
1947 tmp[0] = (char)val;
1948 tmp[1] = '\0';
1949 string_appendn (s, &tmp[0], 1);
1950 string_appendn (s, "'", 1);
1951 }
80283fb2 1952 }
2d53096b 1953 else if (tk == tk_bool)
80283fb2 1954 {
1955 int val = consume_count (mangled);
1956 if (val == 0)
1957 string_appendn (s, "false", 5);
1958 else if (val == 1)
1959 string_appendn (s, "true", 4);
1960 else
1961 success = 0;
1962 }
2d53096b 1963 else if (tk == tk_real)
42c870f1 1964 success = demangle_real_value (work, mangled, s);
73bea962 1965 else if (tk == tk_pointer || tk == tk_reference)
80283fb2 1966 {
0dc64970 1967 if (**mangled == 'Q')
1968 success = demangle_qualified (work, mangled, s,
1969 /*isfuncname=*/0,
1970 /*append=*/1);
80283fb2 1971 else
1972 {
0dc64970 1973 int symbol_len = consume_count (mangled);
1974 if (symbol_len == -1)
1975 return -1;
1976 if (symbol_len == 0)
1977 string_appendn (s, "0", 1);
1978 else
80283fb2 1979 {
0dc64970 1980 char *p = xmalloc (symbol_len + 1), *q;
1981 strncpy (p, *mangled, symbol_len);
1982 p [symbol_len] = '\0';
1983 /* We use cplus_demangle here, rather than
1984 internal_cplus_demangle, because the name of the entity
1985 mangled here does not make use of any of the squangling
1986 or type-code information we have built up thus far; it is
1987 mangled independently. */
1988 q = cplus_demangle (p, work->options);
1989 if (tk == tk_pointer)
1990 string_appendn (s, "&", 1);
1991 /* FIXME: Pointer-to-member constants should get a
1992 qualifying class name here. */
1993 if (q)
1994 {
1995 string_append (s, q);
1996 free (q);
1997 }
1998 else
1999 string_append (s, p);
2000 free (p);
80283fb2 2001 }
0dc64970 2002 *mangled += symbol_len;
80283fb2 2003 }
80283fb2 2004 }
2005
2006 return success;
2007}
2008
99906878 2009/* Demangle the template name in MANGLED. The full name of the
2010 template (e.g., S<int>) is placed in TNAME. The name without the
2011 template parameters (e.g. S) is placed in TRAWNAME if TRAWNAME is
2012 non-NULL. If IS_TYPE is nonzero, this template is a type template,
2013 not a function template. If both IS_TYPE and REMEMBER are nonzero,
f2e5a608 2014 the template is remembered in the list of back-referenceable
99906878 2015 types. */
2016
28e9041c 2017static int
99906878 2018demangle_template (work, mangled, tname, trawname, is_type, remember)
28e9041c 2019 struct work_stuff *work;
2020 const char **mangled;
2021 string *tname;
2022 string *trawname;
402ace4b 2023 int is_type;
99906878 2024 int remember;
28e9041c 2025{
2026 int i;
28e9041c 2027 int r;
2028 int need_comma = 0;
2029 int success = 0;
28e9041c 2030 const char *start;
bdaa26ad 2031 int is_java_array = 0;
28e9041c 2032 string temp;
4350e959 2033 int bindex = 0;
28e9041c 2034
2035 (*mangled)++;
402ace4b 2036 if (is_type)
28e9041c 2037 {
99906878 2038 if (remember)
2039 bindex = register_Btype (work);
402ace4b 2040 start = *mangled;
2041 /* get template name */
f39af051 2042 if (**mangled == 'z')
402ace4b 2043 {
f39af051 2044 int idx;
2045 (*mangled)++;
2046 (*mangled)++;
2047
2048 idx = consume_count_with_underscores (mangled);
0f82222a 2049 if (idx == -1
f39af051 2050 || (work->tmpl_argvec && idx >= work->ntmpl_args)
2051 || consume_count_with_underscores (mangled) == -1)
99906878 2052 return (0);
2053
f39af051 2054 if (work->tmpl_argvec)
2055 {
2056 string_append (tname, work->tmpl_argvec[idx]);
2057 if (trawname)
2058 string_append (trawname, work->tmpl_argvec[idx]);
2059 }
2060 else
2061 {
42c870f1 2062 string_append_template_idx (tname, idx);
f39af051 2063 if (trawname)
42c870f1 2064 string_append_template_idx (trawname, idx);
f39af051 2065 }
402ace4b 2066 }
f39af051 2067 else
402ace4b 2068 {
9fec6063 2069 if ((r = consume_count (mangled)) <= 0
4350e959 2070 || (int) strlen (*mangled) < r)
f39af051 2071 {
2072 return (0);
2073 }
bdaa26ad 2074 is_java_array = (work -> options & DMGL_JAVA)
2075 && strncmp (*mangled, "JArray1Z", 8) == 0;
2076 if (! is_java_array)
2077 {
2078 string_appendn (tname, *mangled, r);
2079 }
f39af051 2080 if (trawname)
2081 string_appendn (trawname, *mangled, r);
f39af051 2082 *mangled += r;
402ace4b 2083 }
28e9041c 2084 }
bdaa26ad 2085 if (!is_java_array)
2086 string_append (tname, "<");
28e9041c 2087 /* get size of template parameter list */
2088 if (!get_count (mangled, &r))
2089 {
2090 return (0);
2091 }
402ace4b 2092 if (!is_type)
2093 {
2094 /* Create an array for saving the template argument values. */
2095 work->tmpl_argvec = (char**) xmalloc (r * sizeof (char *));
2096 work->ntmpl_args = r;
2097 for (i = 0; i < r; i++)
2098 work->tmpl_argvec[i] = 0;
2099 }
28e9041c 2100 for (i = 0; i < r; i++)
2101 {
2102 if (need_comma)
2103 {
2104 string_append (tname, ", ");
2105 }
2106 /* Z for type parameters */
2107 if (**mangled == 'Z')
2108 {
2109 (*mangled)++;
2110 /* temp is initialized in do_type */
2111 success = do_type (work, mangled, &temp);
2112 if (success)
2113 {
2114 string_appends (tname, &temp);
402ace4b 2115
2116 if (!is_type)
2117 {
2118 /* Save the template argument. */
2119 int len = temp.p - temp.b;
2120 work->tmpl_argvec[i] = xmalloc (len + 1);
2121 memcpy (work->tmpl_argvec[i], temp.b, len);
2122 work->tmpl_argvec[i][len] = '\0';
2123 }
28e9041c 2124 }
2125 string_delete(&temp);
2126 if (!success)
2127 {
2128 break;
2129 }
2130 }
f39af051 2131 /* z for template parameters */
2132 else if (**mangled == 'z')
2133 {
2134 int r2;
2135 (*mangled)++;
2136 success = demangle_template_template_parm (work, mangled, tname);
0f82222a 2137
f39af051 2138 if (success
4350e959 2139 && (r2 = consume_count (mangled)) > 0
2140 && (int) strlen (*mangled) >= r2)
f39af051 2141 {
2142 string_append (tname, " ");
2143 string_appendn (tname, *mangled, r2);
2144 if (!is_type)
2145 {
2146 /* Save the template argument. */
2147 int len = r2;
2148 work->tmpl_argvec[i] = xmalloc (len + 1);
2149 memcpy (work->tmpl_argvec[i], *mangled, len);
2150 work->tmpl_argvec[i][len] = '\0';
2151 }
2152 *mangled += r2;
2153 }
2154 if (!success)
2155 {
2156 break;
2157 }
2158 }
28e9041c 2159 else
2160 {
402ace4b 2161 string param;
2162 string* s;
2163
28e9041c 2164 /* otherwise, value parameter */
80283fb2 2165
28e9041c 2166 /* temp is initialized in do_type */
2167 success = do_type (work, mangled, &temp);
28e9041c 2168 string_delete(&temp);
2169 if (!success)
2d53096b 2170 break;
402ace4b 2171
2172 if (!is_type)
2173 {
2174 s = &param;
2175 string_init (s);
2176 }
2177 else
2178 s = tname;
2179
2d53096b 2180 success = demangle_template_value_parm (work, mangled, s,
2181 (type_kind_t) success);
402ace4b 2182
80283fb2 2183 if (!success)
28e9041c 2184 {
80283fb2 2185 if (!is_type)
2186 string_delete (s);
2187 success = 0;
2188 break;
28e9041c 2189 }
80283fb2 2190
402ace4b 2191 if (!is_type)
2192 {
2193 int len = s->p - s->b;
2194 work->tmpl_argvec[i] = xmalloc (len + 1);
2195 memcpy (work->tmpl_argvec[i], s->b, len);
2196 work->tmpl_argvec[i][len] = '\0';
0f82222a 2197
402ace4b 2198 string_appends (tname, s);
2199 string_delete (s);
2200 }
28e9041c 2201 }
2202 need_comma = 1;
2203 }
bdaa26ad 2204 if (is_java_array)
89e5545f 2205 {
bdaa26ad 2206 string_append (tname, "[]");
2207 }
2208 else
2209 {
2210 if (tname->p[-1] == '>')
2211 string_append (tname, " ");
2212 string_append (tname, ">");
89e5545f 2213 }
0f82222a 2214
99906878 2215 if (is_type && remember)
2216 remember_Btype (work, tname->b, LEN_STRING (tname), bindex);
2217
28e9041c 2218 /*
2219 if (work -> static_type)
2220 {
2221 string_append (declp, *mangled + 1);
2222 *mangled += strlen (*mangled);
2223 success = 1;
2224 }
2225 else
2226 {
2227 success = demangle_args (work, mangled, declp);
2228 }
2229 }
2230 */
2231 return (success);
2232}
2233
2234static int
2235arm_pt (work, mangled, n, anchor, args)
2236 struct work_stuff *work;
2237 const char *mangled;
2238 int n;
2239 const char **anchor, **args;
2240{
f75dc4de 2241 /* Check if ARM template with "__pt__" in it ("parameterized type") */
2242 /* Allow HP also here, because HP's cfront compiler follows ARM to some extent */
2243 if ((ARM_DEMANGLING || HP_DEMANGLING) && (*anchor = mystrstr (mangled, "__pt__")))
28e9041c 2244 {
2245 int len;
2246 *args = *anchor + 6;
2247 len = consume_count (args);
9fec6063 2248 if (len == -1)
2249 return 0;
28e9041c 2250 if (*args + len == mangled + n && **args == '_')
2251 {
2252 ++*args;
2253 return 1;
2254 }
2255 }
f75dc4de 2256 if (AUTO_DEMANGLING || EDG_DEMANGLING)
2257 {
2258 if ((*anchor = mystrstr (mangled, "__tm__"))
2259 || (*anchor = mystrstr (mangled, "__ps__"))
2260 || (*anchor = mystrstr (mangled, "__pt__")))
2261 {
2262 int len;
2263 *args = *anchor + 6;
2264 len = consume_count (args);
9fec6063 2265 if (len == -1)
2266 return 0;
f75dc4de 2267 if (*args + len == mangled + n && **args == '_')
2268 {
2269 ++*args;
2270 return 1;
2271 }
2272 }
7c8c70e9 2273 else if ((*anchor = mystrstr (mangled, "__S")))
f75dc4de 2274 {
2275 int len;
2276 *args = *anchor + 3;
2277 len = consume_count (args);
9fec6063 2278 if (len == -1)
2279 return 0;
f75dc4de 2280 if (*args + len == mangled + n && **args == '_')
2281 {
2282 ++*args;
2283 return 1;
2284 }
2285 }
2286 }
2287
28e9041c 2288 return 0;
2289}
2290
2291static void
f75dc4de 2292demangle_arm_hp_template (work, mangled, n, declp)
28e9041c 2293 struct work_stuff *work;
2294 const char **mangled;
2295 int n;
2296 string *declp;
2297{
2298 const char *p;
7c8c70e9 2299 const char *args;
28e9041c 2300 const char *e = *mangled + n;
f75dc4de 2301 string arg;
28e9041c 2302
f75dc4de 2303 /* Check for HP aCC template spec: classXt1t2 where t1, t2 are
2304 template args */
2305 if (HP_DEMANGLING && ((*mangled)[n] == 'X'))
28e9041c 2306 {
f75dc4de 2307 char *start_spec_args = NULL;
2308
2309 /* First check for and omit template specialization pseudo-arguments,
2310 such as in "Spec<#1,#1.*>" */
2311 start_spec_args = strchr (*mangled, '<');
2312 if (start_spec_args && (start_spec_args - *mangled < n))
2313 string_appendn (declp, *mangled, start_spec_args - *mangled);
2314 else
2315 string_appendn (declp, *mangled, n);
2316 (*mangled) += n + 1;
2317 string_init (&arg);
0f82222a 2318 if (work->temp_start == -1) /* non-recursive call */
f75dc4de 2319 work->temp_start = declp->p - declp->b;
2320 string_append (declp, "<");
2321 while (1)
2322 {
2323 string_clear (&arg);
2324 switch (**mangled)
2325 {
2326 case 'T':
2327 /* 'T' signals a type parameter */
2328 (*mangled)++;
2329 if (!do_type (work, mangled, &arg))
2330 goto hpacc_template_args_done;
2331 break;
0f82222a 2332
f75dc4de 2333 case 'U':
2334 case 'S':
2335 /* 'U' or 'S' signals an integral value */
2336 if (!do_hpacc_template_const_value (work, mangled, &arg))
2337 goto hpacc_template_args_done;
2338 break;
0f82222a 2339
f75dc4de 2340 case 'A':
2341 /* 'A' signals a named constant expression (literal) */
2342 if (!do_hpacc_template_literal (work, mangled, &arg))
2343 goto hpacc_template_args_done;
2344 break;
0f82222a 2345
f75dc4de 2346 default:
2347 /* Today, 1997-09-03, we have only the above types
0f82222a 2348 of template parameters */
2349 /* FIXME: maybe this should fail and return null */
f75dc4de 2350 goto hpacc_template_args_done;
2351 }
2352 string_appends (declp, &arg);
2353 /* Check if we're at the end of template args.
2354 0 if at end of static member of template class,
0f82222a 2355 _ if done with template args for a function */
2356 if ((**mangled == '\000') || (**mangled == '_'))
2357 break;
f75dc4de 2358 else
2359 string_append (declp, ",");
2360 }
2361 hpacc_template_args_done:
2362 string_append (declp, ">");
2363 string_delete (&arg);
2364 if (**mangled == '_')
2365 (*mangled)++;
2366 return;
2367 }
2368 /* ARM template? (Also handles HP cfront extensions) */
2369 else if (arm_pt (work, *mangled, n, &p, &args))
2370 {
2371 string type_str;
2372
28e9041c 2373 string_init (&arg);
2374 string_appendn (declp, *mangled, p - *mangled);
f75dc4de 2375 if (work->temp_start == -1) /* non-recursive call */
0f82222a 2376 work->temp_start = declp->p - declp->b;
28e9041c 2377 string_append (declp, "<");
2378 /* should do error checking here */
2379 while (args < e) {
2380 string_clear (&arg);
f75dc4de 2381
2382 /* Check for type or literal here */
2383 switch (*args)
2384 {
2385 /* HP cfront extensions to ARM for template args */
2386 /* spec: Xt1Lv1 where t1 is a type, v1 is a literal value */
2387 /* FIXME: We handle only numeric literals for HP cfront */
2388 case 'X':
0f82222a 2389 /* A typed constant value follows */
f75dc4de 2390 args++;
2391 if (!do_type (work, &args, &type_str))
2392 goto cfront_template_args_done;
2393 string_append (&arg, "(");
2394 string_appends (&arg, &type_str);
2395 string_append (&arg, ")");
2396 if (*args != 'L')
2397 goto cfront_template_args_done;
2398 args++;
2399 /* Now snarf a literal value following 'L' */
2400 if (!snarf_numeric_literal (&args, &arg))
2401 goto cfront_template_args_done;
2402 break;
2403
2404 case 'L':
2405 /* Snarf a literal following 'L' */
2406 args++;
2407 if (!snarf_numeric_literal (&args, &arg))
2408 goto cfront_template_args_done;
2409 break;
2410 default:
0f82222a 2411 /* Not handling other HP cfront stuff */
f75dc4de 2412 if (!do_type (work, &args, &arg))
2413 goto cfront_template_args_done;
2414 }
28e9041c 2415 string_appends (declp, &arg);
2416 string_append (declp, ",");
2417 }
f75dc4de 2418 cfront_template_args_done:
28e9041c 2419 string_delete (&arg);
f75dc4de 2420 if (args >= e)
0f82222a 2421 --declp->p; /* remove extra comma */
28e9041c 2422 string_append (declp, ">");
2423 }
7a1ec54f 2424 else if (n>10 && strncmp (*mangled, "_GLOBAL_", 8) == 0
2425 && (*mangled)[9] == 'N'
2426 && (*mangled)[8] == (*mangled)[10]
2427 && strchr (cplus_markers, (*mangled)[8]))
2428 {
2429 /* A member of the anonymous namespace. */
2430 string_append (declp, "{anonymous}");
2431 }
28e9041c 2432 else
2433 {
0f82222a 2434 if (work->temp_start == -1) /* non-recursive call only */
2435 work->temp_start = 0; /* disable in recursive calls */
28e9041c 2436 string_appendn (declp, *mangled, n);
2437 }
2438 *mangled += n;
2439}
2440
f75dc4de 2441/* Extract a class name, possibly a template with arguments, from the
2442 mangled string; qualifiers, local class indicators, etc. have
2443 already been dealt with */
2444
28e9041c 2445static int
2446demangle_class_name (work, mangled, declp)
2447 struct work_stuff *work;
2448 const char **mangled;
2449 string *declp;
2450{
2451 int n;
2452 int success = 0;
2453
2454 n = consume_count (mangled);
9fec6063 2455 if (n == -1)
2456 return 0;
2457 if ((int) strlen (*mangled) >= n)
28e9041c 2458 {
f75dc4de 2459 demangle_arm_hp_template (work, mangled, n, declp);
28e9041c 2460 success = 1;
2461 }
2462
2463 return (success);
2464}
2465
2466/*
2467
2468LOCAL FUNCTION
2469
2470 demangle_class -- demangle a mangled class sequence
2471
2472SYNOPSIS
2473
2474 static int
2475 demangle_class (struct work_stuff *work, const char **mangled,
2476 strint *declp)
2477
2478DESCRIPTION
2479
2480 DECLP points to the buffer into which demangling is being done.
2481
2482 *MANGLED points to the current token to be demangled. On input,
2483 it points to a mangled class (I.E. "3foo", "13verylongclass", etc.)
2484 On exit, it points to the next token after the mangled class on
2485 success, or the first unconsumed token on failure.
2486
2487 If the CONSTRUCTOR or DESTRUCTOR flags are set in WORK, then
2488 we are demangling a constructor or destructor. In this case
2489 we prepend "class::class" or "class::~class" to DECLP.
2490
2491 Otherwise, we prepend "class::" to the current DECLP.
2492
2493 Reset the constructor/destructor flags once they have been
2494 "consumed". This allows demangle_class to be called later during
2495 the same demangling, to do normal class demangling.
2496
2497 Returns 1 if demangling is successful, 0 otherwise.
2498
2499*/
2500
2501static int
2502demangle_class (work, mangled, declp)
2503 struct work_stuff *work;
2504 const char **mangled;
2505 string *declp;
2506{
2507 int success = 0;
fa4f3779 2508 int btype;
28e9041c 2509 string class_name;
0f82222a 2510 char *save_class_name_end = 0;
28e9041c 2511
2512 string_init (&class_name);
fa4f3779 2513 btype = register_Btype (work);
28e9041c 2514 if (demangle_class_name (work, mangled, &class_name))
2515 {
f75dc4de 2516 save_class_name_end = class_name.p;
28e9041c 2517 if ((work->constructor & 1) || (work->destructor & 1))
2518 {
f75dc4de 2519 /* adjust so we don't include template args */
2520 if (work->temp_start && (work->temp_start != -1))
2521 {
2522 class_name.p = class_name.b + work->temp_start;
2523 }
28e9041c 2524 string_prepends (declp, &class_name);
2525 if (work -> destructor & 1)
2526 {
2527 string_prepend (declp, "~");
2528 work -> destructor -= 1;
2529 }
2530 else
2531 {
0f82222a 2532 work -> constructor -= 1;
28e9041c 2533 }
2534 }
f75dc4de 2535 class_name.p = save_class_name_end;
fa4f3779 2536 remember_Ktype (work, class_name.b, LEN_STRING(&class_name));
2537 remember_Btype (work, class_name.b, LEN_STRING(&class_name), btype);
99906878 2538 string_prepend (declp, SCOPE_STRING (work));
28e9041c 2539 string_prepends (declp, &class_name);
2540 success = 1;
2541 }
2542 string_delete (&class_name);
2543 return (success);
2544}
2545
f2e5a608 2546
2547/* Called when there's a "__" in the mangled name, with `scan' pointing to
2548 the rightmost guess.
2549
2550 Find the correct "__"-sequence where the function name ends and the
2551 signature starts, which is ambiguous with GNU mangling.
2552 Call demangle_signature here, so we can make sure we found the right
2553 one; *mangled will be consumed so caller will not make further calls to
2554 demangle_signature. */
2555
2556static int
2557iterate_demangle_function (work, mangled, declp, scan)
2558 struct work_stuff *work;
2559 const char **mangled;
2560 string *declp;
2561 const char *scan;
2562{
2563 const char *mangle_init = *mangled;
2564 int success = 0;
2565 string decl_init;
2566 struct work_stuff work_init;
2567
2568 if (*(scan + 2) == '\0')
2569 return 0;
2570
2571 /* Do not iterate for some demangling modes, or if there's only one
2572 "__"-sequence. This is the normal case. */
2573 if (ARM_DEMANGLING || LUCID_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING
2574 || mystrstr (scan + 2, "__") == NULL)
2575 {
2576 demangle_function_name (work, mangled, declp, scan);
2577 return 1;
2578 }
2579
2580 /* Save state so we can restart if the guess at the correct "__" was
2581 wrong. */
2582 string_init (&decl_init);
2583 string_appends (&decl_init, declp);
2584 memset (&work_init, 0, sizeof work_init);
2585 work_stuff_copy_to_from (&work_init, work);
2586
2587 /* Iterate over occurrences of __, allowing names and types to have a
2588 "__" sequence in them. We must start with the first (not the last)
2589 occurrence, since "__" most often occur between independent mangled
2590 parts, hence starting at the last occurence inside a signature
2591 might get us a "successful" demangling of the signature. */
2592
2593 while (scan[2])
2594 {
2595 demangle_function_name (work, mangled, declp, scan);
2596 success = demangle_signature (work, mangled, declp);
2597 if (success)
2598 break;
2599
2600 /* Reset demangle state for the next round. */
2601 *mangled = mangle_init;
2602 string_clear (declp);
2603 string_appends (declp, &decl_init);
2604 work_stuff_copy_to_from (work, &work_init);
2605
2606 /* Leave this underscore-sequence. */
2607 scan += 2;
2608
2609 /* Scan for the next "__" sequence. */
2610 while (*scan && (scan[0] != '_' || scan[1] != '_'))
2611 scan++;
2612
2613 /* Move to last "__" in this sequence. */
2614 while (*scan && *scan == '_')
2615 scan++;
2616 scan -= 2;
2617 }
2618
2619 /* Delete saved state. */
2620 delete_work_stuff (&work_init);
2621 string_delete (&decl_init);
2622
2623 return success;
2624}
2625
28e9041c 2626/*
2627
2628LOCAL FUNCTION
2629
2630 demangle_prefix -- consume the mangled name prefix and find signature
2631
2632SYNOPSIS
2633
2634 static int
2635 demangle_prefix (struct work_stuff *work, const char **mangled,
2636 string *declp);
2637
2638DESCRIPTION
2639
2640 Consume and demangle the prefix of the mangled name.
f2e5a608 2641 While processing the function name root, arrange to call
2642 demangle_signature if the root is ambiguous.
28e9041c 2643
2644 DECLP points to the string buffer into which demangled output is
2645 placed. On entry, the buffer is empty. On exit it contains
2646 the root function name, the demangled operator name, or in some
2647 special cases either nothing or the completely demangled result.
2648
2649 MANGLED points to the current pointer into the mangled name. As each
2650 token of the mangled name is consumed, it is updated. Upon entry
2651 the current mangled name pointer points to the first character of
2652 the mangled name. Upon exit, it should point to the first character
2653 of the signature if demangling was successful, or to the first
2654 unconsumed character if demangling of the prefix was unsuccessful.
0f82222a 2655
28e9041c 2656 Returns 1 on success, 0 otherwise.
2657 */
2658
2659static int
2660demangle_prefix (work, mangled, declp)
2661 struct work_stuff *work;
2662 const char **mangled;
2663 string *declp;
2664{
2665 int success = 1;
2666 const char *scan;
2667 int i;
2668
37c9cc60 2669 if (strlen(*mangled) > 6
0f82222a 2670 && (strncmp(*mangled, "_imp__", 6) == 0
37c9cc60 2671 || strncmp(*mangled, "__imp_", 6) == 0))
2672 {
2673 /* it's a symbol imported from a PE dynamic library. Check for both
2674 new style prefix _imp__ and legacy __imp_ used by older versions
2675 of dlltool. */
2676 (*mangled) += 6;
2677 work->dllimported = 1;
2678 }
2679 else if (strlen(*mangled) >= 11 && strncmp(*mangled, "_GLOBAL_", 8) == 0)
28e9041c 2680 {
2681 char *marker = strchr (cplus_markers, (*mangled)[8]);
2682 if (marker != NULL && *marker == (*mangled)[10])
2683 {
2684 if ((*mangled)[9] == 'D')
2685 {
2686 /* it's a GNU global destructor to be executed at program exit */
2687 (*mangled) += 11;
2688 work->destructor = 2;
2689 if (gnu_special (work, mangled, declp))
2690 return success;
2691 }
2692 else if ((*mangled)[9] == 'I')
2693 {
2694 /* it's a GNU global constructor to be executed at program init */
2695 (*mangled) += 11;
2696 work->constructor = 2;
2697 if (gnu_special (work, mangled, declp))
2698 return success;
2699 }
2700 }
2701 }
f75dc4de 2702 else if ((ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING) && strncmp(*mangled, "__std__", 7) == 0)
28e9041c 2703 {
2704 /* it's a ARM global destructor to be executed at program exit */
2705 (*mangled) += 7;
2706 work->destructor = 2;
2707 }
f75dc4de 2708 else if ((ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING) && strncmp(*mangled, "__sti__", 7) == 0)
28e9041c 2709 {
2710 /* it's a ARM global constructor to be executed at program initial */
2711 (*mangled) += 7;
2712 work->constructor = 2;
2713 }
2714
2715 /* This block of code is a reduction in strength time optimization
2716 of:
2717 scan = mystrstr (*mangled, "__"); */
2718
2719 {
2720 scan = *mangled;
2721
2722 do {
2723 scan = strchr (scan, '_');
2724 } while (scan != NULL && *++scan != '_');
2725
2726 if (scan != NULL) --scan;
2727 }
2728
2729 if (scan != NULL)
2730 {
2731 /* We found a sequence of two or more '_', ensure that we start at
2732 the last pair in the sequence. */
2733 i = strspn (scan, "_");
2734 if (i > 2)
2735 {
0f82222a 2736 scan += (i - 2);
28e9041c 2737 }
2738 }
0f82222a 2739
28e9041c 2740 if (scan == NULL)
2741 {
2742 success = 0;
2743 }
2744 else if (work -> static_type)
2745 {
93ce8ce4 2746 if (!ISDIGIT ((unsigned char)scan[0]) && (scan[0] != 't'))
28e9041c 2747 {
2748 success = 0;
2749 }
2750 }
2751 else if ((scan == *mangled)
93ce8ce4 2752 && (ISDIGIT ((unsigned char)scan[2]) || (scan[2] == 'Q')
4350e959 2753 || (scan[2] == 't') || (scan[2] == 'K') || (scan[2] == 'H')))
28e9041c 2754 {
2755 /* The ARM says nothing about the mangling of local variables.
2756 But cfront mangles local variables by prepending __<nesting_level>
2757 to them. As an extension to ARM demangling we handle this case. */
f75dc4de 2758 if ((LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING)
93ce8ce4 2759 && ISDIGIT ((unsigned char)scan[2]))
28e9041c 2760 {
2761 *mangled = scan + 2;
2762 consume_count (mangled);
2763 string_append (declp, *mangled);
2764 *mangled += strlen (*mangled);
0f82222a 2765 success = 1;
28e9041c 2766 }
2767 else
2768 {
2769 /* A GNU style constructor starts with __[0-9Qt]. But cfront uses
2770 names like __Q2_3foo3bar for nested type names. So don't accept
8f71bf1d 2771 this style of constructor for cfront demangling. A GNU
2772 style member-template constructor starts with 'H'. */
f75dc4de 2773 if (!(LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING))
28e9041c 2774 work -> constructor += 1;
2775 *mangled = scan + 2;
2776 }
2777 }
f75dc4de 2778 else if (ARM_DEMANGLING && scan[2] == 'p' && scan[3] == 't')
2779 {
2780 /* Cfront-style parameterized type. Handled later as a signature. */
2781 success = 1;
0f82222a 2782
f75dc4de 2783 /* ARM template? */
2784 demangle_arm_hp_template (work, mangled, strlen (*mangled), declp);
2785 }
2786 else if (EDG_DEMANGLING && ((scan[2] == 't' && scan[3] == 'm')
2787 || (scan[2] == 'p' && scan[3] == 's')
2788 || (scan[2] == 'p' && scan[3] == 't')))
2789 {
2790 /* EDG-style parameterized type. Handled later as a signature. */
2791 success = 1;
0f82222a 2792
f75dc4de 2793 /* EDG template? */
2794 demangle_arm_hp_template (work, mangled, strlen (*mangled), declp);
2795 }
93ce8ce4 2796 else if ((scan == *mangled) && !ISDIGIT ((unsigned char)scan[2])
4350e959 2797 && (scan[2] != 't'))
28e9041c 2798 {
2799 /* Mangled name starts with "__". Skip over any leading '_' characters,
2800 then find the next "__" that separates the prefix from the signature.
2801 */
f75dc4de 2802 if (!(ARM_DEMANGLING || LUCID_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
f39af051 2803 || (arm_special (mangled, declp) == 0))
28e9041c 2804 {
2805 while (*scan == '_')
2806 {
2807 scan++;
2808 }
2809 if ((scan = mystrstr (scan, "__")) == NULL || (*(scan + 2) == '\0'))
2810 {
2811 /* No separator (I.E. "__not_mangled"), or empty signature
2812 (I.E. "__not_mangled_either__") */
2813 success = 0;
2814 }
2815 else
f2e5a608 2816 return iterate_demangle_function (work, mangled, declp, scan);
28e9041c 2817 }
2818 }
28e9041c 2819 else if (*(scan + 2) != '\0')
2820 {
2821 /* Mangled name does not start with "__" but does have one somewhere
2822 in there with non empty stuff after it. Looks like a global
f2e5a608 2823 function name. Iterate over all "__":s until the right
2824 one is found. */
2825 return iterate_demangle_function (work, mangled, declp, scan);
28e9041c 2826 }
2827 else
2828 {
2829 /* Doesn't look like a mangled name */
2830 success = 0;
2831 }
2832
2833 if (!success && (work->constructor == 2 || work->destructor == 2))
2834 {
2835 string_append (declp, *mangled);
2836 *mangled += strlen (*mangled);
2837 success = 1;
0f82222a 2838 }
28e9041c 2839 return (success);
2840}
2841
2842/*
2843
2844LOCAL FUNCTION
2845
2846 gnu_special -- special handling of gnu mangled strings
2847
2848SYNOPSIS
2849
2850 static int
2851 gnu_special (struct work_stuff *work, const char **mangled,
2852 string *declp);
2853
2854
2855DESCRIPTION
2856
2857 Process some special GNU style mangling forms that don't fit
2858 the normal pattern. For example:
2859
2860 _$_3foo (destructor for class foo)
2861 _vt$foo (foo virtual table)
2862 _vt$foo$bar (foo::bar virtual table)
2863 __vt_foo (foo virtual table, new style with thunks)
2864 _3foo$varname (static data member)
2865 _Q22rs2tu$vw (static data member)
2866 __t6vector1Zii (constructor with template)
2867 __thunk_4__$_7ostream (virtual function thunk)
2868 */
2869
2870static int
2871gnu_special (work, mangled, declp)
2872 struct work_stuff *work;
2873 const char **mangled;
2874 string *declp;
2875{
2876 int n;
2877 int success = 1;
2878 const char *p;
2879
2880 if ((*mangled)[0] == '_'
2881 && strchr (cplus_markers, (*mangled)[1]) != NULL
2882 && (*mangled)[2] == '_')
2883 {
2884 /* Found a GNU style destructor, get past "_<CPLUS_MARKER>_" */
2885 (*mangled) += 3;
2886 work -> destructor += 1;
2887 }
2888 else if ((*mangled)[0] == '_'
2889 && (((*mangled)[1] == '_'
2890 && (*mangled)[2] == 'v'
2891 && (*mangled)[3] == 't'
2892 && (*mangled)[4] == '_')
2893 || ((*mangled)[1] == 'v'
2894 && (*mangled)[2] == 't'
2895 && strchr (cplus_markers, (*mangled)[3]) != NULL)))
2896 {
2897 /* Found a GNU style virtual table, get past "_vt<CPLUS_MARKER>"
2898 and create the decl. Note that we consume the entire mangled
2899 input string, which means that demangle_signature has no work
2900 to do. */
2901 if ((*mangled)[2] == 'v')
2902 (*mangled) += 5; /* New style, with thunks: "__vt_" */
2903 else
2904 (*mangled) += 4; /* Old style, no thunks: "_vt<CPLUS_MARKER>" */
2905 while (**mangled != '\0')
2906 {
28e9041c 2907 switch (**mangled)
2908 {
2909 case 'Q':
fa4f3779 2910 case 'K':
28e9041c 2911 success = demangle_qualified (work, mangled, declp, 0, 1);
2912 break;
2913 case 't':
99906878 2914 success = demangle_template (work, mangled, declp, 0, 1,
2915 1);
28e9041c 2916 break;
2917 default:
93ce8ce4 2918 if (ISDIGIT((unsigned char)*mangled[0]))
28e9041c 2919 {
2920 n = consume_count(mangled);
d2d39e09 2921 /* We may be seeing a too-large size, or else a
2922 ".<digits>" indicating a static local symbol. In
2923 any case, declare victory and move on; *don't* try
2924 to use n to allocate. */
4350e959 2925 if (n > (int) strlen (*mangled))
d2d39e09 2926 {
2927 success = 1;
2928 break;
2929 }
28e9041c 2930 }
2931 else
2932 {
2933 n = strcspn (*mangled, cplus_markers);
2934 }
2935 string_appendn (declp, *mangled, n);
2936 (*mangled) += n;
2937 }
2938
3662c79b 2939 p = strpbrk (*mangled, cplus_markers);
28e9041c 2940 if (success && ((p == NULL) || (p == *mangled)))
2941 {
2942 if (p != NULL)
2943 {
99906878 2944 string_append (declp, SCOPE_STRING (work));
28e9041c 2945 (*mangled)++;
2946 }
2947 }
2948 else
2949 {
2950 success = 0;
2951 break;
2952 }
2953 }
2954 if (success)
2955 string_append (declp, " virtual table");
2956 }
2957 else if ((*mangled)[0] == '_'
2958 && (strchr("0123456789Qt", (*mangled)[1]) != NULL)
2959 && (p = strpbrk (*mangled, cplus_markers)) != NULL)
2960 {
2961 /* static data member, "_3foo$varname" for example */
2962 (*mangled)++;
2963 switch (**mangled)
2964 {
2965 case 'Q':
fa4f3779 2966 case 'K':
28e9041c 2967 success = demangle_qualified (work, mangled, declp, 0, 1);
2968 break;
2969 case 't':
99906878 2970 success = demangle_template (work, mangled, declp, 0, 1, 1);
28e9041c 2971 break;
2972 default:
2973 n = consume_count (mangled);
ac126d82 2974 if (n < 0 || n > (long) strlen (*mangled))
9fec6063 2975 {
2976 success = 0;
2977 break;
2978 }
78631810 2979
2980 if (n > 10 && strncmp (*mangled, "_GLOBAL_", 8) == 0
2981 && (*mangled)[9] == 'N'
2982 && (*mangled)[8] == (*mangled)[10]
2983 && strchr (cplus_markers, (*mangled)[8]))
2984 {
2985 /* A member of the anonymous namespace. There's information
2986 about what identifier or filename it was keyed to, but
2987 it's just there to make the mangled name unique; we just
2988 step over it. */
2989 string_append (declp, "{anonymous}");
2990 (*mangled) += n;
2991
2992 /* Now p points to the marker before the N, so we need to
2993 update it to the first marker after what we consumed. */
2994 p = strpbrk (*mangled, cplus_markers);
2995 break;
2996 }
2997
28e9041c 2998 string_appendn (declp, *mangled, n);
2999 (*mangled) += n;
3000 }
3001 if (success && (p == *mangled))
3002 {
3003 /* Consumed everything up to the cplus_marker, append the
3004 variable name. */
3005 (*mangled)++;
99906878 3006 string_append (declp, SCOPE_STRING (work));
28e9041c 3007 n = strlen (*mangled);
3008 string_appendn (declp, *mangled, n);
3009 (*mangled) += n;
3010 }
3011 else
3012 {
3013 success = 0;
3014 }
3015 }
3016 else if (strncmp (*mangled, "__thunk_", 8) == 0)
3017 {
9fec6063 3018 int delta;
3019
3020 (*mangled) += 8;
3021 delta = consume_count (mangled);
3022 if (delta == -1)
3023 success = 0;
28e9041c 3024 else
3025 {
9fec6063 3026 char *method = internal_cplus_demangle (work, ++*mangled);
3027
3028 if (method)
3029 {
3030 char buf[50];
3031 sprintf (buf, "virtual function thunk (delta:%d) for ", -delta);
3032 string_append (declp, buf);
3033 string_append (declp, method);
3034 free (method);
3035 n = strlen (*mangled);
3036 (*mangled) += n;
3037 }
3038 else
3039 {
3040 success = 0;
3041 }
28e9041c 3042 }
3043 }
3044 else if (strncmp (*mangled, "__t", 3) == 0
3045 && ((*mangled)[3] == 'i' || (*mangled)[3] == 'f'))
3046 {
3047 p = (*mangled)[3] == 'i' ? " type_info node" : " type_info function";
3048 (*mangled) += 4;
3049 switch (**mangled)
3050 {
3051 case 'Q':
fa4f3779 3052 case 'K':
28e9041c 3053 success = demangle_qualified (work, mangled, declp, 0, 1);
3054 break;
3055 case 't':
99906878 3056 success = demangle_template (work, mangled, declp, 0, 1, 1);
28e9041c 3057 break;
3058 default:
1a2d2193 3059 success = do_type (work, mangled, declp);
28e9041c 3060 break;
3061 }
3062 if (success && **mangled != '\0')
3063 success = 0;
3064 if (success)
3065 string_append (declp, p);
3066 }
3067 else
3068 {
3069 success = 0;
3070 }
3071 return (success);
3072}
3073
f75dc4de 3074static void
3075recursively_demangle(work, mangled, result, namelength)
3076 struct work_stuff *work;
3077 const char **mangled;
3078 string *result;
3079 int namelength;
3080{
3081 char * recurse = (char *)NULL;
3082 char * recurse_dem = (char *)NULL;
0f82222a 3083
f75dc4de 3084 recurse = (char *) xmalloc (namelength + 1);
3085 memcpy (recurse, *mangled, namelength);
3086 recurse[namelength] = '\000';
0f82222a 3087
f75dc4de 3088 recurse_dem = cplus_demangle (recurse, work->options);
0f82222a 3089
f75dc4de 3090 if (recurse_dem)
3091 {
3092 string_append (result, recurse_dem);
3093 free (recurse_dem);
3094 }
3095 else
3096 {
3097 string_appendn (result, *mangled, namelength);
3098 }
3099 free (recurse);
3100 *mangled += namelength;
3101}
3102
28e9041c 3103/*
3104
3105LOCAL FUNCTION
3106
3107 arm_special -- special handling of ARM/lucid mangled strings
3108
3109SYNOPSIS
3110
3111 static int
f39af051 3112 arm_special (const char **mangled,
3113 string *declp);
28e9041c 3114
3115
3116DESCRIPTION
3117
3118 Process some special ARM style mangling forms that don't fit
3119 the normal pattern. For example:
3120
3121 __vtbl__3foo (foo virtual table)
3122 __vtbl__3foo__3bar (bar::foo virtual table)
3123
3124 */
3125
3126static int
f39af051 3127arm_special (mangled, declp)
28e9041c 3128 const char **mangled;
3129 string *declp;
3130{
3131 int n;
3132 int success = 1;
3133 const char *scan;
3134
3135 if (strncmp (*mangled, ARM_VTABLE_STRING, ARM_VTABLE_STRLEN) == 0)
3136 {
3137 /* Found a ARM style virtual table, get past ARM_VTABLE_STRING
3138 and create the decl. Note that we consume the entire mangled
3139 input string, which means that demangle_signature has no work
3140 to do. */
3141 scan = *mangled + ARM_VTABLE_STRLEN;
3142 while (*scan != '\0') /* first check it can be demangled */
3143 {
3144 n = consume_count (&scan);
9fec6063 3145 if (n == -1)
28e9041c 3146 {
3147 return (0); /* no good */
3148 }
3149 scan += n;
3150 if (scan[0] == '_' && scan[1] == '_')
3151 {
3152 scan += 2;
3153 }
3154 }
3155 (*mangled) += ARM_VTABLE_STRLEN;
3156 while (**mangled != '\0')
3157 {
3158 n = consume_count (mangled);
9fec6063 3159 if (n == -1
ac126d82 3160 || n > (long) strlen (*mangled))
9fec6063 3161 return 0;
28e9041c 3162 string_prependn (declp, *mangled, n);
3163 (*mangled) += n;
3164 if ((*mangled)[0] == '_' && (*mangled)[1] == '_')
3165 {
3166 string_prepend (declp, "::");
3167 (*mangled) += 2;
3168 }
3169 }
3170 string_append (declp, " virtual table");
3171 }
3172 else
3173 {
3174 success = 0;
3175 }
3176 return (success);
3177}
3178
3179/*
3180
3181LOCAL FUNCTION
3182
3183 demangle_qualified -- demangle 'Q' qualified name strings
3184
3185SYNOPSIS
3186
3187 static int
3188 demangle_qualified (struct work_stuff *, const char *mangled,
3189 string *result, int isfuncname, int append);
3190
3191DESCRIPTION
3192
3193 Demangle a qualified name, such as "Q25Outer5Inner" which is
3194 the mangled form of "Outer::Inner". The demangled output is
3195 prepended or appended to the result string according to the
3196 state of the append flag.
3197
3198 If isfuncname is nonzero, then the qualified name we are building
3199 is going to be used as a member function name, so if it is a
3200 constructor or destructor function, append an appropriate
3201 constructor or destructor name. I.E. for the above example,
3202 the result for use as a constructor is "Outer::Inner::Inner"
3203 and the result for use as a destructor is "Outer::Inner::~Inner".
3204
3205BUGS
3206
3207 Numeric conversion is ASCII dependent (FIXME).
3208
3209 */
3210
3211static int
3212demangle_qualified (work, mangled, result, isfuncname, append)
3213 struct work_stuff *work;
3214 const char **mangled;
3215 string *result;
3216 int isfuncname;
3217 int append;
3218{
fa4f3779 3219 int qualifiers = 0;
28e9041c 3220 int success = 1;
28e9041c 3221 char num[2];
3222 string temp;
99906878 3223 string last_name;
3224 int bindex = register_Btype (work);
3225
3226 /* We only make use of ISFUNCNAME if the entity is a constructor or
3227 destructor. */
0f82222a 3228 isfuncname = (isfuncname
99906878 3229 && ((work->constructor & 1) || (work->destructor & 1)));
28e9041c 3230
3231 string_init (&temp);
99906878 3232 string_init (&last_name);
fa4f3779 3233
3234 if ((*mangled)[0] == 'K')
3235 {
3236 /* Squangling qualified name reuse */
3237 int idx;
3238 (*mangled)++;
3239 idx = consume_count_with_underscores (mangled);
e5d3a45b 3240 if (idx == -1 || idx >= work -> numk)
fa4f3779 3241 success = 0;
3242 else
3243 string_append (&temp, work -> ktypevec[idx]);
3244 }
3245 else
3246 switch ((*mangled)[1])
28e9041c 3247 {
3248 case '_':
3249 /* GNU mangled name with more than 9 classes. The count is preceded
3250 by an underscore (to distinguish it from the <= 9 case) and followed
3251 by an underscore. */
42c870f1 3252 (*mangled)++;
3253 qualifiers = consume_count_with_underscores (mangled);
3254 if (qualifiers == -1)
28e9041c 3255 success = 0;
28e9041c 3256 break;
3257
3258 case '1':
3259 case '2':
3260 case '3':
3261 case '4':
3262 case '5':
3263 case '6':
3264 case '7':
3265 case '8':
3266 case '9':
3267 /* The count is in a single digit. */
3268 num[0] = (*mangled)[1];
3269 num[1] = '\0';
3270 qualifiers = atoi (num);
3271
3272 /* If there is an underscore after the digit, skip it. This is
3273 said to be for ARM-qualified names, but the ARM makes no
3274 mention of such an underscore. Perhaps cfront uses one. */
3275 if ((*mangled)[2] == '_')
3276 {
3277 (*mangled)++;
3278 }
3279 (*mangled) += 2;
3280 break;
3281
3282 case '0':
3283 default:
3284 success = 0;
3285 }
3286
3287 if (!success)
3288 return success;
3289
3290 /* Pick off the names and collect them in the temp buffer in the order
3291 in which they are found, separated by '::'. */
3292
3293 while (qualifiers-- > 0)
3294 {
fa4f3779 3295 int remember_K = 1;
99906878 3296 string_clear (&last_name);
3297
0f82222a 3298 if (*mangled[0] == '_')
99906878 3299 (*mangled)++;
3300
28e9041c 3301 if (*mangled[0] == 't')
3302 {
99906878 3303 /* Here we always append to TEMP since we will want to use
3304 the template name without the template parameters as a
3305 constructor or destructor name. The appropriate
3306 (parameter-less) value is returned by demangle_template
3307 in LAST_NAME. We do not remember the template type here,
3308 in order to match the G++ mangling algorithm. */
0f82222a 3309 success = demangle_template(work, mangled, &temp,
99906878 3310 &last_name, 1, 0);
0f82222a 3311 if (!success)
99906878 3312 break;
0f82222a 3313 }
6e7ee99b 3314 else if (*mangled[0] == 'K')
fa4f3779 3315 {
3316 int idx;
3317 (*mangled)++;
3318 idx = consume_count_with_underscores (mangled);
e5d3a45b 3319 if (idx == -1 || idx >= work->numk)
fa4f3779 3320 success = 0;
3321 else
3322 string_append (&temp, work->ktypevec[idx]);
3323 remember_K = 0;
3324
28e9041c 3325 if (!success) break;
3326 }
3327 else
99906878 3328 {
f75dc4de 3329 if (EDG_DEMANGLING)
3330 {
3331 int namelength;
3332 /* Now recursively demangle the qualifier
0f82222a 3333 * This is necessary to deal with templates in
3334 * mangling styles like EDG */
f75dc4de 3335 namelength = consume_count (mangled);
9fec6063 3336 if (namelength == -1)
3337 {
3338 success = 0;
3339 break;
3340 }
f75dc4de 3341 recursively_demangle(work, mangled, &temp, namelength);
3342 }
3343 else
3344 {
3345 success = do_type (work, mangled, &last_name);
3346 if (!success)
3347 break;
3348 string_appends (&temp, &last_name);
3349 }
28e9041c 3350 }
fa4f3779 3351
3352 if (remember_K)
99906878 3353 remember_Ktype (work, temp.b, LEN_STRING (&temp));
fa4f3779 3354
28e9041c 3355 if (qualifiers > 0)
99906878 3356 string_append (&temp, SCOPE_STRING (work));
28e9041c 3357 }
3358
99906878 3359 remember_Btype (work, temp.b, LEN_STRING (&temp), bindex);
3360
28e9041c 3361 /* If we are using the result as a function name, we need to append
3362 the appropriate '::' separated constructor or destructor name.
3363 We do this here because this is the most convenient place, where
3364 we already have a pointer to the name and the length of the name. */
3365
0f82222a 3366 if (isfuncname)
28e9041c 3367 {
99906878 3368 string_append (&temp, SCOPE_STRING (work));
28e9041c 3369 if (work -> destructor & 1)
99906878 3370 string_append (&temp, "~");
3371 string_appends (&temp, &last_name);
28e9041c 3372 }
3373
0f82222a 3374 /* Now either prepend the temp buffer to the result, or append it,
28e9041c 3375 depending upon the state of the append flag. */
3376
3377 if (append)
99906878 3378 string_appends (result, &temp);
28e9041c 3379 else
3380 {
3381 if (!STRING_EMPTY (result))
99906878 3382 string_append (&temp, SCOPE_STRING (work));
28e9041c 3383 string_prepends (result, &temp);
3384 }
3385
99906878 3386 string_delete (&last_name);
28e9041c 3387 string_delete (&temp);
3388 return (success);
3389}
3390
3391/*
3392
3393LOCAL FUNCTION
3394
3395 get_count -- convert an ascii count to integer, consuming tokens
3396
3397SYNOPSIS
3398
3399 static int
3400 get_count (const char **type, int *count)
3401
3402DESCRIPTION
3403
9fec6063 3404 Assume that *type points at a count in a mangled name; set
3405 *count to its value, and set *type to the next character after
3406 the count. There are some weird rules in effect here.
3407
3408 If *type does not point at a string of digits, return zero.
3409
3410 If *type points at a string of digits followed by an
3411 underscore, set *count to their value as an integer, advance
3412 *type to point *after the underscore, and return 1.
3413
3414 If *type points at a string of digits not followed by an
3415 underscore, consume only the first digit. Set *count to its
3416 value as an integer, leave *type pointing after that digit,
3417 and return 1.
3418
3419 The excuse for this odd behavior: in the ARM and HP demangling
3420 styles, a type can be followed by a repeat count of the form
3421 `Nxy', where:
3422
3423 `x' is a single digit specifying how many additional copies
3424 of the type to append to the argument list, and
3425
3426 `y' is one or more digits, specifying the zero-based index of
3427 the first repeated argument in the list. Yes, as you're
3428 unmangling the name you can figure this out yourself, but
3429 it's there anyway.
3430
3431 So, for example, in `bar__3fooFPiN51', the first argument is a
3432 pointer to an integer (`Pi'), and then the next five arguments
3433 are the same (`N5'), and the first repeat is the function's
3434 second argument (`1').
28e9041c 3435*/
3436
3437static int
3438get_count (type, count)
3439 const char **type;
3440 int *count;
3441{
3442 const char *p;
3443 int n;
3444
93ce8ce4 3445 if (!ISDIGIT ((unsigned char)**type))
42c870f1 3446 return (0);
28e9041c 3447 else
3448 {
3449 *count = **type - '0';
3450 (*type)++;
93ce8ce4 3451 if (ISDIGIT ((unsigned char)**type))
28e9041c 3452 {
3453 p = *type;
3454 n = *count;
0f82222a 3455 do
28e9041c 3456 {
3457 n *= 10;
3458 n += *p - '0';
3459 p++;
0f82222a 3460 }
93ce8ce4 3461 while (ISDIGIT ((unsigned char)*p));
28e9041c 3462 if (*p == '_')
3463 {
3464 *type = p + 1;
3465 *count = n;
3466 }
3467 }
3468 }
3469 return (1);
3470}
3471
2d53096b 3472/* RESULT will be initialised here; it will be freed on failure. The
3473 value returned is really a type_kind_t. */
28e9041c 3474
3475static int
3476do_type (work, mangled, result)
3477 struct work_stuff *work;
3478 const char **mangled;
3479 string *result;
3480{
3481 int n;
3482 int done;
3483 int success;
3484 string decl;
3485 const char *remembered_type;
3e04bd45 3486 int type_quals;
fa4f3779 3487 string btype;
2d53096b 3488 type_kind_t tk = tk_none;
28e9041c 3489
fa4f3779 3490 string_init (&btype);
28e9041c 3491 string_init (&decl);
3492 string_init (result);
3493
3494 done = 0;
3495 success = 1;
3496 while (success && !done)
3497 {
3498 int member;
3499 switch (**mangled)
3500 {
3501
3502 /* A pointer type */
3503 case 'P':
3504 case 'p':
3505 (*mangled)++;
bdaa26ad 3506 if (! (work -> options & DMGL_JAVA))
3507 string_prepend (&decl, "*");
2d53096b 3508 if (tk == tk_none)
3509 tk = tk_pointer;
28e9041c 3510 break;
3511
3512 /* A reference type */
3513 case 'R':
3514 (*mangled)++;
3515 string_prepend (&decl, "&");
2d53096b 3516 if (tk == tk_none)
73bea962 3517 tk = tk_reference;
28e9041c 3518 break;
3519
3520 /* An array */
3521 case 'A':
3522 {
2d53096b 3523 ++(*mangled);
69b77066 3524 if (!STRING_EMPTY (&decl)
3525 && (decl.b[0] == '*' || decl.b[0] == '&'))
8f2cc44d 3526 {
3527 string_prepend (&decl, "(");
3528 string_append (&decl, ")");
3529 }
3530 string_append (&decl, "[");
3531 if (**mangled != '_')
3532 success = demangle_template_value_parm (work, mangled, &decl,
3533 tk_integral);
28e9041c 3534 if (**mangled == '_')
2d53096b 3535 ++(*mangled);
3536 string_append (&decl, "]");
28e9041c 3537 break;
3538 }
3539
3540 /* A back reference to a previously seen type */
3541 case 'T':
3542 (*mangled)++;
3543 if (!get_count (mangled, &n) || n >= work -> ntypes)
3544 {
3545 success = 0;
3546 }
3547 else
3548 {
3549 remembered_type = work -> typevec[n];
3550 mangled = &remembered_type;
3551 }
3552 break;
3553
3554 /* A function */
3555 case 'F':
3556 (*mangled)++;
69b77066 3557 if (!STRING_EMPTY (&decl)
3558 && (decl.b[0] == '*' || decl.b[0] == '&'))
28e9041c 3559 {
3560 string_prepend (&decl, "(");
3561 string_append (&decl, ")");
3562 }
3563 /* After picking off the function args, we expect to either find the
3564 function return type (preceded by an '_') or the end of the
3565 string. */
99906878 3566 if (!demangle_nested_args (work, mangled, &decl)
28e9041c 3567 || (**mangled != '_' && **mangled != '\0'))
3568 {
3569 success = 0;
99906878 3570 break;
28e9041c 3571 }
3572 if (success && (**mangled == '_'))
99906878 3573 (*mangled)++;
28e9041c 3574 break;
3575
3576 case 'M':
3577 case 'O':
3578 {
3e04bd45 3579 type_quals = TYPE_UNQUALIFIED;
28e9041c 3580
3581 member = **mangled == 'M';
3582 (*mangled)++;
28e9041c 3583
3584 string_append (&decl, ")");
6c65e8d7 3585
3586 /* We don't need to prepend `::' for a qualified name;
3587 demangle_qualified will do that for us. */
3588 if (**mangled != 'Q')
3589 string_prepend (&decl, SCOPE_STRING (work));
3590
93ce8ce4 3591 if (ISDIGIT ((unsigned char)**mangled))
28e9041c 3592 {
3593 n = consume_count (mangled);
9fec6063 3594 if (n == -1
3595 || (int) strlen (*mangled) < n)
28e9041c 3596 {
3597 success = 0;
3598 break;
3599 }
3600 string_prependn (&decl, *mangled, n);
3601 *mangled += n;
3602 }
0dc64970 3603 else if (**mangled == 'X' || **mangled == 'Y')
3604 {
3605 string temp;
3606 do_type (work, mangled, &temp);
3607 string_prepends (&decl, &temp);
3608 }
3609 else if (**mangled == 't')
28e9041c 3610 {
3611 string temp;
3612 string_init (&temp);
99906878 3613 success = demangle_template (work, mangled, &temp,
3614 NULL, 1, 1);
28e9041c 3615 if (success)
3616 {
3617 string_prependn (&decl, temp.b, temp.p - temp.b);
3618 string_clear (&temp);
3619 }
3620 else
3621 break;
3622 }
6c65e8d7 3623 else if (**mangled == 'Q')
3624 {
3625 success = demangle_qualified (work, mangled, &decl,
3626 /*isfuncnam=*/0,
3627 /*append=*/0);
3628 if (!success)
3629 break;
3630 }
0dc64970 3631 else
3632 {
3633 success = 0;
3634 break;
3635 }
3636
28e9041c 3637 string_prepend (&decl, "(");
3638 if (member)
3639 {
3e04bd45 3640 switch (**mangled)
28e9041c 3641 {
3e04bd45 3642 case 'C':
3643 case 'V':
3644 case 'u':
3645 type_quals |= code_for_qualifier (**mangled);
28e9041c 3646 (*mangled)++;
3e04bd45 3647 break;
3648
3649 default:
3650 break;
28e9041c 3651 }
3e04bd45 3652
28e9041c 3653 if (*(*mangled)++ != 'F')
3654 {
3655 success = 0;
3656 break;
3657 }
3658 }
99906878 3659 if ((member && !demangle_nested_args (work, mangled, &decl))
28e9041c 3660 || **mangled != '_')
3661 {
3662 success = 0;
3663 break;
3664 }
3665 (*mangled)++;
3666 if (! PRINT_ANSI_QUALIFIERS)
3667 {
3668 break;
3669 }
3e04bd45 3670 if (type_quals != TYPE_UNQUALIFIED)
28e9041c 3671 {
3672 APPEND_BLANK (&decl);
3e04bd45 3673 string_append (&decl, qualifier_string (type_quals));
28e9041c 3674 }
3675 break;
3676 }
3677 case 'G':
3678 (*mangled)++;
3679 break;
3680
3681 case 'C':
aff4ad88 3682 case 'V':
3e04bd45 3683 case 'u':
28e9041c 3684 if (PRINT_ANSI_QUALIFIERS)
3685 {
3686 if (!STRING_EMPTY (&decl))
3e04bd45 3687 string_prepend (&decl, " ");
3688
3689 string_prepend (&decl, demangle_qualifier (**mangled));
28e9041c 3690 }
aff4ad88 3691 (*mangled)++;
28e9041c 3692 break;
3693 /*
3694 }
3695 */
3696
3697 /* fall through */
3698 default:
3699 done = 1;
3700 break;
3701 }
3702 }
3703
8f2cc44d 3704 if (success) switch (**mangled)
28e9041c 3705 {
3706 /* A qualified name, such as "Outer::Inner". */
3707 case 'Q':
fa4f3779 3708 case 'K':
3709 {
fa4f3779 3710 success = demangle_qualified (work, mangled, result, 0, 1);
fa4f3779 3711 break;
3712 }
3713
3714 /* A back reference to a previously seen squangled type */
3715 case 'B':
3716 (*mangled)++;
3717 if (!get_count (mangled, &n) || n >= work -> numb)
8f2cc44d 3718 success = 0;
fa4f3779 3719 else
2d53096b 3720 string_append (result, work->btypevec[n]);
28e9041c 3721 break;
3722
8f71bf1d 3723 case 'X':
3724 case 'Y':
3725 /* A template parm. We substitute the corresponding argument. */
3726 {
3727 int idx;
8f71bf1d 3728
3729 (*mangled)++;
3730 idx = consume_count_with_underscores (mangled);
3731
0f82222a 3732 if (idx == -1
8f71bf1d 3733 || (work->tmpl_argvec && idx >= work->ntmpl_args)
3734 || consume_count_with_underscores (mangled) == -1)
3735 {
3736 success = 0;
3737 break;
3738 }
3739
3740 if (work->tmpl_argvec)
3741 string_append (result, work->tmpl_argvec[idx]);
3742 else
42c870f1 3743 string_append_template_idx (result, idx);
8f71bf1d 3744
3745 success = 1;
3746 }
3747 break;
3748
28e9041c 3749 default:
3750 success = demangle_fund_type (work, mangled, result);
2d53096b 3751 if (tk == tk_none)
3752 tk = (type_kind_t) success;
28e9041c 3753 break;
3754 }
3755
3756 if (success)
3757 {
3758 if (!STRING_EMPTY (&decl))
3759 {
3760 string_append (result, " ");
3761 string_appends (result, &decl);
3762 }
3763 }
3764 else
2d53096b 3765 string_delete (result);
28e9041c 3766 string_delete (&decl);
2d53096b 3767
3768 if (success)
3769 /* Assume an integral type, if we're not sure. */
3770 return (int) ((tk == tk_none) ? tk_integral : tk);
3771 else
3772 return 0;
28e9041c 3773}
3774
3775/* Given a pointer to a type string that represents a fundamental type
3776 argument (int, long, unsigned int, etc) in TYPE, a pointer to the
3777 string in which the demangled output is being built in RESULT, and
3778 the WORK structure, decode the types and add them to the result.
3779
3780 For example:
3781
3782 "Ci" => "const int"
3783 "Sl" => "signed long"
3784 "CUs" => "const unsigned short"
3785
2d53096b 3786 The value returned is really a type_kind_t. */
28e9041c 3787
3788static int
3789demangle_fund_type (work, mangled, result)
3790 struct work_stuff *work;
3791 const char **mangled;
3792 string *result;
3793{
3794 int done = 0;
3795 int success = 1;
d54546fb 3796 char buf[10];
6cb730c2 3797 unsigned int dec = 0;
fa4f3779 3798 string btype;
2d53096b 3799 type_kind_t tk = tk_integral;
3800
fa4f3779 3801 string_init (&btype);
28e9041c 3802
3803 /* First pick off any type qualifiers. There can be more than one. */
3804
3805 while (!done)
3806 {
3807 switch (**mangled)
3808 {
3809 case 'C':
3e04bd45 3810 case 'V':
3811 case 'u':
28e9041c 3812 if (PRINT_ANSI_QUALIFIERS)
3813 {
0a5a5994 3814 if (!STRING_EMPTY (result))
3815 string_prepend (result, " ");
3816 string_prepend (result, demangle_qualifier (**mangled));
28e9041c 3817 }
0a5a5994 3818 (*mangled)++;
28e9041c 3819 break;
3820 case 'U':
3821 (*mangled)++;
3822 APPEND_BLANK (result);
3823 string_append (result, "unsigned");
3824 break;
3825 case 'S': /* signed char only */
3826 (*mangled)++;
3827 APPEND_BLANK (result);
3828 string_append (result, "signed");
3829 break;
28e9041c 3830 case 'J':
3831 (*mangled)++;
3832 APPEND_BLANK (result);
8f71bf1d 3833 string_append (result, "__complex");
28e9041c 3834 break;
3835 default:
3836 done = 1;
3837 break;
3838 }
3839 }
3840
3841 /* Now pick off the fundamental type. There can be only one. */
3842
3843 switch (**mangled)
3844 {
3845 case '\0':
3846 case '_':
3847 break;
3848 case 'v':
3849 (*mangled)++;
3850 APPEND_BLANK (result);
3851 string_append (result, "void");
3852 break;
3853 case 'x':
3854 (*mangled)++;
3855 APPEND_BLANK (result);
3856 string_append (result, "long long");
3857 break;
3858 case 'l':
3859 (*mangled)++;
3860 APPEND_BLANK (result);
3861 string_append (result, "long");
3862 break;
3863 case 'i':
3864 (*mangled)++;
3865 APPEND_BLANK (result);
3866 string_append (result, "int");
3867 break;
3868 case 's':
3869 (*mangled)++;
3870 APPEND_BLANK (result);
3871 string_append (result, "short");
3872 break;
3873 case 'b':
3874 (*mangled)++;
3875 APPEND_BLANK (result);
3876 string_append (result, "bool");
2d53096b 3877 tk = tk_bool;
28e9041c 3878 break;
3879 case 'c':
3880 (*mangled)++;
3881 APPEND_BLANK (result);
3882 string_append (result, "char");
2d53096b 3883 tk = tk_char;
28e9041c 3884 break;
3885 case 'w':
3886 (*mangled)++;
3887 APPEND_BLANK (result);
3888 string_append (result, "wchar_t");
2d53096b 3889 tk = tk_char;
28e9041c 3890 break;
3891 case 'r':
3892 (*mangled)++;
3893 APPEND_BLANK (result);
3894 string_append (result, "long double");
2d53096b 3895 tk = tk_real;
28e9041c 3896 break;
3897 case 'd':
3898 (*mangled)++;
3899 APPEND_BLANK (result);
3900 string_append (result, "double");
2d53096b 3901 tk = tk_real;
28e9041c 3902 break;
3903 case 'f':
3904 (*mangled)++;
3905 APPEND_BLANK (result);
3906 string_append (result, "float");
2d53096b 3907 tk = tk_real;
28e9041c 3908 break;
3909 case 'G':
3910 (*mangled)++;
93ce8ce4 3911 if (!ISDIGIT ((unsigned char)**mangled))
28e9041c 3912 {
3913 success = 0;
3914 break;
3915 }
d54546fb 3916 case 'I':
41980611 3917 (*mangled)++;
d54546fb 3918 if (**mangled == '_')
3919 {
3920 int i;
41980611 3921 (*mangled)++;
0f08678d 3922 for (i = 0;
ac126d82 3923 i < (long) sizeof (buf) - 1 && **mangled && **mangled != '_';
41980611 3924 (*mangled)++, i++)
d54546fb 3925 buf[i] = **mangled;
0f08678d 3926 if (**mangled != '_')
3927 {
3928 success = 0;
3929 break;
3930 }
d54546fb 3931 buf[i] = '\0';
41980611 3932 (*mangled)++;
d54546fb 3933 }
3934 else
3935 {
3936 strncpy (buf, *mangled, 2);
0f08678d 3937 buf[2] = '\0';
41980611 3938 *mangled += min (strlen (*mangled), 2);
d54546fb 3939 }
0f82222a 3940 sscanf (buf, "%x", &dec);
6cb730c2 3941 sprintf (buf, "int%u_t", dec);
d54546fb 3942 APPEND_BLANK (result);
3943 string_append (result, buf);
3944 break;
3945
28e9041c 3946 /* fall through */
3947 /* An explicit type, such as "6mytype" or "7integer" */
3948 case '0':
3949 case '1':
3950 case '2':
3951 case '3':
3952 case '4':
3953 case '5':
3954 case '6':
3955 case '7':
3956 case '8':
3957 case '9':
fa4f3779 3958 {
3959 int bindex = register_Btype (work);
3960 string btype;
3961 string_init (&btype);
3962 if (demangle_class_name (work, mangled, &btype)) {
3963 remember_Btype (work, btype.b, LEN_STRING (&btype), bindex);
3964 APPEND_BLANK (result);
3965 string_appends (result, &btype);
3966 }
0f82222a 3967 else
fa4f3779 3968 success = 0;
3969 string_delete (&btype);
3970 break;
28e9041c 3971 }
28e9041c 3972 case 't':
fa4f3779 3973 {
99906878 3974 success = demangle_template (work, mangled, &btype, 0, 1, 1);
fa4f3779 3975 string_appends (result, &btype);
3976 break;
3977 }
28e9041c 3978 default:
3979 success = 0;
3980 break;
3981 }
3982
2d53096b 3983 return success ? ((int) tk) : 0;
28e9041c 3984}
3985
f75dc4de 3986
3987/* Handle a template's value parameter for HP aCC (extension from ARM)
3988 **mangled points to 'S' or 'U' */
3989
3990static int
3991do_hpacc_template_const_value (work, mangled, result)
ac126d82 3992 struct work_stuff *work ATTRIBUTE_UNUSED;
f75dc4de 3993 const char **mangled;
3994 string *result;
3995{
3996 int unsigned_const;
3997
3998 if (**mangled != 'U' && **mangled != 'S')
3999 return 0;
0f82222a 4000
f75dc4de 4001 unsigned_const = (**mangled == 'U');
4002
4003 (*mangled)++;
4004
4005 switch (**mangled)
4006 {
4007 case 'N':
4008 string_append (result, "-");
0f82222a 4009 /* fall through */
f75dc4de 4010 case 'P':
4011 (*mangled)++;
4012 break;
4013 case 'M':
0f82222a 4014 /* special case for -2^31 */
f75dc4de 4015 string_append (result, "-2147483648");
4016 (*mangled)++;
4017 return 1;
4018 default:
4019 return 0;
4020 }
4021
4022 /* We have to be looking at an integer now */
93ce8ce4 4023 if (!(ISDIGIT ((unsigned char)**mangled)))
f75dc4de 4024 return 0;
4025
4026 /* We only deal with integral values for template
4027 parameters -- so it's OK to look only for digits */
93ce8ce4 4028 while (ISDIGIT ((unsigned char)**mangled))
f75dc4de 4029 {
4030 char_str[0] = **mangled;
4031 string_append (result, char_str);
4032 (*mangled)++;
4033 }
4034
4035 if (unsigned_const)
4036 string_append (result, "U");
4037
4038 /* FIXME? Some day we may have 64-bit (or larger :-) ) constants
4039 with L or LL suffixes. pai/1997-09-03 */
0f82222a 4040
4041 return 1; /* success */
f75dc4de 4042}
4043
4044/* Handle a template's literal parameter for HP aCC (extension from ARM)
4045 **mangled is pointing to the 'A' */
4046
4047static int
4048do_hpacc_template_literal (work, mangled, result)
4049 struct work_stuff *work;
4050 const char **mangled;
4051 string *result;
4052{
4053 int literal_len = 0;
f75dc4de 4054 char * recurse;
4055 char * recurse_dem;
0f82222a 4056
f75dc4de 4057 if (**mangled != 'A')
4058 return 0;
4059
4060 (*mangled)++;
4061
4062 literal_len = consume_count (mangled);
4063
9fec6063 4064 if (literal_len <= 0)
f75dc4de 4065 return 0;
4066
4067 /* Literal parameters are names of arrays, functions, etc. and the
4068 canonical representation uses the address operator */
4069 string_append (result, "&");
4070
0f82222a 4071 /* Now recursively demangle the literal name */
f75dc4de 4072 recurse = (char *) xmalloc (literal_len + 1);
4073 memcpy (recurse, *mangled, literal_len);
4074 recurse[literal_len] = '\000';
4075
4076 recurse_dem = cplus_demangle (recurse, work->options);
0f82222a 4077
f75dc4de 4078 if (recurse_dem)
4079 {
4080 string_append (result, recurse_dem);
4081 free (recurse_dem);
4082 }
4083 else
4084 {
4085 string_appendn (result, *mangled, literal_len);
4086 }
4087 (*mangled) += literal_len;
4088 free (recurse);
4089
4090 return 1;
4091}
4092
4093static int
4094snarf_numeric_literal (args, arg)
7c8c70e9 4095 const char ** args;
f75dc4de 4096 string * arg;
4097{
4098 if (**args == '-')
4099 {
4100 char_str[0] = '-';
4101 string_append (arg, char_str);
4102 (*args)++;
4103 }
4104 else if (**args == '+')
4105 (*args)++;
0f82222a 4106
93ce8ce4 4107 if (!ISDIGIT ((unsigned char)**args))
f75dc4de 4108 return 0;
4109
93ce8ce4 4110 while (ISDIGIT ((unsigned char)**args))
f75dc4de 4111 {
4112 char_str[0] = **args;
4113 string_append (arg, char_str);
4114 (*args)++;
4115 }
4116
4117 return 1;
4118}
4119
99906878 4120/* Demangle the next argument, given by MANGLED into RESULT, which
4121 *should be an uninitialized* string. It will be initialized here,
4122 and free'd should anything go wrong. */
28e9041c 4123
4124static int
4125do_arg (work, mangled, result)
4126 struct work_stuff *work;
4127 const char **mangled;
4128 string *result;
4129{
99906878 4130 /* Remember where we started so that we can record the type, for
4131 non-squangling type remembering. */
28e9041c 4132 const char *start = *mangled;
4133
99906878 4134 string_init (result);
4135
4136 if (work->nrepeats > 0)
28e9041c 4137 {
99906878 4138 --work->nrepeats;
4139
4140 if (work->previous_argument == 0)
4141 return 0;
4142
0f82222a 4143 /* We want to reissue the previous type in this argument list. */
99906878 4144 string_appends (result, work->previous_argument);
4145 return 1;
28e9041c 4146 }
99906878 4147
4148 if (**mangled == 'n')
4149 {
4150 /* A squangling-style repeat. */
4151 (*mangled)++;
4152 work->nrepeats = consume_count(mangled);
4153
9fec6063 4154 if (work->nrepeats <= 0)
99906878 4155 /* This was not a repeat count after all. */
4156 return 0;
4157
4158 if (work->nrepeats > 9)
4159 {
4160 if (**mangled != '_')
4161 /* The repeat count should be followed by an '_' in this
4162 case. */
4163 return 0;
4164 else
4165 (*mangled)++;
4166 }
0f82222a 4167
99906878 4168 /* Now, the repeat is all set up. */
4169 return do_arg (work, mangled, result);
4170 }
4171
4172 /* Save the result in WORK->previous_argument so that we can find it
4173 if it's repeated. Note that saving START is not good enough: we
4174 do not want to add additional types to the back-referenceable
4175 type vector when processing a repeated type. */
4176 if (work->previous_argument)
4177 string_clear (work->previous_argument);
28e9041c 4178 else
4179 {
99906878 4180 work->previous_argument = (string*) xmalloc (sizeof (string));
4181 string_init (work->previous_argument);
28e9041c 4182 }
99906878 4183
4184 if (!do_type (work, mangled, work->previous_argument))
4185 return 0;
4186
4187 string_appends (result, work->previous_argument);
4188
4189 remember_type (work, start, *mangled - start);
4190 return 1;
28e9041c 4191}
4192
4193static void
4194remember_type (work, start, len)
4195 struct work_stuff *work;
4196 const char *start;
4197 int len;
4198{
4199 char *tem;
4200
99906878 4201 if (work->forgetting_types)
4202 return;
4203
28e9041c 4204 if (work -> ntypes >= work -> typevec_size)
4205 {
4206 if (work -> typevec_size == 0)
4207 {
4208 work -> typevec_size = 3;
4209 work -> typevec
4210 = (char **) xmalloc (sizeof (char *) * work -> typevec_size);
4211 }
4212 else
4213 {
4214 work -> typevec_size *= 2;
4215 work -> typevec
4216 = (char **) xrealloc ((char *)work -> typevec,
4217 sizeof (char *) * work -> typevec_size);
4218 }
4219 }
4220 tem = xmalloc (len + 1);
4221 memcpy (tem, start, len);
4222 tem[len] = '\0';
4223 work -> typevec[work -> ntypes++] = tem;
4224}
4225
fa4f3779 4226
4227/* Remember a K type class qualifier. */
4228static void
4229remember_Ktype (work, start, len)
4230 struct work_stuff *work;
4231 const char *start;
4232 int len;
4233{
4234 char *tem;
4235
4236 if (work -> numk >= work -> ksize)
4237 {
4238 if (work -> ksize == 0)
4239 {
4240 work -> ksize = 5;
4241 work -> ktypevec
4242 = (char **) xmalloc (sizeof (char *) * work -> ksize);
4243 }
4244 else
4245 {
4246 work -> ksize *= 2;
4247 work -> ktypevec
4248 = (char **) xrealloc ((char *)work -> ktypevec,
4249 sizeof (char *) * work -> ksize);
4250 }
4251 }
4252 tem = xmalloc (len + 1);
4253 memcpy (tem, start, len);
4254 tem[len] = '\0';
4255 work -> ktypevec[work -> numk++] = tem;
4256}
4257
4258/* Register a B code, and get an index for it. B codes are registered
0f82222a 4259 as they are seen, rather than as they are completed, so map<temp<char> >
fa4f3779 4260 registers map<temp<char> > as B0, and temp<char> as B1 */
4261
4262static int
4263register_Btype (work)
4264 struct work_stuff *work;
4265{
4266 int ret;
0f82222a 4267
fa4f3779 4268 if (work -> numb >= work -> bsize)
4269 {
4270 if (work -> bsize == 0)
4271 {
4272 work -> bsize = 5;
4273 work -> btypevec
4274 = (char **) xmalloc (sizeof (char *) * work -> bsize);
4275 }
4276 else
4277 {
4278 work -> bsize *= 2;
4279 work -> btypevec
4280 = (char **) xrealloc ((char *)work -> btypevec,
4281 sizeof (char *) * work -> bsize);
4282 }
4283 }
4284 ret = work -> numb++;
4285 work -> btypevec[ret] = NULL;
4286 return(ret);
4287}
4288
4289/* Store a value into a previously registered B code type. */
4290
4291static void
4292remember_Btype (work, start, len, index)
4293 struct work_stuff *work;
4294 const char *start;
4295 int len, index;
4296{
4297 char *tem;
4298
4299 tem = xmalloc (len + 1);
4300 memcpy (tem, start, len);
4301 tem[len] = '\0';
4302 work -> btypevec[index] = tem;
4303}
4304
4305/* Lose all the info related to B and K type codes. */
4306static void
4307forget_B_and_K_types (work)
4308 struct work_stuff *work;
4309{
4310 int i;
4311
4312 while (work -> numk > 0)
4313 {
4314 i = --(work -> numk);
4315 if (work -> ktypevec[i] != NULL)
4316 {
4317 free (work -> ktypevec[i]);
4318 work -> ktypevec[i] = NULL;
4319 }
4320 }
4321
4322 while (work -> numb > 0)
4323 {
4324 i = --(work -> numb);
4325 if (work -> btypevec[i] != NULL)
4326 {
4327 free (work -> btypevec[i]);
4328 work -> btypevec[i] = NULL;
4329 }
4330 }
4331}
28e9041c 4332/* Forget the remembered types, but not the type vector itself. */
4333
4334static void
4335forget_types (work)
4336 struct work_stuff *work;
4337{
4338 int i;
4339
4340 while (work -> ntypes > 0)
4341 {
4342 i = --(work -> ntypes);
4343 if (work -> typevec[i] != NULL)
4344 {
4345 free (work -> typevec[i]);
4346 work -> typevec[i] = NULL;
4347 }
4348 }
4349}
4350
4351/* Process the argument list part of the signature, after any class spec
4352 has been consumed, as well as the first 'F' character (if any). For
4353 example:
4354
4355 "__als__3fooRT0" => process "RT0"
4356 "complexfunc5__FPFPc_PFl_i" => process "PFPc_PFl_i"
4357
4358 DECLP must be already initialised, usually non-empty. It won't be freed
4359 on failure.
4360
4361 Note that g++ differs significantly from ARM and lucid style mangling
4362 with regards to references to previously seen types. For example, given
4363 the source fragment:
4364
4365 class foo {
4366 public:
4367 foo::foo (int, foo &ia, int, foo &ib, int, foo &ic);
4368 };
4369
4370 foo::foo (int, foo &ia, int, foo &ib, int, foo &ic) { ia = ib = ic; }
4371 void foo (int, foo &ia, int, foo &ib, int, foo &ic) { ia = ib = ic; }
4372
4373 g++ produces the names:
4374
4375 __3fooiRT0iT2iT2
4376 foo__FiR3fooiT1iT1
4377
4378 while lcc (and presumably other ARM style compilers as well) produces:
4379
4380 foo__FiR3fooT1T2T1T2
4381 __ct__3fooFiR3fooT1T2T1T2
4382
99906878 4383 Note that g++ bases its type numbers starting at zero and counts all
4384 previously seen types, while lucid/ARM bases its type numbers starting
28e9041c 4385 at one and only considers types after it has seen the 'F' character
4386 indicating the start of the function args. For lucid/ARM style, we
4387 account for this difference by discarding any previously seen types when
4388 we see the 'F' character, and subtracting one from the type number
4389 reference.
4390
4391 */
4392
4393static int
4394demangle_args (work, mangled, declp)
4395 struct work_stuff *work;
4396 const char **mangled;
4397 string *declp;
4398{
4399 string arg;
4400 int need_comma = 0;
4401 int r;
4402 int t;
4403 const char *tem;
4404 char temptype;
4405
4406 if (PRINT_ARG_TYPES)
4407 {
4408 string_append (declp, "(");
4409 if (**mangled == '\0')
4410 {
4411 string_append (declp, "void");
4412 }
4413 }
4414
99906878 4415 while ((**mangled != '_' && **mangled != '\0' && **mangled != 'e')
4416 || work->nrepeats > 0)
28e9041c 4417 {
4418 if ((**mangled == 'N') || (**mangled == 'T'))
4419 {
4420 temptype = *(*mangled)++;
0f82222a 4421
28e9041c 4422 if (temptype == 'N')
4423 {
4424 if (!get_count (mangled, &r))
4425 {
4426 return (0);
4427 }
4428 }
4429 else
4430 {
4431 r = 1;
4432 }
f75dc4de 4433 if ((HP_DEMANGLING || ARM_DEMANGLING || EDG_DEMANGLING) && work -> ntypes >= 10)
28e9041c 4434 {
4435 /* If we have 10 or more types we might have more than a 1 digit
4436 index so we'll have to consume the whole count here. This
4437 will lose if the next thing is a type name preceded by a
4438 count but it's impossible to demangle that case properly
4439 anyway. Eg if we already have 12 types is T12Pc "(..., type1,
4440 Pc, ...)" or "(..., type12, char *, ...)" */
9fec6063 4441 if ((t = consume_count(mangled)) <= 0)
28e9041c 4442 {
4443 return (0);
4444 }
4445 }
4446 else
4447 {
4448 if (!get_count (mangled, &t))
4449 {
4450 return (0);
4451 }
4452 }
f75dc4de 4453 if (LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
28e9041c 4454 {
4455 t--;
4456 }
4457 /* Validate the type index. Protect against illegal indices from
4458 malformed type strings. */
4459 if ((t < 0) || (t >= work -> ntypes))
4460 {
4461 return (0);
4462 }
99906878 4463 while (work->nrepeats > 0 || --r >= 0)
28e9041c 4464 {
4465 tem = work -> typevec[t];
4466 if (need_comma && PRINT_ARG_TYPES)
4467 {
4468 string_append (declp, ", ");
4469 }
4470 if (!do_arg (work, &tem, &arg))
4471 {
4472 return (0);
4473 }
4474 if (PRINT_ARG_TYPES)
4475 {
4476 string_appends (declp, &arg);
4477 }
4478 string_delete (&arg);
4479 need_comma = 1;
4480 }
4481 }
4482 else
4483 {
99906878 4484 if (need_comma && PRINT_ARG_TYPES)
4485 string_append (declp, ", ");
28e9041c 4486 if (!do_arg (work, mangled, &arg))
99906878 4487 return (0);
28e9041c 4488 if (PRINT_ARG_TYPES)
99906878 4489 string_appends (declp, &arg);
28e9041c 4490 string_delete (&arg);
4491 need_comma = 1;
4492 }
4493 }
4494
4495 if (**mangled == 'e')
4496 {
4497 (*mangled)++;
4498 if (PRINT_ARG_TYPES)
4499 {
4500 if (need_comma)
4501 {
4502 string_append (declp, ",");
4503 }
4504 string_append (declp, "...");
4505 }
4506 }
4507
4508 if (PRINT_ARG_TYPES)
4509 {
4510 string_append (declp, ")");
4511 }
4512 return (1);
4513}
4514
99906878 4515/* Like demangle_args, but for demangling the argument lists of function
4516 and method pointers or references, not top-level declarations. */
4517
88f70ac9 4518static int
99906878 4519demangle_nested_args (work, mangled, declp)
4520 struct work_stuff *work;
4521 const char **mangled;
4522 string *declp;
4523{
4524 string* saved_previous_argument;
4525 int result;
4526 int saved_nrepeats;
4527
4528 /* The G++ name-mangling algorithm does not remember types on nested
4529 argument lists, unless -fsquangling is used, and in that case the
4530 type vector updated by remember_type is not used. So, we turn
4531 off remembering of types here. */
4532 ++work->forgetting_types;
4533
4534 /* For the repeat codes used with -fsquangling, we must keep track of
4535 the last argument. */
4536 saved_previous_argument = work->previous_argument;
4537 saved_nrepeats = work->nrepeats;
4538 work->previous_argument = 0;
4539 work->nrepeats = 0;
4540
4541 /* Actually demangle the arguments. */
4542 result = demangle_args (work, mangled, declp);
0f82222a 4543
99906878 4544 /* Restore the previous_argument field. */
4545 if (work->previous_argument)
4546 string_delete (work->previous_argument);
4547 work->previous_argument = saved_previous_argument;
bdaa26ad 4548 --work->forgetting_types;
99906878 4549 work->nrepeats = saved_nrepeats;
4550
4551 return result;
4552}
4553
28e9041c 4554static void
4555demangle_function_name (work, mangled, declp, scan)
4556 struct work_stuff *work;
4557 const char **mangled;
4558 string *declp;
4559 const char *scan;
4560{
f39af051 4561 size_t i;
28e9041c 4562 string type;
4563 const char *tem;
4564
4565 string_appendn (declp, (*mangled), scan - (*mangled));
4566 string_need (declp, 1);
4567 *(declp -> p) = '\0';
4568
4569 /* Consume the function name, including the "__" separating the name
4570 from the signature. We are guaranteed that SCAN points to the
4571 separator. */
4572
4573 (*mangled) = scan + 2;
f75dc4de 4574 /* We may be looking at an instantiation of a template function:
4575 foo__Xt1t2_Ft3t4, where t1, t2, ... are template arguments and a
4576 following _F marks the start of the function arguments. Handle
4577 the template arguments first. */
0f82222a 4578
f75dc4de 4579 if (HP_DEMANGLING && (**mangled == 'X'))
4580 {
4581 demangle_arm_hp_template (work, mangled, 0, declp);
4582 /* This leaves MANGLED pointing to the 'F' marking func args */
4583 }
28e9041c 4584
f75dc4de 4585 if (LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
28e9041c 4586 {
4587
4588 /* See if we have an ARM style constructor or destructor operator.
4589 If so, then just record it, clear the decl, and return.
4590 We can't build the actual constructor/destructor decl until later,
4591 when we recover the class name from the signature. */
4592
4593 if (strcmp (declp -> b, "__ct") == 0)
4594 {
4595 work -> constructor += 1;
4596 string_clear (declp);
4597 return;
4598 }
4599 else if (strcmp (declp -> b, "__dt") == 0)
4600 {
4601 work -> destructor += 1;
4602 string_clear (declp);
4603 return;
4604 }
4605 }
4606
0f82222a 4607 if (declp->p - declp->b >= 3
28e9041c 4608 && declp->b[0] == 'o'
4609 && declp->b[1] == 'p'
4610 && strchr (cplus_markers, declp->b[2]) != NULL)
4611 {
4612 /* see if it's an assignment expression */
4613 if (declp->p - declp->b >= 10 /* op$assign_ */
4614 && memcmp (declp->b + 3, "assign_", 7) == 0)
4615 {
f0bff53d 4616 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 4617 {
f39af051 4618 int len = declp->p - declp->b - 10;
4350e959 4619 if ((int) strlen (optable[i].in) == len
28e9041c 4620 && memcmp (optable[i].in, declp->b + 10, len) == 0)
4621 {
4622 string_clear (declp);
4623 string_append (declp, "operator");
4624 string_append (declp, optable[i].out);
4625 string_append (declp, "=");
4626 break;
4627 }
4628 }
4629 }
4630 else
4631 {
f0bff53d 4632 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 4633 {
4634 int len = declp->p - declp->b - 3;
0f82222a 4635 if ((int) strlen (optable[i].in) == len
28e9041c 4636 && memcmp (optable[i].in, declp->b + 3, len) == 0)
4637 {
4638 string_clear (declp);
4639 string_append (declp, "operator");
4640 string_append (declp, optable[i].out);
4641 break;
4642 }
4643 }
4644 }
4645 }
4646 else if (declp->p - declp->b >= 5 && memcmp (declp->b, "type", 4) == 0
4647 && strchr (cplus_markers, declp->b[4]) != NULL)
4648 {
4649 /* type conversion operator */
4650 tem = declp->b + 5;
4651 if (do_type (work, &tem, &type))
4652 {
4653 string_clear (declp);
4654 string_append (declp, "operator ");
4655 string_appends (declp, &type);
4656 string_delete (&type);
4657 }
4658 }
4659 else if (declp->b[0] == '_' && declp->b[1] == '_'
4660 && declp->b[2] == 'o' && declp->b[3] == 'p')
4661 {
4662 /* ANSI. */
4663 /* type conversion operator. */
4664 tem = declp->b + 4;
4665 if (do_type (work, &tem, &type))
4666 {
4667 string_clear (declp);
4668 string_append (declp, "operator ");
4669 string_appends (declp, &type);
4670 string_delete (&type);
4671 }
4672 }
4673 else if (declp->b[0] == '_' && declp->b[1] == '_'
93ce8ce4 4674 && ISLOWER((unsigned char)declp->b[2])
4675 && ISLOWER((unsigned char)declp->b[3]))
28e9041c 4676 {
4677 if (declp->b[4] == '\0')
4678 {
4679 /* Operator. */
f0bff53d 4680 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 4681 {
4682 if (strlen (optable[i].in) == 2
4683 && memcmp (optable[i].in, declp->b + 2, 2) == 0)
4684 {
4685 string_clear (declp);
4686 string_append (declp, "operator");
4687 string_append (declp, optable[i].out);
4688 break;
4689 }
4690 }
4691 }
4692 else
4693 {
4694 if (declp->b[2] == 'a' && declp->b[5] == '\0')
4695 {
4696 /* Assignment. */
f0bff53d 4697 for (i = 0; i < ARRAY_SIZE (optable); i++)
28e9041c 4698 {
4699 if (strlen (optable[i].in) == 3
4700 && memcmp (optable[i].in, declp->b + 2, 3) == 0)
4701 {
4702 string_clear (declp);
4703 string_append (declp, "operator");
4704 string_append (declp, optable[i].out);
4705 break;
0f82222a 4706 }
28e9041c 4707 }
4708 }
4709 }
4710 }
4711}
4712
4713/* a mini string-handling package */
4714
4715static void
4716string_need (s, n)
4717 string *s;
4718 int n;
4719{
4720 int tem;
4721
4722 if (s->b == NULL)
4723 {
4724 if (n < 32)
4725 {
4726 n = 32;
4727 }
4728 s->p = s->b = xmalloc (n);
4729 s->e = s->b + n;
4730 }
4731 else if (s->e - s->p < n)
4732 {
4733 tem = s->p - s->b;
4734 n += tem;
4735 n *= 2;
4736 s->b = xrealloc (s->b, n);
4737 s->p = s->b + tem;
4738 s->e = s->b + n;
4739 }
4740}
4741
4742static void
4743string_delete (s)
4744 string *s;
4745{
4746 if (s->b != NULL)
4747 {
4748 free (s->b);
4749 s->b = s->e = s->p = NULL;
4750 }
4751}
4752
4753static void
4754string_init (s)
4755 string *s;
4756{
4757 s->b = s->p = s->e = NULL;
4758}
4759
0f82222a 4760static void
28e9041c 4761string_clear (s)
4762 string *s;
4763{
4764 s->p = s->b;
4765}
4766
4767#if 0
4768
4769static int
4770string_empty (s)
4771 string *s;
4772{
4773 return (s->b == s->p);
4774}
4775
4776#endif
4777
4778static void
4779string_append (p, s)
4780 string *p;
4781 const char *s;
4782{
4783 int n;
4784 if (s == NULL || *s == '\0')
4785 return;
4786 n = strlen (s);
4787 string_need (p, n);
4788 memcpy (p->p, s, n);
4789 p->p += n;
4790}
4791
4792static void
4793string_appends (p, s)
4794 string *p, *s;
4795{
4796 int n;
4797
4798 if (s->b != s->p)
4799 {
4800 n = s->p - s->b;
4801 string_need (p, n);
4802 memcpy (p->p, s->b, n);
4803 p->p += n;
4804 }
4805}
4806
4807static void
4808string_appendn (p, s, n)
4809 string *p;
4810 const char *s;
4811 int n;
4812{
4813 if (n != 0)
4814 {
4815 string_need (p, n);
4816 memcpy (p->p, s, n);
4817 p->p += n;
4818 }
4819}
4820
4821static void
4822string_prepend (p, s)
4823 string *p;
4824 const char *s;
4825{
4826 if (s != NULL && *s != '\0')
4827 {
4828 string_prependn (p, s, strlen (s));
4829 }
4830}
4831
4832static void
4833string_prepends (p, s)
4834 string *p, *s;
4835{
4836 if (s->b != s->p)
4837 {
4838 string_prependn (p, s->b, s->p - s->b);
4839 }
4840}
4841
4842static void
4843string_prependn (p, s, n)
4844 string *p;
4845 const char *s;
4846 int n;
4847{
4848 char *q;
4849
4850 if (n != 0)
4851 {
4852 string_need (p, n);
4853 for (q = p->p - 1; q >= p->b; q--)
4854 {
4855 q[n] = q[0];
4856 }
4857 memcpy (p->b, s, n);
4858 p->p += n;
4859 }
4860}
4861
42c870f1 4862static void
4863string_append_template_idx (s, idx)
4864 string *s;
4865 int idx;
4866{
4867 char buf[INTBUF_SIZE + 1 /* 'T' */];
4868 sprintf(buf, "T%d", idx);
4869 string_append (s, buf);
4870}
4871
28e9041c 4872/* To generate a standalone demangler program for testing purposes,
4873 just compile and link this file with -DMAIN and libiberty.a. When
4874 run, it demangles each command line arg, or each stdin string, and
4875 prints the result on stdout. */
4876
4877#ifdef MAIN
4878
4879#include "getopt.h"
4880
4d84eafd 4881static const char *program_name;
4882static const char *program_version = VERSION;
28e9041c 4883static int flags = DMGL_PARAMS | DMGL_ANSI;
4884
4885static void demangle_it PARAMS ((char *));
4d84eafd 4886static void usage PARAMS ((FILE *, int)) ATTRIBUTE_NORETURN;
4887static void fatal PARAMS ((const char *)) ATTRIBUTE_NORETURN;
59f72e4d 4888static void print_demangler_list PARAMS ((FILE *));
28e9041c 4889
4890static void
4891demangle_it (mangled_name)
4892 char *mangled_name;
4893{
4894 char *result;
4895
4896 result = cplus_demangle (mangled_name, flags);
4897 if (result == NULL)
4898 {
4899 printf ("%s\n", mangled_name);
4900 }
4901 else
4902 {
4903 printf ("%s\n", result);
4904 free (result);
4905 }
4906}
4907
6f572555 4908static void
4909print_demangler_list (stream)
4910 FILE *stream;
4911{
542e9271 4912 const struct demangler_engine *demangler;
6f572555 4913
4914 fprintf (stream, "{%s", libiberty_demanglers->demangling_style_name);
4915
4916 for (demangler = libiberty_demanglers + 1;
4917 demangler->demangling_style != unknown_demangling;
4918 ++demangler)
4919 fprintf (stream, ",%s", demangler->demangling_style_name);
4920
4921 fprintf (stream, "}");
4922}
4923
28e9041c 4924static void
4925usage (stream, status)
4926 FILE *stream;
4927 int status;
0f82222a 4928{
28e9041c 4929 fprintf (stream, "\
6f572555 4930Usage: %s [-_] [-n] [--strip-underscores] [--no-strip-underscores] \n",
28e9041c 4931 program_name);
6f572555 4932
4933 fprintf (stream, "\
4934 [-s ");
4935 print_demangler_list (stream);
4936 fprintf (stream, "]\n");
4937
4938 fprintf (stream, "\
4939 [--format ");
4940 print_demangler_list (stream);
4941 fprintf (stream, "]\n");
4942
4943 fprintf (stream, "\
4944 [--help] [--version] [arg...]\n");
28e9041c 4945 exit (status);
4946}
4947
fee10e05 4948#define MBUF_SIZE 32767
28e9041c 4949char mbuffer[MBUF_SIZE];
4950
4951/* Defined in the automatically-generated underscore.c. */
4952extern int prepends_underscore;
4953
4954int strip_underscore = 0;
4955
4956static struct option long_options[] = {
4957 {"strip-underscores", no_argument, 0, '_'},
4958 {"format", required_argument, 0, 's'},
4959 {"help", no_argument, 0, 'h'},
28e9041c 4960 {"no-strip-underscores", no_argument, 0, 'n'},
4961 {"version", no_argument, 0, 'v'},
4962 {0, no_argument, 0, 0}
4963};
4964
f39af051 4965/* More 'friendly' abort that prints the line and file.
4966 config.h can #define abort fancy_abort if you like that sort of thing. */
4967
4968void
4969fancy_abort ()
4970{
4971 fatal ("Internal gcc abort.");
4972}
4973
5ecd7a78 4974
9087cad2 4975static const char *
4976standard_symbol_characters PARAMS ((void));
4977
4978static const char *
4979hp_symbol_characters PARAMS ((void));
4980
168d63e5 4981static const char *
bb505139 4982gnu_v3_symbol_characters PARAMS ((void));
168d63e5 4983
2fb1c6e9 4984/* Return the string of non-alnum characters that may occur
4985 as a valid symbol component, in the standard assembler symbol
5ecd7a78 4986 syntax. */
5ecd7a78 4987
2fb1c6e9 4988static const char *
4989standard_symbol_characters ()
4990{
4991 return "_$.";
5ecd7a78 4992}
4993
4994
2fb1c6e9 4995/* Return the string of non-alnum characters that may occur
4996 as a valid symbol name component in an HP object file.
5ecd7a78 4997
4998 Note that, since HP's compiler generates object code straight from
4999 C++ source, without going through an assembler, its mangled
5000 identifiers can use all sorts of characters that no assembler would
5001 tolerate, so the alphabet this function creates is a little odd.
5002 Here are some sample mangled identifiers offered by HP:
5003
5004 typeid*__XT24AddressIndExpClassMember_
5005 [Vftptr]key:__dt__32OrdinaryCompareIndExpClassMemberFv
5006 __ct__Q2_9Elf64_Dyn18{unnamed.union.#1}Fv
5007
5008 This still seems really weird to me, since nowhere else in this
5009 file is there anything to recognize curly brackets, parens, etc.
5010 I've talked with Srikanth <srikanth@cup.hp.com>, and he assures me
5011 this is right, but I still strongly suspect that there's a
5012 misunderstanding here.
5013
5014 If we decide it's better for c++filt to use HP's assembler syntax
5015 to scrape identifiers out of its input, here's the definition of
5016 the symbol name syntax from the HP assembler manual:
5017
5018 Symbols are composed of uppercase and lowercase letters, decimal
5019 digits, dollar symbol, period (.), ampersand (&), pound sign(#) and
5020 underscore (_). A symbol can begin with a letter, digit underscore or
5021 dollar sign. If a symbol begins with a digit, it must contain a
5022 non-digit character.
5023
5024 So have fun. */
2fb1c6e9 5025static const char *
5026hp_symbol_characters ()
5ecd7a78 5027{
2fb1c6e9 5028 return "_$.<>#,*&[]:(){}";
5ecd7a78 5029}
5030
5031
168d63e5 5032/* Return the string of non-alnum characters that may occur
bb505139 5033 as a valid symbol component in the GNU C++ V3 ABI mangling
168d63e5 5034 scheme. */
5035
5036static const char *
bb505139 5037gnu_v3_symbol_characters ()
168d63e5 5038{
40e00cb0 5039 return "_$.";
168d63e5 5040}
5041
5042
4d84eafd 5043extern int main PARAMS ((int, char **));
5044
28e9041c 5045int
5046main (argc, argv)
5047 int argc;
5048 char **argv;
5049{
5050 char *result;
5051 int c;
ac126d82 5052 const char *valid_symbols;
39fb1bb6 5053 enum demangling_styles style = auto_demangling;
28e9041c 5054
5055 program_name = argv[0];
5056
5057 strip_underscore = prepends_underscore;
5058
1c1033dd 5059 while ((c = getopt_long (argc, argv, "_ns:", long_options, (int *) 0)) != EOF)
28e9041c 5060 {
5061 switch (c)
5062 {
5063 case '?':
5064 usage (stderr, 1);
5065 break;
5066 case 'h':
5067 usage (stdout, 0);
5068 case 'n':
5069 strip_underscore = 0;
5070 break;
5071 case 'v':
f75dc4de 5072 printf ("GNU %s (C++ demangler), version %s\n", program_name, program_version);
4d84eafd 5073 return (0);
28e9041c 5074 case '_':
5075 strip_underscore = 1;
5076 break;
28e9041c 5077 case 's':
6f572555 5078 {
6f572555 5079 style = cplus_demangle_name_to_style (optarg);
5080 if (style == unknown_demangling)
5081 {
5082 fprintf (stderr, "%s: unknown demangling style `%s'\n",
5083 program_name, optarg);
5084 return (1);
5085 }
5086 else
5087 cplus_demangle_set_style (style);
5088 }
28e9041c 5089 break;
5090 }
5091 }
5092
5093 if (optind < argc)
5094 {
5095 for ( ; optind < argc; optind++)
5096 {
5097 demangle_it (argv[optind]);
5098 }
5099 }
5100 else
5101 {
5ecd7a78 5102 switch (current_demangling_style)
5103 {
5104 case gnu_demangling:
5105 case lucid_demangling:
5106 case arm_demangling:
626946fb 5107 case java_demangling:
5ecd7a78 5108 case edg_demangling:
9628d706 5109 case gnat_demangling:
bb505139 5110 case auto_demangling:
2fb1c6e9 5111 valid_symbols = standard_symbol_characters ();
5ecd7a78 5112 break;
5113 case hp_demangling:
2fb1c6e9 5114 valid_symbols = hp_symbol_characters ();
5ecd7a78 5115 break;
bb505139 5116 case gnu_v3_demangling:
5117 valid_symbols = gnu_v3_symbol_characters ();
168d63e5 5118 break;
5ecd7a78 5119 default:
5120 /* Folks should explicitly indicate the appropriate alphabet for
5121 each demangling. Providing a default would allow the
5122 question to go unconsidered. */
5123 abort ();
5124 }
5125
28e9041c 5126 for (;;)
5127 {
5128 int i = 0;
5129 c = getchar ();
5130 /* Try to read a label. */
93ce8ce4 5131 while (c != EOF && (ISALNUM (c) || strchr (valid_symbols, c)))
28e9041c 5132 {
5133 if (i >= MBUF_SIZE-1)
5134 break;
5135 mbuffer[i++] = c;
5136 c = getchar ();
5137 }
5138 if (i > 0)
5139 {
5140 int skip_first = 0;
5141
d219f684 5142 if (mbuffer[0] == '.' || mbuffer[0] == '$')
28e9041c 5143 ++skip_first;
5144 if (strip_underscore && mbuffer[skip_first] == '_')
5145 ++skip_first;
5146
5147 if (skip_first > i)
5148 skip_first = i;
5149
5150 mbuffer[i] = 0;
163369e7 5151 flags |= (int) style;
28e9041c 5152 result = cplus_demangle (mbuffer + skip_first, flags);
5153 if (result)
5154 {
5155 if (mbuffer[0] == '.')
5156 putc ('.', stdout);
5157 fputs (result, stdout);
5158 free (result);
5159 }
5160 else
5161 fputs (mbuffer, stdout);
5162
5163 fflush (stdout);
5164 }
5165 if (c == EOF)
5166 break;
5167 putchar (c);
04ef60ef 5168 fflush (stdout);
28e9041c 5169 }
5170 }
5171
4d84eafd 5172 return (0);
28e9041c 5173}
5174
5175static void
5176fatal (str)
4d84eafd 5177 const char *str;
28e9041c 5178{
5179 fprintf (stderr, "%s: %s\n", program_name, str);
5180 exit (1);
5181}
5182
4ae63959 5183PTR
28e9041c 5184xmalloc (size)
4ae63959 5185 size_t size;
28e9041c 5186{
4ae63959 5187 register PTR value = (PTR) malloc (size);
28e9041c 5188 if (value == 0)
5189 fatal ("virtual memory exhausted");
5190 return value;
5191}
5192
4ae63959 5193PTR
28e9041c 5194xrealloc (ptr, size)
4ae63959 5195 PTR ptr;
5196 size_t size;
28e9041c 5197{
4ae63959 5198 register PTR value = (PTR) realloc (ptr, size);
28e9041c 5199 if (value == 0)
5200 fatal ("virtual memory exhausted");
5201 return value;
5202}
5203#endif /* main */