1 /* Demangler for GNU C++
2 Copyright 1989, 1991, 1994, 1995, 1996, 1997, 1998, 1999,
3 2000, 2001, 2002, 2003, 2004, 2010 Free Software Foundation, Inc.
4 Written by James Clark (jjc@jclark.uucp)
5 Rewritten by Fred Fish (fnf@cygnus.com) for ARM and Lucid demangling
6 Modified by Satish Pai (pai@apollo.hp.com) for HP demangling
8 This file is part of the libiberty library.
9 Libiberty is free software; you can redistribute it and/or
10 modify it under the terms of the GNU Library General Public
11 License as published by the Free Software Foundation; either
12 version 2 of the License, or (at your option) any later version.
14 In addition to the permissions in the GNU Library General Public
15 License, the Free Software Foundation gives you unlimited permission
16 to link the compiled version of this file into combinations with other
17 programs, and to distribute those combinations without any restriction
18 coming from the use of this file. (The Library Public License
19 restrictions do apply in other respects; for example, they cover
20 modification of the file, and distribution when not linked into a
23 Libiberty is distributed in the hope that it will be useful,
24 but WITHOUT ANY WARRANTY; without even the implied warranty of
25 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
26 Library General Public License for more details.
28 You should have received a copy of the GNU Library General Public
29 License along with libiberty; see the file COPYING.LIB. If
30 not, write to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
31 Boston, MA 02110-1301, USA. */
33 /* This file exports two functions; cplus_mangle_opname and cplus_demangle.
35 This file imports xmalloc and xrealloc, which are like malloc and
36 realloc except that they generate a fatal error if there is no
39 /* This file lives in both GCC and libiberty. When making changes, please
40 try not to break either. */
46 #include "safe-ctype.h"
48 #include <sys/types.h>
60 #undef CURRENT_DEMANGLING_STYLE
61 #define CURRENT_DEMANGLING_STYLE work->options
63 #include "libiberty.h"
65 #define min(X,Y) (((X) < (Y)) ? (X) : (Y))
67 /* A value at least one greater than the maximum number of characters
68 that will be output when using the `%d' format with `printf'. */
69 #define INTBUF_SIZE 32
71 extern void fancy_abort (void) ATTRIBUTE_NORETURN
;
73 /* In order to allow a single demangler executable to demangle strings
74 using various common values of CPLUS_MARKER, as well as any specific
75 one set at compile time, we maintain a string containing all the
76 commonly used ones, and check to see if the marker we are looking for
77 is in that string. CPLUS_MARKER is usually '$' on systems where the
78 assembler can deal with that. Where the assembler can't, it's usually
79 '.' (but on many systems '.' is used for other things). We put the
80 current defined CPLUS_MARKER first (which defaults to '$'), followed
81 by the next most common value, followed by an explicit '$' in case
82 the value of CPLUS_MARKER is not '$'.
84 We could avoid this if we could just get g++ to tell us what the actual
85 cplus marker character is as part of the debug information, perhaps by
86 ensuring that it is the character that terminates the gcc<n>_compiled
87 marker symbol (FIXME). */
89 #if !defined (CPLUS_MARKER)
90 #define CPLUS_MARKER '$'
93 enum demangling_styles current_demangling_style
= auto_demangling
;
95 static char cplus_markers
[] = { CPLUS_MARKER
, '.', '$', '\0' };
97 static char char_str
[2] = { '\000', '\000' };
100 set_cplus_marker_for_demangling (int ch
)
102 cplus_markers
[0] = ch
;
105 typedef struct string
/* Beware: these aren't required to be */
106 { /* '\0' terminated. */
107 char *b
; /* pointer to start of string */
108 char *p
; /* pointer after last character */
109 char *e
; /* pointer after end of allocated space */
112 /* Stuff that is shared between sub-routines.
113 Using a shared structure allows cplus_demangle to be reentrant. */
129 int static_type
; /* A static member function */
130 int temp_start
; /* index in demangled to start of template args */
131 int type_quals
; /* The type qualifiers. */
132 int dllimported
; /* Symbol imported from a PE DLL */
133 char **tmpl_argvec
; /* Template function arguments. */
134 int ntmpl_args
; /* The number of template function arguments. */
135 int forgetting_types
; /* Nonzero if we are not remembering the types
137 string
* previous_argument
; /* The last function argument demangled. */
138 int nrepeats
; /* The number of times to repeat the previous
142 #define PRINT_ANSI_QUALIFIERS (work -> options & DMGL_ANSI)
143 #define PRINT_ARG_TYPES (work -> options & DMGL_PARAMS)
145 static const struct optable
147 const char *const in
;
148 const char *const out
;
151 {"nw", " new", DMGL_ANSI
}, /* new (1.92, ansi) */
152 {"dl", " delete", DMGL_ANSI
}, /* new (1.92, ansi) */
153 {"new", " new", 0}, /* old (1.91, and 1.x) */
154 {"delete", " delete", 0}, /* old (1.91, and 1.x) */
155 {"vn", " new []", DMGL_ANSI
}, /* GNU, pending ansi */
156 {"vd", " delete []", DMGL_ANSI
}, /* GNU, pending ansi */
157 {"as", "=", DMGL_ANSI
}, /* ansi */
158 {"ne", "!=", DMGL_ANSI
}, /* old, ansi */
159 {"eq", "==", DMGL_ANSI
}, /* old, ansi */
160 {"ge", ">=", DMGL_ANSI
}, /* old, ansi */
161 {"gt", ">", DMGL_ANSI
}, /* old, ansi */
162 {"le", "<=", DMGL_ANSI
}, /* old, ansi */
163 {"lt", "<", DMGL_ANSI
}, /* old, ansi */
164 {"plus", "+", 0}, /* old */
165 {"pl", "+", DMGL_ANSI
}, /* ansi */
166 {"apl", "+=", DMGL_ANSI
}, /* ansi */
167 {"minus", "-", 0}, /* old */
168 {"mi", "-", DMGL_ANSI
}, /* ansi */
169 {"ami", "-=", DMGL_ANSI
}, /* ansi */
170 {"mult", "*", 0}, /* old */
171 {"ml", "*", DMGL_ANSI
}, /* ansi */
172 {"amu", "*=", DMGL_ANSI
}, /* ansi (ARM/Lucid) */
173 {"aml", "*=", DMGL_ANSI
}, /* ansi (GNU/g++) */
174 {"convert", "+", 0}, /* old (unary +) */
175 {"negate", "-", 0}, /* old (unary -) */
176 {"trunc_mod", "%", 0}, /* old */
177 {"md", "%", DMGL_ANSI
}, /* ansi */
178 {"amd", "%=", DMGL_ANSI
}, /* ansi */
179 {"trunc_div", "/", 0}, /* old */
180 {"dv", "/", DMGL_ANSI
}, /* ansi */
181 {"adv", "/=", DMGL_ANSI
}, /* ansi */
182 {"truth_andif", "&&", 0}, /* old */
183 {"aa", "&&", DMGL_ANSI
}, /* ansi */
184 {"truth_orif", "||", 0}, /* old */
185 {"oo", "||", DMGL_ANSI
}, /* ansi */
186 {"truth_not", "!", 0}, /* old */
187 {"nt", "!", DMGL_ANSI
}, /* ansi */
188 {"postincrement","++", 0}, /* old */
189 {"pp", "++", DMGL_ANSI
}, /* ansi */
190 {"postdecrement","--", 0}, /* old */
191 {"mm", "--", DMGL_ANSI
}, /* ansi */
192 {"bit_ior", "|", 0}, /* old */
193 {"or", "|", DMGL_ANSI
}, /* ansi */
194 {"aor", "|=", DMGL_ANSI
}, /* ansi */
195 {"bit_xor", "^", 0}, /* old */
196 {"er", "^", DMGL_ANSI
}, /* ansi */
197 {"aer", "^=", DMGL_ANSI
}, /* ansi */
198 {"bit_and", "&", 0}, /* old */
199 {"ad", "&", DMGL_ANSI
}, /* ansi */
200 {"aad", "&=", DMGL_ANSI
}, /* ansi */
201 {"bit_not", "~", 0}, /* old */
202 {"co", "~", DMGL_ANSI
}, /* ansi */
203 {"call", "()", 0}, /* old */
204 {"cl", "()", DMGL_ANSI
}, /* ansi */
205 {"alshift", "<<", 0}, /* old */
206 {"ls", "<<", DMGL_ANSI
}, /* ansi */
207 {"als", "<<=", DMGL_ANSI
}, /* ansi */
208 {"arshift", ">>", 0}, /* old */
209 {"rs", ">>", DMGL_ANSI
}, /* ansi */
210 {"ars", ">>=", DMGL_ANSI
}, /* ansi */
211 {"component", "->", 0}, /* old */
212 {"pt", "->", DMGL_ANSI
}, /* ansi; Lucid C++ form */
213 {"rf", "->", DMGL_ANSI
}, /* ansi; ARM/GNU form */
214 {"indirect", "*", 0}, /* old */
215 {"method_call", "->()", 0}, /* old */
216 {"addr", "&", 0}, /* old (unary &) */
217 {"array", "[]", 0}, /* old */
218 {"vc", "[]", DMGL_ANSI
}, /* ansi */
219 {"compound", ", ", 0}, /* old */
220 {"cm", ", ", DMGL_ANSI
}, /* ansi */
221 {"cond", "?:", 0}, /* old */
222 {"cn", "?:", DMGL_ANSI
}, /* pseudo-ansi */
223 {"max", ">?", 0}, /* old */
224 {"mx", ">?", DMGL_ANSI
}, /* pseudo-ansi */
225 {"min", "<?", 0}, /* old */
226 {"mn", "<?", DMGL_ANSI
}, /* pseudo-ansi */
227 {"nop", "", 0}, /* old (for operator=) */
228 {"rm", "->*", DMGL_ANSI
}, /* ansi */
229 {"sz", "sizeof ", DMGL_ANSI
} /* pseudo-ansi */
232 /* These values are used to indicate the various type varieties.
233 They are all non-zero so that they can be used as `success'
235 typedef enum type_kind_t
246 const struct demangler_engine libiberty_demanglers
[] =
249 NO_DEMANGLING_STYLE_STRING
,
251 "Demangling disabled"
255 AUTO_DEMANGLING_STYLE_STRING
,
257 "Automatic selection based on executable"
261 GNU_DEMANGLING_STYLE_STRING
,
263 "GNU (g++) style demangling"
267 LUCID_DEMANGLING_STYLE_STRING
,
269 "Lucid (lcc) style demangling"
273 ARM_DEMANGLING_STYLE_STRING
,
275 "ARM style demangling"
279 HP_DEMANGLING_STYLE_STRING
,
281 "HP (aCC) style demangling"
285 EDG_DEMANGLING_STYLE_STRING
,
287 "EDG style demangling"
291 GNU_V3_DEMANGLING_STYLE_STRING
,
293 "GNU (g++) V3 ABI-style demangling"
297 JAVA_DEMANGLING_STYLE_STRING
,
299 "Java style demangling"
303 GNAT_DEMANGLING_STYLE_STRING
,
305 "GNAT style demangling"
309 NULL
, unknown_demangling
, NULL
313 #define STRING_EMPTY(str) ((str) -> b == (str) -> p)
314 #define APPEND_BLANK(str) {if (!STRING_EMPTY(str)) \
315 string_append(str, " ");}
316 #define LEN_STRING(str) ( (STRING_EMPTY(str))?0:((str)->p - (str)->b))
318 /* The scope separator appropriate for the language being demangled. */
320 #define SCOPE_STRING(work) ((work->options & DMGL_JAVA) ? "." : "::")
322 #define ARM_VTABLE_STRING "__vtbl__" /* Lucid/ARM virtual table prefix */
323 #define ARM_VTABLE_STRLEN 8 /* strlen (ARM_VTABLE_STRING) */
325 /* Prototypes for local functions */
327 static void delete_work_stuff (struct work_stuff
*);
329 static void delete_non_B_K_work_stuff (struct work_stuff
*);
331 static char *mop_up (struct work_stuff
*, string
*, int);
333 static void squangle_mop_up (struct work_stuff
*);
335 static void work_stuff_copy_to_from (struct work_stuff
*, struct work_stuff
*);
339 demangle_method_args (struct work_stuff
*, const char **, string
*);
343 internal_cplus_demangle (struct work_stuff
*, const char *);
346 demangle_template_template_parm (struct work_stuff
*work
,
347 const char **, string
*);
350 demangle_template (struct work_stuff
*work
, const char **, string
*,
354 arm_pt (struct work_stuff
*, const char *, int, const char **,
358 demangle_class_name (struct work_stuff
*, const char **, string
*);
361 demangle_qualified (struct work_stuff
*, const char **, string
*,
364 static int demangle_class (struct work_stuff
*, const char **, string
*);
366 static int demangle_fund_type (struct work_stuff
*, const char **, string
*);
368 static int demangle_signature (struct work_stuff
*, const char **, string
*);
370 static int demangle_prefix (struct work_stuff
*, const char **, string
*);
372 static int gnu_special (struct work_stuff
*, const char **, string
*);
374 static int arm_special (const char **, string
*);
376 static void string_need (string
*, int);
378 static void string_delete (string
*);
381 string_init (string
*);
383 static void string_clear (string
*);
386 static int string_empty (string
*);
389 static void string_append (string
*, const char *);
391 static void string_appends (string
*, string
*);
393 static void string_appendn (string
*, const char *, int);
395 static void string_prepend (string
*, const char *);
397 static void string_prependn (string
*, const char *, int);
399 static void string_append_template_idx (string
*, int);
401 static int get_count (const char **, int *);
403 static int consume_count (const char **);
405 static int consume_count_with_underscores (const char**);
407 static int demangle_args (struct work_stuff
*, const char **, string
*);
409 static int demangle_nested_args (struct work_stuff
*, const char**, string
*);
411 static int do_type (struct work_stuff
*, const char **, string
*);
413 static int do_arg (struct work_stuff
*, const char **, string
*);
416 demangle_function_name (struct work_stuff
*, const char **, string
*,
420 iterate_demangle_function (struct work_stuff
*,
421 const char **, string
*, const char *);
423 static void remember_type (struct work_stuff
*, const char *, int);
425 static void remember_Btype (struct work_stuff
*, const char *, int, int);
427 static int register_Btype (struct work_stuff
*);
429 static void remember_Ktype (struct work_stuff
*, const char *, int);
431 static void forget_types (struct work_stuff
*);
433 static void forget_B_and_K_types (struct work_stuff
*);
435 static void string_prepends (string
*, string
*);
438 demangle_template_value_parm (struct work_stuff
*, const char**,
439 string
*, type_kind_t
);
442 do_hpacc_template_const_value (struct work_stuff
*, const char **, string
*);
445 do_hpacc_template_literal (struct work_stuff
*, const char **, string
*);
447 static int snarf_numeric_literal (const char **, string
*);
449 /* There is a TYPE_QUAL value for each type qualifier. They can be
450 combined by bitwise-or to form the complete set of qualifiers for a
453 #define TYPE_UNQUALIFIED 0x0
454 #define TYPE_QUAL_CONST 0x1
455 #define TYPE_QUAL_VOLATILE 0x2
456 #define TYPE_QUAL_RESTRICT 0x4
458 static int code_for_qualifier (int);
460 static const char* qualifier_string (int);
462 static const char* demangle_qualifier (int);
464 static int demangle_expression (struct work_stuff
*, const char **, string
*,
468 demangle_integral_value (struct work_stuff
*, const char **, string
*);
471 demangle_real_value (struct work_stuff
*, const char **, string
*);
474 demangle_arm_hp_template (struct work_stuff
*, const char **, int, string
*);
477 recursively_demangle (struct work_stuff
*, const char **, string
*, int);
479 /* Translate count to integer, consuming tokens in the process.
480 Conversion terminates on the first non-digit character.
482 Trying to consume something that isn't a count results in no
483 consumption of input and a return of -1.
485 Overflow consumes the rest of the digits, and returns -1. */
488 consume_count (const char **type
)
492 if (! ISDIGIT ((unsigned char)**type
))
495 while (ISDIGIT ((unsigned char)**type
))
499 /* Check for overflow.
500 We assume that count is represented using two's-complement;
501 no power of two is divisible by ten, so if an overflow occurs
502 when multiplying by ten, the result will not be a multiple of
504 if ((count
% 10) != 0)
506 while (ISDIGIT ((unsigned char) **type
))
511 count
+= **type
- '0';
522 /* Like consume_count, but for counts that are preceded and followed
523 by '_' if they are greater than 10. Also, -1 is returned for
524 failure, since 0 can be a valid value. */
527 consume_count_with_underscores (const char **mangled
)
531 if (**mangled
== '_')
534 if (!ISDIGIT ((unsigned char)**mangled
))
537 idx
= consume_count (mangled
);
538 if (**mangled
!= '_')
539 /* The trailing underscore was missing. */
546 if (**mangled
< '0' || **mangled
> '9')
549 idx
= **mangled
- '0';
556 /* C is the code for a type-qualifier. Return the TYPE_QUAL
557 corresponding to this qualifier. */
560 code_for_qualifier (int c
)
565 return TYPE_QUAL_CONST
;
568 return TYPE_QUAL_VOLATILE
;
571 return TYPE_QUAL_RESTRICT
;
577 /* C was an invalid qualifier. */
581 /* Return the string corresponding to the qualifiers given by
585 qualifier_string (int type_quals
)
589 case TYPE_UNQUALIFIED
:
592 case TYPE_QUAL_CONST
:
595 case TYPE_QUAL_VOLATILE
:
598 case TYPE_QUAL_RESTRICT
:
601 case TYPE_QUAL_CONST
| TYPE_QUAL_VOLATILE
:
602 return "const volatile";
604 case TYPE_QUAL_CONST
| TYPE_QUAL_RESTRICT
:
605 return "const __restrict";
607 case TYPE_QUAL_VOLATILE
| TYPE_QUAL_RESTRICT
:
608 return "volatile __restrict";
610 case TYPE_QUAL_CONST
| TYPE_QUAL_VOLATILE
| TYPE_QUAL_RESTRICT
:
611 return "const volatile __restrict";
617 /* TYPE_QUALS was an invalid qualifier set. */
621 /* C is the code for a type-qualifier. Return the string
622 corresponding to this qualifier. This function should only be
623 called with a valid qualifier code. */
626 demangle_qualifier (int c
)
628 return qualifier_string (code_for_qualifier (c
));
632 cplus_demangle_opname (const char *opname
, char *result
, int options
)
636 struct work_stuff work
[1];
639 len
= strlen(opname
);
642 memset ((char *) work
, 0, sizeof (work
));
643 work
->options
= options
;
645 if (opname
[0] == '_' && opname
[1] == '_'
646 && opname
[2] == 'o' && opname
[3] == 'p')
649 /* type conversion operator. */
651 if (do_type (work
, &tem
, &type
))
653 strcat (result
, "operator ");
654 strncat (result
, type
.b
, type
.p
- type
.b
);
655 string_delete (&type
);
659 else if (opname
[0] == '_' && opname
[1] == '_'
660 && ISLOWER((unsigned char)opname
[2])
661 && ISLOWER((unsigned char)opname
[3]))
663 if (opname
[4] == '\0')
667 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
669 if (strlen (optable
[i
].in
) == 2
670 && memcmp (optable
[i
].in
, opname
+ 2, 2) == 0)
672 strcat (result
, "operator");
673 strcat (result
, optable
[i
].out
);
681 if (opname
[2] == 'a' && opname
[5] == '\0')
685 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
687 if (strlen (optable
[i
].in
) == 3
688 && memcmp (optable
[i
].in
, opname
+ 2, 3) == 0)
690 strcat (result
, "operator");
691 strcat (result
, optable
[i
].out
);
702 && strchr (cplus_markers
, opname
[2]) != NULL
)
704 /* see if it's an assignment expression */
705 if (len
>= 10 /* op$assign_ */
706 && memcmp (opname
+ 3, "assign_", 7) == 0)
709 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
712 if ((int) strlen (optable
[i
].in
) == len1
713 && memcmp (optable
[i
].in
, opname
+ 10, len1
) == 0)
715 strcat (result
, "operator");
716 strcat (result
, optable
[i
].out
);
717 strcat (result
, "=");
726 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
729 if ((int) strlen (optable
[i
].in
) == len1
730 && memcmp (optable
[i
].in
, opname
+ 3, len1
) == 0)
732 strcat (result
, "operator");
733 strcat (result
, optable
[i
].out
);
740 else if (len
>= 5 && memcmp (opname
, "type", 4) == 0
741 && strchr (cplus_markers
, opname
[4]) != NULL
)
743 /* type conversion operator */
745 if (do_type (work
, &tem
, &type
))
747 strcat (result
, "operator ");
748 strncat (result
, type
.b
, type
.p
- type
.b
);
749 string_delete (&type
);
753 squangle_mop_up (work
);
758 /* Takes operator name as e.g. "++" and returns mangled
759 operator name (e.g. "postincrement_expr"), or NULL if not found.
761 If OPTIONS & DMGL_ANSI == 1, return the ANSI name;
762 if OPTIONS & DMGL_ANSI == 0, return the old GNU name. */
765 cplus_mangle_opname (const char *opname
, int options
)
770 len
= strlen (opname
);
771 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
773 if ((int) strlen (optable
[i
].out
) == len
774 && (options
& DMGL_ANSI
) == (optable
[i
].flags
& DMGL_ANSI
)
775 && memcmp (optable
[i
].out
, opname
, len
) == 0)
776 return optable
[i
].in
;
781 /* Add a routine to set the demangling style to be sure it is valid and
782 allow for any demangler initialization that maybe necessary. */
784 enum demangling_styles
785 cplus_demangle_set_style (enum demangling_styles style
)
787 const struct demangler_engine
*demangler
= libiberty_demanglers
;
789 for (; demangler
->demangling_style
!= unknown_demangling
; ++demangler
)
790 if (style
== demangler
->demangling_style
)
792 current_demangling_style
= style
;
793 return current_demangling_style
;
796 return unknown_demangling
;
799 /* Do string name to style translation */
801 enum demangling_styles
802 cplus_demangle_name_to_style (const char *name
)
804 const struct demangler_engine
*demangler
= libiberty_demanglers
;
806 for (; demangler
->demangling_style
!= unknown_demangling
; ++demangler
)
807 if (strcmp (name
, demangler
->demangling_style_name
) == 0)
808 return demangler
->demangling_style
;
810 return unknown_demangling
;
813 /* char *cplus_demangle (const char *mangled, int options)
815 If MANGLED is a mangled function name produced by GNU C++, then
816 a pointer to a @code{malloc}ed string giving a C++ representation
817 of the name will be returned; otherwise NULL will be returned.
818 It is the caller's responsibility to free the string which
821 The OPTIONS arg may contain one or more of the following bits:
823 DMGL_ANSI ANSI qualifiers such as `const' and `void' are
825 DMGL_PARAMS Function parameters are included.
829 cplus_demangle ("foo__1Ai", DMGL_PARAMS) => "A::foo(int)"
830 cplus_demangle ("foo__1Ai", DMGL_PARAMS | DMGL_ANSI) => "A::foo(int)"
831 cplus_demangle ("foo__1Ai", 0) => "A::foo"
833 cplus_demangle ("foo__1Afe", DMGL_PARAMS) => "A::foo(float,...)"
834 cplus_demangle ("foo__1Afe", DMGL_PARAMS | DMGL_ANSI)=> "A::foo(float,...)"
835 cplus_demangle ("foo__1Afe", 0) => "A::foo"
837 Note that any leading underscores, or other such characters prepended by
838 the compilation system, are presumed to have already been stripped from
842 cplus_demangle (const char *mangled
, int options
)
845 struct work_stuff work
[1];
847 if (current_demangling_style
== no_demangling
)
848 return xstrdup (mangled
);
850 memset ((char *) work
, 0, sizeof (work
));
851 work
->options
= options
;
852 if ((work
->options
& DMGL_STYLE_MASK
) == 0)
853 work
->options
|= (int) current_demangling_style
& DMGL_STYLE_MASK
;
855 /* The V3 ABI demangling is implemented elsewhere. */
856 if (GNU_V3_DEMANGLING
|| AUTO_DEMANGLING
)
858 ret
= cplus_demangle_v3 (mangled
, work
->options
);
859 if (ret
|| GNU_V3_DEMANGLING
)
865 ret
= java_demangle_v3 (mangled
);
871 return ada_demangle (mangled
, options
);
873 ret
= internal_cplus_demangle (work
, mangled
);
874 squangle_mop_up (work
);
878 /* Demangle ada names. The encoding is documented in gcc/ada/exp_dbug.ads. */
881 ada_demangle (const char *mangled
, int option ATTRIBUTE_UNUSED
)
888 /* Discard leading _ada_, which is used for library level subprograms. */
889 if (strncmp (mangled
, "_ada_", 5) == 0)
892 /* All ada unit names are lower-case. */
893 if (!ISLOWER (mangled
[0]))
896 /* Most of the demangling will trivially remove chars. Operator names
897 may add one char but because they are always preceeded by '__' which is
898 replaced by '.', they eventually never expand the size.
899 A few special names such as '___elabs' add a few chars (at most 7), but
900 they occur only once. */
901 len0
= strlen (mangled
) + 7 + 1;
902 demangled
= XNEWVEC (char, len0
);
908 /* An entity names is expected. */
911 /* An identifier, which is always lower case. */
914 while (ISLOWER(*p
) || ISDIGIT (*p
)
915 || (p
[0] == '_' && (ISLOWER (p
[1]) || ISDIGIT (p
[1]))));
917 else if (p
[0] == 'O')
919 /* An operator name. */
920 static const char * const operators
[][2] =
921 {{"Oabs", "abs"}, {"Oand", "and"}, {"Omod", "mod"},
922 {"Onot", "not"}, {"Oor", "or"}, {"Orem", "rem"},
923 {"Oxor", "xor"}, {"Oeq", "="}, {"One", "/="},
924 {"Olt", "<"}, {"Ole", "<="}, {"Ogt", ">"},
925 {"Oge", ">="}, {"Oadd", "+"}, {"Osubtract", "-"},
926 {"Oconcat", "&"}, {"Omultiply", "*"}, {"Odivide", "/"},
927 {"Oexpon", "**"}, {NULL
, NULL
}};
930 for (k
= 0; operators
[k
][0] != NULL
; k
++)
932 size_t slen
= strlen (operators
[k
][0]);
933 if (strncmp (p
, operators
[k
][0], slen
) == 0)
936 slen
= strlen (operators
[k
][1]);
938 memcpy (d
, operators
[k
][1], slen
);
944 /* Operator not found. */
945 if (operators
[k
][0] == NULL
)
950 /* Not a GNAT encoding. */
954 /* The name can be directly followed by some uppercase letters. */
955 if (p
[0] == 'T' && p
[1] == 'K')
958 if (p
[2] == 'B' && p
[3] == 0)
960 /* Subprogram for task body. */
963 else if (p
[2] == '_' && p
[3] == '_')
965 /* Inner declarations in a task. */
973 if (p
[0] == 'E' && p
[1] == 0)
975 /* Exception name. */
978 if ((p
[0] == 'P' || p
[0] == 'N') && p
[1] == 0)
980 /* Protected type subprogram. */
983 if ((*p
== 'N' || *p
== 'S') && p
[1] == 0)
985 /* Enumerated type name table. */
992 while (p
[0] == 'n' || p
[0] == 'b')
995 if (p
[0] == 'S' && p
[1] != 0 && (p
[2] == '_' || p
[2] == 0))
997 /* Stream operations. */
1020 else if (p
[0] == 'D')
1022 /* Controlled type operation. */
1045 /* Standard separator. Handled first. */
1050 /* Overloading number. */
1053 while (ISDIGIT (*p
) || (p
[0] == '_' && ISDIGIT (p
[1])));
1057 while (p
[0] == 'n' || p
[0] == 'b')
1061 else if (p
[0] == '_' && p
[1] != '_')
1063 /* Special names. */
1064 static const char * const special
[][2] = {
1065 { "_elabb", "'Elab_Body" },
1066 { "_elabs", "'Elab_Spec" },
1067 { "_size", "'Size" },
1068 { "_alignment", "'Alignment" },
1069 { "_assign", ".\":=\"" },
1074 for (k
= 0; special
[k
][0] != NULL
; k
++)
1076 size_t slen
= strlen (special
[k
][0]);
1077 if (strncmp (p
, special
[k
][0], slen
) == 0)
1080 slen
= strlen (special
[k
][1]);
1081 memcpy (d
, special
[k
][1], slen
);
1086 if (special
[k
][0] != NULL
)
1097 else if (p
[1] == 'B' || p
[1] == 'E')
1099 /* Entry Body or barrier Evaluation. */
1101 while (ISDIGIT (*p
))
1103 if (p
[0] == 's' && p
[1] == 0)
1112 if (p
[0] == '.' && ISDIGIT (p
[1]))
1114 /* Nested subprogram. */
1116 while (ISDIGIT (*p
))
1121 /* End of mangled name. */
1131 len0
= strlen (mangled
);
1132 demangled
= XNEWVEC (char, len0
+ 3);
1134 if (mangled
[0] == '<')
1135 strcpy (demangled
, mangled
);
1137 sprintf (demangled
, "<%s>", mangled
);
1142 /* This function performs most of what cplus_demangle use to do, but
1143 to be able to demangle a name with a B, K or n code, we need to
1144 have a longer term memory of what types have been seen. The original
1145 now initializes and cleans up the squangle code info, while internal
1146 calls go directly to this routine to avoid resetting that info. */
1149 internal_cplus_demangle (struct work_stuff
*work
, const char *mangled
)
1154 char *demangled
= NULL
;
1156 s1
= work
->constructor
;
1157 s2
= work
->destructor
;
1158 s3
= work
->static_type
;
1159 s4
= work
->type_quals
;
1160 work
->constructor
= work
->destructor
= 0;
1161 work
->type_quals
= TYPE_UNQUALIFIED
;
1162 work
->dllimported
= 0;
1164 if ((mangled
!= NULL
) && (*mangled
!= '\0'))
1166 string_init (&decl
);
1168 /* First check to see if gnu style demangling is active and if the
1169 string to be demangled contains a CPLUS_MARKER. If so, attempt to
1170 recognize one of the gnu special forms rather than looking for a
1171 standard prefix. In particular, don't worry about whether there
1172 is a "__" string in the mangled string. Consider "_$_5__foo" for
1175 if ((AUTO_DEMANGLING
|| GNU_DEMANGLING
))
1177 success
= gnu_special (work
, &mangled
, &decl
);
1180 delete_work_stuff (work
);
1181 string_delete (&decl
);
1186 success
= demangle_prefix (work
, &mangled
, &decl
);
1188 if (success
&& (*mangled
!= '\0'))
1190 success
= demangle_signature (work
, &mangled
, &decl
);
1192 if (work
->constructor
== 2)
1194 string_prepend (&decl
, "global constructors keyed to ");
1195 work
->constructor
= 0;
1197 else if (work
->destructor
== 2)
1199 string_prepend (&decl
, "global destructors keyed to ");
1200 work
->destructor
= 0;
1202 else if (work
->dllimported
== 1)
1204 string_prepend (&decl
, "import stub for ");
1205 work
->dllimported
= 0;
1207 demangled
= mop_up (work
, &decl
, success
);
1209 work
->constructor
= s1
;
1210 work
->destructor
= s2
;
1211 work
->static_type
= s3
;
1212 work
->type_quals
= s4
;
1217 /* Clear out and squangling related storage */
1219 squangle_mop_up (struct work_stuff
*work
)
1221 /* clean up the B and K type mangling types. */
1222 forget_B_and_K_types (work
);
1223 if (work
-> btypevec
!= NULL
)
1225 free ((char *) work
-> btypevec
);
1226 work
->btypevec
= NULL
;
1228 if (work
-> ktypevec
!= NULL
)
1230 free ((char *) work
-> ktypevec
);
1231 work
->ktypevec
= NULL
;
1236 /* Copy the work state and storage. */
1239 work_stuff_copy_to_from (struct work_stuff
*to
, struct work_stuff
*from
)
1243 delete_work_stuff (to
);
1245 /* Shallow-copy scalars. */
1246 memcpy (to
, from
, sizeof (*to
));
1248 /* Deep-copy dynamic storage. */
1249 if (from
->typevec_size
)
1250 to
->typevec
= XNEWVEC (char *, from
->typevec_size
);
1252 for (i
= 0; i
< from
->ntypes
; i
++)
1254 int len
= strlen (from
->typevec
[i
]) + 1;
1256 to
->typevec
[i
] = XNEWVEC (char, len
);
1257 memcpy (to
->typevec
[i
], from
->typevec
[i
], len
);
1261 to
->ktypevec
= XNEWVEC (char *, from
->ksize
);
1263 for (i
= 0; i
< from
->numk
; i
++)
1265 int len
= strlen (from
->ktypevec
[i
]) + 1;
1267 to
->ktypevec
[i
] = XNEWVEC (char, len
);
1268 memcpy (to
->ktypevec
[i
], from
->ktypevec
[i
], len
);
1272 to
->btypevec
= XNEWVEC (char *, from
->bsize
);
1274 for (i
= 0; i
< from
->numb
; i
++)
1276 int len
= strlen (from
->btypevec
[i
]) + 1;
1278 to
->btypevec
[i
] = XNEWVEC (char , len
);
1279 memcpy (to
->btypevec
[i
], from
->btypevec
[i
], len
);
1282 if (from
->ntmpl_args
)
1283 to
->tmpl_argvec
= XNEWVEC (char *, from
->ntmpl_args
);
1285 for (i
= 0; i
< from
->ntmpl_args
; i
++)
1287 int len
= strlen (from
->tmpl_argvec
[i
]) + 1;
1289 to
->tmpl_argvec
[i
] = XNEWVEC (char, len
);
1290 memcpy (to
->tmpl_argvec
[i
], from
->tmpl_argvec
[i
], len
);
1293 if (from
->previous_argument
)
1295 to
->previous_argument
= XNEW (string
);
1296 string_init (to
->previous_argument
);
1297 string_appends (to
->previous_argument
, from
->previous_argument
);
1302 /* Delete dynamic stuff in work_stuff that is not to be re-used. */
1305 delete_non_B_K_work_stuff (struct work_stuff
*work
)
1307 /* Discard the remembered types, if any. */
1309 forget_types (work
);
1310 if (work
-> typevec
!= NULL
)
1312 free ((char *) work
-> typevec
);
1313 work
-> typevec
= NULL
;
1314 work
-> typevec_size
= 0;
1316 if (work
->tmpl_argvec
)
1320 for (i
= 0; i
< work
->ntmpl_args
; i
++)
1321 free ((char*) work
->tmpl_argvec
[i
]);
1323 free ((char*) work
->tmpl_argvec
);
1324 work
->tmpl_argvec
= NULL
;
1326 if (work
->previous_argument
)
1328 string_delete (work
->previous_argument
);
1329 free ((char*) work
->previous_argument
);
1330 work
->previous_argument
= NULL
;
1335 /* Delete all dynamic storage in work_stuff. */
1337 delete_work_stuff (struct work_stuff
*work
)
1339 delete_non_B_K_work_stuff (work
);
1340 squangle_mop_up (work
);
1344 /* Clear out any mangled storage */
1347 mop_up (struct work_stuff
*work
, string
*declp
, int success
)
1349 char *demangled
= NULL
;
1351 delete_non_B_K_work_stuff (work
);
1353 /* If demangling was successful, ensure that the demangled string is null
1354 terminated and return it. Otherwise, free the demangling decl. */
1358 string_delete (declp
);
1362 string_appendn (declp
, "", 1);
1363 demangled
= declp
->b
;
1372 demangle_signature -- demangle the signature part of a mangled name
1377 demangle_signature (struct work_stuff *work, const char **mangled,
1382 Consume and demangle the signature portion of the mangled name.
1384 DECLP is the string where demangled output is being built. At
1385 entry it contains the demangled root name from the mangled name
1386 prefix. I.E. either a demangled operator name or the root function
1387 name. In some special cases, it may contain nothing.
1389 *MANGLED points to the current unconsumed location in the mangled
1390 name. As tokens are consumed and demangling is performed, the
1391 pointer is updated to continuously point at the next token to
1394 Demangling GNU style mangled names is nasty because there is no
1395 explicit token that marks the start of the outermost function
1399 demangle_signature (struct work_stuff
*work
,
1400 const char **mangled
, string
*declp
)
1404 int expect_func
= 0;
1405 int expect_return_type
= 0;
1406 const char *oldmangled
= NULL
;
1410 while (success
&& (**mangled
!= '\0'))
1415 oldmangled
= *mangled
;
1416 success
= demangle_qualified (work
, mangled
, declp
, 1, 0);
1418 remember_type (work
, oldmangled
, *mangled
- oldmangled
);
1419 if (AUTO_DEMANGLING
|| GNU_DEMANGLING
)
1425 oldmangled
= *mangled
;
1426 success
= demangle_qualified (work
, mangled
, declp
, 1, 0);
1427 if (AUTO_DEMANGLING
|| GNU_DEMANGLING
)
1435 /* Static member function */
1436 if (oldmangled
== NULL
)
1438 oldmangled
= *mangled
;
1441 work
-> static_type
= 1;
1447 work
->type_quals
|= code_for_qualifier (**mangled
);
1449 /* a qualified member function */
1450 if (oldmangled
== NULL
)
1451 oldmangled
= *mangled
;
1456 /* Local class name follows after "Lnnn_" */
1459 while (**mangled
&& (**mangled
!= '_'))
1470 case '0': case '1': case '2': case '3': case '4':
1471 case '5': case '6': case '7': case '8': case '9':
1472 if (oldmangled
== NULL
)
1474 oldmangled
= *mangled
;
1476 work
->temp_start
= -1; /* uppermost call to demangle_class */
1477 success
= demangle_class (work
, mangled
, declp
);
1480 remember_type (work
, oldmangled
, *mangled
- oldmangled
);
1482 if (AUTO_DEMANGLING
|| GNU_DEMANGLING
|| EDG_DEMANGLING
)
1484 /* EDG and others will have the "F", so we let the loop cycle
1485 if we are looking at one. */
1486 if (**mangled
!= 'F')
1495 success
= do_type (work
, mangled
, &s
);
1498 string_append (&s
, SCOPE_STRING (work
));
1499 string_prepends (declp
, &s
);
1509 /* ARM/HP style demangling includes a specific 'F' character after
1510 the class name. For GNU style, it is just implied. So we can
1511 safely just consume any 'F' at this point and be compatible
1512 with either style. */
1518 /* For lucid/ARM/HP style we have to forget any types we might
1519 have remembered up to this point, since they were not argument
1520 types. GNU style considers all types seen as available for
1521 back references. See comment in demangle_args() */
1523 if (LUCID_DEMANGLING
|| ARM_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
)
1525 forget_types (work
);
1527 success
= demangle_args (work
, mangled
, declp
);
1528 /* After picking off the function args, we expect to either
1529 find the function return type (preceded by an '_') or the
1530 end of the string. */
1531 if (success
&& (AUTO_DEMANGLING
|| EDG_DEMANGLING
) && **mangled
== '_')
1534 /* At this level, we do not care about the return type. */
1535 success
= do_type (work
, mangled
, &tname
);
1536 string_delete (&tname
);
1543 string_init(&trawname
);
1544 string_init(&tname
);
1545 if (oldmangled
== NULL
)
1547 oldmangled
= *mangled
;
1549 success
= demangle_template (work
, mangled
, &tname
,
1553 remember_type (work
, oldmangled
, *mangled
- oldmangled
);
1555 string_append (&tname
, SCOPE_STRING (work
));
1557 string_prepends(declp
, &tname
);
1558 if (work
-> destructor
& 1)
1560 string_prepend (&trawname
, "~");
1561 string_appends (declp
, &trawname
);
1562 work
->destructor
-= 1;
1564 if ((work
->constructor
& 1) || (work
->destructor
& 1))
1566 string_appends (declp
, &trawname
);
1567 work
->constructor
-= 1;
1569 string_delete(&trawname
);
1570 string_delete(&tname
);
1576 if ((AUTO_DEMANGLING
|| GNU_DEMANGLING
) && expect_return_type
)
1578 /* Read the return type. */
1582 success
= do_type (work
, mangled
, &return_type
);
1583 APPEND_BLANK (&return_type
);
1585 string_prepends (declp
, &return_type
);
1586 string_delete (&return_type
);
1590 /* At the outermost level, we cannot have a return type specified,
1591 so if we run into another '_' at this point we are dealing with
1592 a mangled name that is either bogus, or has been mangled by
1593 some algorithm we don't know how to deal with. So just
1594 reject the entire demangling. */
1595 /* However, "_nnn" is an expected suffix for alternate entry point
1596 numbered nnn for a function, with HP aCC, so skip over that
1597 without reporting failure. pai/1997-09-04 */
1601 while (**mangled
&& ISDIGIT ((unsigned char)**mangled
))
1609 if (AUTO_DEMANGLING
|| GNU_DEMANGLING
)
1611 /* A G++ template function. Read the template arguments. */
1612 success
= demangle_template (work
, mangled
, declp
, 0, 0,
1614 if (!(work
->constructor
& 1))
1615 expect_return_type
= 1;
1624 if (AUTO_DEMANGLING
|| GNU_DEMANGLING
)
1626 /* Assume we have stumbled onto the first outermost function
1627 argument token, and start processing args. */
1629 success
= demangle_args (work
, mangled
, declp
);
1633 /* Non-GNU demanglers use a specific token to mark the start
1634 of the outermost function argument tokens. Typically 'F',
1635 for ARM/HP-demangling, for example. So if we find something
1636 we are not prepared for, it must be an error. */
1642 if (AUTO_DEMANGLING || GNU_DEMANGLING)
1645 if (success
&& expect_func
)
1648 if (LUCID_DEMANGLING
|| ARM_DEMANGLING
|| EDG_DEMANGLING
)
1650 forget_types (work
);
1652 success
= demangle_args (work
, mangled
, declp
);
1653 /* Since template include the mangling of their return types,
1654 we must set expect_func to 0 so that we don't try do
1655 demangle more arguments the next time we get here. */
1660 if (success
&& !func_done
)
1662 if (AUTO_DEMANGLING
|| GNU_DEMANGLING
)
1664 /* With GNU style demangling, bar__3foo is 'foo::bar(void)', and
1665 bar__3fooi is 'foo::bar(int)'. We get here when we find the
1666 first case, and need to ensure that the '(void)' gets added to
1667 the current declp. Note that with ARM/HP, the first case
1668 represents the name of a static data member 'foo::bar',
1669 which is in the current declp, so we leave it alone. */
1670 success
= demangle_args (work
, mangled
, declp
);
1673 if (success
&& PRINT_ARG_TYPES
)
1675 if (work
->static_type
)
1676 string_append (declp
, " static");
1677 if (work
->type_quals
!= TYPE_UNQUALIFIED
)
1679 APPEND_BLANK (declp
);
1680 string_append (declp
, qualifier_string (work
->type_quals
));
1690 demangle_method_args (struct work_stuff
*work
, const char **mangled
,
1695 if (work
-> static_type
)
1697 string_append (declp
, *mangled
+ 1);
1698 *mangled
+= strlen (*mangled
);
1703 success
= demangle_args (work
, mangled
, declp
);
1711 demangle_template_template_parm (struct work_stuff
*work
,
1712 const char **mangled
, string
*tname
)
1720 string_append (tname
, "template <");
1721 /* get size of template parameter list */
1722 if (get_count (mangled
, &r
))
1724 for (i
= 0; i
< r
; i
++)
1728 string_append (tname
, ", ");
1731 /* Z for type parameters */
1732 if (**mangled
== 'Z')
1735 string_append (tname
, "class");
1737 /* z for template parameters */
1738 else if (**mangled
== 'z')
1742 demangle_template_template_parm (work
, mangled
, tname
);
1750 /* temp is initialized in do_type */
1751 success
= do_type (work
, mangled
, &temp
);
1754 string_appends (tname
, &temp
);
1756 string_delete(&temp
);
1766 if (tname
->p
[-1] == '>')
1767 string_append (tname
, " ");
1768 string_append (tname
, "> class");
1773 demangle_expression (struct work_stuff
*work
, const char **mangled
,
1774 string
*s
, type_kind_t tk
)
1776 int need_operator
= 0;
1780 string_appendn (s
, "(", 1);
1782 while (success
&& **mangled
!= 'W' && **mangled
!= '\0')
1791 len
= strlen (*mangled
);
1793 for (i
= 0; i
< ARRAY_SIZE (optable
); ++i
)
1795 size_t l
= strlen (optable
[i
].in
);
1798 && memcmp (optable
[i
].in
, *mangled
, l
) == 0)
1800 string_appendn (s
, " ", 1);
1801 string_append (s
, optable
[i
].out
);
1802 string_appendn (s
, " ", 1);
1815 success
= demangle_template_value_parm (work
, mangled
, s
, tk
);
1818 if (**mangled
!= 'W')
1822 string_appendn (s
, ")", 1);
1830 demangle_integral_value (struct work_stuff
*work
,
1831 const char **mangled
, string
*s
)
1835 if (**mangled
== 'E')
1836 success
= demangle_expression (work
, mangled
, s
, tk_integral
);
1837 else if (**mangled
== 'Q' || **mangled
== 'K')
1838 success
= demangle_qualified (work
, mangled
, s
, 0, 1);
1843 /* By default, we let the number decide whether we shall consume an
1845 int multidigit_without_leading_underscore
= 0;
1846 int leave_following_underscore
= 0;
1850 if (**mangled
== '_')
1852 if (mangled
[0][1] == 'm')
1854 /* Since consume_count_with_underscores does not handle the
1855 `m'-prefix we must do it here, using consume_count and
1856 adjusting underscores: we have to consume the underscore
1857 matching the prepended one. */
1858 multidigit_without_leading_underscore
= 1;
1859 string_appendn (s
, "-", 1);
1864 /* Do not consume a following underscore;
1865 consume_count_with_underscores will consume what
1866 should be consumed. */
1867 leave_following_underscore
= 1;
1872 /* Negative numbers are indicated with a leading `m'. */
1873 if (**mangled
== 'm')
1875 string_appendn (s
, "-", 1);
1878 /* Since consume_count_with_underscores does not handle
1879 multi-digit numbers that do not start with an underscore,
1880 and this number can be an integer template parameter,
1881 we have to call consume_count. */
1882 multidigit_without_leading_underscore
= 1;
1883 /* These multi-digit numbers never end on an underscore,
1884 so if there is one then don't eat it. */
1885 leave_following_underscore
= 1;
1888 /* We must call consume_count if we expect to remove a trailing
1889 underscore, since consume_count_with_underscores expects
1890 the leading underscore (that we consumed) if it is to handle
1891 multi-digit numbers. */
1892 if (multidigit_without_leading_underscore
)
1893 value
= consume_count (mangled
);
1895 value
= consume_count_with_underscores (mangled
);
1899 char buf
[INTBUF_SIZE
];
1900 sprintf (buf
, "%d", value
);
1901 string_append (s
, buf
);
1903 /* Numbers not otherwise delimited, might have an underscore
1904 appended as a delimeter, which we should skip.
1906 ??? This used to always remove a following underscore, which
1907 is wrong. If other (arbitrary) cases are followed by an
1908 underscore, we need to do something more radical. */
1910 if ((value
> 9 || multidigit_without_leading_underscore
)
1911 && ! leave_following_underscore
1912 && **mangled
== '_')
1923 /* Demangle the real value in MANGLED. */
1926 demangle_real_value (struct work_stuff
*work
,
1927 const char **mangled
, string
*s
)
1929 if (**mangled
== 'E')
1930 return demangle_expression (work
, mangled
, s
, tk_real
);
1932 if (**mangled
== 'm')
1934 string_appendn (s
, "-", 1);
1937 while (ISDIGIT ((unsigned char)**mangled
))
1939 string_appendn (s
, *mangled
, 1);
1942 if (**mangled
== '.') /* fraction */
1944 string_appendn (s
, ".", 1);
1946 while (ISDIGIT ((unsigned char)**mangled
))
1948 string_appendn (s
, *mangled
, 1);
1952 if (**mangled
== 'e') /* exponent */
1954 string_appendn (s
, "e", 1);
1956 while (ISDIGIT ((unsigned char)**mangled
))
1958 string_appendn (s
, *mangled
, 1);
1967 demangle_template_value_parm (struct work_stuff
*work
, const char **mangled
,
1968 string
*s
, type_kind_t tk
)
1972 if (**mangled
== 'Y')
1974 /* The next argument is a template parameter. */
1978 idx
= consume_count_with_underscores (mangled
);
1980 || (work
->tmpl_argvec
&& idx
>= work
->ntmpl_args
)
1981 || consume_count_with_underscores (mangled
) == -1)
1983 if (work
->tmpl_argvec
)
1984 string_append (s
, work
->tmpl_argvec
[idx
]);
1986 string_append_template_idx (s
, idx
);
1988 else if (tk
== tk_integral
)
1989 success
= demangle_integral_value (work
, mangled
, s
);
1990 else if (tk
== tk_char
)
1994 if (**mangled
== 'm')
1996 string_appendn (s
, "-", 1);
1999 string_appendn (s
, "'", 1);
2000 val
= consume_count(mangled
);
2007 string_appendn (s
, &tmp
[0], 1);
2008 string_appendn (s
, "'", 1);
2011 else if (tk
== tk_bool
)
2013 int val
= consume_count (mangled
);
2015 string_appendn (s
, "false", 5);
2017 string_appendn (s
, "true", 4);
2021 else if (tk
== tk_real
)
2022 success
= demangle_real_value (work
, mangled
, s
);
2023 else if (tk
== tk_pointer
|| tk
== tk_reference
)
2025 if (**mangled
== 'Q')
2026 success
= demangle_qualified (work
, mangled
, s
,
2031 int symbol_len
= consume_count (mangled
);
2032 if (symbol_len
== -1)
2034 if (symbol_len
== 0)
2035 string_appendn (s
, "0", 1);
2038 char *p
= XNEWVEC (char, symbol_len
+ 1), *q
;
2039 strncpy (p
, *mangled
, symbol_len
);
2040 p
[symbol_len
] = '\0';
2041 /* We use cplus_demangle here, rather than
2042 internal_cplus_demangle, because the name of the entity
2043 mangled here does not make use of any of the squangling
2044 or type-code information we have built up thus far; it is
2045 mangled independently. */
2046 q
= cplus_demangle (p
, work
->options
);
2047 if (tk
== tk_pointer
)
2048 string_appendn (s
, "&", 1);
2049 /* FIXME: Pointer-to-member constants should get a
2050 qualifying class name here. */
2053 string_append (s
, q
);
2057 string_append (s
, p
);
2060 *mangled
+= symbol_len
;
2067 /* Demangle the template name in MANGLED. The full name of the
2068 template (e.g., S<int>) is placed in TNAME. The name without the
2069 template parameters (e.g. S) is placed in TRAWNAME if TRAWNAME is
2070 non-NULL. If IS_TYPE is nonzero, this template is a type template,
2071 not a function template. If both IS_TYPE and REMEMBER are nonzero,
2072 the template is remembered in the list of back-referenceable
2076 demangle_template (struct work_stuff
*work
, const char **mangled
,
2077 string
*tname
, string
*trawname
,
2078 int is_type
, int remember
)
2084 int is_java_array
= 0;
2090 /* get template name */
2091 if (**mangled
== 'z')
2097 idx
= consume_count_with_underscores (mangled
);
2099 || (work
->tmpl_argvec
&& idx
>= work
->ntmpl_args
)
2100 || consume_count_with_underscores (mangled
) == -1)
2103 if (work
->tmpl_argvec
)
2105 string_append (tname
, work
->tmpl_argvec
[idx
]);
2107 string_append (trawname
, work
->tmpl_argvec
[idx
]);
2111 string_append_template_idx (tname
, idx
);
2113 string_append_template_idx (trawname
, idx
);
2118 if ((r
= consume_count (mangled
)) <= 0
2119 || (int) strlen (*mangled
) < r
)
2123 is_java_array
= (work
-> options
& DMGL_JAVA
)
2124 && strncmp (*mangled
, "JArray1Z", 8) == 0;
2125 if (! is_java_array
)
2127 string_appendn (tname
, *mangled
, r
);
2130 string_appendn (trawname
, *mangled
, r
);
2135 string_append (tname
, "<");
2136 /* get size of template parameter list */
2137 if (!get_count (mangled
, &r
))
2143 /* Create an array for saving the template argument values. */
2144 work
->tmpl_argvec
= XNEWVEC (char *, r
);
2145 work
->ntmpl_args
= r
;
2146 for (i
= 0; i
< r
; i
++)
2147 work
->tmpl_argvec
[i
] = 0;
2149 for (i
= 0; i
< r
; i
++)
2153 string_append (tname
, ", ");
2155 /* Z for type parameters */
2156 if (**mangled
== 'Z')
2159 /* temp is initialized in do_type */
2160 success
= do_type (work
, mangled
, &temp
);
2163 string_appends (tname
, &temp
);
2167 /* Save the template argument. */
2168 int len
= temp
.p
- temp
.b
;
2169 work
->tmpl_argvec
[i
] = XNEWVEC (char, len
+ 1);
2170 memcpy (work
->tmpl_argvec
[i
], temp
.b
, len
);
2171 work
->tmpl_argvec
[i
][len
] = '\0';
2174 string_delete(&temp
);
2180 /* z for template parameters */
2181 else if (**mangled
== 'z')
2185 success
= demangle_template_template_parm (work
, mangled
, tname
);
2188 && (r2
= consume_count (mangled
)) > 0
2189 && (int) strlen (*mangled
) >= r2
)
2191 string_append (tname
, " ");
2192 string_appendn (tname
, *mangled
, r2
);
2195 /* Save the template argument. */
2197 work
->tmpl_argvec
[i
] = XNEWVEC (char, len
+ 1);
2198 memcpy (work
->tmpl_argvec
[i
], *mangled
, len
);
2199 work
->tmpl_argvec
[i
][len
] = '\0';
2213 /* otherwise, value parameter */
2215 /* temp is initialized in do_type */
2216 success
= do_type (work
, mangled
, &temp
);
2217 string_delete(&temp
);
2229 success
= demangle_template_value_parm (work
, mangled
, s
,
2230 (type_kind_t
) success
);
2242 int len
= s
->p
- s
->b
;
2243 work
->tmpl_argvec
[i
] = XNEWVEC (char, len
+ 1);
2244 memcpy (work
->tmpl_argvec
[i
], s
->b
, len
);
2245 work
->tmpl_argvec
[i
][len
] = '\0';
2247 string_appends (tname
, s
);
2255 string_append (tname
, "[]");
2259 if (tname
->p
[-1] == '>')
2260 string_append (tname
, " ");
2261 string_append (tname
, ">");
2264 if (is_type
&& remember
)
2266 const int bindex
= register_Btype (work
);
2267 remember_Btype (work
, tname
->b
, LEN_STRING (tname
), bindex
);
2271 if (work -> static_type)
2273 string_append (declp, *mangled + 1);
2274 *mangled += strlen (*mangled);
2279 success = demangle_args (work, mangled, declp);
2287 arm_pt (struct work_stuff
*work
, const char *mangled
,
2288 int n
, const char **anchor
, const char **args
)
2290 /* Check if ARM template with "__pt__" in it ("parameterized type") */
2291 /* Allow HP also here, because HP's cfront compiler follows ARM to some extent */
2292 if ((ARM_DEMANGLING
|| HP_DEMANGLING
) && (*anchor
= strstr (mangled
, "__pt__")))
2295 *args
= *anchor
+ 6;
2296 len
= consume_count (args
);
2299 if (*args
+ len
== mangled
+ n
&& **args
== '_')
2305 if (AUTO_DEMANGLING
|| EDG_DEMANGLING
)
2307 if ((*anchor
= strstr (mangled
, "__tm__"))
2308 || (*anchor
= strstr (mangled
, "__ps__"))
2309 || (*anchor
= strstr (mangled
, "__pt__")))
2312 *args
= *anchor
+ 6;
2313 len
= consume_count (args
);
2316 if (*args
+ len
== mangled
+ n
&& **args
== '_')
2322 else if ((*anchor
= strstr (mangled
, "__S")))
2325 *args
= *anchor
+ 3;
2326 len
= consume_count (args
);
2329 if (*args
+ len
== mangled
+ n
&& **args
== '_')
2341 demangle_arm_hp_template (struct work_stuff
*work
, const char **mangled
,
2342 int n
, string
*declp
)
2346 const char *e
= *mangled
+ n
;
2349 /* Check for HP aCC template spec: classXt1t2 where t1, t2 are
2351 if (HP_DEMANGLING
&& ((*mangled
)[n
] == 'X'))
2353 char *start_spec_args
= NULL
;
2356 /* First check for and omit template specialization pseudo-arguments,
2357 such as in "Spec<#1,#1.*>" */
2358 start_spec_args
= strchr (*mangled
, '<');
2359 if (start_spec_args
&& (start_spec_args
- *mangled
< n
))
2360 string_appendn (declp
, *mangled
, start_spec_args
- *mangled
);
2362 string_appendn (declp
, *mangled
, n
);
2363 (*mangled
) += n
+ 1;
2365 if (work
->temp_start
== -1) /* non-recursive call */
2366 work
->temp_start
= declp
->p
- declp
->b
;
2368 /* We want to unconditionally demangle parameter types in
2369 template parameters. */
2370 hold_options
= work
->options
;
2371 work
->options
|= DMGL_PARAMS
;
2373 string_append (declp
, "<");
2376 string_delete (&arg
);
2380 /* 'T' signals a type parameter */
2382 if (!do_type (work
, mangled
, &arg
))
2383 goto hpacc_template_args_done
;
2388 /* 'U' or 'S' signals an integral value */
2389 if (!do_hpacc_template_const_value (work
, mangled
, &arg
))
2390 goto hpacc_template_args_done
;
2394 /* 'A' signals a named constant expression (literal) */
2395 if (!do_hpacc_template_literal (work
, mangled
, &arg
))
2396 goto hpacc_template_args_done
;
2400 /* Today, 1997-09-03, we have only the above types
2401 of template parameters */
2402 /* FIXME: maybe this should fail and return null */
2403 goto hpacc_template_args_done
;
2405 string_appends (declp
, &arg
);
2406 /* Check if we're at the end of template args.
2407 0 if at end of static member of template class,
2408 _ if done with template args for a function */
2409 if ((**mangled
== '\000') || (**mangled
== '_'))
2412 string_append (declp
, ",");
2414 hpacc_template_args_done
:
2415 string_append (declp
, ">");
2416 string_delete (&arg
);
2417 if (**mangled
== '_')
2419 work
->options
= hold_options
;
2422 /* ARM template? (Also handles HP cfront extensions) */
2423 else if (arm_pt (work
, *mangled
, n
, &p
, &args
))
2429 string_appendn (declp
, *mangled
, p
- *mangled
);
2430 if (work
->temp_start
== -1) /* non-recursive call */
2431 work
->temp_start
= declp
->p
- declp
->b
;
2433 /* We want to unconditionally demangle parameter types in
2434 template parameters. */
2435 hold_options
= work
->options
;
2436 work
->options
|= DMGL_PARAMS
;
2438 string_append (declp
, "<");
2439 /* should do error checking here */
2441 string_delete (&arg
);
2443 /* Check for type or literal here */
2446 /* HP cfront extensions to ARM for template args */
2447 /* spec: Xt1Lv1 where t1 is a type, v1 is a literal value */
2448 /* FIXME: We handle only numeric literals for HP cfront */
2450 /* A typed constant value follows */
2452 if (!do_type (work
, &args
, &type_str
))
2453 goto cfront_template_args_done
;
2454 string_append (&arg
, "(");
2455 string_appends (&arg
, &type_str
);
2456 string_delete (&type_str
);
2457 string_append (&arg
, ")");
2459 goto cfront_template_args_done
;
2461 /* Now snarf a literal value following 'L' */
2462 if (!snarf_numeric_literal (&args
, &arg
))
2463 goto cfront_template_args_done
;
2467 /* Snarf a literal following 'L' */
2469 if (!snarf_numeric_literal (&args
, &arg
))
2470 goto cfront_template_args_done
;
2473 /* Not handling other HP cfront stuff */
2475 const char* old_args
= args
;
2476 if (!do_type (work
, &args
, &arg
))
2477 goto cfront_template_args_done
;
2479 /* Fail if we didn't make any progress: prevent infinite loop. */
2480 if (args
== old_args
)
2482 work
->options
= hold_options
;
2487 string_appends (declp
, &arg
);
2488 string_append (declp
, ",");
2490 cfront_template_args_done
:
2491 string_delete (&arg
);
2493 --declp
->p
; /* remove extra comma */
2494 string_append (declp
, ">");
2495 work
->options
= hold_options
;
2497 else if (n
>10 && strncmp (*mangled
, "_GLOBAL_", 8) == 0
2498 && (*mangled
)[9] == 'N'
2499 && (*mangled
)[8] == (*mangled
)[10]
2500 && strchr (cplus_markers
, (*mangled
)[8]))
2502 /* A member of the anonymous namespace. */
2503 string_append (declp
, "{anonymous}");
2507 if (work
->temp_start
== -1) /* non-recursive call only */
2508 work
->temp_start
= 0; /* disable in recursive calls */
2509 string_appendn (declp
, *mangled
, n
);
2514 /* Extract a class name, possibly a template with arguments, from the
2515 mangled string; qualifiers, local class indicators, etc. have
2516 already been dealt with */
2519 demangle_class_name (struct work_stuff
*work
, const char **mangled
,
2525 n
= consume_count (mangled
);
2528 if ((int) strlen (*mangled
) >= n
)
2530 demangle_arm_hp_template (work
, mangled
, n
, declp
);
2541 demangle_class -- demangle a mangled class sequence
2546 demangle_class (struct work_stuff *work, const char **mangled,
2551 DECLP points to the buffer into which demangling is being done.
2553 *MANGLED points to the current token to be demangled. On input,
2554 it points to a mangled class (I.E. "3foo", "13verylongclass", etc.)
2555 On exit, it points to the next token after the mangled class on
2556 success, or the first unconsumed token on failure.
2558 If the CONSTRUCTOR or DESTRUCTOR flags are set in WORK, then
2559 we are demangling a constructor or destructor. In this case
2560 we prepend "class::class" or "class::~class" to DECLP.
2562 Otherwise, we prepend "class::" to the current DECLP.
2564 Reset the constructor/destructor flags once they have been
2565 "consumed". This allows demangle_class to be called later during
2566 the same demangling, to do normal class demangling.
2568 Returns 1 if demangling is successful, 0 otherwise.
2573 demangle_class (struct work_stuff
*work
, const char **mangled
, string
*declp
)
2578 char *save_class_name_end
= 0;
2580 string_init (&class_name
);
2581 btype
= register_Btype (work
);
2582 if (demangle_class_name (work
, mangled
, &class_name
))
2584 save_class_name_end
= class_name
.p
;
2585 if ((work
->constructor
& 1) || (work
->destructor
& 1))
2587 /* adjust so we don't include template args */
2588 if (work
->temp_start
&& (work
->temp_start
!= -1))
2590 class_name
.p
= class_name
.b
+ work
->temp_start
;
2592 string_prepends (declp
, &class_name
);
2593 if (work
-> destructor
& 1)
2595 string_prepend (declp
, "~");
2596 work
-> destructor
-= 1;
2600 work
-> constructor
-= 1;
2603 class_name
.p
= save_class_name_end
;
2604 remember_Ktype (work
, class_name
.b
, LEN_STRING(&class_name
));
2605 remember_Btype (work
, class_name
.b
, LEN_STRING(&class_name
), btype
);
2606 string_prepend (declp
, SCOPE_STRING (work
));
2607 string_prepends (declp
, &class_name
);
2610 string_delete (&class_name
);
2615 /* Called when there's a "__" in the mangled name, with `scan' pointing to
2616 the rightmost guess.
2618 Find the correct "__"-sequence where the function name ends and the
2619 signature starts, which is ambiguous with GNU mangling.
2620 Call demangle_signature here, so we can make sure we found the right
2621 one; *mangled will be consumed so caller will not make further calls to
2622 demangle_signature. */
2625 iterate_demangle_function (struct work_stuff
*work
, const char **mangled
,
2626 string
*declp
, const char *scan
)
2628 const char *mangle_init
= *mangled
;
2631 struct work_stuff work_init
;
2633 if (*(scan
+ 2) == '\0')
2636 /* Do not iterate for some demangling modes, or if there's only one
2637 "__"-sequence. This is the normal case. */
2638 if (ARM_DEMANGLING
|| LUCID_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
2639 || strstr (scan
+ 2, "__") == NULL
)
2640 return demangle_function_name (work
, mangled
, declp
, scan
);
2642 /* Save state so we can restart if the guess at the correct "__" was
2644 string_init (&decl_init
);
2645 string_appends (&decl_init
, declp
);
2646 memset (&work_init
, 0, sizeof work_init
);
2647 work_stuff_copy_to_from (&work_init
, work
);
2649 /* Iterate over occurrences of __, allowing names and types to have a
2650 "__" sequence in them. We must start with the first (not the last)
2651 occurrence, since "__" most often occur between independent mangled
2652 parts, hence starting at the last occurence inside a signature
2653 might get us a "successful" demangling of the signature. */
2657 if (demangle_function_name (work
, mangled
, declp
, scan
))
2659 success
= demangle_signature (work
, mangled
, declp
);
2664 /* Reset demangle state for the next round. */
2665 *mangled
= mangle_init
;
2666 string_clear (declp
);
2667 string_appends (declp
, &decl_init
);
2668 work_stuff_copy_to_from (work
, &work_init
);
2670 /* Leave this underscore-sequence. */
2673 /* Scan for the next "__" sequence. */
2674 while (*scan
&& (scan
[0] != '_' || scan
[1] != '_'))
2677 /* Move to last "__" in this sequence. */
2678 while (*scan
&& *scan
== '_')
2683 /* Delete saved state. */
2684 delete_work_stuff (&work_init
);
2685 string_delete (&decl_init
);
2694 demangle_prefix -- consume the mangled name prefix and find signature
2699 demangle_prefix (struct work_stuff *work, const char **mangled,
2704 Consume and demangle the prefix of the mangled name.
2705 While processing the function name root, arrange to call
2706 demangle_signature if the root is ambiguous.
2708 DECLP points to the string buffer into which demangled output is
2709 placed. On entry, the buffer is empty. On exit it contains
2710 the root function name, the demangled operator name, or in some
2711 special cases either nothing or the completely demangled result.
2713 MANGLED points to the current pointer into the mangled name. As each
2714 token of the mangled name is consumed, it is updated. Upon entry
2715 the current mangled name pointer points to the first character of
2716 the mangled name. Upon exit, it should point to the first character
2717 of the signature if demangling was successful, or to the first
2718 unconsumed character if demangling of the prefix was unsuccessful.
2720 Returns 1 on success, 0 otherwise.
2724 demangle_prefix (struct work_stuff
*work
, const char **mangled
,
2731 if (strlen(*mangled
) > 6
2732 && (strncmp(*mangled
, "_imp__", 6) == 0
2733 || strncmp(*mangled
, "__imp_", 6) == 0))
2735 /* it's a symbol imported from a PE dynamic library. Check for both
2736 new style prefix _imp__ and legacy __imp_ used by older versions
2739 work
->dllimported
= 1;
2741 else if (strlen(*mangled
) >= 11 && strncmp(*mangled
, "_GLOBAL_", 8) == 0)
2743 char *marker
= strchr (cplus_markers
, (*mangled
)[8]);
2744 if (marker
!= NULL
&& *marker
== (*mangled
)[10])
2746 if ((*mangled
)[9] == 'D')
2748 /* it's a GNU global destructor to be executed at program exit */
2750 work
->destructor
= 2;
2751 if (gnu_special (work
, mangled
, declp
))
2754 else if ((*mangled
)[9] == 'I')
2756 /* it's a GNU global constructor to be executed at program init */
2758 work
->constructor
= 2;
2759 if (gnu_special (work
, mangled
, declp
))
2764 else if ((ARM_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
) && strncmp(*mangled
, "__std__", 7) == 0)
2766 /* it's a ARM global destructor to be executed at program exit */
2768 work
->destructor
= 2;
2770 else if ((ARM_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
) && strncmp(*mangled
, "__sti__", 7) == 0)
2772 /* it's a ARM global constructor to be executed at program initial */
2774 work
->constructor
= 2;
2777 /* This block of code is a reduction in strength time optimization
2779 scan = strstr (*mangled, "__"); */
2785 scan
= strchr (scan
, '_');
2786 } while (scan
!= NULL
&& *++scan
!= '_');
2788 if (scan
!= NULL
) --scan
;
2793 /* We found a sequence of two or more '_', ensure that we start at
2794 the last pair in the sequence. */
2795 i
= strspn (scan
, "_");
2806 else if (work
-> static_type
)
2808 if (!ISDIGIT ((unsigned char)scan
[0]) && (scan
[0] != 't'))
2813 else if ((scan
== *mangled
)
2814 && (ISDIGIT ((unsigned char)scan
[2]) || (scan
[2] == 'Q')
2815 || (scan
[2] == 't') || (scan
[2] == 'K') || (scan
[2] == 'H')))
2817 /* The ARM says nothing about the mangling of local variables.
2818 But cfront mangles local variables by prepending __<nesting_level>
2819 to them. As an extension to ARM demangling we handle this case. */
2820 if ((LUCID_DEMANGLING
|| ARM_DEMANGLING
|| HP_DEMANGLING
)
2821 && ISDIGIT ((unsigned char)scan
[2]))
2823 *mangled
= scan
+ 2;
2824 consume_count (mangled
);
2825 string_append (declp
, *mangled
);
2826 *mangled
+= strlen (*mangled
);
2831 /* A GNU style constructor starts with __[0-9Qt]. But cfront uses
2832 names like __Q2_3foo3bar for nested type names. So don't accept
2833 this style of constructor for cfront demangling. A GNU
2834 style member-template constructor starts with 'H'. */
2835 if (!(LUCID_DEMANGLING
|| ARM_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
))
2836 work
-> constructor
+= 1;
2837 *mangled
= scan
+ 2;
2840 else if (ARM_DEMANGLING
&& scan
[2] == 'p' && scan
[3] == 't')
2842 /* Cfront-style parameterized type. Handled later as a signature. */
2846 demangle_arm_hp_template (work
, mangled
, strlen (*mangled
), declp
);
2848 else if (EDG_DEMANGLING
&& ((scan
[2] == 't' && scan
[3] == 'm')
2849 || (scan
[2] == 'p' && scan
[3] == 's')
2850 || (scan
[2] == 'p' && scan
[3] == 't')))
2852 /* EDG-style parameterized type. Handled later as a signature. */
2856 demangle_arm_hp_template (work
, mangled
, strlen (*mangled
), declp
);
2858 else if ((scan
== *mangled
) && !ISDIGIT ((unsigned char)scan
[2])
2859 && (scan
[2] != 't'))
2861 /* Mangled name starts with "__". Skip over any leading '_' characters,
2862 then find the next "__" that separates the prefix from the signature.
2864 if (!(ARM_DEMANGLING
|| LUCID_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
)
2865 || (arm_special (mangled
, declp
) == 0))
2867 while (*scan
== '_')
2871 if ((scan
= strstr (scan
, "__")) == NULL
|| (*(scan
+ 2) == '\0'))
2873 /* No separator (I.E. "__not_mangled"), or empty signature
2874 (I.E. "__not_mangled_either__") */
2878 return iterate_demangle_function (work
, mangled
, declp
, scan
);
2881 else if (*(scan
+ 2) != '\0')
2883 /* Mangled name does not start with "__" but does have one somewhere
2884 in there with non empty stuff after it. Looks like a global
2885 function name. Iterate over all "__":s until the right
2887 return iterate_demangle_function (work
, mangled
, declp
, scan
);
2891 /* Doesn't look like a mangled name */
2895 if (!success
&& (work
->constructor
== 2 || work
->destructor
== 2))
2897 string_append (declp
, *mangled
);
2898 *mangled
+= strlen (*mangled
);
2908 gnu_special -- special handling of gnu mangled strings
2913 gnu_special (struct work_stuff *work, const char **mangled,
2919 Process some special GNU style mangling forms that don't fit
2920 the normal pattern. For example:
2922 _$_3foo (destructor for class foo)
2923 _vt$foo (foo virtual table)
2924 _vt$foo$bar (foo::bar virtual table)
2925 __vt_foo (foo virtual table, new style with thunks)
2926 _3foo$varname (static data member)
2927 _Q22rs2tu$vw (static data member)
2928 __t6vector1Zii (constructor with template)
2929 __thunk_4__$_7ostream (virtual function thunk)
2933 gnu_special (struct work_stuff
*work
, const char **mangled
, string
*declp
)
2939 if ((*mangled
)[0] == '_'
2940 && strchr (cplus_markers
, (*mangled
)[1]) != NULL
2941 && (*mangled
)[2] == '_')
2943 /* Found a GNU style destructor, get past "_<CPLUS_MARKER>_" */
2945 work
-> destructor
+= 1;
2947 else if ((*mangled
)[0] == '_'
2948 && (((*mangled
)[1] == '_'
2949 && (*mangled
)[2] == 'v'
2950 && (*mangled
)[3] == 't'
2951 && (*mangled
)[4] == '_')
2952 || ((*mangled
)[1] == 'v'
2953 && (*mangled
)[2] == 't'
2954 && strchr (cplus_markers
, (*mangled
)[3]) != NULL
)))
2956 /* Found a GNU style virtual table, get past "_vt<CPLUS_MARKER>"
2957 and create the decl. Note that we consume the entire mangled
2958 input string, which means that demangle_signature has no work
2960 if ((*mangled
)[2] == 'v')
2961 (*mangled
) += 5; /* New style, with thunks: "__vt_" */
2963 (*mangled
) += 4; /* Old style, no thunks: "_vt<CPLUS_MARKER>" */
2964 while (**mangled
!= '\0')
2970 success
= demangle_qualified (work
, mangled
, declp
, 0, 1);
2973 success
= demangle_template (work
, mangled
, declp
, 0, 1,
2977 if (ISDIGIT((unsigned char)*mangled
[0]))
2979 n
= consume_count(mangled
);
2980 /* We may be seeing a too-large size, or else a
2981 ".<digits>" indicating a static local symbol. In
2982 any case, declare victory and move on; *don't* try
2983 to use n to allocate. */
2984 if (n
> (int) strlen (*mangled
))
2992 n
= strcspn (*mangled
, cplus_markers
);
2994 string_appendn (declp
, *mangled
, n
);
2998 p
= strpbrk (*mangled
, cplus_markers
);
2999 if (success
&& ((p
== NULL
) || (p
== *mangled
)))
3003 string_append (declp
, SCOPE_STRING (work
));
3014 string_append (declp
, " virtual table");
3016 else if ((*mangled
)[0] == '_'
3017 && (strchr("0123456789Qt", (*mangled
)[1]) != NULL
)
3018 && (p
= strpbrk (*mangled
, cplus_markers
)) != NULL
)
3020 /* static data member, "_3foo$varname" for example */
3026 success
= demangle_qualified (work
, mangled
, declp
, 0, 1);
3029 success
= demangle_template (work
, mangled
, declp
, 0, 1, 1);
3032 n
= consume_count (mangled
);
3033 if (n
< 0 || n
> (long) strlen (*mangled
))
3039 if (n
> 10 && strncmp (*mangled
, "_GLOBAL_", 8) == 0
3040 && (*mangled
)[9] == 'N'
3041 && (*mangled
)[8] == (*mangled
)[10]
3042 && strchr (cplus_markers
, (*mangled
)[8]))
3044 /* A member of the anonymous namespace. There's information
3045 about what identifier or filename it was keyed to, but
3046 it's just there to make the mangled name unique; we just
3048 string_append (declp
, "{anonymous}");
3051 /* Now p points to the marker before the N, so we need to
3052 update it to the first marker after what we consumed. */
3053 p
= strpbrk (*mangled
, cplus_markers
);
3057 string_appendn (declp
, *mangled
, n
);
3060 if (success
&& (p
== *mangled
))
3062 /* Consumed everything up to the cplus_marker, append the
3065 string_append (declp
, SCOPE_STRING (work
));
3066 n
= strlen (*mangled
);
3067 string_appendn (declp
, *mangled
, n
);
3075 else if (strncmp (*mangled
, "__thunk_", 8) == 0)
3080 delta
= consume_count (mangled
);
3085 char *method
= internal_cplus_demangle (work
, ++*mangled
);
3090 sprintf (buf
, "virtual function thunk (delta:%d) for ", -delta
);
3091 string_append (declp
, buf
);
3092 string_append (declp
, method
);
3094 n
= strlen (*mangled
);
3103 else if (strncmp (*mangled
, "__t", 3) == 0
3104 && ((*mangled
)[3] == 'i' || (*mangled
)[3] == 'f'))
3106 p
= (*mangled
)[3] == 'i' ? " type_info node" : " type_info function";
3112 success
= demangle_qualified (work
, mangled
, declp
, 0, 1);
3115 success
= demangle_template (work
, mangled
, declp
, 0, 1, 1);
3118 success
= do_type (work
, mangled
, declp
);
3121 if (success
&& **mangled
!= '\0')
3124 string_append (declp
, p
);
3134 recursively_demangle(struct work_stuff
*work
, const char **mangled
,
3135 string
*result
, int namelength
)
3137 char * recurse
= (char *)NULL
;
3138 char * recurse_dem
= (char *)NULL
;
3140 recurse
= XNEWVEC (char, namelength
+ 1);
3141 memcpy (recurse
, *mangled
, namelength
);
3142 recurse
[namelength
] = '\000';
3144 recurse_dem
= cplus_demangle (recurse
, work
->options
);
3148 string_append (result
, recurse_dem
);
3153 string_appendn (result
, *mangled
, namelength
);
3156 *mangled
+= namelength
;
3163 arm_special -- special handling of ARM/lucid mangled strings
3168 arm_special (const char **mangled,
3174 Process some special ARM style mangling forms that don't fit
3175 the normal pattern. For example:
3177 __vtbl__3foo (foo virtual table)
3178 __vtbl__3foo__3bar (bar::foo virtual table)
3183 arm_special (const char **mangled
, string
*declp
)
3189 if (strncmp (*mangled
, ARM_VTABLE_STRING
, ARM_VTABLE_STRLEN
) == 0)
3191 /* Found a ARM style virtual table, get past ARM_VTABLE_STRING
3192 and create the decl. Note that we consume the entire mangled
3193 input string, which means that demangle_signature has no work
3195 scan
= *mangled
+ ARM_VTABLE_STRLEN
;
3196 while (*scan
!= '\0') /* first check it can be demangled */
3198 n
= consume_count (&scan
);
3201 return (0); /* no good */
3204 if (scan
[0] == '_' && scan
[1] == '_')
3209 (*mangled
) += ARM_VTABLE_STRLEN
;
3210 while (**mangled
!= '\0')
3212 n
= consume_count (mangled
);
3214 || n
> (long) strlen (*mangled
))
3216 string_prependn (declp
, *mangled
, n
);
3218 if ((*mangled
)[0] == '_' && (*mangled
)[1] == '_')
3220 string_prepend (declp
, "::");
3224 string_append (declp
, " virtual table");
3237 demangle_qualified -- demangle 'Q' qualified name strings
3242 demangle_qualified (struct work_stuff *, const char *mangled,
3243 string *result, int isfuncname, int append);
3247 Demangle a qualified name, such as "Q25Outer5Inner" which is
3248 the mangled form of "Outer::Inner". The demangled output is
3249 prepended or appended to the result string according to the
3250 state of the append flag.
3252 If isfuncname is nonzero, then the qualified name we are building
3253 is going to be used as a member function name, so if it is a
3254 constructor or destructor function, append an appropriate
3255 constructor or destructor name. I.E. for the above example,
3256 the result for use as a constructor is "Outer::Inner::Inner"
3257 and the result for use as a destructor is "Outer::Inner::~Inner".
3261 Numeric conversion is ASCII dependent (FIXME).
3266 demangle_qualified (struct work_stuff
*work
, const char **mangled
,
3267 string
*result
, int isfuncname
, int append
)
3274 int bindex
= register_Btype (work
);
3276 /* We only make use of ISFUNCNAME if the entity is a constructor or
3278 isfuncname
= (isfuncname
3279 && ((work
->constructor
& 1) || (work
->destructor
& 1)));
3281 string_init (&temp
);
3282 string_init (&last_name
);
3284 if ((*mangled
)[0] == 'K')
3286 /* Squangling qualified name reuse */
3289 idx
= consume_count_with_underscores (mangled
);
3290 if (idx
== -1 || idx
>= work
-> numk
)
3293 string_append (&temp
, work
-> ktypevec
[idx
]);
3296 switch ((*mangled
)[1])
3299 /* GNU mangled name with more than 9 classes. The count is preceded
3300 by an underscore (to distinguish it from the <= 9 case) and followed
3301 by an underscore. */
3303 qualifiers
= consume_count_with_underscores (mangled
);
3304 if (qualifiers
== -1)
3317 /* The count is in a single digit. */
3318 num
[0] = (*mangled
)[1];
3320 qualifiers
= atoi (num
);
3322 /* If there is an underscore after the digit, skip it. This is
3323 said to be for ARM-qualified names, but the ARM makes no
3324 mention of such an underscore. Perhaps cfront uses one. */
3325 if ((*mangled
)[2] == '_')
3340 /* Pick off the names and collect them in the temp buffer in the order
3341 in which they are found, separated by '::'. */
3343 while (qualifiers
-- > 0)
3346 string_clear (&last_name
);
3348 if (*mangled
[0] == '_')
3351 if (*mangled
[0] == 't')
3353 /* Here we always append to TEMP since we will want to use
3354 the template name without the template parameters as a
3355 constructor or destructor name. The appropriate
3356 (parameter-less) value is returned by demangle_template
3357 in LAST_NAME. We do not remember the template type here,
3358 in order to match the G++ mangling algorithm. */
3359 success
= demangle_template(work
, mangled
, &temp
,
3364 else if (*mangled
[0] == 'K')
3368 idx
= consume_count_with_underscores (mangled
);
3369 if (idx
== -1 || idx
>= work
->numk
)
3372 string_append (&temp
, work
->ktypevec
[idx
]);
3375 if (!success
) break;
3382 /* Now recursively demangle the qualifier
3383 * This is necessary to deal with templates in
3384 * mangling styles like EDG */
3385 namelength
= consume_count (mangled
);
3386 if (namelength
== -1)
3391 recursively_demangle(work
, mangled
, &temp
, namelength
);
3395 string_delete (&last_name
);
3396 success
= do_type (work
, mangled
, &last_name
);
3399 string_appends (&temp
, &last_name
);
3404 remember_Ktype (work
, temp
.b
, LEN_STRING (&temp
));
3407 string_append (&temp
, SCOPE_STRING (work
));
3410 remember_Btype (work
, temp
.b
, LEN_STRING (&temp
), bindex
);
3412 /* If we are using the result as a function name, we need to append
3413 the appropriate '::' separated constructor or destructor name.
3414 We do this here because this is the most convenient place, where
3415 we already have a pointer to the name and the length of the name. */
3419 string_append (&temp
, SCOPE_STRING (work
));
3420 if (work
-> destructor
& 1)
3421 string_append (&temp
, "~");
3422 string_appends (&temp
, &last_name
);
3425 /* Now either prepend the temp buffer to the result, or append it,
3426 depending upon the state of the append flag. */
3429 string_appends (result
, &temp
);
3432 if (!STRING_EMPTY (result
))
3433 string_append (&temp
, SCOPE_STRING (work
));
3434 string_prepends (result
, &temp
);
3437 string_delete (&last_name
);
3438 string_delete (&temp
);
3446 get_count -- convert an ascii count to integer, consuming tokens
3451 get_count (const char **type, int *count)
3455 Assume that *type points at a count in a mangled name; set
3456 *count to its value, and set *type to the next character after
3457 the count. There are some weird rules in effect here.
3459 If *type does not point at a string of digits, return zero.
3461 If *type points at a string of digits followed by an
3462 underscore, set *count to their value as an integer, advance
3463 *type to point *after the underscore, and return 1.
3465 If *type points at a string of digits not followed by an
3466 underscore, consume only the first digit. Set *count to its
3467 value as an integer, leave *type pointing after that digit,
3470 The excuse for this odd behavior: in the ARM and HP demangling
3471 styles, a type can be followed by a repeat count of the form
3474 `x' is a single digit specifying how many additional copies
3475 of the type to append to the argument list, and
3477 `y' is one or more digits, specifying the zero-based index of
3478 the first repeated argument in the list. Yes, as you're
3479 unmangling the name you can figure this out yourself, but
3482 So, for example, in `bar__3fooFPiN51', the first argument is a
3483 pointer to an integer (`Pi'), and then the next five arguments
3484 are the same (`N5'), and the first repeat is the function's
3485 second argument (`1').
3489 get_count (const char **type
, int *count
)
3494 if (!ISDIGIT ((unsigned char)**type
))
3498 *count
= **type
- '0';
3500 if (ISDIGIT ((unsigned char)**type
))
3510 while (ISDIGIT ((unsigned char)*p
));
3521 /* RESULT will be initialised here; it will be freed on failure. The
3522 value returned is really a type_kind_t. */
3525 do_type (struct work_stuff
*work
, const char **mangled
, string
*result
)
3531 const char *remembered_type
;
3533 type_kind_t tk
= tk_none
;
3535 string_init (&decl
);
3536 string_init (result
);
3540 while (success
&& !done
)
3546 /* A pointer type */
3550 if (! (work
-> options
& DMGL_JAVA
))
3551 string_prepend (&decl
, "*");
3556 /* A reference type */
3559 string_prepend (&decl
, "&");
3568 if (!STRING_EMPTY (&decl
)
3569 && (decl
.b
[0] == '*' || decl
.b
[0] == '&'))
3571 string_prepend (&decl
, "(");
3572 string_append (&decl
, ")");
3574 string_append (&decl
, "[");
3575 if (**mangled
!= '_')
3576 success
= demangle_template_value_parm (work
, mangled
, &decl
,
3578 if (**mangled
== '_')
3580 string_append (&decl
, "]");
3584 /* A back reference to a previously seen type */
3587 if (!get_count (mangled
, &n
) || n
>= work
-> ntypes
)
3593 remembered_type
= work
-> typevec
[n
];
3594 mangled
= &remembered_type
;
3601 if (!STRING_EMPTY (&decl
)
3602 && (decl
.b
[0] == '*' || decl
.b
[0] == '&'))
3604 string_prepend (&decl
, "(");
3605 string_append (&decl
, ")");
3607 /* After picking off the function args, we expect to either find the
3608 function return type (preceded by an '_') or the end of the
3610 if (!demangle_nested_args (work
, mangled
, &decl
)
3611 || (**mangled
!= '_' && **mangled
!= '\0'))
3616 if (success
&& (**mangled
== '_'))
3623 type_quals
= TYPE_UNQUALIFIED
;
3625 member
= **mangled
== 'M';
3628 string_append (&decl
, ")");
3630 /* We don't need to prepend `::' for a qualified name;
3631 demangle_qualified will do that for us. */
3632 if (**mangled
!= 'Q')
3633 string_prepend (&decl
, SCOPE_STRING (work
));
3635 if (ISDIGIT ((unsigned char)**mangled
))
3637 n
= consume_count (mangled
);
3639 || (int) strlen (*mangled
) < n
)
3644 string_prependn (&decl
, *mangled
, n
);
3647 else if (**mangled
== 'X' || **mangled
== 'Y')
3650 do_type (work
, mangled
, &temp
);
3651 string_prepends (&decl
, &temp
);
3652 string_delete (&temp
);
3654 else if (**mangled
== 't')
3657 string_init (&temp
);
3658 success
= demangle_template (work
, mangled
, &temp
,
3662 string_prependn (&decl
, temp
.b
, temp
.p
- temp
.b
);
3663 string_delete (&temp
);
3668 else if (**mangled
== 'Q')
3670 success
= demangle_qualified (work
, mangled
, &decl
,
3682 string_prepend (&decl
, "(");
3690 type_quals
|= code_for_qualifier (**mangled
);
3698 if (*(*mangled
)++ != 'F')
3704 if ((member
&& !demangle_nested_args (work
, mangled
, &decl
))
3705 || **mangled
!= '_')
3711 if (! PRINT_ANSI_QUALIFIERS
)
3715 if (type_quals
!= TYPE_UNQUALIFIED
)
3717 APPEND_BLANK (&decl
);
3718 string_append (&decl
, qualifier_string (type_quals
));
3729 if (PRINT_ANSI_QUALIFIERS
)
3731 if (!STRING_EMPTY (&decl
))
3732 string_prepend (&decl
, " ");
3734 string_prepend (&decl
, demangle_qualifier (**mangled
));
3749 if (success
) switch (**mangled
)
3751 /* A qualified name, such as "Outer::Inner". */
3755 success
= demangle_qualified (work
, mangled
, result
, 0, 1);
3759 /* A back reference to a previously seen squangled type */
3762 if (!get_count (mangled
, &n
) || n
>= work
-> numb
)
3765 string_append (result
, work
->btypevec
[n
]);
3770 /* A template parm. We substitute the corresponding argument. */
3775 idx
= consume_count_with_underscores (mangled
);
3778 || (work
->tmpl_argvec
&& idx
>= work
->ntmpl_args
)
3779 || consume_count_with_underscores (mangled
) == -1)
3785 if (work
->tmpl_argvec
)
3786 string_append (result
, work
->tmpl_argvec
[idx
]);
3788 string_append_template_idx (result
, idx
);
3795 success
= demangle_fund_type (work
, mangled
, result
);
3797 tk
= (type_kind_t
) success
;
3803 if (!STRING_EMPTY (&decl
))
3805 string_append (result
, " ");
3806 string_appends (result
, &decl
);
3810 string_delete (result
);
3811 string_delete (&decl
);
3814 /* Assume an integral type, if we're not sure. */
3815 return (int) ((tk
== tk_none
) ? tk_integral
: tk
);
3820 /* Given a pointer to a type string that represents a fundamental type
3821 argument (int, long, unsigned int, etc) in TYPE, a pointer to the
3822 string in which the demangled output is being built in RESULT, and
3823 the WORK structure, decode the types and add them to the result.
3828 "Sl" => "signed long"
3829 "CUs" => "const unsigned short"
3831 The value returned is really a type_kind_t. */
3834 demangle_fund_type (struct work_stuff
*work
,
3835 const char **mangled
, string
*result
)
3839 char buf
[INTBUF_SIZE
+ 5 /* 'int%u_t' */];
3840 unsigned int dec
= 0;
3841 type_kind_t tk
= tk_integral
;
3843 /* First pick off any type qualifiers. There can be more than one. */
3852 if (PRINT_ANSI_QUALIFIERS
)
3854 if (!STRING_EMPTY (result
))
3855 string_prepend (result
, " ");
3856 string_prepend (result
, demangle_qualifier (**mangled
));
3862 APPEND_BLANK (result
);
3863 string_append (result
, "unsigned");
3865 case 'S': /* signed char only */
3867 APPEND_BLANK (result
);
3868 string_append (result
, "signed");
3872 APPEND_BLANK (result
);
3873 string_append (result
, "__complex");
3881 /* Now pick off the fundamental type. There can be only one. */
3890 APPEND_BLANK (result
);
3891 string_append (result
, "void");
3895 APPEND_BLANK (result
);
3896 string_append (result
, "long long");
3900 APPEND_BLANK (result
);
3901 string_append (result
, "long");
3905 APPEND_BLANK (result
);
3906 string_append (result
, "int");
3910 APPEND_BLANK (result
);
3911 string_append (result
, "short");
3915 APPEND_BLANK (result
);
3916 string_append (result
, "bool");
3921 APPEND_BLANK (result
);
3922 string_append (result
, "char");
3927 APPEND_BLANK (result
);
3928 string_append (result
, "wchar_t");
3933 APPEND_BLANK (result
);
3934 string_append (result
, "long double");
3939 APPEND_BLANK (result
);
3940 string_append (result
, "double");
3945 APPEND_BLANK (result
);
3946 string_append (result
, "float");
3951 if (!ISDIGIT ((unsigned char)**mangled
))
3958 if (**mangled
== '_')
3963 i
< (long) sizeof (buf
) - 1 && **mangled
&& **mangled
!= '_';
3966 if (**mangled
!= '_')
3976 strncpy (buf
, *mangled
, 2);
3978 *mangled
+= min (strlen (*mangled
), 2);
3980 sscanf (buf
, "%x", &dec
);
3981 sprintf (buf
, "int%u_t", dec
);
3982 APPEND_BLANK (result
);
3983 string_append (result
, buf
);
3987 /* An explicit type, such as "6mytype" or "7integer" */
3999 int bindex
= register_Btype (work
);
4001 string_init (&btype
);
4002 if (demangle_class_name (work
, mangled
, &btype
)) {
4003 remember_Btype (work
, btype
.b
, LEN_STRING (&btype
), bindex
);
4004 APPEND_BLANK (result
);
4005 string_appends (result
, &btype
);
4009 string_delete (&btype
);
4015 string_init (&btype
);
4016 success
= demangle_template (work
, mangled
, &btype
, 0, 1, 1);
4017 string_appends (result
, &btype
);
4018 string_delete (&btype
);
4026 return success
? ((int) tk
) : 0;
4030 /* Handle a template's value parameter for HP aCC (extension from ARM)
4031 **mangled points to 'S' or 'U' */
4034 do_hpacc_template_const_value (struct work_stuff
*work ATTRIBUTE_UNUSED
,
4035 const char **mangled
, string
*result
)
4039 if (**mangled
!= 'U' && **mangled
!= 'S')
4042 unsigned_const
= (**mangled
== 'U');
4049 string_append (result
, "-");
4055 /* special case for -2^31 */
4056 string_append (result
, "-2147483648");
4063 /* We have to be looking at an integer now */
4064 if (!(ISDIGIT ((unsigned char)**mangled
)))
4067 /* We only deal with integral values for template
4068 parameters -- so it's OK to look only for digits */
4069 while (ISDIGIT ((unsigned char)**mangled
))
4071 char_str
[0] = **mangled
;
4072 string_append (result
, char_str
);
4077 string_append (result
, "U");
4079 /* FIXME? Some day we may have 64-bit (or larger :-) ) constants
4080 with L or LL suffixes. pai/1997-09-03 */
4082 return 1; /* success */
4085 /* Handle a template's literal parameter for HP aCC (extension from ARM)
4086 **mangled is pointing to the 'A' */
4089 do_hpacc_template_literal (struct work_stuff
*work
, const char **mangled
,
4092 int literal_len
= 0;
4096 if (**mangled
!= 'A')
4101 literal_len
= consume_count (mangled
);
4103 if (literal_len
<= 0)
4106 /* Literal parameters are names of arrays, functions, etc. and the
4107 canonical representation uses the address operator */
4108 string_append (result
, "&");
4110 /* Now recursively demangle the literal name */
4111 recurse
= XNEWVEC (char, literal_len
+ 1);
4112 memcpy (recurse
, *mangled
, literal_len
);
4113 recurse
[literal_len
] = '\000';
4115 recurse_dem
= cplus_demangle (recurse
, work
->options
);
4119 string_append (result
, recurse_dem
);
4124 string_appendn (result
, *mangled
, literal_len
);
4126 (*mangled
) += literal_len
;
4133 snarf_numeric_literal (const char **args
, string
*arg
)
4138 string_append (arg
, char_str
);
4141 else if (**args
== '+')
4144 if (!ISDIGIT ((unsigned char)**args
))
4147 while (ISDIGIT ((unsigned char)**args
))
4149 char_str
[0] = **args
;
4150 string_append (arg
, char_str
);
4157 /* Demangle the next argument, given by MANGLED into RESULT, which
4158 *should be an uninitialized* string. It will be initialized here,
4159 and free'd should anything go wrong. */
4162 do_arg (struct work_stuff
*work
, const char **mangled
, string
*result
)
4164 /* Remember where we started so that we can record the type, for
4165 non-squangling type remembering. */
4166 const char *start
= *mangled
;
4168 string_init (result
);
4170 if (work
->nrepeats
> 0)
4174 if (work
->previous_argument
== 0)
4177 /* We want to reissue the previous type in this argument list. */
4178 string_appends (result
, work
->previous_argument
);
4182 if (**mangled
== 'n')
4184 /* A squangling-style repeat. */
4186 work
->nrepeats
= consume_count(mangled
);
4188 if (work
->nrepeats
<= 0)
4189 /* This was not a repeat count after all. */
4192 if (work
->nrepeats
> 9)
4194 if (**mangled
!= '_')
4195 /* The repeat count should be followed by an '_' in this
4202 /* Now, the repeat is all set up. */
4203 return do_arg (work
, mangled
, result
);
4206 /* Save the result in WORK->previous_argument so that we can find it
4207 if it's repeated. Note that saving START is not good enough: we
4208 do not want to add additional types to the back-referenceable
4209 type vector when processing a repeated type. */
4210 if (work
->previous_argument
)
4211 string_delete (work
->previous_argument
);
4213 work
->previous_argument
= XNEW (string
);
4215 if (!do_type (work
, mangled
, work
->previous_argument
))
4218 string_appends (result
, work
->previous_argument
);
4220 remember_type (work
, start
, *mangled
- start
);
4225 remember_type (struct work_stuff
*work
, const char *start
, int len
)
4229 if (work
->forgetting_types
)
4232 if (work
-> ntypes
>= work
-> typevec_size
)
4234 if (work
-> typevec_size
== 0)
4236 work
-> typevec_size
= 3;
4237 work
-> typevec
= XNEWVEC (char *, work
->typevec_size
);
4241 work
-> typevec_size
*= 2;
4243 = XRESIZEVEC (char *, work
->typevec
, work
->typevec_size
);
4246 tem
= XNEWVEC (char, len
+ 1);
4247 memcpy (tem
, start
, len
);
4249 work
-> typevec
[work
-> ntypes
++] = tem
;
4253 /* Remember a K type class qualifier. */
4255 remember_Ktype (struct work_stuff
*work
, const char *start
, int len
)
4259 if (work
-> numk
>= work
-> ksize
)
4261 if (work
-> ksize
== 0)
4264 work
-> ktypevec
= XNEWVEC (char *, work
->ksize
);
4270 = XRESIZEVEC (char *, work
->ktypevec
, work
->ksize
);
4273 tem
= XNEWVEC (char, len
+ 1);
4274 memcpy (tem
, start
, len
);
4276 work
-> ktypevec
[work
-> numk
++] = tem
;
4279 /* Register a B code, and get an index for it. B codes are registered
4280 as they are seen, rather than as they are completed, so map<temp<char> >
4281 registers map<temp<char> > as B0, and temp<char> as B1 */
4284 register_Btype (struct work_stuff
*work
)
4288 if (work
-> numb
>= work
-> bsize
)
4290 if (work
-> bsize
== 0)
4293 work
-> btypevec
= XNEWVEC (char *, work
->bsize
);
4299 = XRESIZEVEC (char *, work
->btypevec
, work
->bsize
);
4302 ret
= work
-> numb
++;
4303 work
-> btypevec
[ret
] = NULL
;
4307 /* Store a value into a previously registered B code type. */
4310 remember_Btype (struct work_stuff
*work
, const char *start
,
4315 tem
= XNEWVEC (char, len
+ 1);
4316 memcpy (tem
, start
, len
);
4318 work
-> btypevec
[index
] = tem
;
4321 /* Lose all the info related to B and K type codes. */
4323 forget_B_and_K_types (struct work_stuff
*work
)
4327 while (work
-> numk
> 0)
4329 i
= --(work
-> numk
);
4330 if (work
-> ktypevec
[i
] != NULL
)
4332 free (work
-> ktypevec
[i
]);
4333 work
-> ktypevec
[i
] = NULL
;
4337 while (work
-> numb
> 0)
4339 i
= --(work
-> numb
);
4340 if (work
-> btypevec
[i
] != NULL
)
4342 free (work
-> btypevec
[i
]);
4343 work
-> btypevec
[i
] = NULL
;
4347 /* Forget the remembered types, but not the type vector itself. */
4350 forget_types (struct work_stuff
*work
)
4354 while (work
-> ntypes
> 0)
4356 i
= --(work
-> ntypes
);
4357 if (work
-> typevec
[i
] != NULL
)
4359 free (work
-> typevec
[i
]);
4360 work
-> typevec
[i
] = NULL
;
4365 /* Process the argument list part of the signature, after any class spec
4366 has been consumed, as well as the first 'F' character (if any). For
4369 "__als__3fooRT0" => process "RT0"
4370 "complexfunc5__FPFPc_PFl_i" => process "PFPc_PFl_i"
4372 DECLP must be already initialised, usually non-empty. It won't be freed
4375 Note that g++ differs significantly from ARM and lucid style mangling
4376 with regards to references to previously seen types. For example, given
4377 the source fragment:
4381 foo::foo (int, foo &ia, int, foo &ib, int, foo &ic);
4384 foo::foo (int, foo &ia, int, foo &ib, int, foo &ic) { ia = ib = ic; }
4385 void foo (int, foo &ia, int, foo &ib, int, foo &ic) { ia = ib = ic; }
4387 g++ produces the names:
4392 while lcc (and presumably other ARM style compilers as well) produces:
4394 foo__FiR3fooT1T2T1T2
4395 __ct__3fooFiR3fooT1T2T1T2
4397 Note that g++ bases its type numbers starting at zero and counts all
4398 previously seen types, while lucid/ARM bases its type numbers starting
4399 at one and only considers types after it has seen the 'F' character
4400 indicating the start of the function args. For lucid/ARM style, we
4401 account for this difference by discarding any previously seen types when
4402 we see the 'F' character, and subtracting one from the type number
4408 demangle_args (struct work_stuff
*work
, const char **mangled
,
4418 if (PRINT_ARG_TYPES
)
4420 string_append (declp
, "(");
4421 if (**mangled
== '\0')
4423 string_append (declp
, "void");
4427 while ((**mangled
!= '_' && **mangled
!= '\0' && **mangled
!= 'e')
4428 || work
->nrepeats
> 0)
4430 if ((**mangled
== 'N') || (**mangled
== 'T'))
4432 temptype
= *(*mangled
)++;
4434 if (temptype
== 'N')
4436 if (!get_count (mangled
, &r
))
4445 if ((HP_DEMANGLING
|| ARM_DEMANGLING
|| EDG_DEMANGLING
) && work
-> ntypes
>= 10)
4447 /* If we have 10 or more types we might have more than a 1 digit
4448 index so we'll have to consume the whole count here. This
4449 will lose if the next thing is a type name preceded by a
4450 count but it's impossible to demangle that case properly
4451 anyway. Eg if we already have 12 types is T12Pc "(..., type1,
4452 Pc, ...)" or "(..., type12, char *, ...)" */
4453 if ((t
= consume_count(mangled
)) <= 0)
4460 if (!get_count (mangled
, &t
))
4465 if (LUCID_DEMANGLING
|| ARM_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
)
4469 /* Validate the type index. Protect against illegal indices from
4470 malformed type strings. */
4471 if ((t
< 0) || (t
>= work
-> ntypes
))
4475 while (work
->nrepeats
> 0 || --r
>= 0)
4477 tem
= work
-> typevec
[t
];
4478 if (need_comma
&& PRINT_ARG_TYPES
)
4480 string_append (declp
, ", ");
4482 if (!do_arg (work
, &tem
, &arg
))
4486 if (PRINT_ARG_TYPES
)
4488 string_appends (declp
, &arg
);
4490 string_delete (&arg
);
4496 if (need_comma
&& PRINT_ARG_TYPES
)
4497 string_append (declp
, ", ");
4498 if (!do_arg (work
, mangled
, &arg
))
4500 if (PRINT_ARG_TYPES
)
4501 string_appends (declp
, &arg
);
4502 string_delete (&arg
);
4507 if (**mangled
== 'e')
4510 if (PRINT_ARG_TYPES
)
4514 string_append (declp
, ",");
4516 string_append (declp
, "...");
4520 if (PRINT_ARG_TYPES
)
4522 string_append (declp
, ")");
4527 /* Like demangle_args, but for demangling the argument lists of function
4528 and method pointers or references, not top-level declarations. */
4531 demangle_nested_args (struct work_stuff
*work
, const char **mangled
,
4534 string
* saved_previous_argument
;
4538 /* The G++ name-mangling algorithm does not remember types on nested
4539 argument lists, unless -fsquangling is used, and in that case the
4540 type vector updated by remember_type is not used. So, we turn
4541 off remembering of types here. */
4542 ++work
->forgetting_types
;
4544 /* For the repeat codes used with -fsquangling, we must keep track of
4545 the last argument. */
4546 saved_previous_argument
= work
->previous_argument
;
4547 saved_nrepeats
= work
->nrepeats
;
4548 work
->previous_argument
= 0;
4551 /* Actually demangle the arguments. */
4552 result
= demangle_args (work
, mangled
, declp
);
4554 /* Restore the previous_argument field. */
4555 if (work
->previous_argument
)
4557 string_delete (work
->previous_argument
);
4558 free ((char *) work
->previous_argument
);
4560 work
->previous_argument
= saved_previous_argument
;
4561 --work
->forgetting_types
;
4562 work
->nrepeats
= saved_nrepeats
;
4567 /* Returns 1 if a valid function name was found or 0 otherwise. */
4570 demangle_function_name (struct work_stuff
*work
, const char **mangled
,
4571 string
*declp
, const char *scan
)
4577 string_appendn (declp
, (*mangled
), scan
- (*mangled
));
4578 string_need (declp
, 1);
4579 *(declp
-> p
) = '\0';
4581 /* Consume the function name, including the "__" separating the name
4582 from the signature. We are guaranteed that SCAN points to the
4585 (*mangled
) = scan
+ 2;
4586 /* We may be looking at an instantiation of a template function:
4587 foo__Xt1t2_Ft3t4, where t1, t2, ... are template arguments and a
4588 following _F marks the start of the function arguments. Handle
4589 the template arguments first. */
4591 if (HP_DEMANGLING
&& (**mangled
== 'X'))
4593 demangle_arm_hp_template (work
, mangled
, 0, declp
);
4594 /* This leaves MANGLED pointing to the 'F' marking func args */
4597 if (LUCID_DEMANGLING
|| ARM_DEMANGLING
|| HP_DEMANGLING
|| EDG_DEMANGLING
)
4600 /* See if we have an ARM style constructor or destructor operator.
4601 If so, then just record it, clear the decl, and return.
4602 We can't build the actual constructor/destructor decl until later,
4603 when we recover the class name from the signature. */
4605 if (strcmp (declp
-> b
, "__ct") == 0)
4607 work
-> constructor
+= 1;
4608 string_clear (declp
);
4611 else if (strcmp (declp
-> b
, "__dt") == 0)
4613 work
-> destructor
+= 1;
4614 string_clear (declp
);
4619 if (declp
->p
- declp
->b
>= 3
4620 && declp
->b
[0] == 'o'
4621 && declp
->b
[1] == 'p'
4622 && strchr (cplus_markers
, declp
->b
[2]) != NULL
)
4624 /* see if it's an assignment expression */
4625 if (declp
->p
- declp
->b
>= 10 /* op$assign_ */
4626 && memcmp (declp
->b
+ 3, "assign_", 7) == 0)
4628 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
4630 int len
= declp
->p
- declp
->b
- 10;
4631 if ((int) strlen (optable
[i
].in
) == len
4632 && memcmp (optable
[i
].in
, declp
->b
+ 10, len
) == 0)
4634 string_clear (declp
);
4635 string_append (declp
, "operator");
4636 string_append (declp
, optable
[i
].out
);
4637 string_append (declp
, "=");
4644 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
4646 int len
= declp
->p
- declp
->b
- 3;
4647 if ((int) strlen (optable
[i
].in
) == len
4648 && memcmp (optable
[i
].in
, declp
->b
+ 3, len
) == 0)
4650 string_clear (declp
);
4651 string_append (declp
, "operator");
4652 string_append (declp
, optable
[i
].out
);
4658 else if (declp
->p
- declp
->b
>= 5 && memcmp (declp
->b
, "type", 4) == 0
4659 && strchr (cplus_markers
, declp
->b
[4]) != NULL
)
4661 /* type conversion operator */
4663 if (do_type (work
, &tem
, &type
))
4665 string_clear (declp
);
4666 string_append (declp
, "operator ");
4667 string_appends (declp
, &type
);
4668 string_delete (&type
);
4671 else if (declp
->b
[0] == '_' && declp
->b
[1] == '_'
4672 && declp
->b
[2] == 'o' && declp
->b
[3] == 'p')
4675 /* type conversion operator. */
4677 if (do_type (work
, &tem
, &type
))
4679 string_clear (declp
);
4680 string_append (declp
, "operator ");
4681 string_appends (declp
, &type
);
4682 string_delete (&type
);
4685 else if (declp
->b
[0] == '_' && declp
->b
[1] == '_'
4686 && ISLOWER((unsigned char)declp
->b
[2])
4687 && ISLOWER((unsigned char)declp
->b
[3]))
4689 if (declp
->b
[4] == '\0')
4692 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
4694 if (strlen (optable
[i
].in
) == 2
4695 && memcmp (optable
[i
].in
, declp
->b
+ 2, 2) == 0)
4697 string_clear (declp
);
4698 string_append (declp
, "operator");
4699 string_append (declp
, optable
[i
].out
);
4706 if (declp
->b
[2] == 'a' && declp
->b
[5] == '\0')
4709 for (i
= 0; i
< ARRAY_SIZE (optable
); i
++)
4711 if (strlen (optable
[i
].in
) == 3
4712 && memcmp (optable
[i
].in
, declp
->b
+ 2, 3) == 0)
4714 string_clear (declp
);
4715 string_append (declp
, "operator");
4716 string_append (declp
, optable
[i
].out
);
4724 /* If a function name was obtained but it's not valid, we were not
4726 if (LEN_STRING (declp
) == 1 && declp
->b
[0] == '.')
4732 /* a mini string-handling package */
4735 string_need (string
*s
, int n
)
4745 s
->p
= s
->b
= XNEWVEC (char, n
);
4748 else if (s
->e
- s
->p
< n
)
4753 s
->b
= XRESIZEVEC (char, s
->b
, n
);
4760 string_delete (string
*s
)
4765 s
->b
= s
->e
= s
->p
= NULL
;
4770 string_init (string
*s
)
4772 s
->b
= s
->p
= s
->e
= NULL
;
4776 string_clear (string
*s
)
4784 string_empty (string
*s
)
4786 return (s
->b
== s
->p
);
4792 string_append (string
*p
, const char *s
)
4795 if (s
== NULL
|| *s
== '\0')
4799 memcpy (p
->p
, s
, n
);
4804 string_appends (string
*p
, string
*s
)
4812 memcpy (p
->p
, s
->b
, n
);
4818 string_appendn (string
*p
, const char *s
, int n
)
4823 memcpy (p
->p
, s
, n
);
4829 string_prepend (string
*p
, const char *s
)
4831 if (s
!= NULL
&& *s
!= '\0')
4833 string_prependn (p
, s
, strlen (s
));
4838 string_prepends (string
*p
, string
*s
)
4842 string_prependn (p
, s
->b
, s
->p
- s
->b
);
4847 string_prependn (string
*p
, const char *s
, int n
)
4854 for (q
= p
->p
- 1; q
>= p
->b
; q
--)
4858 memcpy (p
->b
, s
, n
);
4864 string_append_template_idx (string
*s
, int idx
)
4866 char buf
[INTBUF_SIZE
+ 1 /* 'T' */];
4867 sprintf(buf
, "T%d", idx
);
4868 string_append (s
, buf
);