aboutsummaryrefslogtreecommitdiff
path: root/bfd
diff options
context:
space:
mode:
authorAlan Modra <amodra@gmail.com>2007-04-19 10:51:34 +0000
committerAlan Modra <amodra@gmail.com>2007-04-19 10:51:34 +0000
commit3fad56a3d40bd75f70f60ec513c2dbc8e3e45c12 (patch)
treef22aaf1cddb2b77d1e61813c3061dce9ae774293 /bfd
parent5c068be831d7c23744df791ee11e8466ad43c6fe (diff)
downloadgdb-3fad56a3d40bd75f70f60ec513c2dbc8e3e45c12.zip
gdb-3fad56a3d40bd75f70f60ec513c2dbc8e3e45c12.tar.gz
gdb-3fad56a3d40bd75f70f60ec513c2dbc8e3e45c12.tar.bz2
missed from last commit
Diffstat (limited to 'bfd')
-rw-r--r--bfd/bfd.c85
1 files changed, 84 insertions, 1 deletions
diff --git a/bfd/bfd.c b/bfd/bfd.c
index 381e3d7..2c31e56 100644
--- a/bfd/bfd.c
+++ b/bfd/bfd.c
@@ -1,6 +1,6 @@
/* Generic BFD library interface and support routines.
Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
- 2000, 2001, 2002, 2003, 2004, 2005, 2006
+ 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
Free Software Foundation, Inc.
Written by Cygnus Support.
@@ -207,6 +207,7 @@ CODE_FRAGMENT
#include "sysdep.h"
#include <stdarg.h>
#include "libiberty.h"
+#include "demangle.h"
#include "safe-ctype.h"
#include "bfdlink.h"
#include "libbfd.h"
@@ -1702,3 +1703,85 @@ bfd_emul_set_commonpagesize (const char *emul, bfd_vma size)
offsetof (struct elf_backend_data,
commonpagesize), target);
}
+
+/*
+FUNCTION
+ bfd_demangle
+
+SYNOPSIS
+ char *bfd_demangle (bfd *, const char *, int);
+
+DESCRIPTION
+ Wrapper around cplus_demangle. Strips leading underscores and
+ other such chars that would otherwise confuse the demangler.
+ If passed a g++ v3 ABI mangled name, returns a buffer allocated
+ with malloc holding the demangled name. Returns NULL otherwise
+ and on memory alloc failure.
+*/
+
+char *
+bfd_demangle (bfd *abfd, const char *name, int options)
+{
+ char *res, *alloc;
+ const char *pre, *suf;
+ size_t pre_len;
+
+ if (abfd != NULL
+ && *name != '\0'
+ && bfd_get_symbol_leading_char (abfd) == *name)
+ ++name;
+
+ /* This is a hack for better error reporting on XCOFF, PowerPC64-ELF
+ or the MS PE format. These formats have a number of leading '.'s
+ on at least some symbols, so we remove all dots to avoid
+ confusing the demangler. */
+ pre = name;
+ while (*name == '.' || *name == '$')
+ ++name;
+ pre_len = name - pre;
+
+ /* Strip off @plt and suchlike too. */
+ alloc = NULL;
+ suf = strchr (name, '@');
+ if (suf != NULL)
+ {
+ alloc = bfd_malloc (suf - name + 1);
+ if (alloc == NULL)
+ return NULL;
+ memcpy (alloc, name, suf - name);
+ alloc[suf - name] = '\0';
+ name = alloc;
+ }
+
+ res = cplus_demangle (name, options);
+
+ if (alloc != NULL)
+ free (alloc);
+
+ if (res == NULL)
+ return NULL;
+
+ /* Put back any prefix or suffix. */
+ if (pre_len != 0 || suf != NULL)
+ {
+ size_t len;
+ size_t suf_len;
+ char *final;
+
+ len = strlen (res);
+ if (suf == NULL)
+ suf = res + len;
+ suf_len = strlen (suf) + 1;
+ final = bfd_malloc (pre_len + len + suf_len);
+ if (final == NULL)
+ return NULL;
+
+ memcpy (final, pre, pre_len);
+ memcpy (final + pre_len, res, len);
+ memcpy (final + pre_len + len, suf, suf_len);
+ free (res);
+ res = final;
+ }
+
+ return res;
+}