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