]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blobdiff - binutils/cxxfilt.c
* elfxx-tilegx.c (tilegx_elf_relocate_section): Silence bogus warning.
[thirdparty/binutils-gdb.git] / binutils / cxxfilt.c
index a0e0a0759404f8cb37207027379b31a9a278691d..770df9baf6e0307a9e53f3dca0cd38119f295251 100644 (file)
@@ -1,55 +1,74 @@
 /* Demangler for GNU C++ - main program
    Copyright 1989, 1991, 1994, 1995, 1996, 1997, 1998, 1999,
-   2000, 2001, 2002, 2003 Free Software Foundation, Inc.
+   2000, 2001, 2002, 2003, 2005, 2007 Free Software Foundation, Inc.
    Written by James Clark (jjc@jclark.uucp)
    Rewritten by Fred Fish (fnf@cygnus.com) for ARM and Lucid demangling
    Modified by Satish Pai (pai@apollo.hp.com) for HP demangling
 
-This file is part of GCC.
+   This file is part of GNU Binutils.
 
-GCC is free software; you can redistribute it and/or modify it under
-the terms of the GNU General Public License as published by the Free
-Software Foundation; either version 2, or (at your option) any later
-version.
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3 of the License, or (at
+   your option) any later version.
 
-GCC is distributed in the hope that it will be useful, but WITHOUT ANY
-WARRANTY; without even the implied warranty of MERCHANTABILITY or
-FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-for more details.
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
 
-You should have received a copy of the GNU General Public License
-along with GCC; see the file COPYING.  If not, write to the Free
-Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
-02110-1301, USA.  */
+   You should have received a copy of the GNU General Public License
+   along with GCC; see the file COPYING.  If not, write to the Free
+   Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
+   02110-1301, USA.  */
 
-#include "config.h"
+#include "sysdep.h"
 #include "bfd.h"
-#include "bucomm.h"
 #include "libiberty.h"
 #include "demangle.h"
 #include "getopt.h"
 #include "safe-ctype.h"
+#include "bucomm.h"
 
 static int flags = DMGL_PARAMS | DMGL_ANSI | DMGL_VERBOSE;
+static int strip_underscore = TARGET_PREPENDS_UNDERSCORE;
 
-static void demangle_it (char *);
-static void usage (FILE *, int) ATTRIBUTE_NORETURN;
-static void print_demangler_list (FILE *);
+static const struct option long_options[] =
+{
+  {"strip-underscore", no_argument, NULL, '_'},
+  {"format", required_argument, NULL, 's'},
+  {"help", no_argument, NULL, 'h'},
+  {"no-params", no_argument, NULL, 'p'},
+  {"no-strip-underscores", no_argument, NULL, 'n'},
+  {"no-verbose", no_argument, NULL, 'i'},
+  {"types", no_argument, NULL, 't'},
+  {"version", no_argument, NULL, 'v'},
+  {NULL, no_argument, NULL, 0}
+};
 
 static void
 demangle_it (char *mangled_name)
 {
   char *result;
+  unsigned int skip_first = 0;
+
+  /* _ and $ are sometimes found at the start of function names
+     in assembler sources in order to distinguish them from other
+     names (eg register names).  So skip them here.  */
+  if (mangled_name[0] == '.' || mangled_name[0] == '$')
+    ++skip_first;
+  if (strip_underscore && mangled_name[skip_first] == '_')
+    ++skip_first;
+
+  result = cplus_demangle (mangled_name + skip_first, flags);
 
-  /* For command line args, also try to demangle type encodings.  */
-  result = cplus_demangle (mangled_name, flags | DMGL_TYPES);
   if (result == NULL)
-    {
-      printf ("%s\n", mangled_name);
-    }
+    printf ("%s", mangled_name);
   else
     {
-      printf ("%s\n", result);
+      if (mangled_name[0] == '.')
+       putchar ('.');
+      printf ("%s", result);
       free (result);
     }
 }
