Em Thu, Jan 17, 2019 at 01:01:58PM -0300, Arnaldo Carvalho de Melo escreveu: > Investigating this one now: > > struct desc_ptr { > short unsigned int size; /* 0 2 */ > - long unsigned int address; /* 2 8 */ > + long unsigned int address; /* 0 8 */ > > /* size: 10, cachelines: 1, members: 2 */ > + /* padding: 2 */ > /* last cacheline: 10 bytes */ > + > + /* BRAIN FART ALERT! 10 != 2 + 0(holes), diff = 8 */ > }; > > > The original struct is this, at arch/x86/include/asm/desc_defs.h: > > struct desc_ptr { > unsigned short size; > unsigned long address; > } __attribute__((packed)) ; > > So both DWARF and BTF have the size right, 10 bytes, but BTF gets the > 'address' member offset wrong, from readelf: > > <1><28ed>: Abbrev Number: 17 (DW_TAG_structure_type) > <28ee> DW_AT_name : (indirect string, offset: 0x112bf): desc_ptr > <28f2> DW_AT_byte_size : 10 > <28f3> DW_AT_decl_file : 101 > <28f4> DW_AT_decl_line : 105 > <28f5> DW_AT_decl_column : 8 > <28f6> DW_AT_sibling : <0x2915> > <2><28fa>: Abbrev Number: 1 (DW_TAG_member) > <28fb> DW_AT_name : (indirect string, offset: 0x8b12): size > <28ff> DW_AT_decl_file : 101 > <2900> DW_AT_decl_line : 106 > <2901> DW_AT_decl_column : 17 > <2902> DW_AT_type : <0xd0> > <2906> DW_AT_data_member_location: 0 > <2><2907>: Abbrev Number: 1 (DW_TAG_member) > <2908> DW_AT_name : (indirect string, offset: 0xfa9): address > <290c> DW_AT_decl_file : 101 > <290d> DW_AT_decl_line : 107 > <290e> DW_AT_decl_column : 16 > <290f> DW_AT_type : <0x2a> > <2913> DW_AT_data_member_location: 2 > > If I isolate this in a file and then do the BTF encoding: > > [acme@quaco pahole]$ cat examples/desc_ptr.c > struct desc_ptr { > unsigned short size; > unsigned long address; > } __attribute__((packed)) ; > > struct desc_ptr foo; > [acme@quaco pahole]$ gcc -c -g examples/desc_ptr.c -o examples/desc_ptr.o > [acme@quaco pahole]$ pahole -JV examples/desc_ptr.o > File examples/desc_ptr.o: > [1] STRUCT desc_ptr kind_flag=0 size=10 vlen=2 > size type_id=2 bits_offset=0 > address type_id=3 bits_offset=16 > [2] INT short unsigned int size=2 bit_offset=0 nr_bits=16 encoding=(none) > [3] INT long unsigned int size=8 bit_offset=0 nr_bits=64 encoding=(none) > [4] INT (anon) size=4 bit_offset=0 nr_bits=32 encoding=(none) > [acme@quaco pahole]$ > > Now going thru the code to see why [3] get that bit_offset=0, should be > 16, no? That was just a distraction, the BTF encoding is done right, the problem is when loading the BTF section, in class__fixup_btf_bitfields(), first we set it right: pos->byte_offset = pos->bit_offset / 8; But then, later, this is recalculated as: pos->byte_offset = (((pos->bit_offset / integral_bit_size) * integral_bit_size) / 8); Now trying to recall why this last recalc... - Arnaldo