如何在DWARF转储中读取非完整类型?
例如,我们有一个派生类:
class Base
{
public:
int Base_var1;
int Base_var2;
....
}
class OtherClass : public Base
{
int OtherClass_var1;
int OtherClass_var2;
....
}
OtherClass otherClass();
我们使用GCC编译器编译它,并希望找到otherClass
对象的所有成员。我们得到下一个DWARF转储:
<1><20a>: Abbrev Number: 15 (DW_TAG_variable)
<20b> DW_AT_name : otherClass
<211> DW_AT_type : <0x131>
<1><131>: Abbrev Number: 117 (DW_TAG_class_type)
<132> DW_AT_name : OtherClass
<133> DW_AT_declaration : 1
<134> DW_AT_sibling : <0x150>
<2><135>: Abbrev Number: 45 (DW_TAG_member)
<136> DW_AT_name : OtherClass_var1
<137> DW_AT_type : <0x12>
<138> DW_AT_data_member_location: 2 byte block: 23 8 (DW_OP_plus_uconst: 8)
......
我们有一个变量otherClass
,其类型为0x131
。此类型具有DW_AT_declaration
标志,这意味着这是非完整类型。 0x131
处的类型包含其所有成员(OtherClass_var1
和OtherClass_var2
),但不包含有关派生成员的任何信息。
如果继续阅读DWARF转储,那么在某些地方我们得到这个:
<1><500>: Abbrev Number: 150 (DW_TAG_class_type)
<501> DW_AT_specification: <0x131>
<502> DW_AT_byte_size : 2696
<503> DW_AT_containing_type: <0x560>
<504> DW_AT_sibling : <0x36078>
<2><135>: Abbrev Number: 45 (DW_TAG_member)
<136> DW_AT_name : Base_var1
<137> DW_AT_type : <0x12>
<138> DW_AT_data_member_location: 2 byte block: 23 8
.....
我们的基类有一个定义,这个定义有DW_AT_specification
标签,它显示了在哪里找到这个类的另一部分(主要部分)。
我们如何正确阅读此otherClass
对象?此时我必须存储所有类型的数组,当我得到DW_AT_declaration
标记时,我应该通过数组并找到一个具有此类型规范的类型。
如何获得派生成员的绝对地址?我们有一个变量otherClass
的绝对地址。然后,成员OtherClass_var1
将具有与otherClass
相同的地址。成员OtherClass_var2
的地址为OtherClass_var1
加上字节大小为OtherClass_var1
。但是,我们如何计算派生成员的地址Base_var1
和Base_var2
?