@@ -73,43 +92,34 @@ static void
 usage (FILE *stream, int status)
 {
   fprintf (stream, "\
-Usage: %s [-_] [-n] [--strip-underscores] [--no-strip-underscores]\n\
-       [-p] [--no-params]\n",
-          program_name);
-
+Usage: %s [options] [mangled names]\n", program_name);
   fprintf (stream, "\
-       [-s ");
-  print_demangler_list (stream);
-  fprintf (stream, "]\n");
-
+Options are:\n\
+  [-_|--strip-underscore]     Ignore first leading underscore%s\n",
+          TARGET_PREPENDS_UNDERSCORE ? " (default)" : "");
   fprintf (stream, "\
-       [--format ");
+  [-n|--no-strip-underscore]  Do not ignore a leading underscore%s\n",
+          TARGET_PREPENDS_UNDERSCORE ? "" : " (default)");
+  fprintf (stream, "\
+  [-p|--no-params]            Do not display function arguments\n\
+  [-i|--no-verbose]           Do not show implementation details (if any)\n\
+  [-t|--types]                Also attempt to demangle type encodings\n\
+  [-s|--format ");
   print_demangler_list (stream);
   fprintf (stream, "]\n");
 
   fprintf (stream, "\
-       [@file] [--help] [--version] [arg...]\n");
+  [@<file>]                   Read extra options from <file>\n\
+  [-h|--help]                 Display this information\n\
+  [-v|--version]              Show the version information\n\
+Demangled names are displayed to stdout.\n\
+If a name cannot be demangled it is just echoed to stdout.\n\
+If no names are provided on the command line, stdin is read.\n");
+  if (REPORT_BUGS_TO[0] && status == 0)
+    fprintf (stream, _("Report bugs to %s.\n"), REPORT_BUGS_TO);
   exit (status);
 }
 
-static char mbuffer[32767];
-
-int strip_underscore = 0;
-
-static const struct option long_options[] = {
-  {"strip-underscores", no_argument, 0, '_'},
-  {"format", required_argument, 0, 's'},
-  {"help", no_argument, 0, 'h'},
-  {"no-params", no_argument, 0, 'p'},
-  {"no-strip-underscores", no_argument, 0, 'n'},
-  {"version", no_argument, 0, 'v'},
-  {0, no_argument, 0, 0}
-};
-
-static const char *standard_symbol_characters (void);
-
-static const char *hp_symbol_characters (void);
-
 /* Return the string of non-alnum characters that may occur
    as a valid symbol component, in the standard assembler symbol
    syntax.  */
@@ -120,7 +130,6 @@ standard_symbol_characters (void)
   return "_$.";
 }
 
