Bug 8218 - ptype claims destructors have arg
Summary: ptype claims destructors have arg
Status: RESOLVED FIXED
Alias: None
Product: gdb
Classification: Unclassified
Component: c++ (show other bugs)
Version: unknown
: P3 normal
Target Milestone: 8.0
Assignee: Keith Seitz
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2003-03-03 22:28 UTC by David Carlton
Modified: 2024-01-14 14:28 UTC (History)
7 users (show)

See Also:
Host:
Target:
Build:
Last reconfirmed:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description David Carlton 2003-03-03 22:28:01 UTC
[Converted from Gnats 1113]

ptype claims that destructors take an int arg.

Release:
GNU gdb 2003-03-03-cvs

Environment:
i686-pc-linux-gnu (Red Hat 7.3)
GCC 3.1
DWARF 2

How-To-Repeat:
Compile this:

class C {
public:
  ~C() {}
};

int main()
{
  C c;
}

Then:

jackfruit$ /extra/gdb/mirror/src/gdb/gdb a.out
GNU gdb 2003-03-03-cvs
Copyright 2003 Free Software Foundation, Inc.
GDB is free software, covered by the GNU General Public License, and you are
welcome to change it and/or distribute copies of it under certain conditions.
Type "show copying" to see the conditions.
There is absolutely no warranty for GDB.  Type "show warranty" for details.
This GDB was configured as "i686-pc-linux-gnu"...
(gdb) b main
Breakpoint 1 at 0x8048500: file foo.cc, line 8.
(gdb) r
Starting program: /home/carlton/tmp/a.out 

Breakpoint 1, main () at foo.cc:8
8	  C c;
(gdb) ptype C
type = class C {
  public:
    ~C(int);
}
Comment 1 David Carlton 2003-03-04 17:02:21 UTC
From: carlton@sources.redhat.com
To: gdb-gnats@sourceware.org
Cc:  
Subject: c++/1113
Date: 4 Mar 2003 17:02:21 -0000

 CVSROOT:	/cvs/src
 Module name:	src
 Changes by:	carlton@sourceware.org	2003-03-04 17:02:20
 
 Modified files:
 	gdb/testsuite  : ChangeLog 
 	gdb/testsuite/gdb.c++: templates.exp 
 
 Log message:
 	2003-03-04  David Carlton  <carlton@math.stanford.edu>
 	
 	* gdb.c++/templates.exp (do_tests): Accept valid const in "print
 	Garply<Garply<char> >:: garply".
 	(test_ptype_of_templates): KFAIL "ptype T5<int>" and "ptype t5i"
 	with respect to PR c++/1111; note also PR c++/1113.
 	(test_template_breakpoints): KFAIL "constructor breakpoint" with
 	respect to PR c++/1062.
 	KFAIL "destructor breakpoint" with respect to PR c++/1112.
 
 Patches:
 http://sources.redhat.com/cgi-bin/cvsweb.cgi/src/gdb/testsuite/ChangeLog.diff?cvsroot=src&r1=1.503&r2=1.504
 http://sources.redhat.com/cgi-bin/cvsweb.cgi/src/gdb/testsuite/gdb.c++/templates.exp.diff?cvsroot=src&r1=1.17&r2=1.18
Comment 2 David Blaikie 2013-01-22 17:34:20 UTC
This looks like a GCC bug, not a GDB bug.

Using llvm-dwarfdump, GCC's dwarf for the dtor looks like this:

0x00000051:     DW_TAG_subprogram [5] *
0x00000052:       DW_AT_external [DW_FORM_flag] (0x01)
0x00000053:       DW_AT_name [DW_FORM_string]   ("~C")
0x00000056:       DW_AT_decl_file [DW_FORM_data1]       (0x01)
0x00000057:       DW_AT_decl_line [DW_FORM_data1]       (0x03)
0x00000058:       DW_AT_declaration [DW_FORM_flag]      (0x01)
0x00000059:       DW_AT_object_pointer [DW_FORM_ref4]   (cu + 0x005d => {0x0000005d})
        
0x0000005d:       DW_TAG_formal_parameter [4]
0x0000005e:         DW_AT_type [DW_FORM_ref4]   (cu + 0x006b => {0x0000006b})
0x00000062:         DW_AT_artificial [DW_FORM_flag]     (0x01)

0x00000063:       DW_TAG_formal_parameter [4] 
0x00000064:         DW_AT_type [DW_FORM_ref4]   (cu + 0x0071 => {0x00000071})
0x00000068:         DW_AT_artificial [DW_FORM_flag]     (0x01)

0x00000069:       NULL  
        
0x0000006a:     NULL    

whereas Clang's dwarf looks like this:

0x00000086:     DW_TAG_subprogram [10] *
0x00000087:       DW_AT_accessibility [DW_FORM_data1]   (0x01)
0x00000088:       DW_AT_name [DW_FORM_strp]     ( .debug_str[0x00000049] = "~C")
0x0000008c:       DW_AT_decl_file [DW_FORM_data1]       (0x01)
0x0000008d:       DW_AT_decl_line [DW_FORM_data1]       (0x03)
0x0000008e:       DW_AT_declaration [DW_FORM_flag_present]      (true)
0x0000008e:       DW_AT_external [DW_FORM_flag_present] (true)

0x0000008e:       DW_TAG_formal_parameter [9]
0x0000008f:         DW_AT_type [DW_FORM_ref4]   (cu + 0x006b => {0x0000006b})
0x00000093:         DW_AT_artificial [DW_FORM_flag_present]     (true)
        
