+2016-05-19 Jakub Jelinek <jakub@redhat.com>
+
+ Backported from mainline
+ 2015-11-27 Pedro Alves <palves@redhat.com>
+
+ PR other/61321
+ PR other/61233
+ * demangle.h (enum demangle_component_type)
+ <DEMANGLE_COMPONENT_CONVERSION>: New value.
+
2015-06-26 Release Manager
* GCC 4.9.3 released.
/* A typecast, represented as a unary operator. The one subtree is
the type to which the argument should be cast. */
DEMANGLE_COMPONENT_CAST,
+ /* A conversion operator, represented as a unary operator. The one
+ subtree is the type to which the argument should be converted
+ to. */
+ DEMANGLE_COMPONENT_CONVERSION,
/* A nullary expression. The left subtree is the operator. */
DEMANGLE_COMPONENT_NULLARY,
/* A unary expression. The left subtree is the operator, and the
2016-05-19 Jakub Jelinek <jakub@redhat.com>
Backported from mainline
+ 2015-11-27 Pedro Alves <palves@redhat.com>
+
+ PR other/61321
+ PR other/61233
+ * cp-demangle.c (d_demangle_callback, d_make_comp): Handle
+ DEMANGLE_COMPONENT_CONVERSION.
+ (is_ctor_dtor_or_conversion): Handle DEMANGLE_COMPONENT_CONVERSION
+ instead of DEMANGLE_COMPONENT_CAST.
+ (d_operator_name): Return a DEMANGLE_COMPONENT_CONVERSION
+ component if handling a conversion.
+ (d_count_templates_scopes, d_print_comp_inner): Handle
+ DEMANGLE_COMPONENT_CONVERSION.
+ (d_print_comp_inner): Handle DEMANGLE_COMPONENT_CONVERSION instead
+ of DEMANGLE_COMPONENT_CAST.
+ (d_print_cast): Rename as ...
+ (d_print_conversion): ... this. Adjust comments.
+ (d_print_cast): Rewrite - simply print the left subcomponent.
+ * cp-demint.c (cplus_demangle_fill_component): Handle
+ DEMANGLE_COMPONENT_CONVERSION.
+
+ * testsuite/demangle-expected: Add tests.
+
2015-07-13 Mikhail Maltsev <maltsevm@gmail.com>
* cp-demangle.c (d_dump): Fix syntax error.
static void
d_print_expr_op (struct d_print_info *, int, const struct demangle_component *);
-static void
-d_print_cast (struct d_print_info *, int, const struct demangle_component *);
+static void d_print_cast (struct d_print_info *, int,
+ const struct demangle_component *);
+static void d_print_conversion (struct d_print_info *, int,
+ const struct demangle_component *);
static int d_demangle_callback (const char *, int,
demangle_callbackref, void *);
case DEMANGLE_COMPONENT_CAST:
printf ("cast\n");
break;
+ case DEMANGLE_COMPONENT_CONVERSION:
+ printf ("conversion operator\n");
+ break;
case DEMANGLE_COMPONENT_NULLARY:
printf ("nullary operator\n");
break;
case DEMANGLE_COMPONENT_IMAGINARY:
case DEMANGLE_COMPONENT_VENDOR_TYPE:
case DEMANGLE_COMPONENT_CAST:
+ case DEMANGLE_COMPONENT_CONVERSION:
case DEMANGLE_COMPONENT_JAVA_RESOURCE:
case DEMANGLE_COMPONENT_DECLTYPE:
case DEMANGLE_COMPONENT_PACK_EXPANSION:
return is_ctor_dtor_or_conversion (d_right (dc));
case DEMANGLE_COMPONENT_CTOR:
case DEMANGLE_COMPONENT_DTOR:
- case DEMANGLE_COMPONENT_CAST:
+ case DEMANGLE_COMPONENT_CONVERSION:
return 1;
}
}
{
struct demangle_component *type;
int was_conversion = di->is_conversion;
+ struct demangle_component *res;
di->is_conversion = ! di->is_expression;
type = cplus_demangle_type (di);
+ if (di->is_conversion)
+ res = d_make_comp (di, DEMANGLE_COMPONENT_CONVERSION, type, NULL);
+ else
+ res = d_make_comp (di, DEMANGLE_COMPONENT_CAST, type, NULL);
di->is_conversion = was_conversion;
- return d_make_comp (di, DEMANGLE_COMPONENT_CAST, type, NULL);
+ return res;
}
else
{
case DEMANGLE_COMPONENT_TEMPLATE_ARGLIST:
case DEMANGLE_COMPONENT_INITIALIZER_LIST:
case DEMANGLE_COMPONENT_CAST:
+ case DEMANGLE_COMPONENT_CONVERSION:
case DEMANGLE_COMPONENT_NULLARY:
case DEMANGLE_COMPONENT_UNARY:
case DEMANGLE_COMPONENT_BINARY:
d_print_comp (dpi, options, dc->u.s_extended_operator.name);
return;
- case DEMANGLE_COMPONENT_CAST:
+ case DEMANGLE_COMPONENT_CONVERSION:
d_append_string (dpi, "operator ");
- d_print_cast (dpi, options, dc);
+ d_print_conversion (dpi, options, dc);
return;
case DEMANGLE_COMPONENT_NULLARY:
static void
d_print_cast (struct d_print_info *dpi, int options,
- const struct demangle_component *dc)
+ const struct demangle_component *dc)
+{
+ d_print_comp (dpi, options, d_left (dc));
+}
+
+/* Print a conversion operator. */
+
+static void
+d_print_conversion (struct d_print_info *dpi, int options,
+ const struct demangle_component *dc)
{
struct d_print_template dpt;
- /* For a cast operator, we need the template parameters from
+ /* For a conversion operator, we need the template parameters from
the enclosing template in scope for processing the type. */
if (dpi->current_template != NULL)
{
case DEMANGLE_COMPONENT_IMAGINARY:
case DEMANGLE_COMPONENT_VENDOR_TYPE:
case DEMANGLE_COMPONENT_CAST:
+ case DEMANGLE_COMPONENT_CONVERSION:
if (right != NULL)
return 0;
break;
_QueueNotification_QueueController__$4PPPPPPPM_A_INotice___Z
_QueueNotification_QueueController__$4PPPPPPPM_A_INotice___Z
_QueueNotification_QueueController__$4PPPPPPPM_A_INotice___Z
+#
+# These two are from gcc PR61321, and gcc PR61233 / gdb PR16957
+#
+--format=gnu-v3
+_Z13function_tempIiEv1AIXszcvT_Li999EEE
+void function_temp<int>(A<sizeof ((int)(999))>)
+#
+--format=gnu-v3
+_Z7ZipWithI7QStringS0_5QListZN4oral6detail16AdaptCreateTableI7AccountEES0_RKNS3_16CachedFieldsDataEEUlRKS0_SA_E_ET1_IDTclfp1_cvT__EcvT0__EEEERKT1_ISC_ERKT1_ISD_ET2_
+QList<decltype ({parm#3}((QString)(), (QString)()))> ZipWith<QString, QString, QList, QString oral::detail::AdaptCreateTable<Account>(oral::detail::CachedFieldsData const&)::{lambda(QString const&, QString const&)#1}>(QList<QString oral::detail::AdaptCreateTable<Account>(oral::detail::CachedFieldsData const&)::{lambda(QString const&, QString const&)#1}> const&, QList<QList> const&, QString oral::detail::AdaptCreateTable<Account>(oral::detail::CachedFieldsData const&)::{lambda(QString const&, QString const&)#1})
+#
+# These three are symbols generated by g++'s testsuite, which triggered the same bug as above.
+--format=gnu-v3
+_Z14int_if_addableI1YERiP1AIXszpldecvPT_Li0EdecvS4_Li0EEE
+int& int_if_addable<Y>(A<sizeof ((*((Y*)(0)))+(*((Y*)(0))))>*)
+#
+--format=gnu-v3
+_Z3bazIiEvP1AIXszcl3foocvT__ELCf00000000_00000000EEEE
+void baz<int>(A<sizeof (foo((int)(), (floatcomplex )00000000_00000000))>*)
+#
+--format=gnu-v3
+_Z3fooI1FEN1XIXszdtcl1PclcvT__EEE5arrayEE4TypeEv
+X<sizeof ((P(((F)())())).array)>::Type foo<F>()
--- /dev/null
+/* Demangler fuzzer.
+
+ Copyright (C) 2014 Free Software Foundation, Inc.
+
+ This file is part of GNU libiberty.
+
+ 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.
+
+ 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 this program. If not, see <http://www.gnu.org/licenses/>. */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <time.h>
+#include "demangle.h"
+
+#define MAXLEN 253
+#define ALPMIN 33
+#define ALPMAX 127
+
+static char *program_name;
+
+#define DEFAULT_MAXCOUNT 7500000
+
+static void
+print_usage (FILE *fp, int exit_value)
+{
+ fprintf (fp, "Usage: %s [OPTION]...\n", program_name);
+ fprintf (fp, "Options:\n");
+ fprintf (fp, " -h Display this message.\n");
+ fprintf (fp, " -s SEED Select the random seed to be used.\n");
+ fprintf (fp, " The default is to base one on the");
+ fprintf (fp, " current time.\n");
+ fprintf (fp, " -m MAXCOUNT Exit after MAXCOUNT symbols.\n");
+ fprintf (fp, " The default is %d.", DEFAULT_MAXCOUNT);
+ fprintf (fp, " Set to `-1' for no limit.\n");
+
+ exit (exit_value);
+}
+
+int
+main (int argc, char *argv[])
+{
+ char symbol[2 + MAXLEN + 1] = "_Z";
+ int seed = -1, seed_set = 0;
+ int count = 0, maxcount = DEFAULT_MAXCOUNT;
+ int optchr;
+
+ program_name = argv[0];
+
+ do
+ {
+ optchr = getopt (argc, argv, "hs:m:t:");
+ switch (optchr)
+ {
+ case '?': /* Unrecognized option. */
+ print_usage (stderr, 1);
+ break;
+
+ case 'h':
+ print_usage (stdout, 0);
+ break;
+
+ case 's':
+ seed = atoi (optarg);
+ seed_set = 1;
+ break;
+
+ case 'm':
+ maxcount = atoi (optarg);
+ break;
+ }
+ }
+ while (optchr != -1);
+
+ if (!seed_set)
+ seed = time (NULL);
+ srand (seed);
+ printf ("%s: seed = %d\n", program_name, seed);
+
+ while (maxcount < 0 || count < maxcount)
+ {
+ char *buffer = symbol + 2;
+ int length, i;
+
+ length = rand () % MAXLEN;
+ for (i = 0; i < length; i++)
+ *buffer++ = (rand () % (ALPMAX - ALPMIN)) + ALPMIN;
+
+ *buffer++ = '\0';
+
+ cplus_demangle (symbol, DMGL_AUTO | DMGL_ANSI | DMGL_PARAMS);
+
+ count++;
+ }
+
+ printf ("%s: successfully demangled %d symbols\n", program_name, count);
+ exit (0);
+}