DWARFDebugMacroHeader DWARFDebugMacroHeader::ParseHeader(const DWARFDataExtractor &debug_macro_data, lldb::offset_t *offset) { DWARFDebugMacroHeader header; // Skip over the version field in header. header.m_version = debug_macro_data.GetU16(offset); uint8_t flags = debug_macro_data.GetU8(offset); header.m_offset_is_64_bit = flags & OFFSET_SIZE_MASK ? true : false; if (flags & DEBUG_LINE_OFFSET_MASK) { if (header.m_offset_is_64_bit) header.m_debug_line_offset = debug_macro_data.GetU64(offset); else header.m_debug_line_offset = debug_macro_data.GetU32(offset); } // Skip over the operands table if it is present. if (flags & OPCODE_OPERANDS_TABLE_MASK) SkipOperandTable(debug_macro_data, offset); return header; }
bool DWARFFormValue::ExtractValue(const DWARFDataExtractor& data, lldb::offset_t* offset_ptr, const DWARFCompileUnit* cu) { bool indirect = false; bool is_block = false; m_value.data = NULL; uint8_t ref_addr_size; // Read the value for the form into value and follow and DW_FORM_indirect instances we run into do { indirect = false; switch (m_form) { case DW_FORM_addr: m_value.value.uval = data.GetMaxU64(offset_ptr, DWARFCompileUnit::GetAddressByteSize(cu)); break; case DW_FORM_block2: m_value.value.uval = data.GetU16(offset_ptr); is_block = true; break; case DW_FORM_block4: m_value.value.uval = data.GetU32(offset_ptr); is_block = true; break; case DW_FORM_data2: m_value.value.uval = data.GetU16(offset_ptr); break; case DW_FORM_data4: m_value.value.uval = data.GetU32(offset_ptr); break; case DW_FORM_data8: m_value.value.uval = data.GetU64(offset_ptr); break; case DW_FORM_string: m_value.value.cstr = data.GetCStr(offset_ptr); // Set the string value to also be the data for inlined cstr form values only // so we can tell the difference between DW_FORM_string and DW_FORM_strp form // values; m_value.data = (uint8_t*)m_value.value.cstr; break; case DW_FORM_exprloc: case DW_FORM_block: m_value.value.uval = data.GetULEB128(offset_ptr); is_block = true; break; case DW_FORM_block1: m_value.value.uval = data.GetU8(offset_ptr); is_block = true; break; case DW_FORM_data1: m_value.value.uval = data.GetU8(offset_ptr); break; case DW_FORM_flag: m_value.value.uval = data.GetU8(offset_ptr); break; case DW_FORM_sdata: m_value.value.sval = data.GetSLEB128(offset_ptr); break; case DW_FORM_strp: m_value.value.uval = data.GetMaxU64(offset_ptr, DWARFCompileUnit::IsDWARF64(cu) ? 8 : 4); break; // case DW_FORM_APPLE_db_str: case DW_FORM_udata: m_value.value.uval = data.GetULEB128(offset_ptr); break; case DW_FORM_ref_addr: ref_addr_size = 4; if (cu) { if (cu->GetVersion() <= 2) ref_addr_size = cu->GetAddressByteSize(); else ref_addr_size = cu->IsDWARF64() ? 8 : 4; } m_value.value.uval = data.GetMaxU64(offset_ptr, ref_addr_size); break; case DW_FORM_ref1: m_value.value.uval = data.GetU8(offset_ptr); break; case DW_FORM_ref2: m_value.value.uval = data.GetU16(offset_ptr); break; case DW_FORM_ref4: m_value.value.uval = data.GetU32(offset_ptr); break; case DW_FORM_ref8: m_value.value.uval = data.GetU64(offset_ptr); break; case DW_FORM_ref_udata: m_value.value.uval = data.GetULEB128(offset_ptr); break; case DW_FORM_indirect: m_form = data.GetULEB128(offset_ptr); indirect = true; break; case DW_FORM_sec_offset: m_value.value.uval = data.GetMaxU64(offset_ptr, DWARFCompileUnit::IsDWARF64(cu) ? 8 : 4); break; case DW_FORM_flag_present: m_value.value.uval = 1; break; case DW_FORM_ref_sig8: m_value.value.uval = data.GetU64(offset_ptr); break; default: return false; break; } } while (indirect); if (is_block) { m_value.data = data.PeekData(*offset_ptr, m_value.value.uval); if (m_value.data != NULL) { *offset_ptr += m_value.value.uval; } } return true; }
void DWARFDebugMacroEntry::ReadMacroEntries( const DWARFDataExtractor &debug_macro_data, const DWARFDataExtractor &debug_str_data, const bool offset_is_64_bit, lldb::offset_t *offset, SymbolFileDWARF *sym_file_dwarf, DebugMacrosSP &debug_macros_sp) { #if TODO_REQUIRES_LLVM_ORG_SYNC // This code can go back in once llvm.org macros support is in the relevant // GitHub llvm branch. llvm::dwarf::MacroEntryType type = static_cast<llvm::dwarf::MacroEntryType>(debug_macro_data.GetU8(offset)); while (type != 0) { lldb::offset_t new_offset = 0, str_offset = 0; uint32_t line = 0; const char *macro_str = nullptr; uint32_t debug_line_file_idx = 0; switch (type) { case DW_MACRO_define: case DW_MACRO_undef: line = debug_macro_data.GetULEB128(offset); macro_str = debug_macro_data.GetCStr(offset); if (type == DW_MACRO_define) debug_macros_sp->AddMacroEntry( DebugMacroEntry::CreateDefineEntry(line, macro_str)); else debug_macros_sp->AddMacroEntry( DebugMacroEntry::CreateUndefEntry(line, macro_str)); break; case DW_MACRO_define_indirect: case DW_MACRO_undef_indirect: line = debug_macro_data.GetULEB128(offset); if (offset_is_64_bit) str_offset = debug_macro_data.GetU64(offset); else str_offset = debug_macro_data.GetU32(offset); macro_str = debug_str_data.GetCStr(&str_offset); if (type == DW_MACRO_define_indirect) debug_macros_sp->AddMacroEntry( DebugMacroEntry::CreateDefineEntry(line, macro_str)); else debug_macros_sp->AddMacroEntry( DebugMacroEntry::CreateUndefEntry(line, macro_str)); break; case DW_MACRO_start_file: line = debug_macro_data.GetULEB128(offset); debug_line_file_idx = debug_macro_data.GetULEB128(offset); debug_macros_sp->AddMacroEntry( DebugMacroEntry::CreateStartFileEntry(line, debug_line_file_idx)); break; case DW_MACRO_end_file: // This operation has no operands. debug_macros_sp->AddMacroEntry(DebugMacroEntry::CreateEndFileEntry()); break; case DW_MACRO_transparent_include: if (offset_is_64_bit) new_offset = debug_macro_data.GetU64(offset); else new_offset = debug_macro_data.GetU32(offset); debug_macros_sp->AddMacroEntry(DebugMacroEntry::CreateIndirectEntry( sym_file_dwarf->ParseDebugMacros(&new_offset))); break; default: // TODO: Add support for other standard operations. // TODO: Provide mechanism to hook handling of non-standard/extension // operands. return; } type = static_cast<llvm::dwarf::MacroEntryType>( debug_macro_data.GetU8(offset)); } #endif }
bool DWARFFormValue::ExtractValue(const DWARFDataExtractor &data, lldb::offset_t *offset_ptr) { bool indirect = false; bool is_block = false; m_value.data = NULL; uint8_t ref_addr_size; // Read the value for the form into value and follow and DW_FORM_indirect // instances we run into do { indirect = false; switch (m_form) { case DW_FORM_addr: assert(m_cu); m_value.value.uval = data.GetMaxU64( offset_ptr, DWARFCompileUnit::GetAddressByteSize(m_cu)); break; case DW_FORM_block2: m_value.value.uval = data.GetU16(offset_ptr); is_block = true; break; case DW_FORM_block4: m_value.value.uval = data.GetU32(offset_ptr); is_block = true; break; case DW_FORM_data2: m_value.value.uval = data.GetU16(offset_ptr); break; case DW_FORM_data4: m_value.value.uval = data.GetU32(offset_ptr); break; case DW_FORM_data8: m_value.value.uval = data.GetU64(offset_ptr); break; case DW_FORM_string: m_value.value.cstr = data.GetCStr(offset_ptr); break; case DW_FORM_exprloc: case DW_FORM_block: m_value.value.uval = data.GetULEB128(offset_ptr); is_block = true; break; case DW_FORM_block1: m_value.value.uval = data.GetU8(offset_ptr); is_block = true; break; case DW_FORM_data1: m_value.value.uval = data.GetU8(offset_ptr); break; case DW_FORM_flag: m_value.value.uval = data.GetU8(offset_ptr); break; case DW_FORM_sdata: m_value.value.sval = data.GetSLEB128(offset_ptr); break; case DW_FORM_strp: assert(m_cu); m_value.value.uval = data.GetMaxU64(offset_ptr, DWARFCompileUnit::IsDWARF64(m_cu) ? 8 : 4); break; // case DW_FORM_APPLE_db_str: case DW_FORM_udata: m_value.value.uval = data.GetULEB128(offset_ptr); break; case DW_FORM_ref_addr: assert(m_cu); ref_addr_size = 4; if (m_cu->GetVersion() <= 2) ref_addr_size = m_cu->GetAddressByteSize(); else ref_addr_size = m_cu->IsDWARF64() ? 8 : 4; m_value.value.uval = data.GetMaxU64(offset_ptr, ref_addr_size); break; case DW_FORM_ref1: m_value.value.uval = data.GetU8(offset_ptr); break; case DW_FORM_ref2: m_value.value.uval = data.GetU16(offset_ptr); break; case DW_FORM_ref4: m_value.value.uval = data.GetU32(offset_ptr); break; case DW_FORM_ref8: m_value.value.uval = data.GetU64(offset_ptr); break; case DW_FORM_ref_udata: m_value.value.uval = data.GetULEB128(offset_ptr); break; case DW_FORM_indirect: m_form = data.GetULEB128(offset_ptr); indirect = true; break; case DW_FORM_sec_offset: assert(m_cu); m_value.value.uval = data.GetMaxU64(offset_ptr, DWARFCompileUnit::IsDWARF64(m_cu) ? 8 : 4); break; case DW_FORM_flag_present: m_value.value.uval = 1; break; case DW_FORM_ref_sig8: m_value.value.uval = data.GetU64(offset_ptr); break; case DW_FORM_GNU_str_index: m_value.value.uval = data.GetULEB128(offset_ptr); break; case DW_FORM_GNU_addr_index: m_value.value.uval = data.GetULEB128(offset_ptr); break; default: return false; break; } } while (indirect); if (is_block) { m_value.data = data.PeekData(*offset_ptr, m_value.value.uval); if (m_value.data != NULL) { *offset_ptr += m_value.value.uval; } } return true; }