[gdb/c++] Print destructor the same for gcc and clang
authorTom de Vries <tdevries@suse.de>
Fri, 30 Sep 2022 03:47:54 +0000 (05:47 +0200)
committerTom de Vries <tdevries@suse.de>
Fri, 30 Sep 2022 03:47:54 +0000 (05:47 +0200)
commit137c886e9a624f68cba212ebdb156298957c25c4
treedf46341752b65499df1fe7a3893456461c814ca9
parent4eeb0013059856b8660b4a0351589b096167b4d1
[gdb/c++] Print destructor the same for gcc and clang

Consider the test-case contained in this patch.

With g++ (7.5.0) we have for "ptype A":
...
type = class A {
  public:
    int a;

    A(void);
    ~A();
}
...
and with clang++ (13.0.1):
...
type = class A {
  public:
    int a;

    A(void);
    ~A(void);
}
...
and we observe that the destructor is printed differently.

There's a difference in debug info between the two cases: in the clang case,
there's one artificial parameter, but in the g++ case, there are two, and
these similar cases are handled differently in cp_type_print_method_args.

This is due to this slightly convoluted bit of code:
...
  i = staticp ? 0 : 1;
  if (nargs > i)
    {
      while (i < nargs)
        ...
    }
  else if (varargs)
    gdb_printf (stream, "...");
  else if (language == language_cplus)
    gdb_printf (stream, "void");
...

The purpose of "i = staticp ? 0 : 1" is to skip the printing of the implicit
this parameter.

In commit 5f4d1085085 ("c++/8218: Destructors w/arguments"), skipping of other
artificial parameters was added, but using a different method: rather than
adjusting the potential loop start, it skips the parameter in the loop.

The observed difference in printing is explained by whether we enter the loop:
- in the clang case, the loop is not entered and we print "void".
- in the gcc case, the loop is entered, and nothing is printed.

Fix this by rewriting the code to:
- always enter the loop
- handle whether arguments need printing in the loop
- keep track of how many arguments are printed, and
  use that after the loop to print void etc.
such that we have the same for both gcc and clang:
...
    A(void);
    ~A(void);
...

Note that I consider the discussion of whether we want to print:
- A(void) / ~A(void), or
- A() / ~A()
out-of-scope for this patch.

Tested on x86_64-linux.
gdb/c-typeprint.c
gdb/testsuite/gdb.base/ptype-offsets.exp
gdb/testsuite/gdb.cp/print-method-args.cc [new file with mode: 0644]
gdb/testsuite/gdb.cp/print-method-args.exp [new file with mode: 0644]
gdb/testsuite/gdb.cp/templates.exp