* aclocal.m4 (gcc_AC_CHECK_PROG_VER): New macro.
[official-gcc.git] / libiberty / cplus-dem.c
blob4ea2c95832999f141e4b72282222015cfeb329b3
1 /* Demangler for GNU C++
2 Copyright 1989, 91, 94, 95, 96, 97, 98, 1999 Free Software Foundation, Inc.
3 Written by James Clark (jjc@jclark.uucp)
4 Rewritten by Fred Fish (fnf@cygnus.com) for ARM and Lucid demangling
5 Modified by Satish Pai (pai@apollo.hp.com) for HP demangling
7 This file is part of the libiberty library.
8 Libiberty is free software; you can redistribute it and/or
9 modify it under the terms of the GNU Library General Public
10 License as published by the Free Software Foundation; either
11 version 2 of the License, or (at your option) any later version.
13 Libiberty is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Library General Public License for more details.
18 You should have received a copy of the GNU Library General Public
19 License along with libiberty; see the file COPYING.LIB. If
20 not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, USA. */
23 /* This file exports two functions; cplus_mangle_opname and cplus_demangle.
25 This file imports xmalloc and xrealloc, which are like malloc and
26 realloc except that they generate a fatal error if there is no
27 available memory. */
29 /* This file lives in both GCC and libiberty. When making changes, please
30 try not to break either. */
32 #ifdef HAVE_CONFIG_H
33 #include "config.h"
34 #endif
36 #include <ctype.h>
37 #include <sys/types.h>
38 #include <string.h>
39 #include <stdio.h>
41 #ifdef HAVE_STDLIB_H
42 #include <stdlib.h>
43 #else
44 char * malloc ();
45 char * realloc ();
46 #endif
48 #include <demangle.h>
49 #undef CURRENT_DEMANGLING_STYLE
50 #define CURRENT_DEMANGLING_STYLE work->options
52 #include "libiberty.h"
54 #define min(X,Y) (((X) < (Y)) ? (X) : (Y))
56 /* A value at least one greater than the maximum number of characters
57 that will be output when using the `%d' format with `printf'. */
58 #define INTBUF_SIZE 32
60 extern void fancy_abort PARAMS ((void)) ATTRIBUTE_NORETURN;
62 static const char *mystrstr PARAMS ((const char *, const char *));
64 static const char *
65 mystrstr (s1, s2)
66 const char *s1, *s2;
68 register const char *p = s1;
69 register int len = strlen (s2);
71 for (; (p = strchr (p, *s2)) != 0; p++)
73 if (strncmp (p, s2, len) == 0)
75 return (p);
78 return (0);
81 /* In order to allow a single demangler executable to demangle strings
82 using various common values of CPLUS_MARKER, as well as any specific
83 one set at compile time, we maintain a string containing all the
84 commonly used ones, and check to see if the marker we are looking for
85 is in that string. CPLUS_MARKER is usually '$' on systems where the
86 assembler can deal with that. Where the assembler can't, it's usually
87 '.' (but on many systems '.' is used for other things). We put the
88 current defined CPLUS_MARKER first (which defaults to '$'), followed
89 by the next most common value, followed by an explicit '$' in case
90 the value of CPLUS_MARKER is not '$'.
92 We could avoid this if we could just get g++ to tell us what the actual
93 cplus marker character is as part of the debug information, perhaps by
94 ensuring that it is the character that terminates the gcc<n>_compiled
95 marker symbol (FIXME). */
97 #if !defined (CPLUS_MARKER)
98 #define CPLUS_MARKER '$'
99 #endif
101 enum demangling_styles current_demangling_style = gnu_demangling;
103 static char cplus_markers[] = { CPLUS_MARKER, '.', '$', '\0' };
105 static char char_str[2] = { '\000', '\000' };
107 void
108 set_cplus_marker_for_demangling (ch)
109 int ch;
111 cplus_markers[0] = ch;
114 typedef struct string /* Beware: these aren't required to be */
115 { /* '\0' terminated. */
116 char *b; /* pointer to start of string */
117 char *p; /* pointer after last character */
118 char *e; /* pointer after end of allocated space */
119 } string;
121 /* Stuff that is shared between sub-routines.
122 Using a shared structure allows cplus_demangle to be reentrant. */
124 struct work_stuff
126 int options;
127 char **typevec;
128 char **ktypevec;
129 char **btypevec;
130 int numk;
131 int numb;
132 int ksize;
133 int bsize;
134 int ntypes;
135 int typevec_size;
136 int constructor;
137 int destructor;
138 int static_type; /* A static member function */
139 int temp_start; /* index in demangled to start of template args */
140 int type_quals; /* The type qualifiers. */
141 int dllimported; /* Symbol imported from a PE DLL */
142 char **tmpl_argvec; /* Template function arguments. */
143 int ntmpl_args; /* The number of template function arguments. */
144 int forgetting_types; /* Nonzero if we are not remembering the types
145 we see. */
146 string* previous_argument; /* The last function argument demangled. */
147 int nrepeats; /* The number of times to repeat the previous
148 argument. */
151 #define PRINT_ANSI_QUALIFIERS (work -> options & DMGL_ANSI)
152 #define PRINT_ARG_TYPES (work -> options & DMGL_PARAMS)
154 static const struct optable
156 const char *in;
157 const char *out;
158 int flags;
159 } optable[] = {
160 {"nw", " new", DMGL_ANSI}, /* new (1.92, ansi) */
161 {"dl", " delete", DMGL_ANSI}, /* new (1.92, ansi) */
162 {"new", " new", 0}, /* old (1.91, and 1.x) */
163 {"delete", " delete", 0}, /* old (1.91, and 1.x) */
164 {"vn", " new []", DMGL_ANSI}, /* GNU, pending ansi */
165 {"vd", " delete []", DMGL_ANSI}, /* GNU, pending ansi */
166 {"as", "=", DMGL_ANSI}, /* ansi */
167 {"ne", "!=", DMGL_ANSI}, /* old, ansi */
168 {"eq", "==", DMGL_ANSI}, /* old, ansi */
169 {"ge", ">=", DMGL_ANSI}, /* old, ansi */
170 {"gt", ">", DMGL_ANSI}, /* old, ansi */
171 {"le", "<=", DMGL_ANSI}, /* old, ansi */
172 {"lt", "<", DMGL_ANSI}, /* old, ansi */
173 {"plus", "+", 0}, /* old */
174 {"pl", "+", DMGL_ANSI}, /* ansi */
175 {"apl", "+=", DMGL_ANSI}, /* ansi */
176 {"minus", "-", 0}, /* old */
177 {"mi", "-", DMGL_ANSI}, /* ansi */
178 {"ami", "-=", DMGL_ANSI}, /* ansi */
179 {"mult", "*", 0}, /* old */
180 {"ml", "*", DMGL_ANSI}, /* ansi */
181 {"amu", "*=", DMGL_ANSI}, /* ansi (ARM/Lucid) */
182 {"aml", "*=", DMGL_ANSI}, /* ansi (GNU/g++) */
183 {"convert", "+", 0}, /* old (unary +) */
184 {"negate", "-", 0}, /* old (unary -) */
185 {"trunc_mod", "%", 0}, /* old */
186 {"md", "%", DMGL_ANSI}, /* ansi */
187 {"amd", "%=", DMGL_ANSI}, /* ansi */
188 {"trunc_div", "/", 0}, /* old */
189 {"dv", "/", DMGL_ANSI}, /* ansi */
190 {"adv", "/=", DMGL_ANSI}, /* ansi */
191 {"truth_andif", "&&", 0}, /* old */
192 {"aa", "&&", DMGL_ANSI}, /* ansi */
193 {"truth_orif", "||", 0}, /* old */
194 {"oo", "||", DMGL_ANSI}, /* ansi */
195 {"truth_not", "!", 0}, /* old */
196 {"nt", "!", DMGL_ANSI}, /* ansi */
197 {"postincrement","++", 0}, /* old */
198 {"pp", "++", DMGL_ANSI}, /* ansi */
199 {"postdecrement","--", 0}, /* old */
200 {"mm", "--", DMGL_ANSI}, /* ansi */
201 {"bit_ior", "|", 0}, /* old */
202 {"or", "|", DMGL_ANSI}, /* ansi */
203 {"aor", "|=", DMGL_ANSI}, /* ansi */
204 {"bit_xor", "^", 0}, /* old */
205 {"er", "^", DMGL_ANSI}, /* ansi */
206 {"aer", "^=", DMGL_ANSI}, /* ansi */
207 {"bit_and", "&", 0}, /* old */
208 {"ad", "&", DMGL_ANSI}, /* ansi */
209 {"aad", "&=", DMGL_ANSI}, /* ansi */
210 {"bit_not", "~", 0}, /* old */
211 {"co", "~", DMGL_ANSI}, /* ansi */
212 {"call", "()", 0}, /* old */
213 {"cl", "()", DMGL_ANSI}, /* ansi */
214 {"alshift", "<<", 0}, /* old */
215 {"ls", "<<", DMGL_ANSI}, /* ansi */
216 {"als", "<<=", DMGL_ANSI}, /* ansi */
217 {"arshift", ">>", 0}, /* old */
218 {"rs", ">>", DMGL_ANSI}, /* ansi */
219 {"ars", ">>=", DMGL_ANSI}, /* ansi */
220 {"component", "->", 0}, /* old */
221 {"pt", "->", DMGL_ANSI}, /* ansi; Lucid C++ form */
222 {"rf", "->", DMGL_ANSI}, /* ansi; ARM/GNU form */
223 {"indirect", "*", 0}, /* old */
224 {"method_call", "->()", 0}, /* old */
225 {"addr", "&", 0}, /* old (unary &) */
226 {"array", "[]", 0}, /* old */
227 {"vc", "[]", DMGL_ANSI}, /* ansi */
228 {"compound", ", ", 0}, /* old */
229 {"cm", ", ", DMGL_ANSI}, /* ansi */
230 {"cond", "?:", 0}, /* old */
231 {"cn", "?:", DMGL_ANSI}, /* pseudo-ansi */
232 {"max", ">?", 0}, /* old */
233 {"mx", ">?", DMGL_ANSI}, /* pseudo-ansi */
234 {"min", "<?", 0}, /* old */
235 {"mn", "<?", DMGL_ANSI}, /* pseudo-ansi */
236 {"nop", "", 0}, /* old (for operator=) */
237 {"rm", "->*", DMGL_ANSI}, /* ansi */
238 {"sz", "sizeof ", DMGL_ANSI} /* pseudo-ansi */
241 /* These values are used to indicate the various type varieties.
242 They are all non-zero so that they can be used as `success'
243 values. */
244 typedef enum type_kind_t
246 tk_none,
247 tk_pointer,
248 tk_reference,
249 tk_integral,
250 tk_bool,
251 tk_char,
252 tk_real
253 } type_kind_t;
255 struct demangler_engine libiberty_demanglers[] =
258 AUTO_DEMANGLING_STYLE_STRING,
259 auto_demangling,
260 "Automatic selection based on executable"
264 GNU_DEMANGLING_STYLE_STRING,
265 gnu_demangling,
266 "GNU (g++) style demangling"
270 LUCID_DEMANGLING_STYLE_STRING,
271 lucid_demangling,
272 "Lucid (lcc) style demangling"
276 ARM_DEMANGLING_STYLE_STRING,
277 arm_demangling,
278 "ARM style demangling"
282 HP_DEMANGLING_STYLE_STRING,
283 hp_demangling,
284 "HP (aCC) style demangling"
288 EDG_DEMANGLING_STYLE_STRING,
289 edg_demangling,
290 "EDG style demangling"
294 NULL, unknown_demangling, NULL
298 #define STRING_EMPTY(str) ((str) -> b == (str) -> p)
299 #define PREPEND_BLANK(str) {if (!STRING_EMPTY(str)) \
300 string_prepend(str, " ");}
301 #define APPEND_BLANK(str) {if (!STRING_EMPTY(str)) \
302 string_append(str, " ");}
303 #define LEN_STRING(str) ( (STRING_EMPTY(str))?0:((str)->p - (str)->b))
305 /* The scope separator appropriate for the language being demangled. */
307 #define SCOPE_STRING(work) ((work->options & DMGL_JAVA) ? "." : "::")
309 #define ARM_VTABLE_STRING "__vtbl__" /* Lucid/ARM virtual table prefix */
310 #define ARM_VTABLE_STRLEN 8 /* strlen (ARM_VTABLE_STRING) */
312 /* Prototypes for local functions */
314 static char *
315 mop_up PARAMS ((struct work_stuff *, string *, int));
317 static void
318 squangle_mop_up PARAMS ((struct work_stuff *));
320 #if 0
321 static int
322 demangle_method_args PARAMS ((struct work_stuff *, const char **, string *));
323 #endif
325 static char *
326 internal_cplus_demangle PARAMS ((struct work_stuff *, const char *));
328 static int
329 demangle_template_template_parm PARAMS ((struct work_stuff *work,
330 const char **, string *));
332 static int
333 demangle_template PARAMS ((struct work_stuff *work, const char **, string *,
334 string *, int, int));
336 static int
337 arm_pt PARAMS ((struct work_stuff *, const char *, int, const char **,
338 const char **));
340 static int
341 demangle_class_name PARAMS ((struct work_stuff *, const char **, string *));
343 static int
344 demangle_qualified PARAMS ((struct work_stuff *, const char **, string *,
345 int, int));
347 static int
348 demangle_class PARAMS ((struct work_stuff *, const char **, string *));
350 static int
351 demangle_fund_type PARAMS ((struct work_stuff *, const char **, string *));
353 static int
354 demangle_signature PARAMS ((struct work_stuff *, const char **, string *));
356 static int
357 demangle_prefix PARAMS ((struct work_stuff *, const char **, string *));
359 static int
360 gnu_special PARAMS ((struct work_stuff *, const char **, string *));
362 static int
363 arm_special PARAMS ((const char **, string *));
365 static void
366 string_need PARAMS ((string *, int));
368 static void
369 string_delete PARAMS ((string *));
371 static void
372 string_init PARAMS ((string *));
374 static void
375 string_clear PARAMS ((string *));
377 #if 0
378 static int
379 string_empty PARAMS ((string *));
380 #endif
382 static void
383 string_append PARAMS ((string *, const char *));
385 static void
386 string_appends PARAMS ((string *, string *));
388 static void
389 string_appendn PARAMS ((string *, const char *, int));
391 static void
392 string_prepend PARAMS ((string *, const char *));
394 static void
395 string_prependn PARAMS ((string *, const char *, int));
397 static void
398 string_append_template_idx PARAMS ((string *, int));
400 static int
401 get_count PARAMS ((const char **, int *));
403 static int
404 consume_count PARAMS ((const char **));
406 static int
407 consume_count_with_underscores PARAMS ((const char**));
409 static int
410 demangle_args PARAMS ((struct work_stuff *, const char **, string *));
412 static int
413 demangle_nested_args PARAMS ((struct work_stuff*, const char**, string*));
415 static int
416 do_type PARAMS ((struct work_stuff *, const char **, string *));
418 static int
419 do_arg PARAMS ((struct work_stuff *, const char **, string *));
421 static void
422 demangle_function_name PARAMS ((struct work_stuff *, const char **, string *,
423 const char *));
425 static void
426 remember_type PARAMS ((struct work_stuff *, const char *, int));
428 static void
429 remember_Btype PARAMS ((struct work_stuff *, const char *, int, int));
431 static int
432 register_Btype PARAMS ((struct work_stuff *));
434 static void
435 remember_Ktype PARAMS ((struct work_stuff *, const char *, int));
437 static void
438 forget_types PARAMS ((struct work_stuff *));
440 static void
441 forget_B_and_K_types PARAMS ((struct work_stuff *));
443 static void
444 string_prepends PARAMS ((string *, string *));
446 static int
447 demangle_template_value_parm PARAMS ((struct work_stuff*, const char**,
448 string*, type_kind_t));
450 static int
451 do_hpacc_template_const_value PARAMS ((struct work_stuff *, const char **, string *));
453 static int
454 do_hpacc_template_literal PARAMS ((struct work_stuff *, const char **, string *));
456 static int
457 snarf_numeric_literal PARAMS ((const char **, string *));
459 /* There is a TYPE_QUAL value for each type qualifier. They can be
460 combined by bitwise-or to form the complete set of qualifiers for a
461 type. */
463 #define TYPE_UNQUALIFIED 0x0
464 #define TYPE_QUAL_CONST 0x1
465 #define TYPE_QUAL_VOLATILE 0x2
466 #define TYPE_QUAL_RESTRICT 0x4
468 static int
469 code_for_qualifier PARAMS ((int));
471 static const char*
472 qualifier_string PARAMS ((int));
474 static const char*
475 demangle_qualifier PARAMS ((int));
477 static int
478 demangle_expression PARAMS ((struct work_stuff *, const char **, string *,
479 type_kind_t));
481 static int
482 demangle_integral_value PARAMS ((struct work_stuff *, const char **,
483 string *));
485 static int
486 demangle_real_value PARAMS ((struct work_stuff *, const char **, string *));
488 static void
489 demangle_arm_hp_template PARAMS ((struct work_stuff *, const char **, int,
490 string *));
492 static void
493 recursively_demangle PARAMS ((struct work_stuff *, const char **, string *,
494 int));
496 /* Translate count to integer, consuming tokens in the process.
497 Conversion terminates on the first non-digit character.
499 Trying to consume something that isn't a count results in no
500 consumption of input and a return of -1.
502 Overflow consumes the rest of the digits, and returns -1. */
504 static int
505 consume_count (type)
506 const char **type;
508 int count = 0;
510 if (! isdigit ((unsigned char)**type))
511 return -1;
513 while (isdigit ((unsigned char)**type))
515 count *= 10;
517 /* Check for overflow.
518 We assume that count is represented using two's-complement;
519 no power of two is divisible by ten, so if an overflow occurs
520 when multiplying by ten, the result will not be a multiple of
521 ten. */
522 if ((count % 10) != 0)
524 while (isdigit ((unsigned char) **type))
525 (*type)++;
526 return -1;
529 count += **type - '0';
530 (*type)++;
533 return (count);
537 /* Like consume_count, but for counts that are preceded and followed
538 by '_' if they are greater than 10. Also, -1 is returned for
539 failure, since 0 can be a valid value. */
541 static int
542 consume_count_with_underscores (mangled)
543 const char **mangled;
545 int idx;
547 if (**mangled == '_')
549 (*mangled)++;
550 if (!isdigit ((unsigned char)**mangled))
551 return -1;
553 idx = consume_count (mangled);
554 if (**mangled != '_')
555 /* The trailing underscore was missing. */
556 return -1;
558 (*mangled)++;
560 else
562 if (**mangled < '0' || **mangled > '9')
563 return -1;
565 idx = **mangled - '0';
566 (*mangled)++;
569 return idx;
572 /* C is the code for a type-qualifier. Return the TYPE_QUAL
573 corresponding to this qualifier. */
575 static int
576 code_for_qualifier (c)
577 int c;
579 switch (c)
581 case 'C':
582 return TYPE_QUAL_CONST;
584 case 'V':
585 return TYPE_QUAL_VOLATILE;
587 case 'u':
588 return TYPE_QUAL_RESTRICT;
590 default:
591 break;
594 /* C was an invalid qualifier. */
595 abort ();
598 /* Return the string corresponding to the qualifiers given by
599 TYPE_QUALS. */
601 static const char*
602 qualifier_string (type_quals)
603 int type_quals;
605 switch (type_quals)
607 case TYPE_UNQUALIFIED:
608 return "";
610 case TYPE_QUAL_CONST:
611 return "const";
613 case TYPE_QUAL_VOLATILE:
614 return "volatile";
616 case TYPE_QUAL_RESTRICT:
617 return "__restrict";
619 case TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE:
620 return "const volatile";
622 case TYPE_QUAL_CONST | TYPE_QUAL_RESTRICT:
623 return "const __restrict";
625 case TYPE_QUAL_VOLATILE | TYPE_QUAL_RESTRICT:
626 return "volatile __restrict";
628 case TYPE_QUAL_CONST | TYPE_QUAL_VOLATILE | TYPE_QUAL_RESTRICT:
629 return "const volatile __restrict";
631 default:
632 break;
635 /* TYPE_QUALS was an invalid qualifier set. */
636 abort ();
639 /* C is the code for a type-qualifier. Return the string
640 corresponding to this qualifier. This function should only be
641 called with a valid qualifier code. */
643 static const char*
644 demangle_qualifier (c)
645 int c;
647 return qualifier_string (code_for_qualifier (c));
651 cplus_demangle_opname (opname, result, options)
652 const char *opname;
653 char *result;
654 int options;
656 int len, len1, ret;
657 string type;
658 struct work_stuff work[1];
659 const char *tem;
661 len = strlen(opname);
662 result[0] = '\0';
663 ret = 0;
664 memset ((char *) work, 0, sizeof (work));
665 work->options = options;
667 if (opname[0] == '_' && opname[1] == '_'
668 && opname[2] == 'o' && opname[3] == 'p')
670 /* ANSI. */
671 /* type conversion operator. */
672 tem = opname + 4;
673 if (do_type (work, &tem, &type))
675 strcat (result, "operator ");
676 strncat (result, type.b, type.p - type.b);
677 string_delete (&type);
678 ret = 1;
681 else if (opname[0] == '_' && opname[1] == '_'
682 && islower(opname[2])
683 && islower(opname[3]))
685 if (opname[4] == '\0')
687 /* Operator. */
688 size_t i;
689 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
691 if (strlen (optable[i].in) == 2
692 && memcmp (optable[i].in, opname + 2, 2) == 0)
694 strcat (result, "operator");
695 strcat (result, optable[i].out);
696 ret = 1;
697 break;
701 else
703 if (opname[2] == 'a' && opname[5] == '\0')
705 /* Assignment. */
706 size_t i;
707 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
709 if (strlen (optable[i].in) == 3
710 && memcmp (optable[i].in, opname + 2, 3) == 0)
712 strcat (result, "operator");
713 strcat (result, optable[i].out);
714 ret = 1;
715 break;
721 else if (len >= 3
722 && opname[0] == 'o'
723 && opname[1] == 'p'
724 && strchr (cplus_markers, opname[2]) != NULL)
726 /* see if it's an assignment expression */
727 if (len >= 10 /* op$assign_ */
728 && memcmp (opname + 3, "assign_", 7) == 0)
730 size_t i;
731 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
733 len1 = len - 10;
734 if ((int) strlen (optable[i].in) == len1
735 && memcmp (optable[i].in, opname + 10, len1) == 0)
737 strcat (result, "operator");
738 strcat (result, optable[i].out);
739 strcat (result, "=");
740 ret = 1;
741 break;
745 else
747 size_t i;
748 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
750 len1 = len - 3;
751 if ((int) strlen (optable[i].in) == len1
752 && memcmp (optable[i].in, opname + 3, len1) == 0)
754 strcat (result, "operator");
755 strcat (result, optable[i].out);
756 ret = 1;
757 break;
762 else if (len >= 5 && memcmp (opname, "type", 4) == 0
763 && strchr (cplus_markers, opname[4]) != NULL)
765 /* type conversion operator */
766 tem = opname + 5;
767 if (do_type (work, &tem, &type))
769 strcat (result, "operator ");
770 strncat (result, type.b, type.p - type.b);
771 string_delete (&type);
772 ret = 1;
775 squangle_mop_up (work);
776 return ret;
780 /* Takes operator name as e.g. "++" and returns mangled
781 operator name (e.g. "postincrement_expr"), or NULL if not found.
783 If OPTIONS & DMGL_ANSI == 1, return the ANSI name;
784 if OPTIONS & DMGL_ANSI == 0, return the old GNU name. */
786 const char *
787 cplus_mangle_opname (opname, options)
788 const char *opname;
789 int options;
791 size_t i;
792 int len;
794 len = strlen (opname);
795 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
797 if ((int) strlen (optable[i].out) == len
798 && (options & DMGL_ANSI) == (optable[i].flags & DMGL_ANSI)
799 && memcmp (optable[i].out, opname, len) == 0)
800 return optable[i].in;
802 return (0);
805 /* Add a routine to set the demangling style to be sure it is valid and
806 allow for any demangler initialization that maybe necessary. */
808 enum demangling_styles
809 cplus_demangle_set_style (style)
810 enum demangling_styles style;
812 struct demangler_engine *demangler = libiberty_demanglers;
814 for (; demangler->demangling_style != unknown_demangling; ++demangler)
815 if (style == demangler->demangling_style)
817 current_demangling_style = style;
818 return current_demangling_style;
821 return unknown_demangling;
824 /* Do string name to style translation */
826 enum demangling_styles
827 cplus_demangle_name_to_style (name)
828 const char *name;
830 struct demangler_engine *demangler = libiberty_demanglers;
832 for (; demangler->demangling_style != unknown_demangling; ++demangler)
833 if (strcmp (name, demangler->demangling_style_name) == 0)
834 return demangler->demangling_style;
836 return unknown_demangling;
839 /* char *cplus_demangle (const char *mangled, int options)
841 If MANGLED is a mangled function name produced by GNU C++, then
842 a pointer to a malloced string giving a C++ representation
843 of the name will be returned; otherwise NULL will be returned.
844 It is the caller's responsibility to free the string which
845 is returned.
847 The OPTIONS arg may contain one or more of the following bits:
849 DMGL_ANSI ANSI qualifiers such as `const' and `void' are
850 included.
851 DMGL_PARAMS Function parameters are included.
853 For example,
855 cplus_demangle ("foo__1Ai", DMGL_PARAMS) => "A::foo(int)"
856 cplus_demangle ("foo__1Ai", DMGL_PARAMS | DMGL_ANSI) => "A::foo(int)"
857 cplus_demangle ("foo__1Ai", 0) => "A::foo"
859 cplus_demangle ("foo__1Afe", DMGL_PARAMS) => "A::foo(float,...)"
860 cplus_demangle ("foo__1Afe", DMGL_PARAMS | DMGL_ANSI)=> "A::foo(float,...)"
861 cplus_demangle ("foo__1Afe", 0) => "A::foo"
863 Note that any leading underscores, or other such characters prepended by
864 the compilation system, are presumed to have already been stripped from
865 MANGLED. */
867 char *
868 cplus_demangle (mangled, options)
869 const char *mangled;
870 int options;
872 char *ret;
873 struct work_stuff work[1];
874 memset ((char *) work, 0, sizeof (work));
875 work -> options = options;
876 if ((work -> options & DMGL_STYLE_MASK) == 0)
877 work -> options |= (int) current_demangling_style & DMGL_STYLE_MASK;
879 ret = internal_cplus_demangle (work, mangled);
880 squangle_mop_up (work);
881 return (ret);
885 /* This function performs most of what cplus_demangle use to do, but
886 to be able to demangle a name with a B, K or n code, we need to
887 have a longer term memory of what types have been seen. The original
888 now intializes and cleans up the squangle code info, while internal
889 calls go directly to this routine to avoid resetting that info. */
891 static char *
892 internal_cplus_demangle (work, mangled)
893 struct work_stuff *work;
894 const char *mangled;
897 string decl;
898 int success = 0;
899 char *demangled = NULL;
900 int s1,s2,s3,s4;
901 s1 = work->constructor;
902 s2 = work->destructor;
903 s3 = work->static_type;
904 s4 = work->type_quals;
905 work->constructor = work->destructor = 0;
906 work->type_quals = TYPE_UNQUALIFIED;
907 work->dllimported = 0;
909 if ((mangled != NULL) && (*mangled != '\0'))
911 string_init (&decl);
913 /* First check to see if gnu style demangling is active and if the
914 string to be demangled contains a CPLUS_MARKER. If so, attempt to
915 recognize one of the gnu special forms rather than looking for a
916 standard prefix. In particular, don't worry about whether there
917 is a "__" string in the mangled string. Consider "_$_5__foo" for
918 example. */
920 if ((AUTO_DEMANGLING || GNU_DEMANGLING))
922 success = gnu_special (work, &mangled, &decl);
924 if (!success)
926 success = demangle_prefix (work, &mangled, &decl);
928 if (success && (*mangled != '\0'))
930 success = demangle_signature (work, &mangled, &decl);
932 if (work->constructor == 2)
934 string_prepend (&decl, "global constructors keyed to ");
935 work->constructor = 0;
937 else if (work->destructor == 2)
939 string_prepend (&decl, "global destructors keyed to ");
940 work->destructor = 0;
942 else if (work->dllimported == 1)
944 string_prepend (&decl, "import stub for ");
945 work->dllimported = 0;
947 demangled = mop_up (work, &decl, success);
949 work->constructor = s1;
950 work->destructor = s2;
951 work->static_type = s3;
952 work->type_quals = s4;
953 return (demangled);
957 /* Clear out and squangling related storage */
958 static void
959 squangle_mop_up (work)
960 struct work_stuff *work;
962 /* clean up the B and K type mangling types. */
963 forget_B_and_K_types (work);
964 if (work -> btypevec != NULL)
966 free ((char *) work -> btypevec);
968 if (work -> ktypevec != NULL)
970 free ((char *) work -> ktypevec);
974 /* Clear out any mangled storage */
976 static char *
977 mop_up (work, declp, success)
978 struct work_stuff *work;
979 string *declp;
980 int success;
982 char *demangled = NULL;
984 /* Discard the remembered types, if any. */
986 forget_types (work);
987 if (work -> typevec != NULL)
989 free ((char *) work -> typevec);
990 work -> typevec = NULL;
991 work -> typevec_size = 0;
993 if (work->tmpl_argvec)
995 int i;
997 for (i = 0; i < work->ntmpl_args; i++)
998 if (work->tmpl_argvec[i])
999 free ((char*) work->tmpl_argvec[i]);
1001 free ((char*) work->tmpl_argvec);
1002 work->tmpl_argvec = NULL;
1004 if (work->previous_argument)
1006 string_delete (work->previous_argument);
1007 free ((char*) work->previous_argument);
1008 work->previous_argument = NULL;
1011 /* If demangling was successful, ensure that the demangled string is null
1012 terminated and return it. Otherwise, free the demangling decl. */
1014 if (!success)
1016 string_delete (declp);
1018 else
1020 string_appendn (declp, "", 1);
1021 demangled = declp -> b;
1023 return (demangled);
1028 LOCAL FUNCTION
1030 demangle_signature -- demangle the signature part of a mangled name
1032 SYNOPSIS
1034 static int
1035 demangle_signature (struct work_stuff *work, const char **mangled,
1036 string *declp);
1038 DESCRIPTION
1040 Consume and demangle the signature portion of the mangled name.
1042 DECLP is the string where demangled output is being built. At
1043 entry it contains the demangled root name from the mangled name
1044 prefix. I.E. either a demangled operator name or the root function
1045 name. In some special cases, it may contain nothing.
1047 *MANGLED points to the current unconsumed location in the mangled
1048 name. As tokens are consumed and demangling is performed, the
1049 pointer is updated to continuously point at the next token to
1050 be consumed.
1052 Demangling GNU style mangled names is nasty because there is no
1053 explicit token that marks the start of the outermost function
1054 argument list. */
1056 static int
1057 demangle_signature (work, mangled, declp)
1058 struct work_stuff *work;
1059 const char **mangled;
1060 string *declp;
1062 int success = 1;
1063 int func_done = 0;
1064 int expect_func = 0;
1065 int expect_return_type = 0;
1066 const char *oldmangled = NULL;
1067 string trawname;
1068 string tname;
1070 while (success && (**mangled != '\0'))
1072 switch (**mangled)
1074 case 'Q':
1075 oldmangled = *mangled;
1076 success = demangle_qualified (work, mangled, declp, 1, 0);
1077 if (success)
1078 remember_type (work, oldmangled, *mangled - oldmangled);
1079 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1080 expect_func = 1;
1081 oldmangled = NULL;
1082 break;
1084 case 'K':
1085 oldmangled = *mangled;
1086 success = demangle_qualified (work, mangled, declp, 1, 0);
1087 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1089 expect_func = 1;
1091 oldmangled = NULL;
1092 break;
1094 case 'S':
1095 /* Static member function */
1096 if (oldmangled == NULL)
1098 oldmangled = *mangled;
1100 (*mangled)++;
1101 work -> static_type = 1;
1102 break;
1104 case 'C':
1105 case 'V':
1106 case 'u':
1107 work->type_quals |= code_for_qualifier (**mangled);
1109 /* a qualified member function */
1110 if (oldmangled == NULL)
1111 oldmangled = *mangled;
1112 (*mangled)++;
1113 break;
1115 case 'L':
1116 /* Local class name follows after "Lnnn_" */
1117 if (HP_DEMANGLING)
1119 while (**mangled && (**mangled != '_'))
1120 (*mangled)++;
1121 if (!**mangled)
1122 success = 0;
1123 else
1124 (*mangled)++;
1126 else
1127 success = 0;
1128 break;
1130 case '0': case '1': case '2': case '3': case '4':
1131 case '5': case '6': case '7': case '8': case '9':
1132 if (oldmangled == NULL)
1134 oldmangled = *mangled;
1136 work->temp_start = -1; /* uppermost call to demangle_class */
1137 success = demangle_class (work, mangled, declp);
1138 if (success)
1140 remember_type (work, oldmangled, *mangled - oldmangled);
1142 if (AUTO_DEMANGLING || GNU_DEMANGLING || EDG_DEMANGLING)
1144 /* EDG and others will have the "F", so we let the loop cycle
1145 if we are looking at one. */
1146 if (**mangled != 'F')
1147 expect_func = 1;
1149 oldmangled = NULL;
1150 break;
1152 case 'B':
1154 string s;
1155 success = do_type (work, mangled, &s);
1156 if (success)
1158 string_append (&s, SCOPE_STRING (work));
1159 string_prepends (declp, &s);
1161 oldmangled = NULL;
1162 expect_func = 1;
1164 break;
1166 case 'F':
1167 /* Function */
1168 /* ARM/HP style demangling includes a specific 'F' character after
1169 the class name. For GNU style, it is just implied. So we can
1170 safely just consume any 'F' at this point and be compatible
1171 with either style. */
1173 oldmangled = NULL;
1174 func_done = 1;
1175 (*mangled)++;
1177 /* For lucid/ARM/HP style we have to forget any types we might
1178 have remembered up to this point, since they were not argument
1179 types. GNU style considers all types seen as available for
1180 back references. See comment in demangle_args() */
1182 if (LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
1184 forget_types (work);
1186 success = demangle_args (work, mangled, declp);
1187 /* After picking off the function args, we expect to either
1188 find the function return type (preceded by an '_') or the
1189 end of the string. */
1190 if (success && (AUTO_DEMANGLING || EDG_DEMANGLING) && **mangled == '_')
1192 ++(*mangled);
1193 /* At this level, we do not care about the return type. */
1194 success = do_type (work, mangled, &tname);
1195 string_delete (&tname);
1198 break;
1200 case 't':
1201 /* G++ Template */
1202 string_init(&trawname);
1203 string_init(&tname);
1204 if (oldmangled == NULL)
1206 oldmangled = *mangled;
1208 success = demangle_template (work, mangled, &tname,
1209 &trawname, 1, 1);
1210 if (success)
1212 remember_type (work, oldmangled, *mangled - oldmangled);
1214 string_append (&tname, SCOPE_STRING (work));
1216 string_prepends(declp, &tname);
1217 if (work -> destructor & 1)
1219 string_prepend (&trawname, "~");
1220 string_appends (declp, &trawname);
1221 work->destructor -= 1;
1223 if ((work->constructor & 1) || (work->destructor & 1))
1225 string_appends (declp, &trawname);
1226 work->constructor -= 1;
1228 string_delete(&trawname);
1229 string_delete(&tname);
1230 oldmangled = NULL;
1231 expect_func = 1;
1232 break;
1234 case '_':
1235 if (GNU_DEMANGLING && expect_return_type)
1237 /* Read the return type. */
1238 string return_type;
1239 string_init (&return_type);
1241 (*mangled)++;
1242 success = do_type (work, mangled, &return_type);
1243 APPEND_BLANK (&return_type);
1245 string_prepends (declp, &return_type);
1246 string_delete (&return_type);
1247 break;
1249 else
1250 /* At the outermost level, we cannot have a return type specified,
1251 so if we run into another '_' at this point we are dealing with
1252 a mangled name that is either bogus, or has been mangled by
1253 some algorithm we don't know how to deal with. So just
1254 reject the entire demangling. */
1255 /* However, "_nnn" is an expected suffix for alternate entry point
1256 numbered nnn for a function, with HP aCC, so skip over that
1257 without reporting failure. pai/1997-09-04 */
1258 if (HP_DEMANGLING)
1260 (*mangled)++;
1261 while (**mangled && isdigit ((unsigned char)**mangled))
1262 (*mangled)++;
1264 else
1265 success = 0;
1266 break;
1268 case 'H':
1269 if (GNU_DEMANGLING)
1271 /* A G++ template function. Read the template arguments. */
1272 success = demangle_template (work, mangled, declp, 0, 0,
1274 if (!(work->constructor & 1))
1275 expect_return_type = 1;
1276 (*mangled)++;
1277 break;
1279 else
1280 /* fall through */
1283 default:
1284 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1286 /* Assume we have stumbled onto the first outermost function
1287 argument token, and start processing args. */
1288 func_done = 1;
1289 success = demangle_args (work, mangled, declp);
1291 else
1293 /* Non-GNU demanglers use a specific token to mark the start
1294 of the outermost function argument tokens. Typically 'F',
1295 for ARM/HP-demangling, for example. So if we find something
1296 we are not prepared for, it must be an error. */
1297 success = 0;
1299 break;
1302 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1305 if (success && expect_func)
1307 func_done = 1;
1308 if (LUCID_DEMANGLING || ARM_DEMANGLING || EDG_DEMANGLING)
1310 forget_types (work);
1312 success = demangle_args (work, mangled, declp);
1313 /* Since template include the mangling of their return types,
1314 we must set expect_func to 0 so that we don't try do
1315 demangle more arguments the next time we get here. */
1316 expect_func = 0;
1320 if (success && !func_done)
1322 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1324 /* With GNU style demangling, bar__3foo is 'foo::bar(void)', and
1325 bar__3fooi is 'foo::bar(int)'. We get here when we find the
1326 first case, and need to ensure that the '(void)' gets added to
1327 the current declp. Note that with ARM/HP, the first case
1328 represents the name of a static data member 'foo::bar',
1329 which is in the current declp, so we leave it alone. */
1330 success = demangle_args (work, mangled, declp);
1333 if (success && PRINT_ARG_TYPES)
1335 if (work->static_type)
1336 string_append (declp, " static");
1337 if (work->type_quals != TYPE_UNQUALIFIED)
1339 APPEND_BLANK (declp);
1340 string_append (declp, qualifier_string (work->type_quals));
1344 return (success);
1347 #if 0
1349 static int
1350 demangle_method_args (work, mangled, declp)
1351 struct work_stuff *work;
1352 const char **mangled;
1353 string *declp;
1355 int success = 0;
1357 if (work -> static_type)
1359 string_append (declp, *mangled + 1);
1360 *mangled += strlen (*mangled);
1361 success = 1;
1363 else
1365 success = demangle_args (work, mangled, declp);
1367 return (success);
1370 #endif
1372 static int
1373 demangle_template_template_parm (work, mangled, tname)
1374 struct work_stuff *work;
1375 const char **mangled;
1376 string *tname;
1378 int i;
1379 int r;
1380 int need_comma = 0;
1381 int success = 1;
1382 string temp;
1384 string_append (tname, "template <");
1385 /* get size of template parameter list */
1386 if (get_count (mangled, &r))
1388 for (i = 0; i < r; i++)
1390 if (need_comma)
1392 string_append (tname, ", ");
1395 /* Z for type parameters */
1396 if (**mangled == 'Z')
1398 (*mangled)++;
1399 string_append (tname, "class");
1401 /* z for template parameters */
1402 else if (**mangled == 'z')
1404 (*mangled)++;
1405 success =
1406 demangle_template_template_parm (work, mangled, tname);
1407 if (!success)
1409 break;
1412 else
1414 /* temp is initialized in do_type */
1415 success = do_type (work, mangled, &temp);
1416 if (success)
1418 string_appends (tname, &temp);
1420 string_delete(&temp);
1421 if (!success)
1423 break;
1426 need_comma = 1;
1430 if (tname->p[-1] == '>')
1431 string_append (tname, " ");
1432 string_append (tname, "> class");
1433 return (success);
1436 static int
1437 demangle_expression (work, mangled, s, tk)
1438 struct work_stuff *work;
1439 const char** mangled;
1440 string* s;
1441 type_kind_t tk;
1443 int need_operator = 0;
1444 int success;
1446 success = 1;
1447 string_appendn (s, "(", 1);
1448 (*mangled)++;
1449 while (success && **mangled != 'W' && **mangled != '\0')
1451 if (need_operator)
1453 size_t i;
1454 size_t len;
1456 success = 0;
1458 len = strlen (*mangled);
1460 for (i = 0;
1461 i < sizeof (optable) / sizeof (optable [0]);
1462 ++i)
1464 size_t l = strlen (optable[i].in);
1466 if (l <= len
1467 && memcmp (optable[i].in, *mangled, l) == 0)
1469 string_appendn (s, " ", 1);
1470 string_append (s, optable[i].out);
1471 string_appendn (s, " ", 1);
1472 success = 1;
1473 (*mangled) += l;
1474 break;
1478 if (!success)
1479 break;
1481 else
1482 need_operator = 1;
1484 success = demangle_template_value_parm (work, mangled, s, tk);
1487 if (**mangled != 'W')
1488 success = 0;
1489 else
1491 string_appendn (s, ")", 1);
1492 (*mangled)++;
1495 return success;
1498 static int
1499 demangle_integral_value (work, mangled, s)
1500 struct work_stuff *work;
1501 const char** mangled;
1502 string* s;
1504 int success;
1506 if (**mangled == 'E')
1507 success = demangle_expression (work, mangled, s, tk_integral);
1508 else if (**mangled == 'Q' || **mangled == 'K')
1509 success = demangle_qualified (work, mangled, s, 0, 1);
1510 else
1512 int value;
1514 success = 0;
1516 /* Negative numbers are indicated with a leading `m'. */
1517 if (**mangled == 'm')
1519 string_appendn (s, "-", 1);
1520 (*mangled)++;
1523 /* Read the rest of the number. */
1524 value = consume_count_with_underscores (mangled);
1525 if (value != -1)
1527 char buf[INTBUF_SIZE];
1528 sprintf (buf, "%d", value);
1529 string_append (s, buf);
1531 /* If the next character is an underscore, skip it. */
1532 if (**mangled == '_')
1533 (*mangled)++;
1535 /* All is well. */
1536 success = 1;
1540 return success;
1543 /* Demangle the real value in MANGLED. */
1545 static int
1546 demangle_real_value (work, mangled, s)
1547 struct work_stuff *work;
1548 const char **mangled;
1549 string* s;
1551 if (**mangled == 'E')
1552 return demangle_expression (work, mangled, s, tk_real);
1554 if (**mangled == 'm')
1556 string_appendn (s, "-", 1);
1557 (*mangled)++;
1559 while (isdigit ((unsigned char)**mangled))
1561 string_appendn (s, *mangled, 1);
1562 (*mangled)++;
1564 if (**mangled == '.') /* fraction */
1566 string_appendn (s, ".", 1);
1567 (*mangled)++;
1568 while (isdigit ((unsigned char)**mangled))
1570 string_appendn (s, *mangled, 1);
1571 (*mangled)++;
1574 if (**mangled == 'e') /* exponent */
1576 string_appendn (s, "e", 1);
1577 (*mangled)++;
1578 while (isdigit ((unsigned char)**mangled))
1580 string_appendn (s, *mangled, 1);
1581 (*mangled)++;
1585 return 1;
1588 static int
1589 demangle_template_value_parm (work, mangled, s, tk)
1590 struct work_stuff *work;
1591 const char **mangled;
1592 string* s;
1593 type_kind_t tk;
1595 int success = 1;
1597 if (**mangled == 'Y')
1599 /* The next argument is a template parameter. */
1600 int idx;
1602 (*mangled)++;
1603 idx = consume_count_with_underscores (mangled);
1604 if (idx == -1
1605 || (work->tmpl_argvec && idx >= work->ntmpl_args)
1606 || consume_count_with_underscores (mangled) == -1)
1607 return -1;
1608 if (work->tmpl_argvec)
1609 string_append (s, work->tmpl_argvec[idx]);
1610 else
1611 string_append_template_idx (s, idx);
1613 else if (tk == tk_integral)
1614 success = demangle_integral_value (work, mangled, s);
1615 else if (tk == tk_char)
1617 char tmp[2];
1618 int val;
1619 if (**mangled == 'm')
1621 string_appendn (s, "-", 1);
1622 (*mangled)++;
1624 string_appendn (s, "'", 1);
1625 val = consume_count(mangled);
1626 if (val <= 0)
1627 success = 0;
1628 else
1630 tmp[0] = (char)val;
1631 tmp[1] = '\0';
1632 string_appendn (s, &tmp[0], 1);
1633 string_appendn (s, "'", 1);
1636 else if (tk == tk_bool)
1638 int val = consume_count (mangled);
1639 if (val == 0)
1640 string_appendn (s, "false", 5);
1641 else if (val == 1)
1642 string_appendn (s, "true", 4);
1643 else
1644 success = 0;
1646 else if (tk == tk_real)
1647 success = demangle_real_value (work, mangled, s);
1648 else if (tk == tk_pointer || tk == tk_reference)
1650 if (**mangled == 'Q')
1651 success = demangle_qualified (work, mangled, s,
1652 /*isfuncname=*/0,
1653 /*append=*/1);
1654 else
1656 int symbol_len = consume_count (mangled);
1657 if (symbol_len == -1)
1658 return -1;
1659 if (symbol_len == 0)
1660 string_appendn (s, "0", 1);
1661 else
1663 char *p = xmalloc (symbol_len + 1), *q;
1664 strncpy (p, *mangled, symbol_len);
1665 p [symbol_len] = '\0';
1666 /* We use cplus_demangle here, rather than
1667 internal_cplus_demangle, because the name of the entity
1668 mangled here does not make use of any of the squangling
1669 or type-code information we have built up thus far; it is
1670 mangled independently. */
1671 q = cplus_demangle (p, work->options);
1672 if (tk == tk_pointer)
1673 string_appendn (s, "&", 1);
1674 /* FIXME: Pointer-to-member constants should get a
1675 qualifying class name here. */
1676 if (q)
1678 string_append (s, q);
1679 free (q);
1681 else
1682 string_append (s, p);
1683 free (p);
1685 *mangled += symbol_len;
1689 return success;
1692 /* Demangle the template name in MANGLED. The full name of the
1693 template (e.g., S<int>) is placed in TNAME. The name without the
1694 template parameters (e.g. S) is placed in TRAWNAME if TRAWNAME is
1695 non-NULL. If IS_TYPE is nonzero, this template is a type template,
1696 not a function template. If both IS_TYPE and REMEMBER are nonzero,
1697 the tmeplate is remembered in the list of back-referenceable
1698 types. */
1700 static int
1701 demangle_template (work, mangled, tname, trawname, is_type, remember)
1702 struct work_stuff *work;
1703 const char **mangled;
1704 string *tname;
1705 string *trawname;
1706 int is_type;
1707 int remember;
1709 int i;
1710 int r;
1711 int need_comma = 0;
1712 int success = 0;
1713 const char *start;
1714 int is_java_array = 0;
1715 string temp;
1716 int bindex = 0;
1718 (*mangled)++;
1719 if (is_type)
1721 if (remember)
1722 bindex = register_Btype (work);
1723 start = *mangled;
1724 /* get template name */
1725 if (**mangled == 'z')
1727 int idx;
1728 (*mangled)++;
1729 (*mangled)++;
1731 idx = consume_count_with_underscores (mangled);
1732 if (idx == -1
1733 || (work->tmpl_argvec && idx >= work->ntmpl_args)
1734 || consume_count_with_underscores (mangled) == -1)
1735 return (0);
1737 if (work->tmpl_argvec)
1739 string_append (tname, work->tmpl_argvec[idx]);
1740 if (trawname)
1741 string_append (trawname, work->tmpl_argvec[idx]);
1743 else
1745 string_append_template_idx (tname, idx);
1746 if (trawname)
1747 string_append_template_idx (trawname, idx);
1750 else
1752 if ((r = consume_count (mangled)) <= 0
1753 || (int) strlen (*mangled) < r)
1755 return (0);
1757 is_java_array = (work -> options & DMGL_JAVA)
1758 && strncmp (*mangled, "JArray1Z", 8) == 0;
1759 if (! is_java_array)
1761 string_appendn (tname, *mangled, r);
1763 if (trawname)
1764 string_appendn (trawname, *mangled, r);
1765 *mangled += r;
1768 if (!is_java_array)
1769 string_append (tname, "<");
1770 /* get size of template parameter list */
1771 if (!get_count (mangled, &r))
1773 return (0);
1775 if (!is_type)
1777 /* Create an array for saving the template argument values. */
1778 work->tmpl_argvec = (char**) xmalloc (r * sizeof (char *));
1779 work->ntmpl_args = r;
1780 for (i = 0; i < r; i++)
1781 work->tmpl_argvec[i] = 0;
1783 for (i = 0; i < r; i++)
1785 if (need_comma)
1787 string_append (tname, ", ");
1789 /* Z for type parameters */
1790 if (**mangled == 'Z')
1792 (*mangled)++;
1793 /* temp is initialized in do_type */
1794 success = do_type (work, mangled, &temp);
1795 if (success)
1797 string_appends (tname, &temp);
1799 if (!is_type)
1801 /* Save the template argument. */
1802 int len = temp.p - temp.b;
1803 work->tmpl_argvec[i] = xmalloc (len + 1);
1804 memcpy (work->tmpl_argvec[i], temp.b, len);
1805 work->tmpl_argvec[i][len] = '\0';
1808 string_delete(&temp);
1809 if (!success)
1811 break;
1814 /* z for template parameters */
1815 else if (**mangled == 'z')
1817 int r2;
1818 (*mangled)++;
1819 success = demangle_template_template_parm (work, mangled, tname);
1821 if (success
1822 && (r2 = consume_count (mangled)) > 0
1823 && (int) strlen (*mangled) >= r2)
1825 string_append (tname, " ");
1826 string_appendn (tname, *mangled, r2);
1827 if (!is_type)
1829 /* Save the template argument. */
1830 int len = r2;
1831 work->tmpl_argvec[i] = xmalloc (len + 1);
1832 memcpy (work->tmpl_argvec[i], *mangled, len);
1833 work->tmpl_argvec[i][len] = '\0';
1835 *mangled += r2;
1837 if (!success)
1839 break;
1842 else
1844 string param;
1845 string* s;
1847 /* otherwise, value parameter */
1849 /* temp is initialized in do_type */
1850 success = do_type (work, mangled, &temp);
1851 string_delete(&temp);
1852 if (!success)
1853 break;
1855 if (!is_type)
1857 s = &param;
1858 string_init (s);
1860 else
1861 s = tname;
1863 success = demangle_template_value_parm (work, mangled, s,
1864 (type_kind_t) success);
1866 if (!success)
1868 if (!is_type)
1869 string_delete (s);
1870 success = 0;
1871 break;
1874 if (!is_type)
1876 int len = s->p - s->b;
1877 work->tmpl_argvec[i] = xmalloc (len + 1);
1878 memcpy (work->tmpl_argvec[i], s->b, len);
1879 work->tmpl_argvec[i][len] = '\0';
1881 string_appends (tname, s);
1882 string_delete (s);
1885 need_comma = 1;
1887 if (is_java_array)
1889 string_append (tname, "[]");
1891 else
1893 if (tname->p[-1] == '>')
1894 string_append (tname, " ");
1895 string_append (tname, ">");
1898 if (is_type && remember)
1899 remember_Btype (work, tname->b, LEN_STRING (tname), bindex);
1902 if (work -> static_type)
1904 string_append (declp, *mangled + 1);
1905 *mangled += strlen (*mangled);
1906 success = 1;
1908 else
1910 success = demangle_args (work, mangled, declp);
1914 return (success);
1917 static int
1918 arm_pt (work, mangled, n, anchor, args)
1919 struct work_stuff *work;
1920 const char *mangled;
1921 int n;
1922 const char **anchor, **args;
1924 /* Check if ARM template with "__pt__" in it ("parameterized type") */
1925 /* Allow HP also here, because HP's cfront compiler follows ARM to some extent */
1926 if ((ARM_DEMANGLING || HP_DEMANGLING) && (*anchor = mystrstr (mangled, "__pt__")))
1928 int len;
1929 *args = *anchor + 6;
1930 len = consume_count (args);
1931 if (len == -1)
1932 return 0;
1933 if (*args + len == mangled + n && **args == '_')
1935 ++*args;
1936 return 1;
1939 if (AUTO_DEMANGLING || EDG_DEMANGLING)
1941 if ((*anchor = mystrstr (mangled, "__tm__"))
1942 || (*anchor = mystrstr (mangled, "__ps__"))
1943 || (*anchor = mystrstr (mangled, "__pt__")))
1945 int len;
1946 *args = *anchor + 6;
1947 len = consume_count (args);
1948 if (len == -1)
1949 return 0;
1950 if (*args + len == mangled + n && **args == '_')
1952 ++*args;
1953 return 1;
1956 else if ((*anchor = mystrstr (mangled, "__S")))
1958 int len;
1959 *args = *anchor + 3;
1960 len = consume_count (args);
1961 if (len == -1)
1962 return 0;
1963 if (*args + len == mangled + n && **args == '_')
1965 ++*args;
1966 return 1;
1971 return 0;
1974 static void
1975 demangle_arm_hp_template (work, mangled, n, declp)
1976 struct work_stuff *work;
1977 const char **mangled;
1978 int n;
1979 string *declp;
1981 const char *p;
1982 const char *args;
1983 const char *e = *mangled + n;
1984 string arg;
1986 /* Check for HP aCC template spec: classXt1t2 where t1, t2 are
1987 template args */
1988 if (HP_DEMANGLING && ((*mangled)[n] == 'X'))
1990 char *start_spec_args = NULL;
1992 /* First check for and omit template specialization pseudo-arguments,
1993 such as in "Spec<#1,#1.*>" */
1994 start_spec_args = strchr (*mangled, '<');
1995 if (start_spec_args && (start_spec_args - *mangled < n))
1996 string_appendn (declp, *mangled, start_spec_args - *mangled);
1997 else
1998 string_appendn (declp, *mangled, n);
1999 (*mangled) += n + 1;
2000 string_init (&arg);
2001 if (work->temp_start == -1) /* non-recursive call */
2002 work->temp_start = declp->p - declp->b;
2003 string_append (declp, "<");
2004 while (1)
2006 string_clear (&arg);
2007 switch (**mangled)
2009 case 'T':
2010 /* 'T' signals a type parameter */
2011 (*mangled)++;
2012 if (!do_type (work, mangled, &arg))
2013 goto hpacc_template_args_done;
2014 break;
2016 case 'U':
2017 case 'S':
2018 /* 'U' or 'S' signals an integral value */
2019 if (!do_hpacc_template_const_value (work, mangled, &arg))
2020 goto hpacc_template_args_done;
2021 break;
2023 case 'A':
2024 /* 'A' signals a named constant expression (literal) */
2025 if (!do_hpacc_template_literal (work, mangled, &arg))
2026 goto hpacc_template_args_done;
2027 break;
2029 default:
2030 /* Today, 1997-09-03, we have only the above types
2031 of template parameters */
2032 /* FIXME: maybe this should fail and return null */
2033 goto hpacc_template_args_done;
2035 string_appends (declp, &arg);
2036 /* Check if we're at the end of template args.
2037 0 if at end of static member of template class,
2038 _ if done with template args for a function */
2039 if ((**mangled == '\000') || (**mangled == '_'))
2040 break;
2041 else
2042 string_append (declp, ",");
2044 hpacc_template_args_done:
2045 string_append (declp, ">");
2046 string_delete (&arg);
2047 if (**mangled == '_')
2048 (*mangled)++;
2049 return;
2051 /* ARM template? (Also handles HP cfront extensions) */
2052 else if (arm_pt (work, *mangled, n, &p, &args))
2054 string type_str;
2056 string_init (&arg);
2057 string_appendn (declp, *mangled, p - *mangled);
2058 if (work->temp_start == -1) /* non-recursive call */
2059 work->temp_start = declp->p - declp->b;
2060 string_append (declp, "<");
2061 /* should do error checking here */
2062 while (args < e) {
2063 string_clear (&arg);
2065 /* Check for type or literal here */
2066 switch (*args)
2068 /* HP cfront extensions to ARM for template args */
2069 /* spec: Xt1Lv1 where t1 is a type, v1 is a literal value */
2070 /* FIXME: We handle only numeric literals for HP cfront */
2071 case 'X':
2072 /* A typed constant value follows */
2073 args++;
2074 if (!do_type (work, &args, &type_str))
2075 goto cfront_template_args_done;
2076 string_append (&arg, "(");
2077 string_appends (&arg, &type_str);
2078 string_append (&arg, ")");
2079 if (*args != 'L')
2080 goto cfront_template_args_done;
2081 args++;
2082 /* Now snarf a literal value following 'L' */
2083 if (!snarf_numeric_literal (&args, &arg))
2084 goto cfront_template_args_done;
2085 break;
2087 case 'L':
2088 /* Snarf a literal following 'L' */
2089 args++;
2090 if (!snarf_numeric_literal (&args, &arg))
2091 goto cfront_template_args_done;
2092 break;
2093 default:
2094 /* Not handling other HP cfront stuff */
2095 if (!do_type (work, &args, &arg))
2096 goto cfront_template_args_done;
2098 string_appends (declp, &arg);
2099 string_append (declp, ",");
2101 cfront_template_args_done:
2102 string_delete (&arg);
2103 if (args >= e)
2104 --declp->p; /* remove extra comma */
2105 string_append (declp, ">");
2107 else if (n>10 && strncmp (*mangled, "_GLOBAL_", 8) == 0
2108 && (*mangled)[9] == 'N'
2109 && (*mangled)[8] == (*mangled)[10]
2110 && strchr (cplus_markers, (*mangled)[8]))
2112 /* A member of the anonymous namespace. */
2113 string_append (declp, "{anonymous}");
2115 else
2117 if (work->temp_start == -1) /* non-recursive call only */
2118 work->temp_start = 0; /* disable in recursive calls */
2119 string_appendn (declp, *mangled, n);
2121 *mangled += n;
2124 /* Extract a class name, possibly a template with arguments, from the
2125 mangled string; qualifiers, local class indicators, etc. have
2126 already been dealt with */
2128 static int
2129 demangle_class_name (work, mangled, declp)
2130 struct work_stuff *work;
2131 const char **mangled;
2132 string *declp;
2134 int n;
2135 int success = 0;
2137 n = consume_count (mangled);
2138 if (n == -1)
2139 return 0;
2140 if ((int) strlen (*mangled) >= n)
2142 demangle_arm_hp_template (work, mangled, n, declp);
2143 success = 1;
2146 return (success);
2151 LOCAL FUNCTION
2153 demangle_class -- demangle a mangled class sequence
2155 SYNOPSIS
2157 static int
2158 demangle_class (struct work_stuff *work, const char **mangled,
2159 strint *declp)
2161 DESCRIPTION
2163 DECLP points to the buffer into which demangling is being done.
2165 *MANGLED points to the current token to be demangled. On input,
2166 it points to a mangled class (I.E. "3foo", "13verylongclass", etc.)
2167 On exit, it points to the next token after the mangled class on
2168 success, or the first unconsumed token on failure.
2170 If the CONSTRUCTOR or DESTRUCTOR flags are set in WORK, then
2171 we are demangling a constructor or destructor. In this case
2172 we prepend "class::class" or "class::~class" to DECLP.
2174 Otherwise, we prepend "class::" to the current DECLP.
2176 Reset the constructor/destructor flags once they have been
2177 "consumed". This allows demangle_class to be called later during
2178 the same demangling, to do normal class demangling.
2180 Returns 1 if demangling is successful, 0 otherwise.
2184 static int
2185 demangle_class (work, mangled, declp)
2186 struct work_stuff *work;
2187 const char **mangled;
2188 string *declp;
2190 int success = 0;
2191 int btype;
2192 string class_name;
2193 char *save_class_name_end = 0;
2195 string_init (&class_name);
2196 btype = register_Btype (work);
2197 if (demangle_class_name (work, mangled, &class_name))
2199 save_class_name_end = class_name.p;
2200 if ((work->constructor & 1) || (work->destructor & 1))
2202 /* adjust so we don't include template args */
2203 if (work->temp_start && (work->temp_start != -1))
2205 class_name.p = class_name.b + work->temp_start;
2207 string_prepends (declp, &class_name);
2208 if (work -> destructor & 1)
2210 string_prepend (declp, "~");
2211 work -> destructor -= 1;
2213 else
2215 work -> constructor -= 1;
2218 class_name.p = save_class_name_end;
2219 remember_Ktype (work, class_name.b, LEN_STRING(&class_name));
2220 remember_Btype (work, class_name.b, LEN_STRING(&class_name), btype);
2221 string_prepend (declp, SCOPE_STRING (work));
2222 string_prepends (declp, &class_name);
2223 success = 1;
2225 string_delete (&class_name);
2226 return (success);
2231 LOCAL FUNCTION
2233 demangle_prefix -- consume the mangled name prefix and find signature
2235 SYNOPSIS
2237 static int
2238 demangle_prefix (struct work_stuff *work, const char **mangled,
2239 string *declp);
2241 DESCRIPTION
2243 Consume and demangle the prefix of the mangled name.
2245 DECLP points to the string buffer into which demangled output is
2246 placed. On entry, the buffer is empty. On exit it contains
2247 the root function name, the demangled operator name, or in some
2248 special cases either nothing or the completely demangled result.
2250 MANGLED points to the current pointer into the mangled name. As each
2251 token of the mangled name is consumed, it is updated. Upon entry
2252 the current mangled name pointer points to the first character of
2253 the mangled name. Upon exit, it should point to the first character
2254 of the signature if demangling was successful, or to the first
2255 unconsumed character if demangling of the prefix was unsuccessful.
2257 Returns 1 on success, 0 otherwise.
2260 static int
2261 demangle_prefix (work, mangled, declp)
2262 struct work_stuff *work;
2263 const char **mangled;
2264 string *declp;
2266 int success = 1;
2267 const char *scan;
2268 int i;
2270 if (strlen(*mangled) > 6
2271 && (strncmp(*mangled, "_imp__", 6) == 0
2272 || strncmp(*mangled, "__imp_", 6) == 0))
2274 /* it's a symbol imported from a PE dynamic library. Check for both
2275 new style prefix _imp__ and legacy __imp_ used by older versions
2276 of dlltool. */
2277 (*mangled) += 6;
2278 work->dllimported = 1;
2280 else if (strlen(*mangled) >= 11 && strncmp(*mangled, "_GLOBAL_", 8) == 0)
2282 char *marker = strchr (cplus_markers, (*mangled)[8]);
2283 if (marker != NULL && *marker == (*mangled)[10])
2285 if ((*mangled)[9] == 'D')
2287 /* it's a GNU global destructor to be executed at program exit */
2288 (*mangled) += 11;
2289 work->destructor = 2;
2290 if (gnu_special (work, mangled, declp))
2291 return success;
2293 else if ((*mangled)[9] == 'I')
2295 /* it's a GNU global constructor to be executed at program init */
2296 (*mangled) += 11;
2297 work->constructor = 2;
2298 if (gnu_special (work, mangled, declp))
2299 return success;
2303 else if ((ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING) && strncmp(*mangled, "__std__", 7) == 0)
2305 /* it's a ARM global destructor to be executed at program exit */
2306 (*mangled) += 7;
2307 work->destructor = 2;
2309 else if ((ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING) && strncmp(*mangled, "__sti__", 7) == 0)
2311 /* it's a ARM global constructor to be executed at program initial */
2312 (*mangled) += 7;
2313 work->constructor = 2;
2316 /* This block of code is a reduction in strength time optimization
2318 scan = mystrstr (*mangled, "__"); */
2321 scan = *mangled;
2323 do {
2324 scan = strchr (scan, '_');
2325 } while (scan != NULL && *++scan != '_');
2327 if (scan != NULL) --scan;
2330 if (scan != NULL)
2332 /* We found a sequence of two or more '_', ensure that we start at
2333 the last pair in the sequence. */
2334 i = strspn (scan, "_");
2335 if (i > 2)
2337 scan += (i - 2);
2341 if (scan == NULL)
2343 success = 0;
2345 else if (work -> static_type)
2347 if (!isdigit ((unsigned char)scan[0]) && (scan[0] != 't'))
2349 success = 0;
2352 else if ((scan == *mangled)
2353 && (isdigit ((unsigned char)scan[2]) || (scan[2] == 'Q')
2354 || (scan[2] == 't') || (scan[2] == 'K') || (scan[2] == 'H')))
2356 /* The ARM says nothing about the mangling of local variables.
2357 But cfront mangles local variables by prepending __<nesting_level>
2358 to them. As an extension to ARM demangling we handle this case. */
2359 if ((LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING)
2360 && isdigit ((unsigned char)scan[2]))
2362 *mangled = scan + 2;
2363 consume_count (mangled);
2364 string_append (declp, *mangled);
2365 *mangled += strlen (*mangled);
2366 success = 1;
2368 else
2370 /* A GNU style constructor starts with __[0-9Qt]. But cfront uses
2371 names like __Q2_3foo3bar for nested type names. So don't accept
2372 this style of constructor for cfront demangling. A GNU
2373 style member-template constructor starts with 'H'. */
2374 if (!(LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING))
2375 work -> constructor += 1;
2376 *mangled = scan + 2;
2379 else if (ARM_DEMANGLING && scan[2] == 'p' && scan[3] == 't')
2381 /* Cfront-style parameterized type. Handled later as a signature. */
2382 success = 1;
2384 /* ARM template? */
2385 demangle_arm_hp_template (work, mangled, strlen (*mangled), declp);
2387 else if (EDG_DEMANGLING && ((scan[2] == 't' && scan[3] == 'm')
2388 || (scan[2] == 'p' && scan[3] == 's')
2389 || (scan[2] == 'p' && scan[3] == 't')))
2391 /* EDG-style parameterized type. Handled later as a signature. */
2392 success = 1;
2394 /* EDG template? */
2395 demangle_arm_hp_template (work, mangled, strlen (*mangled), declp);
2397 else if ((scan == *mangled) && !isdigit ((unsigned char)scan[2])
2398 && (scan[2] != 't'))
2400 /* Mangled name starts with "__". Skip over any leading '_' characters,
2401 then find the next "__" that separates the prefix from the signature.
2403 if (!(ARM_DEMANGLING || LUCID_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
2404 || (arm_special (mangled, declp) == 0))
2406 while (*scan == '_')
2408 scan++;
2410 if ((scan = mystrstr (scan, "__")) == NULL || (*(scan + 2) == '\0'))
2412 /* No separator (I.E. "__not_mangled"), or empty signature
2413 (I.E. "__not_mangled_either__") */
2414 success = 0;
2416 else
2418 const char *tmp;
2420 /* Look for the LAST occurrence of __, allowing names to
2421 have the '__' sequence embedded in them. */
2422 if (!(ARM_DEMANGLING || HP_DEMANGLING))
2424 while ((tmp = mystrstr (scan + 2, "__")) != NULL)
2425 scan = tmp;
2427 if (*(scan + 2) == '\0')
2428 success = 0;
2429 else
2430 demangle_function_name (work, mangled, declp, scan);
2434 else if (*(scan + 2) != '\0')
2436 /* Mangled name does not start with "__" but does have one somewhere
2437 in there with non empty stuff after it. Looks like a global
2438 function name. */
2439 demangle_function_name (work, mangled, declp, scan);
2441 else
2443 /* Doesn't look like a mangled name */
2444 success = 0;
2447 if (!success && (work->constructor == 2 || work->destructor == 2))
2449 string_append (declp, *mangled);
2450 *mangled += strlen (*mangled);
2451 success = 1;
2453 return (success);
2458 LOCAL FUNCTION
2460 gnu_special -- special handling of gnu mangled strings
2462 SYNOPSIS
2464 static int
2465 gnu_special (struct work_stuff *work, const char **mangled,
2466 string *declp);
2469 DESCRIPTION
2471 Process some special GNU style mangling forms that don't fit
2472 the normal pattern. For example:
2474 _$_3foo (destructor for class foo)
2475 _vt$foo (foo virtual table)
2476 _vt$foo$bar (foo::bar virtual table)
2477 __vt_foo (foo virtual table, new style with thunks)
2478 _3foo$varname (static data member)
2479 _Q22rs2tu$vw (static data member)
2480 __t6vector1Zii (constructor with template)
2481 __thunk_4__$_7ostream (virtual function thunk)
2484 static int
2485 gnu_special (work, mangled, declp)
2486 struct work_stuff *work;
2487 const char **mangled;
2488 string *declp;
2490 int n;
2491 int success = 1;
2492 const char *p;
2494 if ((*mangled)[0] == '_'
2495 && strchr (cplus_markers, (*mangled)[1]) != NULL
2496 && (*mangled)[2] == '_')
2498 /* Found a GNU style destructor, get past "_<CPLUS_MARKER>_" */
2499 (*mangled) += 3;
2500 work -> destructor += 1;
2502 else if ((*mangled)[0] == '_'
2503 && (((*mangled)[1] == '_'
2504 && (*mangled)[2] == 'v'
2505 && (*mangled)[3] == 't'
2506 && (*mangled)[4] == '_')
2507 || ((*mangled)[1] == 'v'
2508 && (*mangled)[2] == 't'
2509 && strchr (cplus_markers, (*mangled)[3]) != NULL)))
2511 /* Found a GNU style virtual table, get past "_vt<CPLUS_MARKER>"
2512 and create the decl. Note that we consume the entire mangled
2513 input string, which means that demangle_signature has no work
2514 to do. */
2515 if ((*mangled)[2] == 'v')
2516 (*mangled) += 5; /* New style, with thunks: "__vt_" */
2517 else
2518 (*mangled) += 4; /* Old style, no thunks: "_vt<CPLUS_MARKER>" */
2519 while (**mangled != '\0')
2521 switch (**mangled)
2523 case 'Q':
2524 case 'K':
2525 success = demangle_qualified (work, mangled, declp, 0, 1);
2526 break;
2527 case 't':
2528 success = demangle_template (work, mangled, declp, 0, 1,
2530 break;
2531 default:
2532 if (isdigit((unsigned char)*mangled[0]))
2534 n = consume_count(mangled);
2535 /* We may be seeing a too-large size, or else a
2536 ".<digits>" indicating a static local symbol. In
2537 any case, declare victory and move on; *don't* try
2538 to use n to allocate. */
2539 if (n > (int) strlen (*mangled))
2541 success = 1;
2542 break;
2545 else
2547 n = strcspn (*mangled, cplus_markers);
2549 string_appendn (declp, *mangled, n);
2550 (*mangled) += n;
2553 p = strpbrk (*mangled, cplus_markers);
2554 if (success && ((p == NULL) || (p == *mangled)))
2556 if (p != NULL)
2558 string_append (declp, SCOPE_STRING (work));
2559 (*mangled)++;
2562 else
2564 success = 0;
2565 break;
2568 if (success)
2569 string_append (declp, " virtual table");
2571 else if ((*mangled)[0] == '_'
2572 && (strchr("0123456789Qt", (*mangled)[1]) != NULL)
2573 && (p = strpbrk (*mangled, cplus_markers)) != NULL)
2575 /* static data member, "_3foo$varname" for example */
2576 (*mangled)++;
2577 switch (**mangled)
2579 case 'Q':
2580 case 'K':
2581 success = demangle_qualified (work, mangled, declp, 0, 1);
2582 break;
2583 case 't':
2584 success = demangle_template (work, mangled, declp, 0, 1, 1);
2585 break;
2586 default:
2587 n = consume_count (mangled);
2588 if (n < 0 || n > (long) strlen (*mangled))
2590 success = 0;
2591 break;
2593 string_appendn (declp, *mangled, n);
2594 (*mangled) += n;
2596 if (success && (p == *mangled))
2598 /* Consumed everything up to the cplus_marker, append the
2599 variable name. */
2600 (*mangled)++;
2601 string_append (declp, SCOPE_STRING (work));
2602 n = strlen (*mangled);
2603 string_appendn (declp, *mangled, n);
2604 (*mangled) += n;
2606 else
2608 success = 0;
2611 else if (strncmp (*mangled, "__thunk_", 8) == 0)
2613 int delta;
2615 (*mangled) += 8;
2616 delta = consume_count (mangled);
2617 if (delta == -1)
2618 success = 0;
2619 else
2621 char *method = internal_cplus_demangle (work, ++*mangled);
2623 if (method)
2625 char buf[50];
2626 sprintf (buf, "virtual function thunk (delta:%d) for ", -delta);
2627 string_append (declp, buf);
2628 string_append (declp, method);
2629 free (method);
2630 n = strlen (*mangled);
2631 (*mangled) += n;
2633 else
2635 success = 0;
2639 else if (strncmp (*mangled, "__t", 3) == 0
2640 && ((*mangled)[3] == 'i' || (*mangled)[3] == 'f'))
2642 p = (*mangled)[3] == 'i' ? " type_info node" : " type_info function";
2643 (*mangled) += 4;
2644 switch (**mangled)
2646 case 'Q':
2647 case 'K':
2648 success = demangle_qualified (work, mangled, declp, 0, 1);
2649 break;
2650 case 't':
2651 success = demangle_template (work, mangled, declp, 0, 1, 1);
2652 break;
2653 default:
2654 success = demangle_fund_type (work, mangled, declp);
2655 break;
2657 if (success && **mangled != '\0')
2658 success = 0;
2659 if (success)
2660 string_append (declp, p);
2662 else
2664 success = 0;
2666 return (success);
2669 static void
2670 recursively_demangle(work, mangled, result, namelength)
2671 struct work_stuff *work;
2672 const char **mangled;
2673 string *result;
2674 int namelength;
2676 char * recurse = (char *)NULL;
2677 char * recurse_dem = (char *)NULL;
2679 recurse = (char *) xmalloc (namelength + 1);
2680 memcpy (recurse, *mangled, namelength);
2681 recurse[namelength] = '\000';
2683 recurse_dem = cplus_demangle (recurse, work->options);
2685 if (recurse_dem)
2687 string_append (result, recurse_dem);
2688 free (recurse_dem);
2690 else
2692 string_appendn (result, *mangled, namelength);
2694 free (recurse);
2695 *mangled += namelength;
2700 LOCAL FUNCTION
2702 arm_special -- special handling of ARM/lucid mangled strings
2704 SYNOPSIS
2706 static int
2707 arm_special (const char **mangled,
2708 string *declp);
2711 DESCRIPTION
2713 Process some special ARM style mangling forms that don't fit
2714 the normal pattern. For example:
2716 __vtbl__3foo (foo virtual table)
2717 __vtbl__3foo__3bar (bar::foo virtual table)
2721 static int
2722 arm_special (mangled, declp)
2723 const char **mangled;
2724 string *declp;
2726 int n;
2727 int success = 1;
2728 const char *scan;
2730 if (strncmp (*mangled, ARM_VTABLE_STRING, ARM_VTABLE_STRLEN) == 0)
2732 /* Found a ARM style virtual table, get past ARM_VTABLE_STRING
2733 and create the decl. Note that we consume the entire mangled
2734 input string, which means that demangle_signature has no work
2735 to do. */
2736 scan = *mangled + ARM_VTABLE_STRLEN;
2737 while (*scan != '\0') /* first check it can be demangled */
2739 n = consume_count (&scan);
2740 if (n == -1)
2742 return (0); /* no good */
2744 scan += n;
2745 if (scan[0] == '_' && scan[1] == '_')
2747 scan += 2;
2750 (*mangled) += ARM_VTABLE_STRLEN;
2751 while (**mangled != '\0')
2753 n = consume_count (mangled);
2754 if (n == -1
2755 || n > (long) strlen (*mangled))
2756 return 0;
2757 string_prependn (declp, *mangled, n);
2758 (*mangled) += n;
2759 if ((*mangled)[0] == '_' && (*mangled)[1] == '_')
2761 string_prepend (declp, "::");
2762 (*mangled) += 2;
2765 string_append (declp, " virtual table");
2767 else
2769 success = 0;
2771 return (success);
2776 LOCAL FUNCTION
2778 demangle_qualified -- demangle 'Q' qualified name strings
2780 SYNOPSIS
2782 static int
2783 demangle_qualified (struct work_stuff *, const char *mangled,
2784 string *result, int isfuncname, int append);
2786 DESCRIPTION
2788 Demangle a qualified name, such as "Q25Outer5Inner" which is
2789 the mangled form of "Outer::Inner". The demangled output is
2790 prepended or appended to the result string according to the
2791 state of the append flag.
2793 If isfuncname is nonzero, then the qualified name we are building
2794 is going to be used as a member function name, so if it is a
2795 constructor or destructor function, append an appropriate
2796 constructor or destructor name. I.E. for the above example,
2797 the result for use as a constructor is "Outer::Inner::Inner"
2798 and the result for use as a destructor is "Outer::Inner::~Inner".
2800 BUGS
2802 Numeric conversion is ASCII dependent (FIXME).
2806 static int
2807 demangle_qualified (work, mangled, result, isfuncname, append)
2808 struct work_stuff *work;
2809 const char **mangled;
2810 string *result;
2811 int isfuncname;
2812 int append;
2814 int qualifiers = 0;
2815 int success = 1;
2816 char num[2];
2817 string temp;
2818 string last_name;
2819 int bindex = register_Btype (work);
2821 /* We only make use of ISFUNCNAME if the entity is a constructor or
2822 destructor. */
2823 isfuncname = (isfuncname
2824 && ((work->constructor & 1) || (work->destructor & 1)));
2826 string_init (&temp);
2827 string_init (&last_name);
2829 if ((*mangled)[0] == 'K')
2831 /* Squangling qualified name reuse */
2832 int idx;
2833 (*mangled)++;
2834 idx = consume_count_with_underscores (mangled);
2835 if (idx == -1 || idx >= work -> numk)
2836 success = 0;
2837 else
2838 string_append (&temp, work -> ktypevec[idx]);
2840 else
2841 switch ((*mangled)[1])
2843 case '_':
2844 /* GNU mangled name with more than 9 classes. The count is preceded
2845 by an underscore (to distinguish it from the <= 9 case) and followed
2846 by an underscore. */
2847 (*mangled)++;
2848 qualifiers = consume_count_with_underscores (mangled);
2849 if (qualifiers == -1)
2850 success = 0;
2851 break;
2853 case '1':
2854 case '2':
2855 case '3':
2856 case '4':
2857 case '5':
2858 case '6':
2859 case '7':
2860 case '8':
2861 case '9':
2862 /* The count is in a single digit. */
2863 num[0] = (*mangled)[1];
2864 num[1] = '\0';
2865 qualifiers = atoi (num);
2867 /* If there is an underscore after the digit, skip it. This is
2868 said to be for ARM-qualified names, but the ARM makes no
2869 mention of such an underscore. Perhaps cfront uses one. */
2870 if ((*mangled)[2] == '_')
2872 (*mangled)++;
2874 (*mangled) += 2;
2875 break;
2877 case '0':
2878 default:
2879 success = 0;
2882 if (!success)
2883 return success;
2885 /* Pick off the names and collect them in the temp buffer in the order
2886 in which they are found, separated by '::'. */
2888 while (qualifiers-- > 0)
2890 int remember_K = 1;
2891 string_clear (&last_name);
2893 if (*mangled[0] == '_')
2894 (*mangled)++;
2896 if (*mangled[0] == 't')
2898 /* Here we always append to TEMP since we will want to use
2899 the template name without the template parameters as a
2900 constructor or destructor name. The appropriate
2901 (parameter-less) value is returned by demangle_template
2902 in LAST_NAME. We do not remember the template type here,
2903 in order to match the G++ mangling algorithm. */
2904 success = demangle_template(work, mangled, &temp,
2905 &last_name, 1, 0);
2906 if (!success)
2907 break;
2909 else if (*mangled[0] == 'K')
2911 int idx;
2912 (*mangled)++;
2913 idx = consume_count_with_underscores (mangled);
2914 if (idx == -1 || idx >= work->numk)
2915 success = 0;
2916 else
2917 string_append (&temp, work->ktypevec[idx]);
2918 remember_K = 0;
2920 if (!success) break;
2922 else
2924 if (EDG_DEMANGLING)
2926 int namelength;
2927 /* Now recursively demangle the qualifier
2928 * This is necessary to deal with templates in
2929 * mangling styles like EDG */
2930 namelength = consume_count (mangled);
2931 if (namelength == -1)
2933 success = 0;
2934 break;
2936 recursively_demangle(work, mangled, &temp, namelength);
2938 else
2940 success = do_type (work, mangled, &last_name);
2941 if (!success)
2942 break;
2943 string_appends (&temp, &last_name);
2947 if (remember_K)
2948 remember_Ktype (work, temp.b, LEN_STRING (&temp));
2950 if (qualifiers > 0)
2951 string_append (&temp, SCOPE_STRING (work));
2954 remember_Btype (work, temp.b, LEN_STRING (&temp), bindex);
2956 /* If we are using the result as a function name, we need to append
2957 the appropriate '::' separated constructor or destructor name.
2958 We do this here because this is the most convenient place, where
2959 we already have a pointer to the name and the length of the name. */
2961 if (isfuncname)
2963 string_append (&temp, SCOPE_STRING (work));
2964 if (work -> destructor & 1)
2965 string_append (&temp, "~");
2966 string_appends (&temp, &last_name);
2969 /* Now either prepend the temp buffer to the result, or append it,
2970 depending upon the state of the append flag. */
2972 if (append)
2973 string_appends (result, &temp);
2974 else
2976 if (!STRING_EMPTY (result))
2977 string_append (&temp, SCOPE_STRING (work));
2978 string_prepends (result, &temp);
2981 string_delete (&last_name);
2982 string_delete (&temp);
2983 return (success);
2988 LOCAL FUNCTION
2990 get_count -- convert an ascii count to integer, consuming tokens
2992 SYNOPSIS
2994 static int
2995 get_count (const char **type, int *count)
2997 DESCRIPTION
2999 Assume that *type points at a count in a mangled name; set
3000 *count to its value, and set *type to the next character after
3001 the count. There are some weird rules in effect here.
3003 If *type does not point at a string of digits, return zero.
3005 If *type points at a string of digits followed by an
3006 underscore, set *count to their value as an integer, advance
3007 *type to point *after the underscore, and return 1.
3009 If *type points at a string of digits not followed by an
3010 underscore, consume only the first digit. Set *count to its
3011 value as an integer, leave *type pointing after that digit,
3012 and return 1.
3014 The excuse for this odd behavior: in the ARM and HP demangling
3015 styles, a type can be followed by a repeat count of the form
3016 `Nxy', where:
3018 `x' is a single digit specifying how many additional copies
3019 of the type to append to the argument list, and
3021 `y' is one or more digits, specifying the zero-based index of
3022 the first repeated argument in the list. Yes, as you're
3023 unmangling the name you can figure this out yourself, but
3024 it's there anyway.
3026 So, for example, in `bar__3fooFPiN51', the first argument is a
3027 pointer to an integer (`Pi'), and then the next five arguments
3028 are the same (`N5'), and the first repeat is the function's
3029 second argument (`1').
3032 static int
3033 get_count (type, count)
3034 const char **type;
3035 int *count;
3037 const char *p;
3038 int n;
3040 if (!isdigit ((unsigned char)**type))
3041 return (0);
3042 else
3044 *count = **type - '0';
3045 (*type)++;
3046 if (isdigit ((unsigned char)**type))
3048 p = *type;
3049 n = *count;
3052 n *= 10;
3053 n += *p - '0';
3054 p++;
3056 while (isdigit ((unsigned char)*p));
3057 if (*p == '_')
3059 *type = p + 1;
3060 *count = n;
3064 return (1);
3067 /* RESULT will be initialised here; it will be freed on failure. The
3068 value returned is really a type_kind_t. */
3070 static int
3071 do_type (work, mangled, result)
3072 struct work_stuff *work;
3073 const char **mangled;
3074 string *result;
3076 int n;
3077 int done;
3078 int success;
3079 string decl;
3080 const char *remembered_type;
3081 int type_quals;
3082 string btype;
3083 type_kind_t tk = tk_none;
3085 string_init (&btype);
3086 string_init (&decl);
3087 string_init (result);
3089 done = 0;
3090 success = 1;
3091 while (success && !done)
3093 int member;
3094 switch (**mangled)
3097 /* A pointer type */
3098 case 'P':
3099 case 'p':
3100 (*mangled)++;
3101 if (! (work -> options & DMGL_JAVA))
3102 string_prepend (&decl, "*");
3103 if (tk == tk_none)
3104 tk = tk_pointer;
3105 break;
3107 /* A reference type */
3108 case 'R':
3109 (*mangled)++;
3110 string_prepend (&decl, "&");
3111 if (tk == tk_none)
3112 tk = tk_reference;
3113 break;
3115 /* An array */
3116 case 'A':
3118 ++(*mangled);
3119 if (!STRING_EMPTY (&decl)
3120 && (decl.b[0] == '*' || decl.b[0] == '&'))
3122 string_prepend (&decl, "(");
3123 string_append (&decl, ")");
3125 string_append (&decl, "[");
3126 if (**mangled != '_')
3127 success = demangle_template_value_parm (work, mangled, &decl,
3128 tk_integral);
3129 if (**mangled == '_')
3130 ++(*mangled);
3131 string_append (&decl, "]");
3132 break;
3135 /* A back reference to a previously seen type */
3136 case 'T':
3137 (*mangled)++;
3138 if (!get_count (mangled, &n) || n >= work -> ntypes)
3140 success = 0;
3142 else
3144 remembered_type = work -> typevec[n];
3145 mangled = &remembered_type;
3147 break;
3149 /* A function */
3150 case 'F':
3151 (*mangled)++;
3152 if (!STRING_EMPTY (&decl)
3153 && (decl.b[0] == '*' || decl.b[0] == '&'))
3155 string_prepend (&decl, "(");
3156 string_append (&decl, ")");
3158 /* After picking off the function args, we expect to either find the
3159 function return type (preceded by an '_') or the end of the
3160 string. */
3161 if (!demangle_nested_args (work, mangled, &decl)
3162 || (**mangled != '_' && **mangled != '\0'))
3164 success = 0;
3165 break;
3167 if (success && (**mangled == '_'))
3168 (*mangled)++;
3169 break;
3171 case 'M':
3172 case 'O':
3174 type_quals = TYPE_UNQUALIFIED;
3176 member = **mangled == 'M';
3177 (*mangled)++;
3179 string_append (&decl, ")");
3181 /* We don't need to prepend `::' for a qualified name;
3182 demangle_qualified will do that for us. */
3183 if (**mangled != 'Q')
3184 string_prepend (&decl, SCOPE_STRING (work));
3186 if (isdigit ((unsigned char)**mangled))
3188 n = consume_count (mangled);
3189 if (n == -1
3190 || (int) strlen (*mangled) < n)
3192 success = 0;
3193 break;
3195 string_prependn (&decl, *mangled, n);
3196 *mangled += n;
3198 else if (**mangled == 'X' || **mangled == 'Y')
3200 string temp;
3201 do_type (work, mangled, &temp);
3202 string_prepends (&decl, &temp);
3204 else if (**mangled == 't')
3206 string temp;
3207 string_init (&temp);
3208 success = demangle_template (work, mangled, &temp,
3209 NULL, 1, 1);
3210 if (success)
3212 string_prependn (&decl, temp.b, temp.p - temp.b);
3213 string_clear (&temp);
3215 else
3216 break;
3218 else if (**mangled == 'Q')
3220 success = demangle_qualified (work, mangled, &decl,
3221 /*isfuncnam=*/0,
3222 /*append=*/0);
3223 if (!success)
3224 break;
3226 else
3228 success = 0;
3229 break;
3232 string_prepend (&decl, "(");
3233 if (member)
3235 switch (**mangled)
3237 case 'C':
3238 case 'V':
3239 case 'u':
3240 type_quals |= code_for_qualifier (**mangled);
3241 (*mangled)++;
3242 break;
3244 default:
3245 break;
3248 if (*(*mangled)++ != 'F')
3250 success = 0;
3251 break;
3254 if ((member && !demangle_nested_args (work, mangled, &decl))
3255 || **mangled != '_')
3257 success = 0;
3258 break;
3260 (*mangled)++;
3261 if (! PRINT_ANSI_QUALIFIERS)
3263 break;
3265 if (type_quals != TYPE_UNQUALIFIED)
3267 APPEND_BLANK (&decl);
3268 string_append (&decl, qualifier_string (type_quals));
3270 break;
3272 case 'G':
3273 (*mangled)++;
3274 break;
3276 case 'C':
3277 case 'V':
3278 case 'u':
3279 if (PRINT_ANSI_QUALIFIERS)
3281 if (!STRING_EMPTY (&decl))
3282 string_prepend (&decl, " ");
3284 string_prepend (&decl, demangle_qualifier (**mangled));
3286 (*mangled)++;
3287 break;
3292 /* fall through */
3293 default:
3294 done = 1;
3295 break;
3299 if (success) switch (**mangled)
3301 /* A qualified name, such as "Outer::Inner". */
3302 case 'Q':
3303 case 'K':
3305 success = demangle_qualified (work, mangled, result, 0, 1);
3306 break;
3309 /* A back reference to a previously seen squangled type */
3310 case 'B':
3311 (*mangled)++;
3312 if (!get_count (mangled, &n) || n >= work -> numb)
3313 success = 0;
3314 else
3315 string_append (result, work->btypevec[n]);
3316 break;
3318 case 'X':
3319 case 'Y':
3320 /* A template parm. We substitute the corresponding argument. */
3322 int idx;
3324 (*mangled)++;
3325 idx = consume_count_with_underscores (mangled);
3327 if (idx == -1
3328 || (work->tmpl_argvec && idx >= work->ntmpl_args)
3329 || consume_count_with_underscores (mangled) == -1)
3331 success = 0;
3332 break;
3335 if (work->tmpl_argvec)
3336 string_append (result, work->tmpl_argvec[idx]);
3337 else
3338 string_append_template_idx (result, idx);
3340 success = 1;
3342 break;
3344 default:
3345 success = demangle_fund_type (work, mangled, result);
3346 if (tk == tk_none)
3347 tk = (type_kind_t) success;
3348 break;
3351 if (success)
3353 if (!STRING_EMPTY (&decl))
3355 string_append (result, " ");
3356 string_appends (result, &decl);
3359 else
3360 string_delete (result);
3361 string_delete (&decl);
3363 if (success)
3364 /* Assume an integral type, if we're not sure. */
3365 return (int) ((tk == tk_none) ? tk_integral : tk);
3366 else
3367 return 0;
3370 /* Given a pointer to a type string that represents a fundamental type
3371 argument (int, long, unsigned int, etc) in TYPE, a pointer to the
3372 string in which the demangled output is being built in RESULT, and
3373 the WORK structure, decode the types and add them to the result.
3375 For example:
3377 "Ci" => "const int"
3378 "Sl" => "signed long"
3379 "CUs" => "const unsigned short"
3381 The value returned is really a type_kind_t. */
3383 static int
3384 demangle_fund_type (work, mangled, result)
3385 struct work_stuff *work;
3386 const char **mangled;
3387 string *result;
3389 int done = 0;
3390 int success = 1;
3391 char buf[10];
3392 int dec = 0;
3393 string btype;
3394 type_kind_t tk = tk_integral;
3396 string_init (&btype);
3398 /* First pick off any type qualifiers. There can be more than one. */
3400 while (!done)
3402 switch (**mangled)
3404 case 'C':
3405 case 'V':
3406 case 'u':
3407 if (PRINT_ANSI_QUALIFIERS)
3409 if (!STRING_EMPTY (result))
3410 string_prepend (result, " ");
3411 string_prepend (result, demangle_qualifier (**mangled));
3413 (*mangled)++;
3414 break;
3415 case 'U':
3416 (*mangled)++;
3417 APPEND_BLANK (result);
3418 string_append (result, "unsigned");
3419 break;
3420 case 'S': /* signed char only */
3421 (*mangled)++;
3422 APPEND_BLANK (result);
3423 string_append (result, "signed");
3424 break;
3425 case 'J':
3426 (*mangled)++;
3427 APPEND_BLANK (result);
3428 string_append (result, "__complex");
3429 break;
3430 default:
3431 done = 1;
3432 break;
3436 /* Now pick off the fundamental type. There can be only one. */
3438 switch (**mangled)
3440 case '\0':
3441 case '_':
3442 break;
3443 case 'v':
3444 (*mangled)++;
3445 APPEND_BLANK (result);
3446 string_append (result, "void");
3447 break;
3448 case 'x':
3449 (*mangled)++;
3450 APPEND_BLANK (result);
3451 string_append (result, "long long");
3452 break;
3453 case 'l':
3454 (*mangled)++;
3455 APPEND_BLANK (result);
3456 string_append (result, "long");
3457 break;
3458 case 'i':
3459 (*mangled)++;
3460 APPEND_BLANK (result);
3461 string_append (result, "int");
3462 break;
3463 case 's':
3464 (*mangled)++;
3465 APPEND_BLANK (result);
3466 string_append (result, "short");
3467 break;
3468 case 'b':
3469 (*mangled)++;
3470 APPEND_BLANK (result);
3471 string_append (result, "bool");
3472 tk = tk_bool;
3473 break;
3474 case 'c':
3475 (*mangled)++;
3476 APPEND_BLANK (result);
3477 string_append (result, "char");
3478 tk = tk_char;
3479 break;
3480 case 'w':
3481 (*mangled)++;
3482 APPEND_BLANK (result);
3483 string_append (result, "wchar_t");
3484 tk = tk_char;
3485 break;
3486 case 'r':
3487 (*mangled)++;
3488 APPEND_BLANK (result);
3489 string_append (result, "long double");
3490 tk = tk_real;
3491 break;
3492 case 'd':
3493 (*mangled)++;
3494 APPEND_BLANK (result);
3495 string_append (result, "double");
3496 tk = tk_real;
3497 break;
3498 case 'f':
3499 (*mangled)++;
3500 APPEND_BLANK (result);
3501 string_append (result, "float");
3502 tk = tk_real;
3503 break;
3504 case 'G':
3505 (*mangled)++;
3506 if (!isdigit ((unsigned char)**mangled))
3508 success = 0;
3509 break;
3511 case 'I':
3512 (*mangled)++;
3513 if (**mangled == '_')
3515 int i;
3516 (*mangled)++;
3517 for (i = 0;
3518 i < (long) sizeof (buf) - 1 && **mangled && **mangled != '_';
3519 (*mangled)++, i++)
3520 buf[i] = **mangled;
3521 if (**mangled != '_')
3523 success = 0;
3524 break;
3526 buf[i] = '\0';
3527 (*mangled)++;
3529 else
3531 strncpy (buf, *mangled, 2);
3532 buf[2] = '\0';
3533 *mangled += min (strlen (*mangled), 2);
3535 sscanf (buf, "%x", &dec);
3536 sprintf (buf, "int%i_t", dec);
3537 APPEND_BLANK (result);
3538 string_append (result, buf);
3539 break;
3541 /* fall through */
3542 /* An explicit type, such as "6mytype" or "7integer" */
3543 case '0':
3544 case '1':
3545 case '2':
3546 case '3':
3547 case '4':
3548 case '5':
3549 case '6':
3550 case '7':
3551 case '8':
3552 case '9':
3554 int bindex = register_Btype (work);
3555 string btype;
3556 string_init (&btype);
3557 if (demangle_class_name (work, mangled, &btype)) {
3558 remember_Btype (work, btype.b, LEN_STRING (&btype), bindex);
3559 APPEND_BLANK (result);
3560 string_appends (result, &btype);
3562 else
3563 success = 0;
3564 string_delete (&btype);
3565 break;
3567 case 't':
3569 success = demangle_template (work, mangled, &btype, 0, 1, 1);
3570 string_appends (result, &btype);
3571 break;
3573 default:
3574 success = 0;
3575 break;
3578 return success ? ((int) tk) : 0;
3582 /* Handle a template's value parameter for HP aCC (extension from ARM)
3583 **mangled points to 'S' or 'U' */
3585 static int
3586 do_hpacc_template_const_value (work, mangled, result)
3587 struct work_stuff *work ATTRIBUTE_UNUSED;
3588 const char **mangled;
3589 string *result;
3591 int unsigned_const;
3593 if (**mangled != 'U' && **mangled != 'S')
3594 return 0;
3596 unsigned_const = (**mangled == 'U');
3598 (*mangled)++;
3600 switch (**mangled)
3602 case 'N':
3603 string_append (result, "-");
3604 /* fall through */
3605 case 'P':
3606 (*mangled)++;
3607 break;
3608 case 'M':
3609 /* special case for -2^31 */
3610 string_append (result, "-2147483648");
3611 (*mangled)++;
3612 return 1;
3613 default:
3614 return 0;
3617 /* We have to be looking at an integer now */
3618 if (!(isdigit ((unsigned char)**mangled)))
3619 return 0;
3621 /* We only deal with integral values for template
3622 parameters -- so it's OK to look only for digits */
3623 while (isdigit ((unsigned char)**mangled))
3625 char_str[0] = **mangled;
3626 string_append (result, char_str);
3627 (*mangled)++;
3630 if (unsigned_const)
3631 string_append (result, "U");
3633 /* FIXME? Some day we may have 64-bit (or larger :-) ) constants
3634 with L or LL suffixes. pai/1997-09-03 */
3636 return 1; /* success */
3639 /* Handle a template's literal parameter for HP aCC (extension from ARM)
3640 **mangled is pointing to the 'A' */
3642 static int
3643 do_hpacc_template_literal (work, mangled, result)
3644 struct work_stuff *work;
3645 const char **mangled;
3646 string *result;
3648 int literal_len = 0;
3649 char * recurse;
3650 char * recurse_dem;
3652 if (**mangled != 'A')
3653 return 0;
3655 (*mangled)++;
3657 literal_len = consume_count (mangled);
3659 if (literal_len <= 0)
3660 return 0;
3662 /* Literal parameters are names of arrays, functions, etc. and the
3663 canonical representation uses the address operator */
3664 string_append (result, "&");
3666 /* Now recursively demangle the literal name */
3667 recurse = (char *) xmalloc (literal_len + 1);
3668 memcpy (recurse, *mangled, literal_len);
3669 recurse[literal_len] = '\000';
3671 recurse_dem = cplus_demangle (recurse, work->options);
3673 if (recurse_dem)
3675 string_append (result, recurse_dem);
3676 free (recurse_dem);
3678 else
3680 string_appendn (result, *mangled, literal_len);
3682 (*mangled) += literal_len;
3683 free (recurse);
3685 return 1;
3688 static int
3689 snarf_numeric_literal (args, arg)
3690 const char ** args;
3691 string * arg;
3693 if (**args == '-')
3695 char_str[0] = '-';
3696 string_append (arg, char_str);
3697 (*args)++;
3699 else if (**args == '+')
3700 (*args)++;
3702 if (!isdigit ((unsigned char)**args))
3703 return 0;
3705 while (isdigit ((unsigned char)**args))
3707 char_str[0] = **args;
3708 string_append (arg, char_str);
3709 (*args)++;
3712 return 1;
3715 /* Demangle the next argument, given by MANGLED into RESULT, which
3716 *should be an uninitialized* string. It will be initialized here,
3717 and free'd should anything go wrong. */
3719 static int
3720 do_arg (work, mangled, result)
3721 struct work_stuff *work;
3722 const char **mangled;
3723 string *result;
3725 /* Remember where we started so that we can record the type, for
3726 non-squangling type remembering. */
3727 const char *start = *mangled;
3729 string_init (result);
3731 if (work->nrepeats > 0)
3733 --work->nrepeats;
3735 if (work->previous_argument == 0)
3736 return 0;
3738 /* We want to reissue the previous type in this argument list. */
3739 string_appends (result, work->previous_argument);
3740 return 1;
3743 if (**mangled == 'n')
3745 /* A squangling-style repeat. */
3746 (*mangled)++;
3747 work->nrepeats = consume_count(mangled);
3749 if (work->nrepeats <= 0)
3750 /* This was not a repeat count after all. */
3751 return 0;
3753 if (work->nrepeats > 9)
3755 if (**mangled != '_')
3756 /* The repeat count should be followed by an '_' in this
3757 case. */
3758 return 0;
3759 else
3760 (*mangled)++;
3763 /* Now, the repeat is all set up. */
3764 return do_arg (work, mangled, result);
3767 /* Save the result in WORK->previous_argument so that we can find it
3768 if it's repeated. Note that saving START is not good enough: we
3769 do not want to add additional types to the back-referenceable
3770 type vector when processing a repeated type. */
3771 if (work->previous_argument)
3772 string_clear (work->previous_argument);
3773 else
3775 work->previous_argument = (string*) xmalloc (sizeof (string));
3776 string_init (work->previous_argument);
3779 if (!do_type (work, mangled, work->previous_argument))
3780 return 0;
3782 string_appends (result, work->previous_argument);
3784 remember_type (work, start, *mangled - start);
3785 return 1;
3788 static void
3789 remember_type (work, start, len)
3790 struct work_stuff *work;
3791 const char *start;
3792 int len;
3794 char *tem;
3796 if (work->forgetting_types)
3797 return;
3799 if (work -> ntypes >= work -> typevec_size)
3801 if (work -> typevec_size == 0)
3803 work -> typevec_size = 3;
3804 work -> typevec
3805 = (char **) xmalloc (sizeof (char *) * work -> typevec_size);
3807 else
3809 work -> typevec_size *= 2;
3810 work -> typevec
3811 = (char **) xrealloc ((char *)work -> typevec,
3812 sizeof (char *) * work -> typevec_size);
3815 tem = xmalloc (len + 1);
3816 memcpy (tem, start, len);
3817 tem[len] = '\0';
3818 work -> typevec[work -> ntypes++] = tem;
3822 /* Remember a K type class qualifier. */
3823 static void
3824 remember_Ktype (work, start, len)
3825 struct work_stuff *work;
3826 const char *start;
3827 int len;
3829 char *tem;
3831 if (work -> numk >= work -> ksize)
3833 if (work -> ksize == 0)
3835 work -> ksize = 5;
3836 work -> ktypevec
3837 = (char **) xmalloc (sizeof (char *) * work -> ksize);
3839 else
3841 work -> ksize *= 2;
3842 work -> ktypevec
3843 = (char **) xrealloc ((char *)work -> ktypevec,
3844 sizeof (char *) * work -> ksize);
3847 tem = xmalloc (len + 1);
3848 memcpy (tem, start, len);
3849 tem[len] = '\0';
3850 work -> ktypevec[work -> numk++] = tem;
3853 /* Register a B code, and get an index for it. B codes are registered
3854 as they are seen, rather than as they are completed, so map<temp<char> >
3855 registers map<temp<char> > as B0, and temp<char> as B1 */
3857 static int
3858 register_Btype (work)
3859 struct work_stuff *work;
3861 int ret;
3863 if (work -> numb >= work -> bsize)
3865 if (work -> bsize == 0)
3867 work -> bsize = 5;
3868 work -> btypevec
3869 = (char **) xmalloc (sizeof (char *) * work -> bsize);
3871 else
3873 work -> bsize *= 2;
3874 work -> btypevec
3875 = (char **) xrealloc ((char *)work -> btypevec,
3876 sizeof (char *) * work -> bsize);
3879 ret = work -> numb++;
3880 work -> btypevec[ret] = NULL;
3881 return(ret);
3884 /* Store a value into a previously registered B code type. */
3886 static void
3887 remember_Btype (work, start, len, index)
3888 struct work_stuff *work;
3889 const char *start;
3890 int len, index;
3892 char *tem;
3894 tem = xmalloc (len + 1);
3895 memcpy (tem, start, len);
3896 tem[len] = '\0';
3897 work -> btypevec[index] = tem;
3900 /* Lose all the info related to B and K type codes. */
3901 static void
3902 forget_B_and_K_types (work)
3903 struct work_stuff *work;
3905 int i;
3907 while (work -> numk > 0)
3909 i = --(work -> numk);
3910 if (work -> ktypevec[i] != NULL)
3912 free (work -> ktypevec[i]);
3913 work -> ktypevec[i] = NULL;
3917 while (work -> numb > 0)
3919 i = --(work -> numb);
3920 if (work -> btypevec[i] != NULL)
3922 free (work -> btypevec[i]);
3923 work -> btypevec[i] = NULL;
3927 /* Forget the remembered types, but not the type vector itself. */
3929 static void
3930 forget_types (work)
3931 struct work_stuff *work;
3933 int i;
3935 while (work -> ntypes > 0)
3937 i = --(work -> ntypes);
3938 if (work -> typevec[i] != NULL)
3940 free (work -> typevec[i]);
3941 work -> typevec[i] = NULL;
3946 /* Process the argument list part of the signature, after any class spec
3947 has been consumed, as well as the first 'F' character (if any). For
3948 example:
3950 "__als__3fooRT0" => process "RT0"
3951 "complexfunc5__FPFPc_PFl_i" => process "PFPc_PFl_i"
3953 DECLP must be already initialised, usually non-empty. It won't be freed
3954 on failure.
3956 Note that g++ differs significantly from ARM and lucid style mangling
3957 with regards to references to previously seen types. For example, given
3958 the source fragment:
3960 class foo {
3961 public:
3962 foo::foo (int, foo &ia, int, foo &ib, int, foo &ic);
3965 foo::foo (int, foo &ia, int, foo &ib, int, foo &ic) { ia = ib = ic; }
3966 void foo (int, foo &ia, int, foo &ib, int, foo &ic) { ia = ib = ic; }
3968 g++ produces the names:
3970 __3fooiRT0iT2iT2
3971 foo__FiR3fooiT1iT1
3973 while lcc (and presumably other ARM style compilers as well) produces:
3975 foo__FiR3fooT1T2T1T2
3976 __ct__3fooFiR3fooT1T2T1T2
3978 Note that g++ bases its type numbers starting at zero and counts all
3979 previously seen types, while lucid/ARM bases its type numbers starting
3980 at one and only considers types after it has seen the 'F' character
3981 indicating the start of the function args. For lucid/ARM style, we
3982 account for this difference by discarding any previously seen types when
3983 we see the 'F' character, and subtracting one from the type number
3984 reference.
3988 static int
3989 demangle_args (work, mangled, declp)
3990 struct work_stuff *work;
3991 const char **mangled;
3992 string *declp;
3994 string arg;
3995 int need_comma = 0;
3996 int r;
3997 int t;
3998 const char *tem;
3999 char temptype;
4001 if (PRINT_ARG_TYPES)
4003 string_append (declp, "(");
4004 if (**mangled == '\0')
4006 string_append (declp, "void");
4010 while ((**mangled != '_' && **mangled != '\0' && **mangled != 'e')
4011 || work->nrepeats > 0)
4013 if ((**mangled == 'N') || (**mangled == 'T'))
4015 temptype = *(*mangled)++;
4017 if (temptype == 'N')
4019 if (!get_count (mangled, &r))
4021 return (0);
4024 else
4026 r = 1;
4028 if ((HP_DEMANGLING || ARM_DEMANGLING || EDG_DEMANGLING) && work -> ntypes >= 10)
4030 /* If we have 10 or more types we might have more than a 1 digit
4031 index so we'll have to consume the whole count here. This
4032 will lose if the next thing is a type name preceded by a
4033 count but it's impossible to demangle that case properly
4034 anyway. Eg if we already have 12 types is T12Pc "(..., type1,
4035 Pc, ...)" or "(..., type12, char *, ...)" */
4036 if ((t = consume_count(mangled)) <= 0)
4038 return (0);
4041 else
4043 if (!get_count (mangled, &t))
4045 return (0);
4048 if (LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
4050 t--;
4052 /* Validate the type index. Protect against illegal indices from
4053 malformed type strings. */
4054 if ((t < 0) || (t >= work -> ntypes))
4056 return (0);
4058 while (work->nrepeats > 0 || --r >= 0)
4060 tem = work -> typevec[t];
4061 if (need_comma && PRINT_ARG_TYPES)
4063 string_append (declp, ", ");
4065 if (!do_arg (work, &tem, &arg))
4067 return (0);
4069 if (PRINT_ARG_TYPES)
4071 string_appends (declp, &arg);
4073 string_delete (&arg);
4074 need_comma = 1;
4077 else
4079 if (need_comma && PRINT_ARG_TYPES)
4080 string_append (declp, ", ");
4081 if (!do_arg (work, mangled, &arg))
4082 return (0);
4083 if (PRINT_ARG_TYPES)
4084 string_appends (declp, &arg);
4085 string_delete (&arg);
4086 need_comma = 1;
4090 if (**mangled == 'e')
4092 (*mangled)++;
4093 if (PRINT_ARG_TYPES)
4095 if (need_comma)
4097 string_append (declp, ",");
4099 string_append (declp, "...");
4103 if (PRINT_ARG_TYPES)
4105 string_append (declp, ")");
4107 return (1);
4110 /* Like demangle_args, but for demangling the argument lists of function
4111 and method pointers or references, not top-level declarations. */
4113 static int
4114 demangle_nested_args (work, mangled, declp)
4115 struct work_stuff *work;
4116 const char **mangled;
4117 string *declp;
4119 string* saved_previous_argument;
4120 int result;
4121 int saved_nrepeats;
4123 /* The G++ name-mangling algorithm does not remember types on nested
4124 argument lists, unless -fsquangling is used, and in that case the
4125 type vector updated by remember_type is not used. So, we turn
4126 off remembering of types here. */
4127 ++work->forgetting_types;
4129 /* For the repeat codes used with -fsquangling, we must keep track of
4130 the last argument. */
4131 saved_previous_argument = work->previous_argument;
4132 saved_nrepeats = work->nrepeats;
4133 work->previous_argument = 0;
4134 work->nrepeats = 0;
4136 /* Actually demangle the arguments. */
4137 result = demangle_args (work, mangled, declp);
4139 /* Restore the previous_argument field. */
4140 if (work->previous_argument)
4141 string_delete (work->previous_argument);
4142 work->previous_argument = saved_previous_argument;
4143 --work->forgetting_types;
4144 work->nrepeats = saved_nrepeats;
4146 return result;
4149 static void
4150 demangle_function_name (work, mangled, declp, scan)
4151 struct work_stuff *work;
4152 const char **mangled;
4153 string *declp;
4154 const char *scan;
4156 size_t i;
4157 string type;
4158 const char *tem;
4160 string_appendn (declp, (*mangled), scan - (*mangled));
4161 string_need (declp, 1);
4162 *(declp -> p) = '\0';
4164 /* Consume the function name, including the "__" separating the name
4165 from the signature. We are guaranteed that SCAN points to the
4166 separator. */
4168 (*mangled) = scan + 2;
4169 /* We may be looking at an instantiation of a template function:
4170 foo__Xt1t2_Ft3t4, where t1, t2, ... are template arguments and a
4171 following _F marks the start of the function arguments. Handle
4172 the template arguments first. */
4174 if (HP_DEMANGLING && (**mangled == 'X'))
4176 demangle_arm_hp_template (work, mangled, 0, declp);
4177 /* This leaves MANGLED pointing to the 'F' marking func args */
4180 if (LUCID_DEMANGLING || ARM_DEMANGLING || HP_DEMANGLING || EDG_DEMANGLING)
4183 /* See if we have an ARM style constructor or destructor operator.
4184 If so, then just record it, clear the decl, and return.
4185 We can't build the actual constructor/destructor decl until later,
4186 when we recover the class name from the signature. */
4188 if (strcmp (declp -> b, "__ct") == 0)
4190 work -> constructor += 1;
4191 string_clear (declp);
4192 return;
4194 else if (strcmp (declp -> b, "__dt") == 0)
4196 work -> destructor += 1;
4197 string_clear (declp);
4198 return;
4202 if (declp->p - declp->b >= 3
4203 && declp->b[0] == 'o'
4204 && declp->b[1] == 'p'
4205 && strchr (cplus_markers, declp->b[2]) != NULL)
4207 /* see if it's an assignment expression */
4208 if (declp->p - declp->b >= 10 /* op$assign_ */
4209 && memcmp (declp->b + 3, "assign_", 7) == 0)
4211 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
4213 int len = declp->p - declp->b - 10;
4214 if ((int) strlen (optable[i].in) == len
4215 && memcmp (optable[i].in, declp->b + 10, len) == 0)
4217 string_clear (declp);
4218 string_append (declp, "operator");
4219 string_append (declp, optable[i].out);
4220 string_append (declp, "=");
4221 break;
4225 else
4227 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
4229 int len = declp->p - declp->b - 3;
4230 if ((int) strlen (optable[i].in) == len
4231 && memcmp (optable[i].in, declp->b + 3, len) == 0)
4233 string_clear (declp);
4234 string_append (declp, "operator");
4235 string_append (declp, optable[i].out);
4236 break;
4241 else if (declp->p - declp->b >= 5 && memcmp (declp->b, "type", 4) == 0
4242 && strchr (cplus_markers, declp->b[4]) != NULL)
4244 /* type conversion operator */
4245 tem = declp->b + 5;
4246 if (do_type (work, &tem, &type))
4248 string_clear (declp);
4249 string_append (declp, "operator ");
4250 string_appends (declp, &type);
4251 string_delete (&type);
4254 else if (declp->b[0] == '_' && declp->b[1] == '_'
4255 && declp->b[2] == 'o' && declp->b[3] == 'p')
4257 /* ANSI. */
4258 /* type conversion operator. */
4259 tem = declp->b + 4;
4260 if (do_type (work, &tem, &type))
4262 string_clear (declp);
4263 string_append (declp, "operator ");
4264 string_appends (declp, &type);
4265 string_delete (&type);
4268 else if (declp->b[0] == '_' && declp->b[1] == '_'
4269 && islower(declp->b[2])
4270 && islower(declp->b[3]))
4272 if (declp->b[4] == '\0')
4274 /* Operator. */
4275 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
4277 if (strlen (optable[i].in) == 2
4278 && memcmp (optable[i].in, declp->b + 2, 2) == 0)
4280 string_clear (declp);
4281 string_append (declp, "operator");
4282 string_append (declp, optable[i].out);
4283 break;
4287 else
4289 if (declp->b[2] == 'a' && declp->b[5] == '\0')
4291 /* Assignment. */
4292 for (i = 0; i < sizeof (optable) / sizeof (optable[0]); i++)
4294 if (strlen (optable[i].in) == 3
4295 && memcmp (optable[i].in, declp->b + 2, 3) == 0)
4297 string_clear (declp);
4298 string_append (declp, "operator");
4299 string_append (declp, optable[i].out);
4300 break;
4308 /* a mini string-handling package */
4310 static void
4311 string_need (s, n)
4312 string *s;
4313 int n;
4315 int tem;
4317 if (s->b == NULL)
4319 if (n < 32)
4321 n = 32;
4323 s->p = s->b = xmalloc (n);
4324 s->e = s->b + n;
4326 else if (s->e - s->p < n)
4328 tem = s->p - s->b;
4329 n += tem;
4330 n *= 2;
4331 s->b = xrealloc (s->b, n);
4332 s->p = s->b + tem;
4333 s->e = s->b + n;
4337 static void
4338 string_delete (s)
4339 string *s;
4341 if (s->b != NULL)
4343 free (s->b);
4344 s->b = s->e = s->p = NULL;
4348 static void
4349 string_init (s)
4350 string *s;
4352 s->b = s->p = s->e = NULL;
4355 static void
4356 string_clear (s)
4357 string *s;
4359 s->p = s->b;
4362 #if 0
4364 static int
4365 string_empty (s)
4366 string *s;
4368 return (s->b == s->p);
4371 #endif
4373 static void
4374 string_append (p, s)
4375 string *p;
4376 const char *s;
4378 int n;
4379 if (s == NULL || *s == '\0')
4380 return;
4381 n = strlen (s);
4382 string_need (p, n);
4383 memcpy (p->p, s, n);
4384 p->p += n;
4387 static void
4388 string_appends (p, s)
4389 string *p, *s;
4391 int n;
4393 if (s->b != s->p)
4395 n = s->p - s->b;
4396 string_need (p, n);
4397 memcpy (p->p, s->b, n);
4398 p->p += n;
4402 static void
4403 string_appendn (p, s, n)
4404 string *p;
4405 const char *s;
4406 int n;
4408 if (n != 0)
4410 string_need (p, n);
4411 memcpy (p->p, s, n);
4412 p->p += n;
4416 static void
4417 string_prepend (p, s)
4418 string *p;
4419 const char *s;
4421 if (s != NULL && *s != '\0')
4423 string_prependn (p, s, strlen (s));
4427 static void
4428 string_prepends (p, s)
4429 string *p, *s;
4431 if (s->b != s->p)
4433 string_prependn (p, s->b, s->p - s->b);
4437 static void
4438 string_prependn (p, s, n)
4439 string *p;
4440 const char *s;
4441 int n;
4443 char *q;
4445 if (n != 0)
4447 string_need (p, n);
4448 for (q = p->p - 1; q >= p->b; q--)
4450 q[n] = q[0];
4452 memcpy (p->b, s, n);
4453 p->p += n;
4457 static void
4458 string_append_template_idx (s, idx)
4459 string *s;
4460 int idx;
4462 char buf[INTBUF_SIZE + 1 /* 'T' */];
4463 sprintf(buf, "T%d", idx);
4464 string_append (s, buf);
4467 /* To generate a standalone demangler program for testing purposes,
4468 just compile and link this file with -DMAIN and libiberty.a. When
4469 run, it demangles each command line arg, or each stdin string, and
4470 prints the result on stdout. */
4472 #ifdef MAIN
4474 #include "getopt.h"
4476 static const char *program_name;
4477 static const char *program_version = VERSION;
4478 static int flags = DMGL_PARAMS | DMGL_ANSI;
4480 static void demangle_it PARAMS ((char *));
4481 static void usage PARAMS ((FILE *, int)) ATTRIBUTE_NORETURN;
4482 static void fatal PARAMS ((const char *)) ATTRIBUTE_NORETURN;
4484 static void
4485 demangle_it (mangled_name)
4486 char *mangled_name;
4488 char *result;
4490 result = cplus_demangle (mangled_name, flags);
4491 if (result == NULL)
4493 printf ("%s\n", mangled_name);
4495 else
4497 printf ("%s\n", result);
4498 free (result);
4502 static void
4503 print_demangler_list (stream)
4504 FILE *stream;
4506 struct demangler_engine *demangler;
4508 fprintf (stream, "{%s", libiberty_demanglers->demangling_style_name);
4510 for (demangler = libiberty_demanglers + 1;
4511 demangler->demangling_style != unknown_demangling;
4512 ++demangler)
4513 fprintf (stream, ",%s", demangler->demangling_style_name);
4515 fprintf (stream, "}");
4518 static void
4519 usage (stream, status)
4520 FILE *stream;
4521 int status;
4523 fprintf (stream, "\
4524 Usage: %s [-_] [-n] [--strip-underscores] [--no-strip-underscores] \n",
4525 program_name);
4527 fprintf (stream, "\
4528 [-s ");
4529 print_demangler_list (stream);
4530 fprintf (stream, "]\n");
4532 fprintf (stream, "\
4533 [--format ");
4534 print_demangler_list (stream);
4535 fprintf (stream, "]\n");
4537 fprintf (stream, "\
4538 [--help] [--version] [arg...]\n");
4539 exit (status);
4542 #define MBUF_SIZE 32767
4543 char mbuffer[MBUF_SIZE];
4545 /* Defined in the automatically-generated underscore.c. */
4546 extern int prepends_underscore;
4548 int strip_underscore = 0;
4550 static struct option long_options[] = {
4551 {"strip-underscores", no_argument, 0, '_'},
4552 {"format", required_argument, 0, 's'},
4553 {"help", no_argument, 0, 'h'},
4554 {"java", no_argument, 0, 'j'},
4555 {"no-strip-underscores", no_argument, 0, 'n'},
4556 {"version", no_argument, 0, 'v'},
4557 {0, no_argument, 0, 0}
4560 /* More 'friendly' abort that prints the line and file.
4561 config.h can #define abort fancy_abort if you like that sort of thing. */
4563 void
4564 fancy_abort ()
4566 fatal ("Internal gcc abort.");
4570 static const char *
4571 standard_symbol_characters PARAMS ((void));
4573 static const char *
4574 hp_symbol_characters PARAMS ((void));
4576 /* Return the string of non-alnum characters that may occur
4577 as a valid symbol component, in the standard assembler symbol
4578 syntax. */
4580 static const char *
4581 standard_symbol_characters ()
4583 return "_$.";
4587 /* Return the string of non-alnum characters that may occur
4588 as a valid symbol name component in an HP object file.
4590 Note that, since HP's compiler generates object code straight from
4591 C++ source, without going through an assembler, its mangled
4592 identifiers can use all sorts of characters that no assembler would
4593 tolerate, so the alphabet this function creates is a little odd.
4594 Here are some sample mangled identifiers offered by HP:
4596 typeid*__XT24AddressIndExpClassMember_
4597 [Vftptr]key:__dt__32OrdinaryCompareIndExpClassMemberFv
4598 __ct__Q2_9Elf64_Dyn18{unnamed.union.#1}Fv
4600 This still seems really weird to me, since nowhere else in this
4601 file is there anything to recognize curly brackets, parens, etc.
4602 I've talked with Srikanth <srikanth@cup.hp.com>, and he assures me
4603 this is right, but I still strongly suspect that there's a
4604 misunderstanding here.
4606 If we decide it's better for c++filt to use HP's assembler syntax
4607 to scrape identifiers out of its input, here's the definition of
4608 the symbol name syntax from the HP assembler manual:
4610 Symbols are composed of uppercase and lowercase letters, decimal
4611 digits, dollar symbol, period (.), ampersand (&), pound sign(#) and
4612 underscore (_). A symbol can begin with a letter, digit underscore or
4613 dollar sign. If a symbol begins with a digit, it must contain a
4614 non-digit character.
4616 So have fun. */
4617 static const char *
4618 hp_symbol_characters ()
4620 return "_$.<>#,*&[]:(){}";
4624 extern int main PARAMS ((int, char **));
4627 main (argc, argv)
4628 int argc;
4629 char **argv;
4631 char *result;
4632 int c;
4633 const char *valid_symbols;
4635 program_name = argv[0];
4637 strip_underscore = prepends_underscore;
4639 while ((c = getopt_long (argc, argv, "_ns:j", long_options, (int *) 0)) != EOF)
4641 switch (c)
4643 case '?':
4644 usage (stderr, 1);
4645 break;
4646 case 'h':
4647 usage (stdout, 0);
4648 case 'n':
4649 strip_underscore = 0;
4650 break;
4651 case 'v':
4652 printf ("GNU %s (C++ demangler), version %s\n", program_name, program_version);
4653 return (0);
4654 case '_':
4655 strip_underscore = 1;
4656 break;
4657 case 'j':
4658 flags |= DMGL_JAVA;
4659 break;
4660 case 's':
4662 enum demangling_styles style;
4664 style = cplus_demangle_name_to_style (optarg);
4665 if (style == unknown_demangling)
4667 fprintf (stderr, "%s: unknown demangling style `%s'\n",
4668 program_name, optarg);
4669 return (1);
4671 else
4672 cplus_demangle_set_style (style);
4674 break;
4678 if (optind < argc)
4680 for ( ; optind < argc; optind++)
4682 demangle_it (argv[optind]);
4685 else
4687 switch (current_demangling_style)
4689 case gnu_demangling:
4690 case lucid_demangling:
4691 case arm_demangling:
4692 case edg_demangling:
4693 valid_symbols = standard_symbol_characters ();
4694 break;
4695 case hp_demangling:
4696 valid_symbols = hp_symbol_characters ();
4697 break;
4698 default:
4699 /* Folks should explicitly indicate the appropriate alphabet for
4700 each demangling. Providing a default would allow the
4701 question to go unconsidered. */
4702 abort ();
4705 for (;;)
4707 int i = 0;
4708 c = getchar ();
4709 /* Try to read a label. */
4710 while (c != EOF && (isalnum (c) || strchr (valid_symbols, c)))
4712 if (i >= MBUF_SIZE-1)
4713 break;
4714 mbuffer[i++] = c;
4715 c = getchar ();
4717 if (i > 0)
4719 int skip_first = 0;
4721 if (mbuffer[0] == '.')
4722 ++skip_first;
4723 if (strip_underscore && mbuffer[skip_first] == '_')
4724 ++skip_first;
4726 if (skip_first > i)
4727 skip_first = i;
4729 mbuffer[i] = 0;
4731 result = cplus_demangle (mbuffer + skip_first, flags);
4732 if (result)
4734 if (mbuffer[0] == '.')
4735 putc ('.', stdout);
4736 fputs (result, stdout);
4737 free (result);
4739 else
4740 fputs (mbuffer, stdout);
4742 fflush (stdout);
4744 if (c == EOF)
4745 break;
4746 putchar (c);
4750 return (0);
4753 static void
4754 fatal (str)
4755 const char *str;
4757 fprintf (stderr, "%s: %s\n", program_name, str);
4758 exit (1);
4762 xmalloc (size)
4763 size_t size;
4765 register PTR value = (PTR) malloc (size);
4766 if (value == 0)
4767 fatal ("virtual memory exhausted");
4768 return value;
4772 xrealloc (ptr, size)
4773 PTR ptr;
4774 size_t size;
4776 register PTR value = (PTR) realloc (ptr, size);
4777 if (value == 0)
4778 fatal ("virtual memory exhausted");
4779 return value;
4781 #endif /* main */