1 /* Demangler for IA64 / g++ standard C++ ABI.
2 Copyright (C) 2000 CodeSourcery LLC.
3 Written by Alex Samuel <samuel@codesourcery.com>.
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20 /* This file implements demangling of C++ names mangled according to
21 the IA64 / g++ standard C++ ABI. Use the cp_demangle function to
22 demangle a mangled name, or compile with the preprocessor macro
23 STANDALONE_DEMANGLER defined to create a demangling filter
36 #if defined(CP_DEMANGLE_DEBUG) || defined(STANDALONE_DEMANGLER)
45 #include "libiberty.h"
46 #include "dyn-string.h"
48 /* If CP_DEMANGLE_DEBUG is defined, a trace of the grammar evaluation,
49 and other debugging output, will be generated. */
50 #ifdef CP_DEMANGLE_DEBUG
51 #define DEMANGLE_TRACE(PRODUCTION, DM) \
52 fprintf (stderr, " -> %-24s at position %3d\n", \
53 (PRODUCTION), current_position (DM));
55 #define DEMANGLE_TRACE(PRODUCTION, DM)
58 /* If flag_verbose is zero, some simplifications will be made to the
59 output to make it easier to read and supress details that are
60 generally not of interest to the average C++ programmer.
61 Otherwise, the demangled representation will attempt to convey as
62 much information as the mangled form. */
63 static int flag_verbose;
65 /* If flag_strict is non-zero, demangle strictly according to the
66 specification -- don't demangle special g++ manglings. */
67 static int flag_strict;
69 /* String_list_t is an extended form of dyn_string_t which provides a link
70 field. A string_list_t may safely be cast to and used as a
73 struct string_list_def
75 struct dyn_string string;
76 struct string_list_def *next;
79 typedef struct string_list_def *string_list_t;
81 /* Data structure representing a potential substitution. */
83 struct substitution_def
85 /* The demangled text of the substitution. */
88 /* The template parameter that this represents, indexed from zero.
89 If this is not a template paramter number, the value is
91 int template_parm_number;
93 /* Whether this substitution represents a template item. */
97 #define NOT_TEMPLATE_PARM (-1)
99 /* Data structure representing a template argument list. */
101 struct template_arg_list_def
103 /* The next (lower) template argument list in the stack of currently
104 active template arguments. */
105 struct template_arg_list_def *next;
107 /* The first element in the list of template arguments in
108 left-to-right order. */
109 string_list_t first_argument;
111 /* The last element in the arguments lists. */
112 string_list_t last_argument;
115 typedef struct template_arg_list_def *template_arg_list_t;
117 /* Data structure to maintain the state of the current demangling. */
119 struct demangling_def
121 /* The full mangled name being mangled. */
124 /* Pointer into name at the current position. */
127 /* Stack for strings containing demangled result generated so far.
128 Text is emitted to the topmost (first) string. */
129 string_list_t result;
131 /* The number of presently available substitutions. */
132 int num_substitutions;
134 /* The allocated size of the substitutions array. */
135 int substitutions_allocated;
137 /* An array of available substitutions. The number of elements in
138 the array is given by num_substitions, and the allocated array
139 size in substitutions_size.
141 The most recent substition is at the end, so
143 - `S_' corresponds to substititutions[num_substitutions - 1]
144 - `S0_' corresponds to substititutions[num_substitutions - 2]
147 struct substitution_def *substitutions;
149 /* The stack of template argument lists. */
150 template_arg_list_t template_arg_lists;
152 /* The most recently demangled source-name. */
153 dyn_string_t last_source_name;
156 typedef struct demangling_def *demangling_t;
158 /* This type is the standard return code from most functions. Values
159 other than STATUS_OK contain descriptive messages. */
160 typedef const char *status_t;
162 /* Special values that can be used as a status_t. */
163 #define STATUS_OK NULL
164 #define STATUS_ERROR "Error."
165 #define STATUS_UNIMPLEMENTED "Unimplemented."
166 #define STATUS_INTERNAL_ERROR "Internal error."
168 static void int_to_dyn_string
169 PARAMS ((int, dyn_string_t));
170 static string_list_t string_list_new
172 static void string_list_delete
173 PARAMS ((string_list_t));
174 static void result_close_template_list
175 PARAMS ((demangling_t));
176 static void result_push
177 PARAMS ((demangling_t));
178 static string_list_t result_pop
179 PARAMS ((demangling_t));
180 static int substitution_start
181 PARAMS ((demangling_t));
182 static void substitution_add
183 PARAMS ((demangling_t, int, int, int));
184 static dyn_string_t substitution_get
185 PARAMS ((demangling_t, int, int *));
186 #ifdef CP_DEMANGLE_DEBUG
187 static void substitutions_print
188 PARAMS ((demangling_t, FILE *));
190 static template_arg_list_t template_arg_list_new
192 static void template_arg_list_delete
193 PARAMS ((template_arg_list_t));
194 static void template_arg_list_add_arg
195 PARAMS ((template_arg_list_t, string_list_t));
196 static string_list_t template_arg_list_get_arg
197 PARAMS ((template_arg_list_t, int));
198 static void push_template_arg_list
199 PARAMS ((demangling_t, template_arg_list_t));
200 static void pop_to_template_arg_list
201 PARAMS ((demangling_t, template_arg_list_t));
202 #ifdef CP_DEMANGLE_DEBUG
203 static void template_arg_list_print
204 PARAMS ((template_arg_list_t, FILE *));
206 static template_arg_list_t current_template_arg_list
207 PARAMS ((demangling_t));
208 static demangling_t demangling_new
210 static void demangling_delete
211 PARAMS ((demangling_t));
213 /* The last character of DS. Warning: DS is evaluated twice. */
214 #define dyn_string_last_char(DS) \
215 (dyn_string_buf (DS)[dyn_string_length (DS) - 1])
217 /* Append a space character (` ') to DS if it does not already end
219 #define dyn_string_append_space(DS) \
222 if (dyn_string_length (DS) > 0 \
223 && dyn_string_last_char (DS) != ' ') \
224 dyn_string_append_char ((DS), ' '); \
228 /* Returns the index of the current position in the mangled name. */
229 #define current_position(DM) ((DM)->next - (DM)->name)
231 /* Returns the character at the current position of the mangled name. */
232 #define peek_char(DM) (*((DM)->next))
234 /* Returns the character one past the current position of the mangled
236 #define peek_char_next(DM) \
237 (peek_char (DM) == '\0' ? '\0' : (*((DM)->next + 1)))
239 /* Returns the character at the current position, and advances the
240 current position to the next character. */
241 #define next_char(DM) (*((DM)->next)++)
243 /* Returns non-zero if the current position is the end of the mangled
244 name, i.e. one past the last character. */
245 #define end_of_name_p(DM) (peek_char (DM) == '\0')
247 /* Advances the current position by one character. */
248 #define advance_char(DM) (++(DM)->next)
250 /* Returns the string containing the current demangled result. */
251 #define result_string(DM) (&(DM)->result->string)
253 /* Appends a dyn_string_t to the demangled result. */
254 #define result_append_string(DM, STRING) \
255 dyn_string_append (&(DM)->result->string, (STRING))
257 /* Appends NUL-terminated string CSTR to the demangled result. */
258 #define result_append(DM, CSTR) \
259 dyn_string_append_cstr (&(DM)->result->string, (CSTR))
261 /* Appends character CHAR to the demangled result. */
262 #define result_append_char(DM, CHAR) \
263 dyn_string_append_char (&(DM)->result->string, (CHAR))
265 /* The length of the current demangled result. */
266 #define result_length(DM) \
267 dyn_string_length (&(DM)->result->string)
269 /* Appends a space to the demangled result if the last character is
271 #define result_append_space(DM) \
272 dyn_string_append_space (&(DM)->result->string)
274 /* Evaluate EXPR, which must produce a status_t. If the status code
275 indicates an error, return from the current function with that
277 #define RETURN_IF_ERROR(EXPR) \
281 if (s != STATUS_OK) \
286 /* Appends a base 10 representation of VALUE to DS. */
289 int_to_dyn_string (value, ds)
296 /* Handle zero up front. */
299 dyn_string_append_char (ds, '0');
303 /* For negative numbers, emit a minus sign. */
306 dyn_string_append_char (ds, '-');
310 /* Find the power of 10 of the first digit. */
318 /* Write the digits. */
321 int digit = value / mask;
322 dyn_string_append_char (ds, '0' + digit);
323 value -= digit * mask;
328 /* Creates a new string list node. The contents of the string are
329 empty, but the initial buffer allocation is LENGTH. The string
330 list node should be deleted with string_list_delete. */
333 string_list_new (length)
337 (string_list_t) xmalloc (sizeof (struct string_list_def));
338 dyn_string_init ((dyn_string_t) s, length);
342 /* Deletes the entire string list starting at NODE. */
345 string_list_delete (node)
350 string_list_t next = node->next;
356 /* Appends a greater-than character to the demangled result. If the
357 last character is a greater-than character, a space is inserted
358 first, so that the two greater-than characters don't look like a
359 right shift token. */
362 result_close_template_list (dm)
365 dyn_string_t s = &dm->result->string;
366 if (dyn_string_last_char (s) == '>')
367 dyn_string_append_char (s, ' ');
368 dyn_string_append_char (s, '>');
371 /* Allocates and pushes a new string onto the demangled results stack
372 for DM. Subsequent demangling with DM will emit to the new string. */
378 string_list_t new_string = string_list_new (0);
379 new_string->next = (string_list_t) dm->result;
380 dm->result = new_string;
383 /* Removes and returns the topmost element on the demangled results
384 stack for DM. The caller assumes ownership for the returned
391 string_list_t top = dm->result;
392 dm->result = top->next;
396 /* Returns the start position of a fragment of the demangled result
397 that will be a substitution candidate. Should be called at the
398 start of productions that can add substitutions. */
401 substitution_start (dm)
404 return result_length (dm);
407 /* Adds the suffix of the current demangled result of DM starting at
408 START_POSITION as a potential substitution. If TEMPLATE_P is
409 non-zero, this potential substitution is a template-id.
411 If TEMPLATE_PARM_NUMBER is not NOT_TEMPLATE_PARM, the substitution
412 is for that particular <template-param>, and is distinct from other
413 otherwise-identical types and other <template-param>s with
414 different indices. */
417 substitution_add (dm, start_position, template_p, template_parm_number)
421 int template_parm_number;
423 dyn_string_t result = result_string (dm);
424 dyn_string_t substitution = dyn_string_new (0);
427 dyn_string_substring (substitution,
428 result, start_position, result_length (dm));
430 /* Check whether SUBSTITUTION already occurs. */
431 for (i = 0; i < dm->num_substitutions; ++i)
432 if (dyn_string_eq (dm->substitutions[i].text, substitution)
433 && dm->substitutions[i].template_parm_number == template_parm_number)
434 /* Found SUBSTITUTION already present. */
436 /* Callers expect this function to take ownership of
437 SUBSTITUTION, so delete it. */
438 dyn_string_delete (substitution);
442 /* If there's no room for the new entry, grow the array. */
443 if (dm->substitutions_allocated == dm->num_substitutions)
445 dm->substitutions_allocated *= 2;
446 dm->substitutions = (struct substitution_def *)
447 xrealloc (dm->substitutions,
448 sizeof (struct substitution_def)
449 * dm->substitutions_allocated);
452 /* Add the substitution to the array. */
453 dm->substitutions[i].text = substitution;
454 dm->substitutions[i].template_p = template_p;
455 dm->substitutions[i].template_parm_number = template_parm_number;
456 ++dm->num_substitutions;
458 #ifdef CP_DEMANGLE_DEBUG
459 substitutions_print (dm, stderr);
463 /* Returns the Nth-most-recent substitution. Sets *TEMPLATE_P to
464 non-zero if the substitution is a template-id, zero otherwise.
465 N is numbered from zero. DM retains ownership of the returned
466 string. If N is negative, or equal to or greater than the current
467 number of substitution candidates, returns NULL. */
470 substitution_get (dm, n, template_p)
475 struct substitution_def *sub;
477 /* Make sure N is in the valid range. */
478 if (n < 0 || n >= dm->num_substitutions)
481 sub = &(dm->substitutions[n]);
482 *template_p = sub->template_p;
486 #ifdef CP_DEMANGLE_DEBUG
487 /* Debugging routine to print the current substitutions to FP. */
490 substitutions_print (dm, fp)
495 int num = dm->num_substitutions;
497 fprintf (fp, "SUBSTITUTIONS:\n");
498 for (seq_id = -1; seq_id < num - 1; ++seq_id)
501 dyn_string_t text = substitution_get (dm, seq_id + 1, &template_p);
504 fprintf (fp, " S_ ");
506 fprintf (fp, " S%d_", seq_id);
507 fprintf (fp, " %c: %s\n", template_p ? '*' : ' ', dyn_string_buf (text));
511 #endif /* CP_DEMANGLE_DEBUG */
513 /* Creates a new template argument list. */
515 static template_arg_list_t
516 template_arg_list_new (void)
518 template_arg_list_t new_list
519 = (template_arg_list_t) xmalloc (sizeof (struct template_arg_list_def));
520 /* Initialize the new list to have no arguments. */
521 new_list->first_argument = NULL;
522 new_list->last_argument = NULL;
523 /* Return the new list. */
527 /* Deletes a template argument list and the template arguments it
531 template_arg_list_delete (list)
532 template_arg_list_t list;
534 /* If there are any arguments on LIST, delete them. */
535 if (list->first_argument != NULL)
536 string_list_delete (list->first_argument);
541 /* Adds ARG to the template argument list ARG_LIST. */
544 template_arg_list_add_arg (arg_list, arg)
545 template_arg_list_t arg_list;
548 if (arg_list->first_argument == NULL)
549 /* If there were no arguments before, ARG is the first one. */
550 arg_list->first_argument = arg;
552 /* Make ARG the last argument on the list. */
553 arg_list->last_argument->next = arg;
554 /* Make ARG the last on the list. */
555 arg_list->last_argument = arg;
559 /* Returns the template arugment at position INDEX in template
560 argument list ARG_LIST. */
563 template_arg_list_get_arg (arg_list, index)
564 template_arg_list_t arg_list;
567 string_list_t arg = arg_list->first_argument;
568 /* Scan down the list of arguments to find the one at position
574 /* Ran out of arguments before INDEX hit zero. That's an
578 /* Return the argument at position INDEX. */
582 /* Pushes ARG_LIST onto the top of the template argument list stack. */
585 push_template_arg_list (dm, arg_list)
587 template_arg_list_t arg_list;
589 arg_list->next = dm->template_arg_lists;
590 dm->template_arg_lists = arg_list;
591 #ifdef CP_DEMANGLE_DEBUG
592 fprintf (stderr, " ** pushing template arg list\n");
593 template_arg_list_print (arg_list, stderr);
597 /* Pops and deletes elements on the template argument list stack until
598 arg_list is the topmost element. If arg_list is NULL, all elements
599 are popped and deleted. */
602 pop_to_template_arg_list (dm, arg_list)
604 template_arg_list_t arg_list;
606 while (dm->template_arg_lists != arg_list)
608 template_arg_list_t top = dm->template_arg_lists;
609 /* Disconnect the topmost element from the list. */
610 dm->template_arg_lists = top->next;
611 /* Delete the popped element. */
612 template_arg_list_delete (top);
613 #ifdef CP_DEMANGLE_DEBUG
614 fprintf (stderr, " ** removing template arg list\n");
619 #ifdef CP_DEMANGLE_DEBUG
621 /* Prints the contents of ARG_LIST to FP. */
624 template_arg_list_print (arg_list, fp)
625 template_arg_list_t arg_list;
631 fprintf (fp, "TEMPLATE ARGUMENT LIST:\n");
632 for (arg = arg_list->first_argument; arg != NULL; arg = arg->next)
635 fprintf (fp, " T_ : ");
637 fprintf (fp, " T%d_ : ", index);
639 fprintf (fp, "%s\n", dyn_string_buf ((dyn_string_t) arg));
643 #endif /* CP_DEMANGLE_DEBUG */
645 /* Returns the topmost element on the stack of template argument
646 lists. If there is no list of template arguments, returns NULL. */
648 static template_arg_list_t
649 current_template_arg_list (dm)
652 return dm->template_arg_lists;
655 /* Allocates a demangling_t object for demangling mangled NAME. A new
656 result must be pushed before the returned object can be used. */
659 demangling_new (name)
662 demangling_t dm = (demangling_t)
663 xmalloc (sizeof (struct demangling_def));
668 dm->last_source_name = dyn_string_new (0);
669 dm->num_substitutions = 0;
670 dm->substitutions_allocated = 10;
671 dm->substitutions = (struct substitution_def *)
672 xmalloc (dm->substitutions_allocated * sizeof (struct substitution_def));
673 dm->template_arg_lists = NULL;
678 /* Deallocates a demangling_t object and all memory associated with
682 demangling_delete (dm)
686 template_arg_list_t arg_list = dm->template_arg_lists;
688 /* Delete the stack of template argument lists. */
689 while (arg_list != NULL)
691 template_arg_list_t next = arg_list->next;
692 template_arg_list_delete (arg_list);
695 /* Delete the list of substitutions. */
696 for (i = dm->num_substitutions; --i >= 0; )
697 dyn_string_delete (dm->substitutions[i].text);
698 free (dm->substitutions);
699 /* Delete the demangled result. */
700 string_list_delete (dm->result);
701 /* Delete the stored identifier name. */
702 dyn_string_delete (dm->last_source_name);
703 /* Delete the context object itself. */
707 /* These functions demangle an alternative of the corresponding
708 production in the mangling spec. The first argument of each is a
709 demangling context structure for the current demangling
710 operation. Most emit demangled text directly to the topmost result
711 string on the result string stack in the demangling context
714 static status_t demangle_char
715 PARAMS ((demangling_t, char));
716 static status_t demangle_mangled_name
717 PARAMS ((demangling_t));
718 static status_t demangle_encoding
719 PARAMS ((demangling_t));
720 static status_t demangle_name
721 PARAMS ((demangling_t, int *));
722 static status_t demangle_nested_name
723 PARAMS ((demangling_t, int *));
724 static status_t demangle_prefix
725 PARAMS ((demangling_t, int *));
726 static status_t demangle_unqualified_name
727 PARAMS ((demangling_t));
728 static status_t demangle_source_name
729 PARAMS ((demangling_t));
730 static status_t demangle_number
731 PARAMS ((demangling_t, int *, int, int));
732 static status_t demangle_number_literally
733 PARAMS ((demangling_t, dyn_string_t, int, int));
734 static status_t demangle_identifier
735 PARAMS ((demangling_t, int, dyn_string_t));
736 static status_t demangle_operator_name
737 PARAMS ((demangling_t, int, int *));
738 static status_t demangle_special_name
739 PARAMS ((demangling_t));
740 static status_t demangle_ctor_dtor_name
741 PARAMS ((demangling_t));
742 static status_t demangle_type_ptr
743 PARAMS ((demangling_t));
744 static status_t demangle_type
745 PARAMS ((demangling_t));
746 static status_t demangle_CV_qualifiers
747 PARAMS ((demangling_t, dyn_string_t));
748 static status_t demangle_builtin_type
749 PARAMS ((demangling_t));
750 static status_t demangle_function_type
751 PARAMS ((demangling_t, int));
752 static status_t demangle_bare_function_type
753 PARAMS ((demangling_t, int));
754 static status_t demangle_class_enum_type
755 PARAMS ((demangling_t, int *));
756 static status_t demangle_array_type
757 PARAMS ((demangling_t));
758 static status_t demangle_template_param
759 PARAMS ((demangling_t, int *));
760 static status_t demangle_template_args
761 PARAMS ((demangling_t));
762 static status_t demangle_literal
763 PARAMS ((demangling_t));
764 static status_t demangle_template_arg
765 PARAMS ((demangling_t));
766 static status_t demangle_expression
767 PARAMS ((demangling_t));;
768 static status_t demangle_scope_expression
769 PARAMS ((demangling_t));
770 static status_t demangle_expr_primary
771 PARAMS ((demangling_t));;
772 static status_t demangle_substitution
773 PARAMS ((demangling_t, int *, int *));
774 static status_t demangle_local_name
775 PARAMS ((demangling_t));
776 static status_t demangle_discriminator
777 PARAMS ((demangling_t, int));
779 /* When passed to demangle_bare_function_type, indicates that the
780 function's return type is not encoded before its parameter types. */
781 #define BFT_NO_RETURN_TYPE -1
783 /* Check that the next character is C. If so, consume it. If not,
787 demangle_char (dm, c)
791 static char *error_message = NULL;
793 if (peek_char (dm) == c)
800 if (error_message == NULL)
801 error_message = strdup ("Expected ?");
802 error_message[9] = c;
803 return error_message;
807 /* Demangles and emits a <mangled-name>.
809 <mangled-name> ::= _Z <encoding> */
812 demangle_mangled_name (dm)
815 DEMANGLE_TRACE ("mangled-name", dm);
816 RETURN_IF_ERROR (demangle_char (dm, '_'));
817 RETURN_IF_ERROR (demangle_char (dm, 'Z'));
818 RETURN_IF_ERROR (demangle_encoding (dm));
822 /* Demangles and emits an <encoding>.
824 <encoding> ::= <function name> <bare-function-type>
826 ::= <substitution> */
829 demangle_encoding (dm)
833 int special_std_substitution;
835 int start = substitution_start (dm);
836 template_arg_list_t old_arg_list = current_template_arg_list (dm);
837 char peek = peek_char (dm);
839 DEMANGLE_TRACE ("encoding", dm);
841 /* Remember where the name starts. If it turns out to be a template
842 function, we'll have to insert the return type here. */
843 start_position = result_length (dm);
847 RETURN_IF_ERROR (demangle_substitution (dm, &template_p,
848 &special_std_substitution));
849 if (special_std_substitution)
851 /* This was the magic `std::' substitution. */
852 result_append (dm, "::");
853 RETURN_IF_ERROR (demangle_encoding (dm));
856 else if (peek == 'G' || peek == 'T')
857 RETURN_IF_ERROR (demangle_special_name (dm));
860 /* Now demangle the name. */
861 RETURN_IF_ERROR (demangle_name (dm, &template_p));
863 /* If there's anything left, the name was a function name, with
864 maybe its return type, and its parameters types, following. */
865 if (!end_of_name_p (dm)
866 && peek_char (dm) != 'E')
869 /* Template functions have their return type encoded. The
870 return type should be inserted at start_position. */
872 (demangle_bare_function_type (dm, start_position));
874 /* Non-template functions don't have their return type
877 (demangle_bare_function_type (dm, BFT_NO_RETURN_TYPE));
880 substitution_add (dm, start, template_p, NOT_TEMPLATE_PARM);
883 /* Pop off template argument lists that were built during the
884 mangling of this name, to restore the old template context. */
885 pop_to_template_arg_list (dm, old_arg_list);
890 /* Demangles and emits a <name>.
892 <name> ::= <unscoped-name>
893 ::= <unscoped-template-name> <template-args>
897 <unscoped-name> ::= <unqualified-name>
898 ::= St <unqualified-name> # ::std::
900 <unscoped-template-name>
902 ::= <substitution> */
905 demangle_name (dm, template_p)
909 int special_std_substitution;
910 int start = substitution_start (dm);
912 DEMANGLE_TRACE ("name", dm);
914 switch (peek_char (dm))
917 /* This is a <nested-name>. */
918 RETURN_IF_ERROR (demangle_nested_name (dm, template_p));
922 RETURN_IF_ERROR (demangle_local_name (dm));
926 /* The `St' substitution allows a name nested in std:: to appear
927 without being enclosed in a nested name.
928 <name> ::= St <unqualified-name> # ::std:: */
929 if (peek_char_next (dm) == 't')
931 (void) next_char (dm);
932 (void) next_char (dm);
933 result_append (dm, "std::");
934 RETURN_IF_ERROR (demangle_unqualified_name (dm));
938 RETURN_IF_ERROR (demangle_substitution (dm, template_p,
939 &special_std_substitution));
940 if (special_std_substitution)
942 /* This was the magic `std::' substitution. We can have
943 a <nested-name> or one of the unscoped names
945 result_append (dm, "::");
946 RETURN_IF_ERROR (demangle_name (dm, template_p));
952 /* This is an <unscoped-name> or <unscoped-template-name>. */
953 RETURN_IF_ERROR (demangle_unqualified_name (dm));
955 /* If the <unqualified-name> is followed by template args, this
956 is an <unscoped-template-name>. */
957 if (peek_char (dm) == 'I')
959 /* Add a substitution for the unqualified template name. */
960 substitution_add (dm, start, 0, NOT_TEMPLATE_PARM);
962 RETURN_IF_ERROR (demangle_template_args (dm));
974 /* Demangles and emits a <nested-name>.
976 <nested-name> ::= N [<CV-qualifiers>] <prefix> <component> E */
979 demangle_nested_name (dm, template_p)
985 DEMANGLE_TRACE ("nested-name", dm);
987 RETURN_IF_ERROR (demangle_char (dm, 'N'));
989 peek = peek_char (dm);
990 if (peek == 'r' || peek == 'V' || peek == 'K')
992 /* Snarf up and emit CV qualifiers. */
993 dyn_string_t cv_qualifiers = dyn_string_new (24);
994 demangle_CV_qualifiers (dm, cv_qualifiers);
995 result_append_string (dm, cv_qualifiers);
996 dyn_string_delete (cv_qualifiers);
997 result_append_space (dm);
1000 RETURN_IF_ERROR (demangle_prefix (dm, template_p));
1001 /* No need to demangle the final <component>; demangle_prefix will
1003 RETURN_IF_ERROR (demangle_char (dm, 'E'));
1008 /* Demangles and emits a <prefix>.
1010 <prefix> ::= <prefix> <component>
1011 ::= <template-prefix> <template-args>
1015 <template-prefix> ::= <prefix>
1018 <component> ::= <unqualified-name>
1022 demangle_prefix (dm, template_p)
1026 int start = substitution_start (dm);
1029 /* TEMPLATE_P is updated as we decend the nesting chain. After
1030 <template-args>, it is set to non-zero; after everything else it
1033 DEMANGLE_TRACE ("prefix", dm);
1040 if (end_of_name_p (dm))
1041 return "Unexpected end of name in <compound-name>.";
1043 peek = peek_char (dm);
1045 if (isdigit ((unsigned char) peek)
1046 || (peek >= 'a' && peek <= 'z')
1047 || peek == 'C' || peek == 'D'
1050 /* We have another level of scope qualification. */
1052 result_append (dm, "::");
1057 /* The substitution determines whether this is a
1059 RETURN_IF_ERROR (demangle_substitution (dm, template_p,
1063 RETURN_IF_ERROR (demangle_unqualified_name (dm));
1067 else if (peek == 'Z')
1068 RETURN_IF_ERROR (demangle_local_name (dm));
1069 else if (peek == 'I')
1072 return STATUS_INTERNAL_ERROR;
1073 /* The template name is a substitution candidate. */
1074 substitution_add (dm, start, 0, NOT_TEMPLATE_PARM);
1075 RETURN_IF_ERROR (demangle_template_args (dm));
1078 else if (peek == 'E')
1082 return "Unexpected character in <compound-name>.";
1084 /* Add a new substitution for the prefix thus far. */
1085 substitution_add (dm, start, *template_p, NOT_TEMPLATE_PARM);
1089 /* Demangles and emits an <unqualified-name>. If the
1090 <unqualified-name> is a function and the first element in the
1091 argument list should be taken to be its return type,
1092 ENCODE_RETURN_TYPE is non-zero.
1094 <unqualified-name> ::= <operator-name>
1096 ::= <source-name> */
1099 demangle_unqualified_name (dm)
1102 char peek = peek_char (dm);
1104 DEMANGLE_TRACE ("unqualified-name", dm);
1106 if (isdigit ((unsigned char) peek))
1107 RETURN_IF_ERROR (demangle_source_name (dm));
1108 else if (peek >= 'a' && peek <= 'z')
1111 RETURN_IF_ERROR (demangle_operator_name (dm, 0, &num_args));
1113 else if (peek == 'C' || peek == 'D')
1114 RETURN_IF_ERROR (demangle_ctor_dtor_name (dm));
1116 return "Unexpected character in <unqualified-name>.";
1121 /* Demangles and emits <source-name>.
1123 <source-name> ::= <length number> <identifier> */
1126 demangle_source_name (dm)
1131 DEMANGLE_TRACE ("source-name", dm);
1133 /* Decode the length of the identifier. */
1134 RETURN_IF_ERROR (demangle_number (dm, &length, 10, 0));
1136 return "Zero length in <source-name>.";
1138 /* Now the identifier itself. It's placed into last_source_name,
1139 where it can be used to build a constructor or destructor name. */
1140 RETURN_IF_ERROR (demangle_identifier (dm, length,
1141 dm->last_source_name));
1144 result_append_string (dm, dm->last_source_name);
1149 /* Demangles a number, either a <number> or a <positive-number> at the
1150 current position, consuming all consecutive digit characters. Sets
1151 *VALUE to the resulting numberand returns STATUS_OK. The number is
1152 interpreted as BASE, which must be either 10 or 36. If IS_SIGNED
1153 is non-zero, negative numbers -- prefixed with `n' -- are accepted.
1155 <number> ::= [n] <positive-number>
1157 <positive-number> ::= <decimal integer> */
1160 demangle_number (dm, value, base, is_signed)
1166 dyn_string_t number = dyn_string_new (10);
1168 DEMANGLE_TRACE ("number", dm);
1170 demangle_number_literally (dm, number, base, is_signed);
1171 *value = strtol (dyn_string_buf (number), NULL, base);
1172 dyn_string_delete (number);
1177 /* Demangles a number at the current position. The digits (and minus
1178 sign, if present) that make up the number are appended to STR.
1179 Only base-BASE digits are accepted; BASE must be either 10 or 36.
1180 If IS_SIGNED, negative numbers -- prefixed with `n' -- are
1181 accepted. Does not consume a trailing underscore or other
1182 terminating character. */
1185 demangle_number_literally (dm, str, base, is_signed)
1191 DEMANGLE_TRACE ("number*", dm);
1193 if (base != 10 && base != 36)
1194 return STATUS_INTERNAL_ERROR;
1196 /* An `n' denotes a negative number. */
1197 if (is_signed && peek_char (dm) == 'n')
1199 /* Skip past the n. */
1201 /* The normal way to write a negative number is with a minus
1203 dyn_string_append_char (str, '-');
1206 /* Loop until we hit a non-digit. */
1209 char peek = peek_char (dm);
1210 if (isdigit ((unsigned char) peek)
1211 || (base == 36 && peek >= 'A' && peek <= 'Z'))
1212 /* Accumulate digits. */
1213 dyn_string_append_char (str, next_char (dm));
1215 /* Not a digit? All done. */
1222 /* Demangles an identifier at the current position of LENGTH
1223 characters and places it in IDENTIFIER. */
1226 demangle_identifier (dm, length, identifier)
1229 dyn_string_t identifier;
1231 DEMANGLE_TRACE ("identifier", dm);
1233 dyn_string_clear (identifier);
1234 dyn_string_resize (identifier, length);
1235 while (length-- > 0)
1237 if (end_of_name_p (dm))
1238 return "Unexpected end of name in <identifier>.";
1239 dyn_string_append_char (identifier, next_char (dm));
1245 /* Demangles and emits an <operator-name>. If SHORT_NAME is non-zero,
1246 the short form is emitted; otherwise the full source form
1247 (`operator +' etc.) is emitted. *NUM_ARGS is set to the number of
1248 operands that the operator takes.
1299 ::= cv <type> # cast
1300 ::= vx <source-name> # vendor extended operator */
1303 demangle_operator_name (dm, short_name, num_args)
1308 struct operator_code
1310 /* The mangled code for this operator. */
1312 /* The source name of this operator. */
1314 /* The number of arguments this operator takes. */
1318 struct operator_code operators[] =
1329 { "da", "delete[]" , 1 },
1331 { "dl", "delete" , 1 },
1339 { "lS", "<<=" , 2 },
1348 { "na", "new[]" , 1 },
1352 { "nw", "new" , 1 },
1358 { "pm", "->*" , 2 },
1363 { "rS", ">>=" , 2 },
1366 { "sz", "sizeof" , 1 }
1369 const int num_operators =
1370 sizeof (operators) / sizeof (struct operator_code);
1372 int c0 = next_char (dm);
1373 int c1 = next_char (dm);
1374 struct operator_code* p1 = operators;
1375 struct operator_code* p2 = operators + num_operators;
1377 DEMANGLE_TRACE ("operator-name", dm);
1379 /* Is this a vendor extended operator? */
1380 if (c0 == 'v' && c1 == 'x')
1382 result_append (dm, "operator");
1383 RETURN_IF_ERROR (demangle_source_name (dm));
1388 /* Is this a conversion operator? */
1389 if (c0 == 'c' && c1 == 'v')
1391 result_append (dm, "operator ");
1392 /* Demangle the converted-to type. */
1393 RETURN_IF_ERROR (demangle_type (dm));
1398 /* Perform a binary search for the operator code. */
1401 struct operator_code* p = p1 + (p2 - p1) / 2;
1402 char match0 = p->code[0];
1403 char match1 = p->code[1];
1405 if (c0 == match0 && c1 == match1)
1409 result_append (dm, "operator");
1410 result_append (dm, p->name);
1411 *num_args = p->num_args;
1417 /* Couldn't find it. */
1418 return "Unknown code in <operator-name>.";
1421 if (c0 < match0 || (c0 == match0 && c1 < match1))
1428 /* Demangles and emits a <special-name>.
1430 <special-name> ::= GV <object name> # Guard variable
1431 ::= Th[n] <offset number> _ <base name> <base encoding>
1432 # non-virtual base override thunk
1433 ::= Tv[n] <offset number> _ <vcall offset number>
1435 # virtual base override thunk
1436 ::= TV <type> # virtual table
1438 ::= TI <type> # typeinfo structure
1439 ::= TS <type> # typeinfo name
1441 Also demangles the special g++ mangling,
1443 <special-name> ::= CT <type> <offset number> _ <base type>
1444 # construction vtable */
1447 demangle_special_name (dm)
1450 dyn_string_t number;
1452 char peek = peek_char (dm);
1454 DEMANGLE_TRACE ("special-name", dm);
1458 /* A guard variable name. Consume the G. */
1460 RETURN_IF_ERROR (demangle_char (dm, 'V'));
1461 result_append (dm, "guard variable for ");
1462 RETURN_IF_ERROR (demangle_name (dm, &unused));
1464 else if (peek == 'T')
1466 /* Other C++ implementation miscellania. Consume the T. */
1469 switch (peek_char (dm))
1472 /* Virtual table. */
1474 result_append (dm, "vtable for ");
1475 RETURN_IF_ERROR (demangle_type (dm));
1479 /* VTT structure. */
1481 result_append (dm, "VTT for ");
1482 RETURN_IF_ERROR (demangle_type (dm));
1486 /* Typeinfo structure. */
1488 result_append (dm, "typeinfo for ");
1489 RETURN_IF_ERROR (demangle_type (dm));
1493 /* Character string containing type name, used in typeinfo. */
1495 result_append (dm, "typeinfo name for ");
1496 RETURN_IF_ERROR (demangle_type (dm));
1500 /* Non-virtual thunk. */
1502 result_append (dm, "non-virtual thunk");
1503 /* Demangle and emit the offset. */
1504 number = dyn_string_new (4);
1505 demangle_number_literally (dm, number, 10, 1);
1506 /* Don't display the offset unless in verbose mode. */
1509 result_append_char (dm, ' ');
1510 result_append_string (dm, number);
1512 dyn_string_delete (number);
1513 /* Demangle the separator. */
1514 RETURN_IF_ERROR (demangle_char (dm, '_'));
1515 /* Demangle and emit the target name and function type. */
1516 result_append (dm, " to ");
1517 RETURN_IF_ERROR (demangle_encoding (dm));
1521 /* Virtual thunk. */
1523 result_append (dm, "virtual thunk ");
1524 /* Demangle and emit the offset. */
1525 number = dyn_string_new (4);
1526 demangle_number_literally (dm, number, 10, 1);
1527 /* Don't display the offset unless in verbose mode. */
1530 result_append_string (dm, number);
1531 result_append_char (dm, ' ');
1533 dyn_string_delete (number);
1534 /* Demangle the separator. */
1535 RETURN_IF_ERROR (demangle_char (dm, '_'));
1536 /* Demangle and emit the vcall offset. */
1537 number = dyn_string_new (4);
1538 demangle_number_literally (dm, number, 10, 1);
1539 /* Don't display the vcall offset unless in verbose mode. */
1542 result_append_string (dm, number);
1543 result_append_char (dm, ' ');
1545 dyn_string_delete (number);
1546 /* Demangle the separator. */
1547 RETURN_IF_ERROR (demangle_char (dm, '_'));
1548 /* Demangle and emit the target function. */
1549 result_append (dm, "to ");
1550 RETURN_IF_ERROR (demangle_encoding (dm));
1554 /* TC is a special g++ mangling for a construction vtable. */
1558 result_append (dm, "construction vtable for ");
1559 RETURN_IF_ERROR (demangle_type (dm));
1560 /* Demangle the offset. */
1561 number = dyn_string_new (4);
1562 demangle_number_literally (dm, number, 10, 1);
1563 /* Demangle the underscore separator. */
1564 RETURN_IF_ERROR (demangle_char (dm, '_'));
1565 /* Demangle the base type. */
1566 result_append (dm, "-in-");
1567 RETURN_IF_ERROR (demangle_type (dm));
1568 /* Don't display the offset unless in verbose mode. */
1571 result_append_char (dm, ' ');
1572 result_append_string (dm, number);
1574 dyn_string_delete (number);
1577 /* If flag_strict, fall through. */
1580 return "Unrecognized <special-name>.";
1584 return STATUS_ERROR;
1589 /* Demangles and emits a <ctor-dtor-name>.
1592 ::= C1 # complete object (in-charge) ctor
1593 ::= C2 # base object (not-in-charge) ctor
1594 ::= C3 # complete object (in-charge) allocating ctor
1595 ::= C4 # base object (not-in-charge) allocating ctor
1596 ::= D0 # deleting (in-charge) dtor
1597 ::= D1 # complete object (in-charge) dtor
1598 ::= D2 # base object (not-in-charge) dtor */
1601 demangle_ctor_dtor_name (dm)
1604 static const char *const ctor_flavors[] =
1608 "in-charge allocating",
1609 "not-in-charge allocating"
1611 static const char *const dtor_flavors[] =
1613 "in-charge deleting",
1619 char peek = peek_char (dm);
1621 DEMANGLE_TRACE ("ctor-dtor-name", dm);
1625 /* A constructor name. Consume the C. */
1627 if (peek_char (dm) < '1' || peek_char (dm) > '4')
1628 return "Unrecognized constructor.";
1629 result_append_string (dm, dm->last_source_name);
1630 /* Print the flavor of the constructor if in verbose mode. */
1631 flavor = next_char (dm) - '1';
1634 result_append (dm, "[");
1635 result_append (dm, ctor_flavors[flavor]);
1636 result_append_char (dm, ']');
1639 else if (peek == 'D')
1641 /* A destructor name. Consume the D. */
1643 if (peek_char (dm) < '0' || peek_char (dm) > '2')
1644 return "Unrecognized destructor.";
1645 result_append_char (dm, '~');
1646 result_append_string (dm, dm->last_source_name);
1647 /* Print the flavor of the destructor if in verbose mode. */
1648 flavor = next_char (dm) - '0';
1651 result_append (dm, " [");
1652 result_append (dm, dtor_flavors[flavor]);
1653 result_append_char (dm, ']');
1657 return STATUS_ERROR;
1662 /* Handle pointer, reference, and pointer-to-member cases for
1663 demangle_type. All consecutive `P's, `R's, and 'M's are joined to
1664 build a pointer/reference type. We snarf all these, plus the
1665 following <type>, all at once since we need to know whether we have
1666 a pointer to data or pointer to function to construct the right
1667 output syntax. C++'s pointer syntax is hairy.
1671 ::= <pointer-to-member-type>
1673 <pointer-to-member-type> ::= M </class/ type> </member/ type> */
1676 demangle_type_ptr (dm)
1682 /* Collect pointer symbols into this string. */
1683 dyn_string_t symbols = dyn_string_new (10);
1685 DEMANGLE_TRACE ("type*", dm);
1687 /* Scan forward, collecting pointers and references into symbols,
1688 until we hit something else. Then emit the type. */
1691 next = peek_char (dm);
1694 dyn_string_append_char (symbols, '*');
1697 else if (next == 'R')
1699 dyn_string_append_char (symbols, '&');
1702 else if (next == 'M')
1704 /* Pointer-to-member. */
1705 dyn_string_t class_type;
1710 /* Capture the type of which this is a pointer-to-member. */
1712 RETURN_IF_ERROR (demangle_type (dm));
1713 class_type = (dyn_string_t) result_pop (dm);
1715 /* Build the pointer-to-member notation. It comes before
1716 other pointer and reference qualifiers -- */
1717 dyn_string_prepend_cstr (symbols, "::*");
1718 dyn_string_prepend (symbols, class_type);
1719 dyn_string_delete (class_type);
1721 if (peek_char (dm) == 'F')
1724 /* Demangle the type of the pointed-to member. */
1725 status = demangle_type (dm);
1726 /* Make it pretty. */
1727 result_append_space (dm);
1728 /* Add the pointer-to-member syntax, and other pointer and
1729 reference symbols. */
1730 result_append_string (dm, symbols);
1732 dyn_string_delete (symbols);
1734 RETURN_IF_ERROR (status);
1737 else if (next == 'F')
1739 /* Ooh, tricky, a pointer-to-function. */
1740 int position = result_length (dm);
1741 result_append_char (dm, '(');
1742 result_append_string (dm, symbols);
1743 result_append_char (dm, ')');
1744 dyn_string_delete (symbols);
1746 RETURN_IF_ERROR (demangle_function_type (dm, position));
1751 /* No more pointe or reference tokens. Finish up. */
1752 status = demangle_type (dm);
1754 result_append_string (dm, symbols);
1755 dyn_string_delete (symbols);
1757 RETURN_IF_ERROR (status);
1763 /* Demangles and emits a <type>.
1765 <type> ::= <builtin-type>
1767 ::= <class-enum-type>
1769 ::= <pointer-to-member-type>
1770 ::= <template-param>
1771 ::= <CV-qualifiers> <type>
1772 ::= P <type> # pointer-to
1773 ::= R <type> # reference-to
1774 ::= C <type> # complex pair (C 2000)
1775 ::= G <type> # imaginary (C 2000)
1776 ::= U <source-name> <type> # vendor extended type qualifier
1777 ::= <substitution> */
1783 int start = substitution_start (dm);
1784 char peek = peek_char (dm);
1786 int special_std_substitution;
1787 int is_builtin_type = 0;
1788 template_arg_list_t old_arg_list = current_template_arg_list (dm);
1789 int template_parm = NOT_TEMPLATE_PARM;
1791 DEMANGLE_TRACE ("type", dm);
1793 /* A <class-enum-type> can start with a digit (a <source-name>), an
1794 N (a <nested-name>), or a Z (a <local-name>). */
1795 if (isdigit ((unsigned char) peek) || peek == 'N' || peek == 'Z')
1796 RETURN_IF_ERROR (demangle_class_enum_type (dm, &template_p));
1797 else if (peek >= 'a' && peek <= 'z')
1799 RETURN_IF_ERROR (demangle_builtin_type (dm));
1800 is_builtin_type = 1;
1810 dyn_string_t cv_qualifiers = dyn_string_new (24);
1811 demangle_CV_qualifiers (dm, cv_qualifiers);
1813 /* If the qualifiers apply to a pointer or reference, they
1814 need to come after the whole qualified type. */
1815 if (peek_char (dm) == 'P' || peek_char (dm) == 'R')
1817 status = demangle_type (dm);
1818 result_append_space (dm);
1819 result_append_string (dm, cv_qualifiers);
1821 /* Otherwise, the qualifiers come first. */
1824 result_append_string (dm, cv_qualifiers);
1825 result_append_space (dm);
1826 status = demangle_type (dm);
1829 dyn_string_delete (cv_qualifiers);
1830 RETURN_IF_ERROR (status);
1835 return "Non-pointer or -reference function type.";
1838 RETURN_IF_ERROR (demangle_array_type (dm));
1842 RETURN_IF_ERROR (demangle_template_param (dm, &template_parm));
1846 RETURN_IF_ERROR (demangle_substitution (dm, &template_p,
1847 &special_std_substitution));
1848 if (special_std_substitution)
1850 /* This was the magic `std::' substitution. What follows
1851 must be a class name in that namespace. */
1852 result_append (dm, "::");
1853 RETURN_IF_ERROR (demangle_class_enum_type (dm, &template_p));
1860 RETURN_IF_ERROR (demangle_type_ptr (dm));
1864 /* A C99 complex type. */
1865 result_append (dm, "complex ");
1867 RETURN_IF_ERROR (demangle_type (dm));
1871 /* A C99 imaginary type. */
1872 result_append (dm, "imaginary ");
1874 RETURN_IF_ERROR (demangle_type (dm));
1878 /* Vendor extended type qualifier. */
1880 RETURN_IF_ERROR (demangle_source_name (dm));
1881 result_append_char (dm, ' ');
1882 RETURN_IF_ERROR (demangle_type (dm));
1886 return "Unexpected character in <type>.";
1889 /* Unqualified builin types are not substitution candidates. */
1890 if (!is_builtin_type)
1891 /* Add a new substitution for the type. If this type was a
1892 <template-param>, pass its index since from the point of
1893 substitutions, a <template-param> token is a substitution
1894 candidate distinct from the type that is substituted for it. */
1895 substitution_add (dm, start, template_p, template_parm);
1897 /* Pop off template argument lists added during mangling of this
1899 pop_to_template_arg_list (dm, old_arg_list);
1904 /* C++ source names of builtin types, indexed by the mangled code
1905 letter's position in the alphabet ('a' -> 0, 'b' -> 1, etc). */
1906 static const char *const builtin_type_names[26] =
1908 "signed char", /* a */
1912 "long double", /* e */
1914 "__float128", /* g */
1915 "unsigned char", /* h */
1920 "unsigned long", /* m */
1922 "unsigned __int128", /* o */
1927 "unsigned short", /* t */
1931 "long long", /* x */
1932 "unsigned long long", /* y */
1936 /* Demangles and emits a <builtin-type>.
1938 <builtin-type> ::= v # void
1943 ::= h # unsigned char
1945 ::= t # unsigned short
1947 ::= j # unsigned int
1949 ::= m # unsigned long
1950 ::= x # long long, __int64
1951 ::= y # unsigned long long, __int64
1953 ::= o # unsigned __int128
1956 ::= e # long double, __float80
1959 ::= u <source-name> # vendor extended type */
1962 demangle_builtin_type (dm)
1966 char code = peek_char (dm);
1968 DEMANGLE_TRACE ("builtin-type", dm);
1973 RETURN_IF_ERROR (demangle_source_name (dm));
1976 else if (code >= 'a' && code <= 'z')
1978 const char *type_name = builtin_type_names[code - 'a'];
1979 if (type_name == NULL)
1980 return "Unrecognized <builtin-type> code.";
1982 result_append (dm, type_name);
1987 return "Non-alphabetic <builtin-type> code.";
1990 /* Demangles all consecutive CV-qualifiers (const, volatile, and
1991 restrict) at the current position. The qualifiers are appended to
1992 QUALIFIERS. Returns STATUS_OK. */
1995 demangle_CV_qualifiers (dm, qualifiers)
1997 dyn_string_t qualifiers;
1999 DEMANGLE_TRACE ("CV-qualifiers", dm);
2003 switch (peek_char (dm))
2006 dyn_string_append_space (qualifiers);
2007 dyn_string_append_cstr (qualifiers, "restrict");
2011 dyn_string_append_space (qualifiers);
2012 dyn_string_append_cstr (qualifiers, "volatile");
2016 dyn_string_append_space (qualifiers);
2017 dyn_string_append_cstr (qualifiers, "const");
2028 /* Demangles and emits a <function-type> FUNCTION_NAME_POS is the
2029 position in the result string of the start of the function
2030 identifier, at which the function's return type will be inserted.
2032 <function-type> ::= F [Y] <bare-function-type> E */
2035 demangle_function_type (dm, function_name_pos)
2037 int function_name_pos;
2039 DEMANGLE_TRACE ("function-type", dm);
2040 RETURN_IF_ERROR (demangle_char (dm, 'F'));
2041 if (peek_char (dm) == 'Y')
2043 /* Indicate this function has C linkage if in verbose mode. */
2045 result_append (dm, " [extern \"C\"] ");
2048 RETURN_IF_ERROR (demangle_bare_function_type (dm, function_name_pos));
2049 RETURN_IF_ERROR (demangle_char (dm, 'E'));
2053 /* Demangles and emits a <bare-function-type>. RETURN_TYPE_POS is the
2054 position in the result string at which the function return type
2055 should be inserted. If RETURN_TYPE_POS is BFT_NO_RETURN_TYPE, the
2056 function's return type is assumed not to be encoded.
2058 <bare-function-type> ::= <signature type>+ */
2061 demangle_bare_function_type (dm, return_type_pos)
2063 int return_type_pos;
2065 /* Sequence is the index of the current function parameter, counting
2066 from zero. The value -1 denotes the return type. */
2068 (return_type_pos == BFT_NO_RETURN_TYPE ? 0 : -1);
2070 DEMANGLE_TRACE ("bare-function-type", dm);
2072 result_append_char (dm, '(');
2073 while (!end_of_name_p (dm) && peek_char (dm) != 'E')
2076 /* We're decoding the function's return type. */
2078 dyn_string_t return_type;
2080 /* Decode the return type off to the side. */
2082 RETURN_IF_ERROR (demangle_type (dm));
2083 return_type = (dyn_string_t) result_pop (dm);
2085 /* Add a space to the end of the type. */
2086 dyn_string_append_space (return_type);
2088 /* Insert the return type where we've been asked to. */
2089 dyn_string_insert (result_string (dm), return_type_pos,
2091 dyn_string_delete (return_type);
2095 /* Skip `void' parameter types. One should only occur as
2096 the only type in a parameter list; in that case, we want
2097 to print `foo ()' instead of `foo (void)'. */
2098 if (peek_char (dm) == 'v')
2100 /* Consume the v. */
2104 /* Separate parameter types by commas. */
2106 result_append (dm, ", ");
2107 /* Demangle the type. */
2108 RETURN_IF_ERROR (demangle_type (dm));
2113 result_append_char (dm, ')');
2118 /* Demangles and emits a <class-enum-type>. *TEMPLATE_P is set to
2119 non-zero if the type is a template-id, zero otherwise.
2121 <class-enum-type> ::= <name> */
2124 demangle_class_enum_type (dm, template_p)
2128 DEMANGLE_TRACE ("class-enum-type", dm);
2130 RETURN_IF_ERROR (demangle_name (dm, template_p));
2134 /* Demangles and emits an <array-type>.
2136 <array-type> ::= A [<dimension number>] _ <element type> */
2139 demangle_array_type (dm)
2142 dyn_string_t array_size = dyn_string_new (10);
2144 RETURN_IF_ERROR (demangle_char (dm, 'A'));
2146 /* Demangle the array size into array_size. */
2147 RETURN_IF_ERROR (demangle_number_literally (dm, array_size, 10, 0));
2149 /* Demangle the base type of the array. */
2150 RETURN_IF_ERROR (demangle_char (dm, '_'));
2151 RETURN_IF_ERROR (demangle_type (dm));
2153 /* Emit the array dimension syntax. */
2154 result_append_char (dm, '[');
2155 result_append_string (dm, array_size);
2156 result_append_char (dm, ']');
2157 dyn_string_delete (array_size);
2162 /* Demangles and emits a <template-param>. The zero-indexed position
2163 in the parameter list is placed in *TEMPLATE_PARM_NUMBER.
2165 <template-param> ::= T_ # first template parameter
2166 ::= T <parameter-2 number> _ */
2169 demangle_template_param (dm, template_parm_number)
2171 int *template_parm_number;
2174 template_arg_list_t current_arg_list = current_template_arg_list (dm);
2177 DEMANGLE_TRACE ("template-param", dm);
2179 /* Make sure there is a template argmust list in which to look up
2180 this parameter reference. */
2181 if (current_arg_list == NULL)
2182 return "Template parameter outside of template.";
2184 RETURN_IF_ERROR (demangle_char (dm, 'T'));
2185 if (peek_char (dm) == '_')
2189 RETURN_IF_ERROR (demangle_number (dm, &parm_number, 10, 0));
2192 RETURN_IF_ERROR (demangle_char (dm, '_'));
2194 arg = template_arg_list_get_arg (current_arg_list, parm_number);
2196 /* parm_number exceeded the number of arguments in the current
2197 template argument list. */
2198 return "Template parameter number out of bounds.";
2199 result_append_string (dm, (dyn_string_t) arg);
2201 if (peek_char (dm) == 'I')
2202 RETURN_IF_ERROR (demangle_template_args (dm));
2204 *template_parm_number = parm_number;
2208 /* Demangles and emits a <template-args>.
2210 <template-args> ::= I <template-arg>+ E */
2213 demangle_template_args (dm)
2217 template_arg_list_t arg_list = template_arg_list_new ();
2219 /* Preserve the most recently demangled source name. */
2220 dyn_string_t old_last_source_name = dm->last_source_name;
2221 dm->last_source_name = dyn_string_new (0);
2223 DEMANGLE_TRACE ("template-args", dm);
2225 RETURN_IF_ERROR (demangle_char (dm, 'I'));
2226 result_append_char (dm, '<');
2234 result_append (dm, ", ");
2236 /* Capture the template arg. */
2238 RETURN_IF_ERROR (demangle_template_arg (dm));
2239 arg = result_pop (dm);
2241 /* Emit it in the demangled name. */
2242 result_append_string (dm, (dyn_string_t) arg);
2244 /* Save it for use in expanding <template-param>s. */
2245 template_arg_list_add_arg (arg_list, arg);
2247 while (peek_char (dm) != 'E');
2248 /* Append the '>'. */
2249 result_close_template_list (dm);
2251 /* Consume the 'E'. */
2254 /* Restore the most recent demangled source name. */
2255 dyn_string_delete (dm->last_source_name);
2256 dm->last_source_name = old_last_source_name;
2258 /* Push the list onto the top of the stack of template argument
2259 lists, so that arguments from it are used from now on when
2260 expanding <template-param>s. */
2261 push_template_arg_list (dm, arg_list);
2266 /* This function, which does not correspond to a production in the
2267 mangling spec, handles the `literal' production for both
2268 <template-arg> and <expr-primary>. It does not expect or consume
2269 the initial `L' or final `E'. The demangling is given by:
2271 <literal> ::= <type> </value/ number>
2273 and the emitted output is `(type)number'. */
2276 demangle_literal (dm)
2279 dyn_string_t value = dyn_string_new (0);
2280 char peek = peek_char (dm);
2282 DEMANGLE_TRACE ("literal", dm);
2284 if (!flag_verbose && peek >= 'a' && peek <= 'z')
2286 /* If not in verbose mode and this is a builtin type, see if we
2287 can produce simpler numerical output. In particular, for
2288 integer types shorter than `long', just write the number
2289 without type information; for bools, write `true' or `false'.
2290 Other refinements could be made here too. */
2292 /* This constant string is used to map from <builtin-type> codes
2293 (26 letters of the alphabet) to codes that determine how the
2294 value will be displayed. The codes are:
2298 A space means the value will be represented using cast
2300 static const char *const code_map = "ibi iii ll ii i ";
2302 char code = code_map[peek - 'a'];
2303 /* FIXME: Implement demangling of floats and doubles. */
2305 return STATUS_UNIMPLEMENTED;
2308 /* It's a boolean. */
2311 /* Consume the b. */
2313 /* Look at the next character. It should be 0 or 1,
2314 corresponding to false or true, respectively. */
2315 value = peek_char (dm);
2317 result_append (dm, "false");
2318 else if (value == '1')
2319 result_append (dm, "true");
2321 return "Unrecognized bool constant.";
2322 /* Consume the 0 or 1. */
2326 else if (code == 'i' || code == 'l')
2328 /* It's an integer or long. */
2330 /* Consume the type character. */
2332 /* Demangle the number and write it out. */
2333 RETURN_IF_ERROR (demangle_number_literally (dm, value, 10, 1));
2334 result_append_string (dm, value);
2335 /* For long integers, append an l. */
2337 result_append_char (dm, code);
2340 /* ...else code == ' ', so fall through to represent this
2341 literal's type explicitly using cast syntax. */
2344 result_append_char (dm, '(');
2345 RETURN_IF_ERROR (demangle_type (dm));
2346 result_append_char (dm, ')');
2348 RETURN_IF_ERROR (demangle_number_literally (dm, value, 10, 1));
2349 result_append_string (dm, value);
2350 dyn_string_delete (value);
2355 /* Demangles and emits a <template-arg>.
2357 <template-arg> ::= <type> # type
2358 ::= L <type> <value number> E # literal
2359 ::= LZ <encoding> E # external name
2360 ::= X <expression> E # expression */
2363 demangle_template_arg (dm)
2366 DEMANGLE_TRACE ("template-arg", dm);
2368 switch (peek_char (dm))
2373 if (peek_char (dm) == 'Z')
2375 /* External name. */
2377 /* FIXME: Standard is contradictory here. */
2378 RETURN_IF_ERROR (demangle_encoding (dm));
2381 RETURN_IF_ERROR (demangle_literal (dm));
2382 RETURN_IF_ERROR (demangle_char (dm, 'E'));
2388 RETURN_IF_ERROR (demangle_expression (dm));
2392 RETURN_IF_ERROR (demangle_type (dm));
2399 /* Demangles and emits an <expression>.
2401 <expression> ::= <unary operator-name> <expression>
2402 ::= <binary operator-name> <expression> <expression>
2404 ::= <scope-expression> */
2407 demangle_expression (dm)
2410 char peek = peek_char (dm);
2412 DEMANGLE_TRACE ("expression", dm);
2414 if (peek == 'L' || peek == 'T')
2415 RETURN_IF_ERROR (demangle_expr_primary (dm));
2416 else if (peek == 's' && peek_char_next (dm) == 'r')
2417 RETURN_IF_ERROR (demangle_scope_expression (dm));
2419 /* An operator expression. */
2422 dyn_string_t operator_name;
2424 /* We have an operator name. Since we want to output binary
2425 operations in infix notation, capture the operator name
2428 RETURN_IF_ERROR (demangle_operator_name (dm, 1, &num_args));
2429 operator_name = (dyn_string_t) result_pop (dm);
2431 /* If it's binary, do an operand first. */
2434 result_append_char (dm, '(');
2435 RETURN_IF_ERROR (demangle_expression (dm));
2436 result_append_char (dm, ')');
2439 /* Now emit the operator, followed by its second (if binary) or
2440 only (if unary) operand. */
2441 result_append_string (dm, operator_name);
2442 dyn_string_delete (operator_name);
2443 result_append_char (dm, '(');
2444 RETURN_IF_ERROR (demangle_expression (dm));
2445 result_append_char (dm, ')');
2447 /* The ternary operator takes a third operand. */
2450 result_append (dm, ":(");
2451 RETURN_IF_ERROR (demangle_expression (dm));
2452 result_append_char (dm, ')');
2459 /* Demangles and emits a <scope-expression>.
2461 <scope-expression> ::= sr <qualifying type> <source-name>
2462 ::= sr <qualifying type> <encoding> */
2465 demangle_scope_expression (dm)
2468 RETURN_IF_ERROR (demangle_char (dm, 's'));
2469 RETURN_IF_ERROR (demangle_char (dm, 'r'));
2470 RETURN_IF_ERROR (demangle_type (dm));
2471 result_append (dm, "::");
2472 RETURN_IF_ERROR (demangle_encoding (dm));
2476 /* Demangles and emits an <expr-primary>.
2478 <expr-primary> ::= <template-param>
2479 ::= L <type> <value number> E # literal
2480 ::= L <mangled-name> E # external name */
2483 demangle_expr_primary (dm)
2486 char peek = peek_char (dm);
2489 DEMANGLE_TRACE ("expr-primary", dm);
2492 RETURN_IF_ERROR (demangle_template_param (dm, &unused));
2493 else if (peek == 'L')
2495 /* Consume the `L'. */
2497 peek = peek_char (dm);
2500 RETURN_IF_ERROR (demangle_mangled_name (dm));
2502 RETURN_IF_ERROR (demangle_literal (dm));
2504 RETURN_IF_ERROR (demangle_char (dm, 'E'));
2507 return STATUS_ERROR;
2512 /* Demangles and emits a <substitution>. Sets *TEMPLATE_P to non-zero
2513 if the substitution is the name of a template, zero otherwise. If
2514 the substitution token is St, which corresponds to the `::std::'
2515 namespace and can appear in a non-nested name, sets
2516 *SPECIAL_STD_SUBSTITUTION to non-zero; zero otherwise.
2518 <substitution> ::= S <seq-id> _
2522 ::= Sa # ::std::allocator
2523 ::= Sb # ::std::basic_string
2524 ::= Ss # ::std::basic_string<char,
2525 ::std::char_traits<char>,
2526 ::std::allocator<char> >
2527 ::= Si # ::std::basic_istream<char,
2528 std::char_traits<char> >
2529 ::= So # ::std::basic_ostream<char,
2530 std::char_traits<char> >
2531 ::= Sd # ::std::basic_iostream<char,
2532 std::char_traits<char> >
2536 demangle_substitution (dm, template_p, special_std_substitution)
2539 int *special_std_substitution;
2545 DEMANGLE_TRACE ("substitution", dm);
2547 RETURN_IF_ERROR (demangle_char (dm, 'S'));
2548 *special_std_substitution = 0;
2550 /* Scan the substitution sequence index. A missing number denotes
2552 peek = peek_char (dm);
2555 /* If the following character is 0-9 or a capital letter, interpret
2556 the sequence up to the next underscore as a base-36 substitution
2558 else if (isdigit ((unsigned char) peek)
2559 || (peek >= 'A' && peek <= 'Z'))
2560 RETURN_IF_ERROR (demangle_number (dm, &seq_id, 36, 0));
2566 result_append (dm, "std");
2567 *special_std_substitution = 1;
2571 result_append (dm, "std::allocator");
2572 dyn_string_copy_cstr (dm->last_source_name, "allocator");
2576 result_append (dm, "std::basic_string");
2577 dyn_string_copy_cstr (dm->last_source_name, "basic_string");
2583 result_append (dm, "std::string");
2584 dyn_string_copy_cstr (dm->last_source_name, "string");
2588 result_append (dm, "std::basic_string<char, std::char_traits<char>, std::allocator<char> >");
2589 dyn_string_copy_cstr (dm->last_source_name, "basic_string");
2596 result_append (dm, "std::istream");
2597 dyn_string_copy_cstr (dm->last_source_name, "istream");
2601 result_append (dm, "std::basic_istream<char, std::char_traints<char> >");
2602 dyn_string_copy_cstr (dm->last_source_name, "basic_istream");
2609 result_append (dm, "std::ostream");
2610 dyn_string_copy_cstr (dm->last_source_name, "ostream");
2614 result_append (dm, "std::basic_ostream<char, std::char_traits<char> >");
2615 dyn_string_copy_cstr (dm->last_source_name, "basic_ostream");
2622 result_append (dm, "std::iostream");
2623 dyn_string_copy_cstr (dm->last_source_name, "iostream");
2627 result_append (dm, "std::basic_iostream<char, std::char_traits<char> >");
2628 dyn_string_copy_cstr (dm->last_source_name, "basic_iostream");
2633 return "Unrecognized <substitution>.";
2640 /* Look up the substitution text. Since `S_' is the most recent
2641 substitution, `S0_' is the second-most-recent, etc., shift the
2642 numbering by one. */
2643 text = substitution_get (dm, seq_id + 1, template_p);
2645 return "Substitution number out of range.";
2647 /* Emit the substitution text. */
2648 result_append_string (dm, text);
2650 RETURN_IF_ERROR (demangle_char (dm, '_'));
2654 /* Demangles and emits a <local-name>.
2656 <local-name> := Z <function encoding> E <entity name> [<discriminator>]
2657 := Z <function encoding> E s [<discriminator>] */
2660 demangle_local_name (dm)
2663 DEMANGLE_TRACE ("local-name", dm);
2665 RETURN_IF_ERROR (demangle_char (dm, 'Z'));
2666 RETURN_IF_ERROR (demangle_encoding (dm));
2667 RETURN_IF_ERROR (demangle_char (dm, 'E'));
2668 result_append (dm, "'s ");
2670 if (peek_char (dm) == 's')
2672 /* Local character string literal. */
2673 result_append (dm, "string literal");
2674 /* Consume the s. */
2676 RETURN_IF_ERROR (demangle_discriminator (dm, 0));
2681 result_append (dm, "local ");
2682 /* Local name for some other entity. Demangle its name. */
2683 RETURN_IF_ERROR (demangle_name (dm, &unused));
2684 RETURN_IF_ERROR (demangle_discriminator (dm, 1));
2690 /* Optimonally demangles and emits a <discriminator>. If there is no
2691 <discriminator> at the current position in the mangled string, the
2692 descriminator is assumed to be zero. Emit the discriminator number
2693 in parentheses, unless SUPPRESS_FIRST is non-zero and the
2694 discriminator is zero.
2696 <discriminator> ::= _ <number> */
2699 demangle_discriminator (dm, suppress_first)
2703 /* Output for <discriminator>s to the demangled name is completely
2704 supressed if not in verbose mode. */
2706 if (peek_char (dm) == '_')
2708 /* Consume the underscore. */
2711 result_append (dm, " [#");
2712 /* Check if there's a number following the underscore. */
2713 if (isdigit ((unsigned char) peek_char (dm)))
2716 /* Demangle the number. */
2717 RETURN_IF_ERROR (demangle_number (dm, &discriminator, 10, 0));
2719 /* Write the discriminator. The mangled number is two
2720 less than the discriminator ordinal, counting from
2722 int_to_dyn_string (discriminator + 2,
2723 (dyn_string_t) dm->result);
2728 /* A missing digit correspond to one. */
2729 result_append_char (dm, '1');
2732 result_append_char (dm, ']');
2734 else if (!suppress_first)
2737 result_append (dm, " [#0]");
2743 /* Demangle NAME into RESULT, which must be an initialized
2744 dyn_string_t. On success, returns STATUS_OK. On failure, returns
2745 an error message, and the contents of RESULT are unchanged. */
2748 cp_demangle (name, result)
2750 dyn_string_t result;
2753 int length = strlen (name);
2755 if (length > 2 && name[0] == '_' && name[1] == 'Z')
2757 demangling_t dm = demangling_new (name);
2760 status = demangle_mangled_name (dm);
2762 if (status == STATUS_OK)
2764 dyn_string_t demangled = (dyn_string_t) result_pop (dm);
2765 dyn_string_copy (result, demangled);
2766 dyn_string_delete (demangled);
2769 demangling_delete (dm);
2773 /* It's evidently not a mangled C++ name. It could be the name
2774 of something with C linkage, though, so just copy NAME into
2776 dyn_string_copy_cstr (result, name);
2783 /* Variant entry point for integration with the existing cplus-dem
2784 demangler. Attempts to demangle MANGLED. If the demangling
2785 succeeds, returns a buffer, allocated with malloc, containing the
2786 demangled name. The caller must deallocate the buffer using free.
2787 If the demangling failes, returns NULL. */
2790 cplus_demangle_new_abi (mangled)
2791 const char* mangled;
2793 /* Create a dyn_string to hold the demangled name. */
2794 dyn_string_t demangled = dyn_string_new (0);
2795 /* Attempt the demangling. */
2796 status_t status = cp_demangle ((char *) mangled, demangled);
2797 if (status == STATUS_OK)
2798 /* Demangling succeeded. */
2800 /* Grab the demangled result from the dyn_string. It was
2801 allocated with malloc, so we can return it directly. */
2802 char *return_value = dyn_string_release (demangled);
2803 /* The dyn_string can go away. */
2804 dyn_string_delete (demangled);
2805 /* Hand back the demangled name. */
2806 return return_value;
2809 /* Demangling failed. */
2811 dyn_string_delete (demangled);
2816 #ifdef STANDALONE_DEMANGLER
2820 static void print_usage
2821 PARAMS ((FILE* fp, int exit_value));
2823 /* Non-zero if CHAR is a character than can occur in a mangled name. */
2824 #define is_mangled_char(CHAR) \
2825 (isalnum ((unsigned char) (CHAR)) || (CHAR) == '_')
2827 /* The name of this program, as invoked. */
2828 const char* program_name;
2830 /* Prints usage summary to FP and then exits with EXIT_VALUE. */
2833 print_usage (fp, exit_value)
2837 fprintf (fp, "Usage: %s [options] [names ...]\n", program_name);
2838 fprintf (fp, "Options:\n", program_name);
2839 fprintf (fp, " -h,--help Display this message.\n");
2840 fprintf (fp, " -s,--strict Demangle standard names only.\n");
2841 fprintf (fp, " -v,--verbose Produce verbose demanglings.\n");
2842 fprintf (fp, "If names are provided, they are demangled. Otherwise filters standard input.\n");
2847 /* Option specification for getopt_long. */
2848 static struct option long_options[] =
2850 { "help", no_argument, NULL, 'h' },
2851 { "strict", no_argument, NULL, 's' },
2852 { "verbose", no_argument, NULL, 'v' },
2853 { NULL, no_argument, NULL, 0 },
2856 /* Main entry for a demangling filter executable. It will demangle
2857 its command line arguments, if any. If none are provided, it will
2858 filter stdin to stdout, replacing any recognized mangled C++ names
2859 with their demangled equivalents. */
2870 /* Use the program name of this program, as invoked. */
2871 program_name = argv[0];
2873 /* Parse options. */
2876 opt_char = getopt_long (argc, argv, "hsv", long_options, NULL);
2879 case '?': /* Unrecognized option. */
2880 print_usage (stderr, 1);
2884 print_usage (stdout, 0);
2896 while (opt_char != -1);
2899 /* No command line arguments were provided. Filter stdin. */
2901 dyn_string_t mangled = dyn_string_new (3);
2902 dyn_string_t demangled = dyn_string_new (0);
2905 /* Read all of input. */
2906 while (!feof (stdin))
2908 char c = getchar ();
2910 /* The first character of a mangled name is an underscore. */
2915 /* It's not a mangled name. Print the character and go
2922 /* The second character of a mangled name is a capital `Z'. */
2927 /* It's not a mangled name. Print the previous
2928 underscore, the `Z', and go on. */
2934 /* Start keeping track of the candidate mangled name. */
2935 dyn_string_append_char (mangled, '_');
2936 dyn_string_append_char (mangled, 'Z');
2938 /* Pile characters into mangled until we hit one that can't
2939 occur in a mangled name. */
2941 while (!feof (stdin) && is_mangled_char (c))
2943 dyn_string_append_char (mangled, c);
2949 /* Attempt to demangle the name. */
2950 status = cp_demangle (dyn_string_buf (mangled), demangled);
2952 /* If the demangling succeeded, great! Print out the
2953 demangled version. */
2954 if (status == STATUS_OK)
2955 fputs (dyn_string_buf (demangled), stdout);
2956 /* Otherwise, it might not have been a mangled name. Just
2957 print out the original text. */
2959 fputs (dyn_string_buf (mangled), stdout);
2961 /* If we haven't hit EOF yet, we've read one character that
2962 can't occur in a mangled name, so print it out. */
2966 /* Clear the candidate mangled name, to start afresh next
2967 time we hit a `_Z'. */
2968 dyn_string_clear (mangled);
2971 dyn_string_delete (mangled);
2972 dyn_string_delete (demangled);
2975 /* Demangle command line arguments. */
2977 dyn_string_t result = dyn_string_new (0);
2979 /* Loop over command line arguments. */
2980 for (i = optind; i < argc; ++i)
2982 /* Attempt to demangle. */
2983 status = cp_demangle (argv[i], result);
2985 /* If it worked, print the demangled name. */
2986 if (status == STATUS_OK)
2987 printf ("%s\n", dyn_string_buf (result));
2988 /* If not, print the error message to stderr instead. */
2990 fprintf (stderr, "%s\n", status);
2992 dyn_string_delete (result);
2998 #endif /* STANDALONE_DEMANGLER */