This post is about the llvm/DebugInfo/DWARF library. I want to write a tool to get the type information of a specific C variable in an elf. For example:
// test.c
int myVariable = 3;
int main() { return myVariable; }
some_compiler -g test.c -o test.out
mytool test.out myVariable
# should print that myVariable has type int, the size of int, etc
I read the llvm-dwarfdump source code and made this tool that worked on gcc DWARF32 version 5 elf, but it failed to work on elf produced by the armcl compiler embedded in TI’s CCS IDE. The debug info has format DWARF32 version 3. Here is the elf produced by armcl with the above test.c: test.out
The code of my tool:
// die must have attribute DW_AT_type, return that type's DWARFDie
llvm::DWARFDie GetDW_AT_type(llvm::DWARFDie die);
void FindVariableType() {
lvm::DWARFDie variable = FindVariableByName("myVariable");
// variable.dump(); // OK, variable.dump() does print the DW_TAG_variable's info
auto typeDie = GetDW_AT_type(variable);
assert(typeDie.isValid()); // fail
}
llvm::DWARFDie GetDW_AT_type(llvm::DWARFDie die) {
// from llvm::DWARFFormValue::dump
auto offset = die.find(llvm::dwarf::DW_AT_type)->getRawValue(); // 0x1e4 for this case
auto unit = die.getDwarfUnit();
auto unitOffset = unit->getOffset(); // 0 for this case
return unit->getDIEForOffset(offset + unitOffset);
}
If variable.dump() is uncommented, the following lines are printed:
0x00000099: DW_TAG_variable
DW_AT_location (DW_OP_addr 0x208)
DW_AT_name ("myVariable")
DW_AT_decl_column (0x05)
DW_AT_decl_file ("some_path/test.c")
DW_AT_decl_line (2)
DW_AT_external (0x01)
DW_AT_type (0x00000000000001e4 "int")
DW_AT_MIPS_fde ("myVariable")
and here is the section of int that llvm-dwarfdump prints for the same elf:
0x000001e4: DW_TAG_base_type
DW_AT_name ("int")
DW_AT_byte_size (0x04)
DW_AT_encoding (DW_ATE_signed)
The problem is llvm::DWARFUnit::getDIEForOffset() returns an invalid DWARFDie although that DIE should exist. Is my GetDW_AT_type
implementation correct or is it a llvm library bug? The llvm libraries I’m using has version 17.0.6.