LLVM 17.0.0git
ELF.cpp
Go to the documentation of this file.
1//===- ELF.cpp - ELF object file implementation ---------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "llvm/Object/ELF.h"
12
13using namespace llvm;
14using namespace object;
15
16#define STRINGIFY_ENUM_CASE(ns, name) \
17 case ns::name: \
18 return #name;
19
20#define ELF_RELOC(name, value) STRINGIFY_ENUM_CASE(ELF, name)
21
23 uint32_t Type) {
24 switch (Machine) {
25 case ELF::EM_68K:
26 switch (Type) {
27#include "llvm/BinaryFormat/ELFRelocs/M68k.def"
28 default:
29 break;
30 }
31 break;
32 case ELF::EM_X86_64:
33 switch (Type) {
34#include "llvm/BinaryFormat/ELFRelocs/x86_64.def"
35 default:
36 break;
37 }
38 break;
39 case ELF::EM_386:
40 case ELF::EM_IAMCU:
41 switch (Type) {
42#include "llvm/BinaryFormat/ELFRelocs/i386.def"
43 default:
44 break;
45 }
46 break;
47 case ELF::EM_MIPS:
48 switch (Type) {
49#include "llvm/BinaryFormat/ELFRelocs/Mips.def"
50 default:
51 break;
52 }
53 break;
54 case ELF::EM_AARCH64:
55 switch (Type) {
56#include "llvm/BinaryFormat/ELFRelocs/AArch64.def"
57 default:
58 break;
59 }
60 break;
61 case ELF::EM_ARM:
62 switch (Type) {
63#include "llvm/BinaryFormat/ELFRelocs/ARM.def"
64 default:
65 break;
66 }
67 break;
70 switch (Type) {
71#include "llvm/BinaryFormat/ELFRelocs/ARC.def"
72 default:
73 break;
74 }
75 break;
76 case ELF::EM_AVR:
77 switch (Type) {
78#include "llvm/BinaryFormat/ELFRelocs/AVR.def"
79 default:
80 break;
81 }
82 break;
83 case ELF::EM_HEXAGON:
84 switch (Type) {
85#include "llvm/BinaryFormat/ELFRelocs/Hexagon.def"
86 default:
87 break;
88 }
89 break;
90 case ELF::EM_LANAI:
91 switch (Type) {
92#include "llvm/BinaryFormat/ELFRelocs/Lanai.def"
93 default:
94 break;
95 }
96 break;
97 case ELF::EM_PPC:
98 switch (Type) {
99#include "llvm/BinaryFormat/ELFRelocs/PowerPC.def"
100 default:
101 break;
102 }
103 break;
104 case ELF::EM_PPC64:
105 switch (Type) {
106#include "llvm/BinaryFormat/ELFRelocs/PowerPC64.def"
107 default:
108 break;
109 }
110 break;
111 case ELF::EM_RISCV:
112 switch (Type) {
113#include "llvm/BinaryFormat/ELFRelocs/RISCV.def"
114 default:
115 break;
116 }
117 break;
118 case ELF::EM_S390:
119 switch (Type) {
120#include "llvm/BinaryFormat/ELFRelocs/SystemZ.def"
121 default:
122 break;
123 }
124 break;
125 case ELF::EM_SPARC:
127 case ELF::EM_SPARCV9:
128 switch (Type) {
129#include "llvm/BinaryFormat/ELFRelocs/Sparc.def"
130 default:
131 break;
132 }
133 break;
134 case ELF::EM_AMDGPU:
135 switch (Type) {
136#include "llvm/BinaryFormat/ELFRelocs/AMDGPU.def"
137 default:
138 break;
139 }
140 break;
141 case ELF::EM_BPF:
142 switch (Type) {
143#include "llvm/BinaryFormat/ELFRelocs/BPF.def"
144 default:
145 break;
146 }
147 break;
148 case ELF::EM_MSP430:
149 switch (Type) {
150#include "llvm/BinaryFormat/ELFRelocs/MSP430.def"
151 default:
152 break;
153 }
154 break;
155 case ELF::EM_VE:
156 switch (Type) {
157#include "llvm/BinaryFormat/ELFRelocs/VE.def"
158 default:
159 break;
160 }
161 break;
162 case ELF::EM_CSKY:
163 switch (Type) {
164#include "llvm/BinaryFormat/ELFRelocs/CSKY.def"
165 default:
166 break;
167 }
168 break;
170 switch (Type) {
171#include "llvm/BinaryFormat/ELFRelocs/LoongArch.def"
172 default:
173 break;
174 }
175 break;
176 case ELF::EM_XTENSA:
177 switch (Type) {
178#include "llvm/BinaryFormat/ELFRelocs/Xtensa.def"
179 default:
180 break;
181 }
182 break;
183 default:
184 break;
185 }
186 return "Unknown";
187}
188
189#undef ELF_RELOC
190
192 switch (Machine) {
193 case ELF::EM_X86_64:
194 return ELF::R_X86_64_RELATIVE;
195 case ELF::EM_386:
196 case ELF::EM_IAMCU:
197 return ELF::R_386_RELATIVE;
198 case ELF::EM_MIPS:
199 break;
200 case ELF::EM_AARCH64:
201 return ELF::R_AARCH64_RELATIVE;
202 case ELF::EM_ARM:
203 return ELF::R_ARM_RELATIVE;
206 return ELF::R_ARC_RELATIVE;
207 case ELF::EM_AVR:
208 break;
209 case ELF::EM_HEXAGON:
210 return ELF::R_HEX_RELATIVE;
211 case ELF::EM_LANAI:
212 break;
213 case ELF::EM_PPC:
214 break;
215 case ELF::EM_PPC64:
216 return ELF::R_PPC64_RELATIVE;
217 case ELF::EM_RISCV:
218 return ELF::R_RISCV_RELATIVE;
219 case ELF::EM_S390:
220 return ELF::R_390_RELATIVE;
221 case ELF::EM_SPARC:
223 case ELF::EM_SPARCV9:
224 return ELF::R_SPARC_RELATIVE;
225 case ELF::EM_CSKY:
226 return ELF::R_CKCORE_RELATIVE;
227 case ELF::EM_VE:
228 return ELF::R_VE_RELATIVE;
229 case ELF::EM_AMDGPU:
230 break;
231 case ELF::EM_BPF:
232 break;
234 return ELF::R_LARCH_RELATIVE;
235 default:
236 break;
237 }
238 return 0;
239}
240
242 switch (Machine) {
243 case ELF::EM_ARM:
244 switch (Type) {
245 STRINGIFY_ENUM_CASE(ELF, SHT_ARM_EXIDX);
246 STRINGIFY_ENUM_CASE(ELF, SHT_ARM_PREEMPTMAP);
247 STRINGIFY_ENUM_CASE(ELF, SHT_ARM_ATTRIBUTES);
248 STRINGIFY_ENUM_CASE(ELF, SHT_ARM_DEBUGOVERLAY);
249 STRINGIFY_ENUM_CASE(ELF, SHT_ARM_OVERLAYSECTION);
250 }
251 break;
252 case ELF::EM_HEXAGON:
253 switch (Type) { STRINGIFY_ENUM_CASE(ELF, SHT_HEX_ORDERED); }
254 break;
255 case ELF::EM_X86_64:
256 switch (Type) { STRINGIFY_ENUM_CASE(ELF, SHT_X86_64_UNWIND); }
257 break;
258 case ELF::EM_MIPS:
260 switch (Type) {
261 STRINGIFY_ENUM_CASE(ELF, SHT_MIPS_REGINFO);
262 STRINGIFY_ENUM_CASE(ELF, SHT_MIPS_OPTIONS);
263 STRINGIFY_ENUM_CASE(ELF, SHT_MIPS_DWARF);
264 STRINGIFY_ENUM_CASE(ELF, SHT_MIPS_ABIFLAGS);
265 }
266 break;
267 case ELF::EM_MSP430:
268 switch (Type) { STRINGIFY_ENUM_CASE(ELF, SHT_MSP430_ATTRIBUTES); }
269 break;
270 case ELF::EM_RISCV:
271 switch (Type) { STRINGIFY_ENUM_CASE(ELF, SHT_RISCV_ATTRIBUTES); }
272 break;
273 case ELF::EM_AARCH64:
274 switch (Type) {
275 STRINGIFY_ENUM_CASE(ELF, SHT_AARCH64_MEMTAG_GLOBALS_DYNAMIC);
276 STRINGIFY_ENUM_CASE(ELF, SHT_AARCH64_MEMTAG_GLOBALS_STATIC);
277 }
278 default:
279 break;
280 }
281
282 switch (Type) {
283 STRINGIFY_ENUM_CASE(ELF, SHT_NULL);
284 STRINGIFY_ENUM_CASE(ELF, SHT_PROGBITS);
285 STRINGIFY_ENUM_CASE(ELF, SHT_SYMTAB);
286 STRINGIFY_ENUM_CASE(ELF, SHT_STRTAB);
287 STRINGIFY_ENUM_CASE(ELF, SHT_RELA);
288 STRINGIFY_ENUM_CASE(ELF, SHT_HASH);
289 STRINGIFY_ENUM_CASE(ELF, SHT_DYNAMIC);
290 STRINGIFY_ENUM_CASE(ELF, SHT_NOTE);
291 STRINGIFY_ENUM_CASE(ELF, SHT_NOBITS);
292 STRINGIFY_ENUM_CASE(ELF, SHT_REL);
293 STRINGIFY_ENUM_CASE(ELF, SHT_SHLIB);
294 STRINGIFY_ENUM_CASE(ELF, SHT_DYNSYM);
295 STRINGIFY_ENUM_CASE(ELF, SHT_INIT_ARRAY);
296 STRINGIFY_ENUM_CASE(ELF, SHT_FINI_ARRAY);
297 STRINGIFY_ENUM_CASE(ELF, SHT_PREINIT_ARRAY);
298 STRINGIFY_ENUM_CASE(ELF, SHT_GROUP);
299 STRINGIFY_ENUM_CASE(ELF, SHT_SYMTAB_SHNDX);
300 STRINGIFY_ENUM_CASE(ELF, SHT_RELR);
301 STRINGIFY_ENUM_CASE(ELF, SHT_ANDROID_REL);
302 STRINGIFY_ENUM_CASE(ELF, SHT_ANDROID_RELA);
303 STRINGIFY_ENUM_CASE(ELF, SHT_ANDROID_RELR);
304 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_ODRTAB);
305 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_LINKER_OPTIONS);
306 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_CALL_GRAPH_PROFILE);
307 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_ADDRSIG);
308 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_DEPENDENT_LIBRARIES);
309 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_SYMPART);
310 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_PART_EHDR);
311 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_PART_PHDR);
312 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_BB_ADDR_MAP_V0);
313 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_BB_ADDR_MAP);
314 STRINGIFY_ENUM_CASE(ELF, SHT_LLVM_OFFLOADING);
315 STRINGIFY_ENUM_CASE(ELF, SHT_GNU_ATTRIBUTES);
316 STRINGIFY_ENUM_CASE(ELF, SHT_GNU_HASH);
317 STRINGIFY_ENUM_CASE(ELF, SHT_GNU_verdef);
318 STRINGIFY_ENUM_CASE(ELF, SHT_GNU_verneed);
319 STRINGIFY_ENUM_CASE(ELF, SHT_GNU_versym);
320 default:
321 return "Unknown";
322 }
323}
324
325template <class ELFT>
326std::vector<typename ELFT::Rel>
327ELFFile<ELFT>::decode_relrs(Elf_Relr_Range relrs) const {
328 // This function decodes the contents of an SHT_RELR packed relocation
329 // section.
330 //
331 // Proposal for adding SHT_RELR sections to generic-abi is here:
332 // https://groups.google.com/forum/#!topic/generic-abi/bX460iggiKg
333 //
334 // The encoded sequence of Elf64_Relr entries in a SHT_RELR section looks
335 // like [ AAAAAAAA BBBBBBB1 BBBBBBB1 ... AAAAAAAA BBBBBB1 ... ]
336 //
337 // i.e. start with an address, followed by any number of bitmaps. The address
338 // entry encodes 1 relocation. The subsequent bitmap entries encode up to 63
339 // relocations each, at subsequent offsets following the last address entry.
340 //
341 // The bitmap entries must have 1 in the least significant bit. The assumption
342 // here is that an address cannot have 1 in lsb. Odd addresses are not
343 // supported.
344 //
345 // Excluding the least significant bit in the bitmap, each non-zero bit in
346 // the bitmap represents a relocation to be applied to a corresponding machine
347 // word that follows the base address word. The second least significant bit
348 // represents the machine word immediately following the initial address, and
349 // each bit that follows represents the next word, in linear order. As such,
350 // a single bitmap can encode up to 31 relocations in a 32-bit object, and
351 // 63 relocations in a 64-bit object.
352 //
353 // This encoding has a couple of interesting properties:
354 // 1. Looking at any entry, it is clear whether it's an address or a bitmap:
355 // even means address, odd means bitmap.
356 // 2. Just a simple list of addresses is a valid encoding.
357
358 Elf_Rel Rel;
359 Rel.r_info = 0;
360 Rel.setType(getRelativeRelocationType(), false);
361 std::vector<Elf_Rel> Relocs;
362
363 // Word type: uint32_t for Elf32, and uint64_t for Elf64.
364 using Addr = typename ELFT::uint;
365
366 Addr Base = 0;
367 for (Elf_Relr R : relrs) {
368 typename ELFT::uint Entry = R;
369 if ((Entry & 1) == 0) {
370 // Even entry: encodes the offset for next relocation.
371 Rel.r_offset = Entry;
372 Relocs.push_back(Rel);
373 // Set base offset for subsequent bitmap entries.
374 Base = Entry + sizeof(Addr);
375 } else {
376 // Odd entry: encodes bitmap for relocations starting at base.
377 for (Addr Offset = Base; (Entry >>= 1) != 0; Offset += sizeof(Addr))
378 if ((Entry & 1) != 0) {
379 Rel.r_offset = Offset;
380 Relocs.push_back(Rel);
381 }
382 Base += (CHAR_BIT * sizeof(Entry) - 1) * sizeof(Addr);
383 }
384 }
385
386 return Relocs;
387}
388
389template <class ELFT>
391ELFFile<ELFT>::android_relas(const Elf_Shdr &Sec) const {
392 // This function reads relocations in Android's packed relocation format,
393 // which is based on SLEB128 and delta encoding.
394 Expected<ArrayRef<uint8_t>> ContentsOrErr = getSectionContents(Sec);
395 if (!ContentsOrErr)
396 return ContentsOrErr.takeError();
397 ArrayRef<uint8_t> Content = *ContentsOrErr;
398 if (Content.size() < 4 || Content[0] != 'A' || Content[1] != 'P' ||
399 Content[2] != 'S' || Content[3] != '2')
400 return createError("invalid packed relocation header");
401 DataExtractor Data(Content, isLE(), ELFT::Is64Bits ? 8 : 4);
402 DataExtractor::Cursor Cur(/*Offset=*/4);
403
404 uint64_t NumRelocs = Data.getSLEB128(Cur);
405 uint64_t Offset = Data.getSLEB128(Cur);
406 uint64_t Addend = 0;
407
408 if (!Cur)
409 return std::move(Cur.takeError());
410
411 std::vector<Elf_Rela> Relocs;
412 Relocs.reserve(NumRelocs);
413 while (NumRelocs) {
414 uint64_t NumRelocsInGroup = Data.getSLEB128(Cur);
415 if (!Cur)
416 return std::move(Cur.takeError());
417 if (NumRelocsInGroup > NumRelocs)
418 return createError("relocation group unexpectedly large");
419 NumRelocs -= NumRelocsInGroup;
420
421 uint64_t GroupFlags = Data.getSLEB128(Cur);
422 bool GroupedByInfo = GroupFlags & ELF::RELOCATION_GROUPED_BY_INFO_FLAG;
423 bool GroupedByOffsetDelta = GroupFlags & ELF::RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG;
424 bool GroupedByAddend = GroupFlags & ELF::RELOCATION_GROUPED_BY_ADDEND_FLAG;
425 bool GroupHasAddend = GroupFlags & ELF::RELOCATION_GROUP_HAS_ADDEND_FLAG;
426
427 uint64_t GroupOffsetDelta;
428 if (GroupedByOffsetDelta)
429 GroupOffsetDelta = Data.getSLEB128(Cur);
430
431 uint64_t GroupRInfo;
432 if (GroupedByInfo)
433 GroupRInfo = Data.getSLEB128(Cur);
434
435 if (GroupedByAddend && GroupHasAddend)
436 Addend += Data.getSLEB128(Cur);
437
438 if (!GroupHasAddend)
439 Addend = 0;
440
441 for (uint64_t I = 0; Cur && I != NumRelocsInGroup; ++I) {
442 Elf_Rela R;
443 Offset += GroupedByOffsetDelta ? GroupOffsetDelta : Data.getSLEB128(Cur);
444 R.r_offset = Offset;
445 R.r_info = GroupedByInfo ? GroupRInfo : Data.getSLEB128(Cur);
446 if (GroupHasAddend && !GroupedByAddend)
447 Addend += Data.getSLEB128(Cur);
448 R.r_addend = Addend;
449 Relocs.push_back(R);
450 }
451 if (!Cur)
452 return std::move(Cur.takeError());
453 }
454
455 return Relocs;
456}
457
458template <class ELFT>
459std::string ELFFile<ELFT>::getDynamicTagAsString(unsigned Arch,
460 uint64_t Type) const {
461#define DYNAMIC_STRINGIFY_ENUM(tag, value) \
462 case value: \
463 return #tag;
464
465#define DYNAMIC_TAG(n, v)
466 switch (Arch) {
467 case ELF::EM_AARCH64:
468 switch (Type) {
469#define AARCH64_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value)
470#include "llvm/BinaryFormat/DynamicTags.def"
471#undef AARCH64_DYNAMIC_TAG
472 }
473 break;
474
475 case ELF::EM_HEXAGON:
476 switch (Type) {
477#define HEXAGON_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value)
478#include "llvm/BinaryFormat/DynamicTags.def"
479#undef HEXAGON_DYNAMIC_TAG
480 }
481 break;
482
483 case ELF::EM_MIPS:
484 switch (Type) {
485#define MIPS_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value)
486#include "llvm/BinaryFormat/DynamicTags.def"
487#undef MIPS_DYNAMIC_TAG
488 }
489 break;
490
491 case ELF::EM_PPC:
492 switch (Type) {
493#define PPC_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value)
494#include "llvm/BinaryFormat/DynamicTags.def"
495#undef PPC_DYNAMIC_TAG
496 }
497 break;
498
499 case ELF::EM_PPC64:
500 switch (Type) {
501#define PPC64_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value)
502#include "llvm/BinaryFormat/DynamicTags.def"
503#undef PPC64_DYNAMIC_TAG
504 }
505 break;
506
507 case ELF::EM_RISCV:
508 switch (Type) {
509#define RISCV_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value)
510#include "llvm/BinaryFormat/DynamicTags.def"
511#undef RISCV_DYNAMIC_TAG
512 }
513 break;
514 }
515#undef DYNAMIC_TAG
516 switch (Type) {
517// Now handle all dynamic tags except the architecture specific ones
518#define AARCH64_DYNAMIC_TAG(name, value)
519#define MIPS_DYNAMIC_TAG(name, value)
520#define HEXAGON_DYNAMIC_TAG(name, value)
521#define PPC_DYNAMIC_TAG(name, value)
522#define PPC64_DYNAMIC_TAG(name, value)
523#define RISCV_DYNAMIC_TAG(name, value)
524// Also ignore marker tags such as DT_HIOS (maps to DT_VERNEEDNUM), etc.
525#define DYNAMIC_TAG_MARKER(name, value)
526#define DYNAMIC_TAG(name, value) case value: return #name;
527#include "llvm/BinaryFormat/DynamicTags.def"
528#undef DYNAMIC_TAG
529#undef AARCH64_DYNAMIC_TAG
530#undef MIPS_DYNAMIC_TAG
531#undef HEXAGON_DYNAMIC_TAG
532#undef PPC_DYNAMIC_TAG
533#undef PPC64_DYNAMIC_TAG
534#undef RISCV_DYNAMIC_TAG
535#undef DYNAMIC_TAG_MARKER
536#undef DYNAMIC_STRINGIFY_ENUM
537 default:
538 return "<unknown:>0x" + utohexstr(Type, true);
539 }
540}
541
542template <class ELFT>
544 return getDynamicTagAsString(getHeader().e_machine, Type);
545}
546
547template <class ELFT>
550
551 auto ProgramHeadersOrError = program_headers();
552 if (!ProgramHeadersOrError)
553 return ProgramHeadersOrError.takeError();
554
555 for (const Elf_Phdr &Phdr : *ProgramHeadersOrError) {
556 if (Phdr.p_type == ELF::PT_DYNAMIC) {
557 Dyn = ArrayRef(reinterpret_cast<const Elf_Dyn *>(base() + Phdr.p_offset),
558 Phdr.p_filesz / sizeof(Elf_Dyn));
559 break;
560 }
561 }
562
563 // If we can't find the dynamic section in the program headers, we just fall
564 // back on the sections.
565 if (Dyn.empty()) {
566 auto SectionsOrError = sections();
567 if (!SectionsOrError)
568 return SectionsOrError.takeError();
569
570 for (const Elf_Shdr &Sec : *SectionsOrError) {
571 if (Sec.sh_type == ELF::SHT_DYNAMIC) {
572 Expected<ArrayRef<Elf_Dyn>> DynOrError =
573 getSectionContentsAsArray<Elf_Dyn>(Sec);
574 if (!DynOrError)
575 return DynOrError.takeError();
576 Dyn = *DynOrError;
577 break;
578 }
579 }
580
581 if (!Dyn.data())
582 return ArrayRef<Elf_Dyn>();
583 }
584
585 if (Dyn.empty())
586 return createError("invalid empty dynamic section");
587
588 if (Dyn.back().d_tag != ELF::DT_NULL)
589 return createError("dynamic sections must be DT_NULL terminated");
590
591 return Dyn;
592}
593
594template <class ELFT>
597 auto ProgramHeadersOrError = program_headers();
598 if (!ProgramHeadersOrError)
599 return ProgramHeadersOrError.takeError();
600
602
603 for (const Elf_Phdr &Phdr : *ProgramHeadersOrError)
604 if (Phdr.p_type == ELF::PT_LOAD)
605 LoadSegments.push_back(const_cast<Elf_Phdr *>(&Phdr));
606
607 auto SortPred = [](const Elf_Phdr_Impl<ELFT> *A,
608 const Elf_Phdr_Impl<ELFT> *B) {
609 return A->p_vaddr < B->p_vaddr;
610 };
611 if (!llvm::is_sorted(LoadSegments, SortPred)) {
612 if (Error E =
613 WarnHandler("loadable segments are unsorted by virtual address"))
614 return std::move(E);
615 llvm::stable_sort(LoadSegments, SortPred);
616 }
617
618 const Elf_Phdr *const *I = llvm::upper_bound(
619 LoadSegments, VAddr, [](uint64_t VAddr, const Elf_Phdr_Impl<ELFT> *Phdr) {
620 return VAddr < Phdr->p_vaddr;
621 });
622
623 if (I == LoadSegments.begin())
624 return createError("virtual address is not in any segment: 0x" +
625 Twine::utohexstr(VAddr));
626 --I;
627 const Elf_Phdr &Phdr = **I;
628 uint64_t Delta = VAddr - Phdr.p_vaddr;
629 if (Delta >= Phdr.p_filesz)
630 return createError("virtual address is not in any segment: 0x" +
631 Twine::utohexstr(VAddr));
632
633 uint64_t Offset = Phdr.p_offset + Delta;
634 if (Offset >= getBufSize())
635 return createError("can't map virtual address 0x" +
636 Twine::utohexstr(VAddr) + " to the segment with index " +
637 Twine(&Phdr - (*ProgramHeadersOrError).data() + 1) +
638 ": the segment ends at 0x" +
639 Twine::utohexstr(Phdr.p_offset + Phdr.p_filesz) +
640 ", which is greater than the file size (0x" +
641 Twine::utohexstr(getBufSize()) + ")");
642
643 return base() + Offset;
644}
645
646template <class ELFT>
649 const Elf_Shdr *RelaSec) const {
650 bool IsRelocatable = getHeader().e_type == ELF::ET_REL;
651
652 // This DenseMap maps the offset of each function (the location of the
653 // reference to the function in the SHT_LLVM_BB_ADDR_MAP section) to the
654 // addend (the location of the function in the text section).
655 llvm::DenseMap<uint64_t, uint64_t> FunctionOffsetTranslations;
656 if (IsRelocatable && RelaSec) {
657 assert(RelaSec &&
658 "Can't read a SHT_LLVM_BB_ADDR_MAP section in a relocatable "
659 "object file without providing a relocation section.");
660 Expected<Elf_Rela_Range> Relas = this->relas(*RelaSec);
661 if (!Relas)
662 return createError("unable to read relocations for section " +
663 describe(*this, Sec) + ": " +
664 toString(Relas.takeError()));
665 for (Elf_Rela Rela : *Relas)
666 FunctionOffsetTranslations[Rela.r_offset] = Rela.r_addend;
667 }
668 Expected<ArrayRef<uint8_t>> ContentsOrErr = getSectionContents(Sec);
669 if (!ContentsOrErr)
670 return ContentsOrErr.takeError();
671 ArrayRef<uint8_t> Content = *ContentsOrErr;
672 DataExtractor Data(Content, isLE(), ELFT::Is64Bits ? 8 : 4);
673 std::vector<BBAddrMap> FunctionEntries;
674
676 Error ULEBSizeErr = Error::success();
677 Error MetadataDecodeErr = Error::success();
678 // Helper to extract and decode the next ULEB128 value as uint32_t.
679 // Returns zero and sets ULEBSizeErr if the ULEB128 value exceeds the uint32_t
680 // limit.
681 // Also returns zero if ULEBSizeErr is already in an error state.
682 auto ReadULEB128AsUInt32 = [&Data, &Cur, &ULEBSizeErr]() -> uint32_t {
683 // Bail out and do not extract data if ULEBSizeErr is already set.
684 if (ULEBSizeErr)
685 return 0;
686 uint64_t Offset = Cur.tell();
687 uint64_t Value = Data.getULEB128(Cur);
688 if (Value > UINT32_MAX) {
689 ULEBSizeErr = createError(
690 "ULEB128 value at offset 0x" + Twine::utohexstr(Offset) +
691 " exceeds UINT32_MAX (0x" + Twine::utohexstr(Value) + ")");
692 return 0;
693 }
694 return static_cast<uint32_t>(Value);
695 };
696
697 uint8_t Version = 0;
698 while (!ULEBSizeErr && !MetadataDecodeErr && Cur &&
699 Cur.tell() < Content.size()) {
700 if (Sec.sh_type == ELF::SHT_LLVM_BB_ADDR_MAP) {
701 Version = Data.getU8(Cur);
702 if (!Cur)
703 break;
704 if (Version > 2)
705 return createError("unsupported SHT_LLVM_BB_ADDR_MAP version: " +
706 Twine(static_cast<int>(Version)));
707 Data.getU8(Cur); // Feature byte
708 }
709 uint64_t SectionOffset = Cur.tell();
710 uintX_t Address = static_cast<uintX_t>(Data.getAddress(Cur));
711 if (!Cur)
712 return Cur.takeError();
713 if (IsRelocatable) {
714 assert(Address == 0);
715 auto FOTIterator = FunctionOffsetTranslations.find(SectionOffset);
716 if (FOTIterator == FunctionOffsetTranslations.end()) {
717 return createError("failed to get relocation data for offset: " +
718 Twine::utohexstr(SectionOffset) + " in section " +
719 describe(*this, Sec));
720 }
721 Address = FOTIterator->second;
722 }
723 uint32_t NumBlocks = ReadULEB128AsUInt32();
724 std::vector<BBAddrMap::BBEntry> BBEntries;
725 uint32_t PrevBBEndOffset = 0;
726 for (uint32_t BlockIndex = 0;
727 !MetadataDecodeErr && !ULEBSizeErr && Cur && (BlockIndex < NumBlocks);
728 ++BlockIndex) {
729 uint32_t ID = Version >= 2 ? ReadULEB128AsUInt32() : BlockIndex;
730 uint32_t Offset = ReadULEB128AsUInt32();
731 uint32_t Size = ReadULEB128AsUInt32();
732 uint32_t MD = ReadULEB128AsUInt32();
733 if (Version >= 1) {
734 // Offset is calculated relative to the end of the previous BB.
735 Offset += PrevBBEndOffset;
736 PrevBBEndOffset = Offset + Size;
737 }
740 if (!MetadataOrErr) {
741 MetadataDecodeErr = MetadataOrErr.takeError();
742 break;
743 }
744 BBEntries.push_back({ID, Offset, Size, *MetadataOrErr});
745 }
746 FunctionEntries.push_back({Address, std::move(BBEntries)});
747 }
748 // Either Cur is in the error state, or we have an error in ULEBSizeErr or
749 // MetadataDecodeErr (but not both), but we join all errors here to be safe.
750 if (!Cur || ULEBSizeErr || MetadataDecodeErr)
751 return joinErrors(joinErrors(Cur.takeError(), std::move(ULEBSizeErr)),
752 std::move(MetadataDecodeErr));
753 return FunctionEntries;
754}
755
756template <class ELFT>
760 std::function<Expected<bool>(const Elf_Shdr &)> IsMatch) const {
762 Error Errors = Error::success();
763 for (const Elf_Shdr &Sec : cantFail(this->sections())) {
764 Expected<bool> DoesSectionMatch = IsMatch(Sec);
765 if (!DoesSectionMatch) {
766 Errors = joinErrors(std::move(Errors), DoesSectionMatch.takeError());
767 continue;
768 }
769 if (*DoesSectionMatch) {
770 if (SecToRelocMap.insert(std::make_pair(&Sec, (const Elf_Shdr *)nullptr))
771 .second)
772 continue;
773 }
774
775 if (Sec.sh_type != ELF::SHT_RELA && Sec.sh_type != ELF::SHT_REL)
776 continue;
777
778 Expected<const Elf_Shdr *> RelSecOrErr = this->getSection(Sec.sh_info);
779 if (!RelSecOrErr) {
780 Errors = joinErrors(std::move(Errors),
781 createError(describe(*this, Sec) +
782 ": failed to get a relocated section: " +
783 toString(RelSecOrErr.takeError())));
784 continue;
785 }
786 const Elf_Shdr *ContentsSec = *RelSecOrErr;
787 Expected<bool> DoesRelTargetMatch = IsMatch(*ContentsSec);
788 if (!DoesRelTargetMatch) {
789 Errors = joinErrors(std::move(Errors), DoesRelTargetMatch.takeError());
790 continue;
791 }
792 if (*DoesRelTargetMatch)
793 SecToRelocMap[ContentsSec] = &Sec;
794 }
795 if(Errors)
796 return std::move(Errors);
797 return SecToRelocMap;
798}
799
800template class llvm::object::ELFFile<ELF32LE>;
801template class llvm::object::ELFFile<ELF32BE>;
802template class llvm::object::ELFFile<ELF64LE>;
803template class llvm::object::ELFFile<ELF64BE>;
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
T Content
uint64_t Addr
uint64_t Size
#define I(x, y, z)
Definition: MD5.cpp:58
#define STRINGIFY_ENUM_CASE(ns, name)
Definition: ELF.cpp:16
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition: ArrayRef.h:41
const T & back() const
back - Get the last element.
Definition: ArrayRef.h:172
bool empty() const
empty - Check if the array is empty.
Definition: ArrayRef.h:158
const T * data() const
Definition: ArrayRef.h:160
A class representing a position in a DataExtractor, as well as any error encountered during extractio...
Definition: DataExtractor.h:54
uint64_t tell() const
Return the current position of this Cursor.
Definition: DataExtractor.h:71
Error takeError()
Return error contained inside this Cursor, if any.
Definition: DataExtractor.h:78
iterator find(const_arg_type_t< KeyT > Val)
Definition: DenseMap.h:155
iterator end()
Definition: DenseMap.h:84
Lightweight error class with error context and mandatory checking.
Definition: Error.h:156
static ErrorSuccess success()
Create a success value.
Definition: Error.h:330
Tagged union holding either a T or a Error.
Definition: Error.h:470
Error takeError()
Take ownership of the stored error.
Definition: Error.h:597
This class implements a map that also provides access to all stored values in a deterministic order.
Definition: MapVector.h:37
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Definition: MapVector.h:118
void push_back(const T &Elt)
Definition: SmallVector.h:416
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1200
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:50
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition: Twine.h:81
static Twine utohexstr(const uint64_t &Val)
Definition: Twine.h:404
The instances of the Type class are immutable: once they are created, they are never changed.
Definition: Type.h:45
LLVM Value Representation.
Definition: Value.h:74
An efficient, type-erasing, non-owning reference to a callable.
Expected< std::vector< Elf_Rela > > android_relas(const Elf_Shdr &Sec) const
Definition: ELF.cpp:391
std::string getDynamicTagAsString(unsigned Arch, uint64_t Type) const
Definition: ELF.cpp:459
Expected< std::vector< BBAddrMap > > decodeBBAddrMap(const Elf_Shdr &Sec, const Elf_Shdr *RelaSec=nullptr) const
Returns a vector of BBAddrMap structs corresponding to each function within the text section that the...
Definition: ELF.cpp:648
Expected< Elf_Dyn_Range > dynamicEntries() const
Definition: ELF.cpp:548
Expected< const uint8_t * > toMappedAddr(uint64_t VAddr, WarningHandler WarnHandler=&defaultWarningHandler) const
Definition: ELF.cpp:596
Expected< MapVector< const Elf_Shdr *, const Elf_Shdr * > > getSectionAndRelocations(std::function< Expected< bool >(const Elf_Shdr &)> IsMatch) const
Returns a map from every section matching IsMatch to its relocation section, or nullptr if it has no ...
Definition: ELF.cpp:759
std::vector< Elf_Rel > decode_relrs(Elf_Relr_Range relrs) const
Definition: ELF.cpp:327
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
Definition: CallingConv.h:24
@ EM_MSP430
Definition: ELF.h:222
@ EM_S390
Definition: ELF.h:150
@ EM_PPC64
Definition: ELF.h:149
@ EM_SPARC
Definition: ELF.h:135
@ EM_CSKY
Definition: ELF.h:321
@ EM_SPARC32PLUS
Definition: ELF.h:146
@ EM_MIPS_RS3_LE
Definition: ELF.h:143
@ EM_68K
Definition: ELF.h:137
@ EM_386
Definition: ELF.h:136
@ EM_LOONGARCH
Definition: ELF.h:322
@ EM_BPF
Definition: ELF.h:319
@ EM_PPC
Definition: ELF.h:148
@ EM_X86_64
Definition: ELF.h:178
@ EM_HEXAGON
Definition: ELF.h:257
@ EM_LANAI
Definition: ELF.h:318
@ EM_MIPS
Definition: ELF.h:141
@ EM_SPARCV9
Definition: ELF.h:159
@ EM_AARCH64
Definition: ELF.h:280
@ EM_XTENSA
Definition: ELF.h:211
@ EM_ARC_COMPACT2
Definition: ELF.h:291
@ EM_RISCV
Definition: ELF.h:317
@ EM_ARC_COMPACT
Definition: ELF.h:209
@ EM_ARM
Definition: ELF.h:156
@ EM_VE
Definition: ELF.h:320
@ EM_IAMCU
Definition: ELF.h:139
@ EM_AMDGPU
Definition: ELF.h:316
@ EM_AVR
Definition: ELF.h:199
@ SHT_REL
Definition: ELF.h:1008
@ SHT_DYNAMIC
Definition: ELF.h:1005
@ SHT_LLVM_BB_ADDR_MAP
Definition: ELF.h:1037
@ SHT_RELA
Definition: ELF.h:1003
@ RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG
Definition: ELF.h:1798
@ RELOCATION_GROUPED_BY_INFO_FLAG
Definition: ELF.h:1797
@ RELOCATION_GROUPED_BY_ADDEND_FLAG
Definition: ELF.h:1799
@ RELOCATION_GROUP_HAS_ADDEND_FLAG
Definition: ELF.h:1800
@ ET_REL
Definition: ELF.h:116
@ PT_LOAD
Definition: ELF.h:1387
@ PT_DYNAMIC
Definition: ELF.h:1388
std::optional< const char * > toString(const std::optional< DWARFFormValue > &V)
Take an optional DWARFFormValue and try to extract a string value from it.
Expected< const typename ELFT::Shdr * > getSection(typename ELFT::ShdrRange Sections, uint32_t Index)
Definition: ELF.h:438
Error createError(const Twine &Err)
Definition: Error.h:84
StringRef getELFRelocationTypeName(uint32_t Machine, uint32_t Type)
Definition: ELF.cpp:22
uint32_t getELFRelativeRelocationType(uint32_t Machine)
Definition: ELF.cpp:191
static std::string describe(const ELFFile< ELFT > &Obj, const typename ELFT::Shdr &Sec)
Definition: ELF.h:143
StringRef getELFSectionTypeName(uint32_t Machine, uint32_t Type)
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
@ Offset
Definition: DWP.cpp:406
void stable_sort(R &&Range)
Definition: STLExtras.h:2063
auto upper_bound(R &&Range, T &&Value)
Provide wrappers to std::upper_bound which take ranges instead of having to pass begin/end explicitly...
Definition: STLExtras.h:2051
Error joinErrors(Error E1, Error E2)
Concatenate errors.
Definition: Error.h:427
bool is_sorted(R &&Range, Compare C)
Wrapper function around std::is_sorted to check if elements in a range R are sorted with respect to a...
Definition: STLExtras.h:1999
void cantFail(Error Err, const char *Msg=nullptr)
Report a fatal error if Err is a failure value.
Definition: Error.h:745
static Expected< Metadata > decode(uint32_t V)
Definition: ELFTypes.h:828