-
 /* Return the string of non-alnum characters that may occur
    as a valid symbol name component in an HP object file.
 
@@ -162,7 +171,6 @@ extern int main (int, char **);
 int
 main (int argc, char **argv)
 {
-  char *result;
   int c;
   const char *valid_symbols;
   enum demangling_styles style = auto_demangling;
@@ -172,9 +180,7 @@ main (int argc, char **argv)
 
   expandargv (&argc, &argv);
 
-  strip_underscore = TARGET_PREPENDS_UNDERSCORE;
-
-  while ((c = getopt_long (argc, argv, "_nps:", long_options, (int *) 0)) != EOF)
+  while ((c = getopt_long (argc, argv, "_hinps:tv", long_options, (int *) 0)) != EOF)
     {
       switch (c)
        {
@@ -189,24 +195,27 @@ main (int argc, char **argv)
        case 'p':
          flags &= ~ DMGL_PARAMS;
          break;
+       case 't':
+         flags |= DMGL_TYPES;
+         break;
+       case 'i':
+         flags &= ~ DMGL_VERBOSE;
+         break;
        case 'v':
          print_version ("c++filt");
-         return (0);
+         return 0;
        case '_':
          strip_underscore = 1;
          break;
        case 's':
-         {
-           style = cplus_demangle_name_to_style (optarg);
-           if (style == unknown_demangling)
-             {
-               fprintf (stderr, "%s: unknown demangling style `%s'\n",
-                        program_name, optarg);
-               return (1);
-             }
-           else
-             cplus_demangle_set_style (style);
-         }
+         style = cplus_demangle_name_to_style (optarg);
+         if (style == unknown_demangling)
+           {
+             fprintf (stderr, "%s: unknown demangling style `%s'\n",
+                      program_name, optarg);
+             return 1;
+           }
+         cplus_demangle_set_style (style);
          break;
        }
     }
@@ -216,77 +225,65 @@ main (int argc, char **argv)
       for ( ; optind < argc; optind++)
        {
          demangle_it (argv[optind]);
+         putchar ('\n');
        }
+
+      return 0;
     }
-  else
+
+  switch (current_demangling_style)
     {
-      switch (current_demangling_style)
+    case gnu_demangling:
+    case lucid_demangling:
+    case arm_demangling:
+    case java_demangling:
+    case edg_demangling:
+    case gnat_demangling:
+    case gnu_v3_demangling:
+    case auto_demangling:
+      valid_symbols = standard_symbol_characters ();
+      break;
+    case hp_demangling:
+      valid_symbols = hp_symbol_characters ();
+      break;
+    default:
+      /* Folks should explicitly indicate the appropriate alphabet for
+        each demangling.  Providing a default would allow the
+        question to go unconsidered.  */
+      fatal ("Internal error: no symbol alphabet for current style");
+    }
+
+  for (;;)
+    {
+      static char mbuffer[32767];
+      unsigned i = 0;
+
+      c = getchar ();
+      /* Try to read a mangled name.  */
+      while (c != EOF && (ISALNUM (c) || strchr (valid_symbols, c)))
        {
-       case gnu_demangling:
-       case lucid_demangling:
-       case arm_demangling:
-       case java_demangling:
-       case edg_demangling:
-       case gnat_demangling:
-       case gnu_v3_demangling:
-       case auto_demangling:
-         valid_symbols = standard_symbol_characters ();
-         break;
-       case hp_demangling:
-         valid_symbols = hp_symbol_characters ();
-         break;
-       default:
-         /* Folks should explicitly indicate the appropriate alphabet for
-            each demangling.  Providing a default would allow the
-            question to go unconsidered.  */
-         fatal ("Internal error: no symbol alphabet for current style");
+         if (i >= sizeof (mbuffer) - 1)
+           break;
+         mbuffer[i++] = c;
+         c = getchar ();
        }
 
-      for (;;)
+      if (i > 0)
        {
-         unsigned i = 0;
-         c = getchar ();
-         /* Try to read a label.  */
-         while (c != EOF && (ISALNUM (c) || strchr (valid_symbols, c)))
-           {
-             if (i >= sizeof (mbuffer) - 1)
-               break;
-             mbuffer[i++] = c;
-             c = getchar ();
-           }
-         if (i > 0)
-           {
-             unsigned skip_first = 0;
-
-             mbuffer[i] = 0;
-             if (mbuffer[0] == '.' || mbuffer[0] == '$')
-               ++skip_first;
-             if (strip_underscore && mbuffer[skip_first] == '_')
-               ++skip_first;
-
-             if (skip_first > i)
-               skip_first = i;
-
-             flags |= (int) style;
-             result = cplus_demangle (mbuffer + skip_first, flags);
-             if (result)
-               {
-                 if (mbuffer[0] == '.')
-                   putc ('.', stdout);
-                 fputs (result, stdout);
-                 free (result);
-               }
-             else
-               fputs (mbuffer, stdout);
-
-             fflush (stdout);
-           }
-         if (c == EOF)
-           break;
-         putchar (c);
-         fflush (stdout);
+         mbuffer[i] = 0;
+         demangle_it (mbuffer);
        }
+
+      if (c == EOF)
+       break;
+
+      /* Echo the whitespace characters so that the output looks
+        like the input, only with the mangled names demangled.  */
+      putchar (c);
+      if (c == '\n')
+       fflush (stdout);
     }
 
-  return (0);
+  fflush (stdout);
+  return 0;
 }