Image.cpp 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387
  1. /*
  2. * Copyright (c) 2018-2021, Andreas Kling <kling@serenityos.org>
  3. *
  4. * SPDX-License-Identifier: BSD-2-Clause
  5. */
  6. #include <AK/Debug.h>
  7. #include <AK/Demangle.h>
  8. #include <AK/Memory.h>
  9. #include <AK/QuickSort.h>
  10. #include <AK/StringBuilder.h>
  11. #include <AK/StringView.h>
  12. #include <LibELF/Image.h>
  13. #include <LibELF/Validation.h>
  14. namespace ELF {
  15. Image::Image(ReadonlyBytes bytes, bool verbose_logging)
  16. : m_buffer(bytes.data())
  17. , m_size(bytes.size())
  18. , m_verbose_logging(verbose_logging)
  19. {
  20. parse();
  21. }
  22. Image::Image(const u8* buffer, size_t size, bool verbose_logging)
  23. : Image(ReadonlyBytes { buffer, size }, verbose_logging)
  24. {
  25. }
  26. Image::~Image()
  27. {
  28. }
  29. #if ELF_IMAGE_DEBUG
  30. static const char* object_file_type_to_string(Elf32_Half type)
  31. {
  32. switch (type) {
  33. case ET_NONE:
  34. return "None";
  35. case ET_REL:
  36. return "Relocatable";
  37. case ET_EXEC:
  38. return "Executable";
  39. case ET_DYN:
  40. return "Shared object";
  41. case ET_CORE:
  42. return "Core";
  43. default:
  44. return "(?)";
  45. }
  46. }
  47. #endif
  48. StringView Image::section_index_to_string(unsigned index) const
  49. {
  50. VERIFY(m_valid);
  51. if (index == SHN_UNDEF)
  52. return "Undefined"sv;
  53. if (index >= SHN_LORESERVE)
  54. return "Reserved"sv;
  55. return section(index).name();
  56. }
  57. unsigned Image::symbol_count() const
  58. {
  59. VERIFY(m_valid);
  60. if (!section_count())
  61. return 0;
  62. return section(m_symbol_table_section_index).entry_count();
  63. }
  64. void Image::dump() const
  65. {
  66. #if ELF_IMAGE_DEBUG
  67. dbgln("ELF::Image({:p}) {{", this);
  68. dbgln(" is_valid: {}", is_valid());
  69. if (!is_valid()) {
  70. dbgln("}}");
  71. return;
  72. }
  73. dbgln(" type: {}", object_file_type_to_string(header().e_type));
  74. dbgln(" machine: {}", header().e_machine);
  75. dbgln(" entry: {:x}", header().e_entry);
  76. dbgln(" shoff: {}", header().e_shoff);
  77. dbgln(" shnum: {}", header().e_shnum);
  78. dbgln(" phoff: {}", header().e_phoff);
  79. dbgln(" phnum: {}", header().e_phnum);
  80. dbgln(" shstrndx: {}", header().e_shstrndx);
  81. for_each_program_header([&](const ProgramHeader& program_header) {
  82. dbgln(" Program Header {}: {{", program_header.index());
  83. dbgln(" type: {:x}", program_header.type());
  84. dbgln(" offset: {:x}", program_header.offset());
  85. dbgln(" flags: {:x}", program_header.flags());
  86. dbgln(" }}");
  87. return IterationDecision::Continue;
  88. });
  89. for (unsigned i = 0; i < header().e_shnum; ++i) {
  90. const auto& section = this->section(i);
  91. dbgln(" Section {}: {{", i);
  92. dbgln(" name: {}", section.name());
  93. dbgln(" type: {:x}", section.type());
  94. dbgln(" offset: {:x}", section.offset());
  95. dbgln(" size: {}", section.size());
  96. dbgln(" ");
  97. dbgln(" }}");
  98. }
  99. dbgln("Symbol count: {} (table is {})", symbol_count(), m_symbol_table_section_index);
  100. for (unsigned i = 1; i < symbol_count(); ++i) {
  101. const auto& sym = symbol(i);
  102. dbgln("Symbol @{}:", i);
  103. dbgln(" Name: {}", sym.name());
  104. dbgln(" In section: {}", section_index_to_string(sym.section_index()));
  105. dbgln(" Value: {}", sym.value());
  106. dbgln(" Size: {}", sym.size());
  107. }
  108. dbgln("}}");
  109. #endif
  110. }
  111. unsigned Image::section_count() const
  112. {
  113. VERIFY(m_valid);
  114. return header().e_shnum;
  115. }
  116. unsigned Image::program_header_count() const
  117. {
  118. VERIFY(m_valid);
  119. return header().e_phnum;
  120. }
  121. bool Image::parse()
  122. {
  123. if (m_size < sizeof(Elf32_Ehdr) || !validate_elf_header(header(), m_size, m_verbose_logging)) {
  124. if (m_verbose_logging)
  125. dbgln("ELF::Image::parse(): ELF Header not valid");
  126. return m_valid = false;
  127. }
  128. if (!validate_program_headers(header(), m_size, m_buffer, m_size, nullptr, m_verbose_logging)) {
  129. if (m_verbose_logging)
  130. dbgln("ELF::Image::parse(): ELF Program Headers not valid");
  131. return m_valid = false;
  132. }
  133. m_valid = true;
  134. // First locate the string tables.
  135. for (unsigned i = 0; i < section_count(); ++i) {
  136. auto& sh = section_header(i);
  137. if (sh.sh_type == SHT_SYMTAB) {
  138. if (m_symbol_table_section_index && m_symbol_table_section_index != i)
  139. return m_valid = false;
  140. m_symbol_table_section_index = i;
  141. }
  142. if (sh.sh_type == SHT_STRTAB && i != header().e_shstrndx) {
  143. if (section_header_table_string(sh.sh_name) == ELF_STRTAB)
  144. m_string_table_section_index = i;
  145. }
  146. }
  147. return m_valid;
  148. }
  149. StringView Image::table_string(unsigned table_index, unsigned offset) const
  150. {
  151. VERIFY(m_valid);
  152. auto& sh = section_header(table_index);
  153. if (sh.sh_type != SHT_STRTAB)
  154. return nullptr;
  155. size_t computed_offset = sh.sh_offset + offset;
  156. if (computed_offset >= m_size) {
  157. if (m_verbose_logging)
  158. dbgln("SHENANIGANS! Image::table_string() computed offset outside image.");
  159. return {};
  160. }
  161. size_t max_length = min(m_size - computed_offset, (size_t)PAGE_SIZE);
  162. size_t length = strnlen(raw_data(sh.sh_offset + offset), max_length);
  163. return { raw_data(sh.sh_offset + offset), length };
  164. }
  165. StringView Image::section_header_table_string(unsigned offset) const
  166. {
  167. VERIFY(m_valid);
  168. return table_string(header().e_shstrndx, offset);
  169. }
  170. StringView Image::table_string(unsigned offset) const
  171. {
  172. VERIFY(m_valid);
  173. return table_string(m_string_table_section_index, offset);
  174. }
  175. const char* Image::raw_data(unsigned offset) const
  176. {
  177. VERIFY(offset < m_size); // Callers must check indices into raw_data()'s result are also in bounds.
  178. return reinterpret_cast<const char*>(m_buffer) + offset;
  179. }
  180. const Elf32_Ehdr& Image::header() const
  181. {
  182. VERIFY(m_size >= sizeof(Elf32_Ehdr));
  183. return *reinterpret_cast<const Elf32_Ehdr*>(raw_data(0));
  184. }
  185. const Elf32_Phdr& Image::program_header_internal(unsigned index) const
  186. {
  187. VERIFY(m_valid);
  188. VERIFY(index < header().e_phnum);
  189. return *reinterpret_cast<const Elf32_Phdr*>(raw_data(header().e_phoff + (index * sizeof(Elf32_Phdr))));
  190. }
  191. const Elf32_Shdr& Image::section_header(unsigned index) const
  192. {
  193. VERIFY(m_valid);
  194. VERIFY(index < header().e_shnum);
  195. return *reinterpret_cast<const Elf32_Shdr*>(raw_data(header().e_shoff + (index * header().e_shentsize)));
  196. }
  197. Image::Symbol Image::symbol(unsigned index) const
  198. {
  199. VERIFY(m_valid);
  200. VERIFY(index < symbol_count());
  201. auto* raw_syms = reinterpret_cast<const Elf32_Sym*>(raw_data(section(m_symbol_table_section_index).offset()));
  202. return Symbol(*this, index, raw_syms[index]);
  203. }
  204. Image::Section Image::section(unsigned index) const
  205. {
  206. VERIFY(m_valid);
  207. VERIFY(index < section_count());
  208. return Section(*this, index);
  209. }
  210. Image::ProgramHeader Image::program_header(unsigned index) const
  211. {
  212. VERIFY(m_valid);
  213. VERIFY(index < program_header_count());
  214. return ProgramHeader(*this, index);
  215. }
  216. Image::Relocation Image::RelocationSection::relocation(unsigned index) const
  217. {
  218. VERIFY(index < relocation_count());
  219. auto* rels = reinterpret_cast<const Elf32_Rel*>(m_image.raw_data(offset()));
  220. return Relocation(m_image, rels[index]);
  221. }
  222. Image::RelocationSection Image::Section::relocations() const
  223. {
  224. StringBuilder builder;
  225. builder.append(".rel"sv);
  226. builder.append(name());
  227. auto relocation_section = m_image.lookup_section(builder.to_string());
  228. if (relocation_section.type() != SHT_REL)
  229. return static_cast<const RelocationSection>(m_image.section(0));
  230. dbgln_if(ELF_IMAGE_DEBUG, "Found relocations for {} in {}", name(), relocation_section.name());
  231. return static_cast<const RelocationSection>(relocation_section);
  232. }
  233. Image::Section Image::lookup_section(const String& name) const
  234. {
  235. VERIFY(m_valid);
  236. for (unsigned i = 0; i < section_count(); ++i) {
  237. auto section = this->section(i);
  238. if (section.name() == name)
  239. return section;
  240. }
  241. return section(0);
  242. }
  243. StringView Image::Symbol::raw_data() const
  244. {
  245. auto section = this->section();
  246. return { section.raw_data() + (value() - section.address()), size() };
  247. }
  248. Optional<Image::Symbol> Image::find_demangled_function(const String& name) const
  249. {
  250. Optional<Image::Symbol> found;
  251. for_each_symbol([&](const Image::Symbol& symbol) {
  252. if (symbol.type() != STT_FUNC)
  253. return IterationDecision::Continue;
  254. if (symbol.is_undefined())
  255. return IterationDecision::Continue;
  256. auto demangled = demangle(symbol.name());
  257. auto index_of_paren = demangled.index_of("(");
  258. if (index_of_paren.has_value()) {
  259. demangled = demangled.substring(0, index_of_paren.value());
  260. }
  261. if (demangled != name)
  262. return IterationDecision::Continue;
  263. found = symbol;
  264. return IterationDecision::Break;
  265. });
  266. return found;
  267. }
  268. Optional<Image::Symbol> Image::find_symbol(u32 address, u32* out_offset) const
  269. {
  270. auto symbol_count = this->symbol_count();
  271. if (!symbol_count)
  272. return {};
  273. SortedSymbol* sorted_symbols = nullptr;
  274. if (m_sorted_symbols.is_empty()) {
  275. m_sorted_symbols.ensure_capacity(symbol_count);
  276. for_each_symbol([this](const auto& symbol) {
  277. m_sorted_symbols.append({ symbol.value(), symbol.name(), {}, symbol });
  278. return IterationDecision::Continue;
  279. });
  280. quick_sort(m_sorted_symbols, [](auto& a, auto& b) {
  281. return a.address < b.address;
  282. });
  283. }
  284. sorted_symbols = m_sorted_symbols.data();
  285. for (size_t i = 0; i < symbol_count; ++i) {
  286. if (sorted_symbols[i].address > address) {
  287. if (i == 0)
  288. return {};
  289. auto& symbol = sorted_symbols[i - 1];
  290. if (out_offset)
  291. *out_offset = address - symbol.address;
  292. return symbol.symbol;
  293. }
  294. }
  295. return {};
  296. }
  297. String Image::symbolicate(u32 address, u32* out_offset) const
  298. {
  299. auto symbol_count = this->symbol_count();
  300. if (!symbol_count) {
  301. if (out_offset)
  302. *out_offset = 0;
  303. return "??";
  304. }
  305. SortedSymbol* sorted_symbols = nullptr;
  306. if (m_sorted_symbols.is_empty()) {
  307. m_sorted_symbols.ensure_capacity(symbol_count);
  308. for_each_symbol([this](const auto& symbol) {
  309. m_sorted_symbols.append({ symbol.value(), symbol.name(), {}, symbol });
  310. return IterationDecision::Continue;
  311. });
  312. quick_sort(m_sorted_symbols, [](auto& a, auto& b) {
  313. return a.address < b.address;
  314. });
  315. }
  316. sorted_symbols = m_sorted_symbols.data();
  317. for (size_t i = 0; i < symbol_count; ++i) {
  318. if (sorted_symbols[i].address > address) {
  319. if (i == 0) {
  320. if (out_offset)
  321. *out_offset = 0;
  322. return "!!";
  323. }
  324. auto& symbol = sorted_symbols[i - 1];
  325. auto& demangled_name = symbol.demangled_name;
  326. if (demangled_name.is_null()) {
  327. demangled_name = demangle(symbol.name);
  328. }
  329. if (out_offset) {
  330. *out_offset = address - symbol.address;
  331. return demangled_name;
  332. }
  333. return String::formatted("{} +{:#x}", demangled_name, address - symbol.address);
  334. }
  335. }
  336. if (out_offset)
  337. *out_offset = 0;
  338. return "??";
  339. }
  340. } // end namespace ELF