https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81001

            Bug ID: 81001
           Summary: incorrect debug info for parameter that is const
                    pointer to typedef of array
           Product: gcc
           Version: 7.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: debug
          Assignee: unassigned at gcc dot gnu.org
          Reporter: ian at airs dot com
  Target Milestone: ---

I am using a fairly recent trunk (SVN revision 248521).

Compiling this program gives me correct debug info:

typedef unsigned char Bar;
void foo(Bar* f){}        // this works
void foo2(const Bar* f){} // this confuses cgo
void x() {
  foo(0);
  foo2(0);
}

Using readelf --debug=info, the debug info for foo's parameter is correctly
represented as a pointer to a typedef of unsigned char:

 <2><a8>: Abbrev Number: 7 (DW_TAG_formal_parameter)
    <a9>   DW_AT_name        : f        
    <ab>   DW_AT_decl_file   : 1        
    <ac>   DW_AT_decl_line   : 2        
    <ad>   DW_AT_type        : <0xb5>   
    <b1>   DW_AT_location    : 2 byte block: 91 68      (DW_OP_fbreg: -24)
 <2><b4>: Abbrev Number: 0
 <1><b5>: Abbrev Number: 8 (DW_TAG_pointer_type)
    <b6>   DW_AT_byte_size   : 8        
    <b7>   DW_AT_type        : <0x2d>   


    <2d>: Abbrev Number: 2 (DW_TAG_typedef)
    <2e>   DW_AT_name        : Bar      
    <32>   DW_AT_decl_file   : 1        
    <33>   DW_AT_decl_line   : 1        
    <34>   DW_AT_type        : <0x3d>   

    <3d>: Abbrev Number: 4 (DW_TAG_base_type)
    <3e>   DW_AT_byte_size   : 1        
    <3f>   DW_AT_encoding    : 8        (unsigned char)

The debug info for foo2's parameter is also correctly represented as a pointer
to a const variant of the same typedef:

 <2><78>: Abbrev Number: 7 (DW_TAG_formal_parameter)
    <79>   DW_AT_name        : f        
    <7b>   DW_AT_decl_file   : 1        
    <7c>   DW_AT_decl_line   : 3        
    <7d>   DW_AT_type        : <0x85>   
    <81>   DW_AT_location    : 2 byte block: 91 68      (DW_OP_fbreg: -24)
 <2><84>: Abbrev Number: 0
 <1><85>: Abbrev Number: 8 (DW_TAG_pointer_type)
    <86>   DW_AT_byte_size   : 8        
    <87>   DW_AT_type        : <0x38>   

    <38>: Abbrev Number: 3 (DW_TAG_const_type)
    <39>   DW_AT_type        : <0x2d>   

Compiling this similar program--changing the typedef from unsigned char to an
array of unsigned char--gives me incorrect debug info.

typedef unsigned char Bar[12];
void foo(Bar* f){}        // this works
void foo2(const Bar* f){} // this confuses cgo
void x() {
  foo(0);
  foo2(0);
}

The debug info for foo's parameter is correct:

 <2><ba>: Abbrev Number: 8 (DW_TAG_formal_parameter)
    <bb>   DW_AT_name        : f        
    <bd>   DW_AT_decl_file   : 1        
    <be>   DW_AT_decl_line   : 2        
    <bf>   DW_AT_type        : <0xc7>   
    <c3>   DW_AT_location    : 2 byte block: 91 68      (DW_OP_fbreg: -24)
 <2><c6>: Abbrev Number: 0
 <1><c7>: Abbrev Number: 9 (DW_TAG_pointer_type)
    <c8>   DW_AT_byte_size   : 8        
    <c9>   DW_AT_type        : <0x2d>   

    <2d>: Abbrev Number: 2 (DW_TAG_typedef)
    <2e>   DW_AT_name        : Bar      
    <32>   DW_AT_decl_file   : 1        
    <33>   DW_AT_decl_line   : 1        
    <34>   DW_AT_type        : <0x38>   

    <38>: Abbrev Number: 3 (DW_TAG_array_type)
    <39>   DW_AT_type        : <0x4f>   
    <3d>   DW_AT_sibling     : <0x48>   

    <4f>: Abbrev Number: 5 (DW_TAG_base_type)
    <50>   DW_AT_byte_size   : 1        
    <51>   DW_AT_encoding    : 8        (unsigned char)
    <52>   DW_AT_name        : (indirect string, offset: 0x86): unsigned char  

But the debug info for foo2's parameter is incorrect:

 <2><8a>: Abbrev Number: 8 (DW_TAG_formal_parameter)
    <8b>   DW_AT_name        : f        
    <8d>   DW_AT_decl_file   : 1        
    <8e>   DW_AT_decl_line   : 3        
    <8f>   DW_AT_type        : <0x97>   
    <93>   DW_AT_location    : 2 byte block: 91 68      (DW_OP_fbreg: -24)
 <2><96>: Abbrev Number: 0
 <1><97>: Abbrev Number: 9 (DW_TAG_pointer_type)
    <98>   DW_AT_byte_size   : 8        
    <99>   DW_AT_type        : <0x38>   

As you can see, the debug info for foo2's parameter says that it is a pointer
to an array of unsigned char.  The const qualifier has been lost.  The fact
that it is a pointer to a typedef has been lost.  What we should see here is
something like we saw for the first program: the pointer type should refer to a
DW_TAG_const_type that refers to the DW_TAG_typedef.

Reply via email to