0x00000093:       NULL  
        
0x00000094:     NULL

And GDB's output when given your example and compiled with Clang is:

(well I modified the example a bit: struct C { C() {} ~C() {} }; int main() { C c; } (mostly I was curious whether "(void)" was the way GDB was printing things generally or whether it would print the ctor as "()" instead)):

ptype C
type = struct C {
  public:
    C(void);
    ~C(void);
}

Shall we close this & open a GCC bug instead? (& change the kfail to an xfail referencing the GCC bug - and add the correct pattern so Clang can pass this test)
Comment 3 Tom Tromey 2013-01-22 18:05:34 UTC
(In reply to comment #2)

> 0x00000063:       DW_TAG_formal_parameter [4] 
> 0x00000064:         DW_AT_type [DW_FORM_ref4]   (cu + 0x0071 => {0x00000071})
> 0x00000068:         DW_AT_artificial [DW_FORM_flag]     (0x01)

> Shall we close this & open a GCC bug instead? (& change the kfail to an xfail
> referencing the GCC bug - and add the correct pattern so Clang can pass this
> test)

Arguably it is still a gdb bug since the parameter is marked artificial.
I think that gdb may be making an explicit choice here, though, since
c_type_print_args explicitly prints artificial arguments.

There is a GCC bug in this area: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=37237
It may not seem related but if you read the comments, the gist
is that GCC is just emitting DWARF for one of the constructors,
whereas it should probably emit DWARF for all of them.

Adding a pattern for clang to pass seems fine to me.
Comment 4 Keith Seitz 2017-03-08 21:28:45 UTC
(In reply to Tom Tromey from comment #3)
> Arguably it is still a gdb bug since the parameter is marked artificial.
> I think that gdb may be making an explicit choice here, though, since
> c_type_print_args explicitly prints artificial arguments.

Yeah, this just bit me, too, while trying to write some tests using cp_test_ptype_class. It kept failing on the dtor, "~foo(int)".

The problem here is that cp_type_print_method_args doesn't ignore artificial arguments, except possibly the first one if the method isn't static. [That seems equally dubious to me, too. Compilers don't *have* to implement methods using artificial `this'. :-)]

In any case, I'm working up a patch. To see ~foo(int) in 2017 is just plain disheartening!

I don't think this should harm Clang in any way, but if there is test suite massaging needed, I don't think there would be a problem with that.
Comment 5 Sourceware Commits 2017-03-10 18:34:19 UTC
The master branch has been updated by Keith Seitz <kseitz@sourceware.org>:

https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=5f4d10850850cd95af5e95a16848c8c07a273d88

commit 5f4d10850850cd95af5e95a16848c8c07a273d88
Author: Keith Seitz <keiths@redhat.com>
Date:   Fri Mar 10 10:32:09 2017 -0800

    c++/8218: Destructors w/arguments.
    
    For a long time now, c++/8218 has noted that GDB is printing argument types
    for destructors:
    
    (gdb) ptype A
    type = class A {
      public:
        ~A(int);
    }
    
    This happens because cp_type_print_method_args doesn't ignore artificial
    arguments.  [It ignores the first `this' pointer because it simply skips
    the first argument for any non-static function.]
    
    This patch fixes this:
    
    (gdb) ptype  A
    type = class A {
      public:
        ~A();
    }
    
    I've adjusted gdb.cp/templates.exp to account for this and added a new
    passing regexp.
    
    gdb/ChangeLog
    
    	PR c++/8218
    	* c-typeprint.c (cp_type_print_method_args): Skip artificial arguments.
    
    gdb/testsuite/ChangeLog
    
    	PR c++/8128
    	* gdb.cp/templates.exp (test_ptype_of_templates): Remove argument
    	type from destructor regexps.
    	Add a branch which actually passes the test.
    	Adjust "ptype t5i" test names.
Comment 6 Sergio Durigan Junior 2017-11-17 15:40:23 UTC
Bug 8128 has been closed, but commit 5f4d10850850cd95af5e95a16848c8c07a273d88 apparently fixes this one.
Comment 7 Hannes Domani 2024-01-14 14:28:42 UTC
(In reply to Sourceware Commits from comment #5)
> The master branch has been updated by Keith Seitz <kseitz@sourceware.org>:
> 
> https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;
> h=5f4d10850850cd95af5e95a16848c8c07a273d88
> 
> commit 5f4d10850850cd95af5e95a16848c8c07a273d88
> Author: Keith Seitz <keiths@redhat.com>
> Date:   Fri Mar 10 10:32:09 2017 -0800
> 
>     c++/8218: Destructors w/arguments.
>     
>     For a long time now, c++/8218 has noted that GDB is printing argument
> types
>     for destructors:
>     
>     (gdb) ptype A
>     type = class A {
>       public:
>         ~A(int);
>     }
>     
>     This happens because cp_type_print_method_args doesn't ignore artificial
>     arguments.  [It ignores the first `this' pointer because it simply skips
>     the first argument for any non-static function.]
>     
>     This patch fixes this:
>     
>     (gdb) ptype  A
>     type = class A {
>       public:
>         ~A();
>     }
>     
>     I've adjusted gdb.cp/templates.exp to account for this and added a new
>     passing regexp.
>     
>     gdb/ChangeLog
>     
>     	PR c++/8218
>     	* c-typeprint.c (cp_type_print_method_args): Skip artificial arguments.

Fixed.