diff options
author | David Chisnall <dchisnall@pathscale.com> | 2014-05-09 01:35:37 +0000 |
---|---|---|
committer | Android Git Automerger <android-git-automerger@android.com> | 2014-05-09 01:35:37 +0000 |
commit | 91803f2ab9d35835dba736e0e8d3e278c8d9a5a9 (patch) | |
tree | bb73f482e21023b96a8679fe85a2a8fe790eb34e | |
parent | fd73d28a296b1ec7e3a6acdce171b0fa18b6746e (diff) | |
parent | af6a0de8a8e9daf8e79a0e2b59b4a023e39ae9e5 (diff) | |
download | libcxxrt-91803f2ab9d35835dba736e0e8d3e278c8d9a5a9.tar.gz |
am af6a0de8: Import r2179 of the libelftc demangler.
* commit 'af6a0de8a8e9daf8e79a0e2b59b4a023e39ae9e5':
Import r2179 of the libelftc demangler.
-rw-r--r-- | src/libelftc_dem_gnu3.c | 62 |
1 files changed, 49 insertions, 13 deletions
diff --git a/src/libelftc_dem_gnu3.c b/src/libelftc_dem_gnu3.c index b0428c9..de35518 100644 --- a/src/libelftc_dem_gnu3.c +++ b/src/libelftc_dem_gnu3.c @@ -405,6 +405,7 @@ static int cpp_demangle_read_expression_trinary(struct cpp_demangle_data *, const char *, size_t, const char *, size_t); static int cpp_demangle_read_function(struct cpp_demangle_data *, int *, struct vector_type_qualifier *); +static int cpp_demangle_local_source_name(struct cpp_demangle_data *ddata); static int cpp_demangle_read_local_name(struct cpp_demangle_data *); static int cpp_demangle_read_name(struct cpp_demangle_data *); static int cpp_demangle_read_nested_name(struct cpp_demangle_data *); @@ -453,11 +454,19 @@ __cxa_demangle_gnu3(const char *org) struct cpp_demangle_data ddata; ssize_t org_len; unsigned int limit; - char *rtn; + char *rtn = NULL; if (org == NULL) return (NULL); + if (org_len > 11 && !strncmp(org, "_GLOBAL__I_", 11)) { + if ((rtn = malloc(org_len + 19)) == NULL) + return (NULL); + snprintf(rtn, org_len + 19, + "global constructors keyed to %s", org + 11); + return (rtn); + } + // Try demangling as a type for short encodings if (((org_len = strlen(org)) < 2) || (org[0] != '_' || org[1] != 'Z' )) { if (!cpp_demangle_data_init(&ddata, org)) @@ -467,13 +476,6 @@ __cxa_demangle_gnu3(const char *org) rtn = vector_str_get_flat(&ddata.output, (size_t *) NULL); goto clean; } - if (org_len > 11 && !strncmp(org, "_GLOBAL__I_", 11)) { - if ((rtn = malloc(org_len + 19)) == NULL) - return (NULL); - snprintf(rtn, org_len + 19, - "global constructors keyed to %s", org + 11); - return (rtn); - } if (!cpp_demangle_data_init(&ddata, org + 2)) @@ -604,13 +606,12 @@ cpp_demangle_push_fp(struct cpp_demangle_data *ddata, return (0); rtn = 0; - if ((len = strlen(f)) > 0 && - cpp_demangle_push_str(ddata, f, len)) - rtn = 1; + if ((len = strlen(f)) > 0) + rtn = cpp_demangle_push_str(ddata, f, len); free(f); - return (0); + return (rtn); } static int @@ -655,6 +656,7 @@ cpp_demangle_push_subst_v(struct cpp_demangle_data *ddata, struct vector_str *v) return (0); rtn = cpp_demangle_push_subst(ddata, str, str_len); + free(str); return (rtn); @@ -2054,7 +2056,7 @@ clean: free(subst_str); vector_str_dest(&v); - return (1); + return (rtn); } static int @@ -2996,6 +2998,40 @@ cpp_demangle_read_uqname(struct cpp_demangle_data *ddata) if (ELFTC_ISDIGIT(*ddata->cur) != 0) return (cpp_demangle_read_sname(ddata)); + + /* local source name */ + if (*ddata->cur == 'L') + return (cpp_demangle_local_source_name(ddata)); + + return (1); +} + +/* + * Read local source name. + * + * References: + * http://gcc.gnu.org/bugzilla/show_bug.cgi?id=31775 + * http://gcc.gnu.org/viewcvs?view=rev&revision=124467 + */ +static int +cpp_demangle_local_source_name(struct cpp_demangle_data *ddata) +{ + /* L */ + if (ddata == NULL || *ddata->cur != 'L') + return (0); + ++ddata->cur; + + /* source name */ + if (!cpp_demangle_read_sname(ddata)) + return (0); + + /* discriminator */ + if (*ddata->cur == '_') { + ++ddata->cur; + while (ELFTC_ISDIGIT(*ddata->cur) != 0) + ++ddata->cur; + } + return (1); } |