LLVM 20.0.0git
ELFTypes.h
Go to the documentation of this file.
1//===- ELFTypes.h - Endian specific types for ELF ---------------*- C++ -*-===//
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#ifndef LLVM_OBJECT_ELFTYPES_H
10#define LLVM_OBJECT_ELFTYPES_H
11
12#include "llvm/ADT/ArrayRef.h"
13#include "llvm/ADT/StringRef.h"
15#include "llvm/Object/Error.h"
18#include "llvm/Support/Endian.h"
19#include "llvm/Support/Error.h"
21#include <cassert>
22#include <cstdint>
23#include <cstring>
24#include <type_traits>
25
26namespace llvm {
27namespace object {
28
29template <class ELFT> struct Elf_Ehdr_Impl;
30template <class ELFT> struct Elf_Shdr_Impl;
31template <class ELFT> struct Elf_Sym_Impl;
32template <class ELFT> struct Elf_Dyn_Impl;
33template <class ELFT> struct Elf_Phdr_Impl;
34template <class ELFT, bool isRela> struct Elf_Rel_Impl;
35template <bool Is64> struct Elf_Crel_Impl;
36template <class ELFT> struct Elf_Verdef_Impl;
37template <class ELFT> struct Elf_Verdaux_Impl;
38template <class ELFT> struct Elf_Verneed_Impl;
39template <class ELFT> struct Elf_Vernaux_Impl;
40template <class ELFT> struct Elf_Versym_Impl;
41template <class ELFT> struct Elf_Hash_Impl;
42template <class ELFT> struct Elf_GnuHash_Impl;
43template <class ELFT> struct Elf_Chdr_Impl;
44template <class ELFT> struct Elf_Nhdr_Impl;
45template <class ELFT> class Elf_Note_Impl;
46template <class ELFT> class Elf_Note_Iterator_Impl;
47template <class ELFT> struct Elf_CGProfile_Impl;
48
49template <endianness E, bool Is64> struct ELFType {
50private:
51 template <typename Ty>
53
54public:
55 static const endianness Endianness = E;
56 static const bool Is64Bits = Is64;
57
58 using uint = std::conditional_t<Is64, uint64_t, uint32_t>;
87
95};
96
101
102// Use an alignment of 2 for the typedefs since that is the worst case for
103// ELF files in archives.
104
105// I really don't like doing this, but the alternative is copypasta.
106#define LLVM_ELF_IMPORT_TYPES_ELFT(ELFT) \
107 using Elf_Addr = typename ELFT::Addr; \
108 using Elf_Off = typename ELFT::Off; \
109 using Elf_Half = typename ELFT::Half; \
110 using Elf_Word = typename ELFT::Word; \
111 using Elf_Sword = typename ELFT::Sword; \
112 using Elf_Xword = typename ELFT::Xword; \
113 using Elf_Sxword = typename ELFT::Sxword; \
114 using uintX_t = typename ELFT::uint; \
115 using Elf_Ehdr = typename ELFT::Ehdr; \
116 using Elf_Shdr = typename ELFT::Shdr; \
117 using Elf_Sym = typename ELFT::Sym; \
118 using Elf_Dyn = typename ELFT::Dyn; \
119 using Elf_Phdr = typename ELFT::Phdr; \
120 using Elf_Rel = typename ELFT::Rel; \
121 using Elf_Rela = typename ELFT::Rela; \
122 using Elf_Crel = typename ELFT::Crel; \
123 using Elf_Relr = typename ELFT::Relr; \
124 using Elf_Verdef = typename ELFT::Verdef; \
125 using Elf_Verdaux = typename ELFT::Verdaux; \
126 using Elf_Verneed = typename ELFT::Verneed; \
127 using Elf_Vernaux = typename ELFT::Vernaux; \
128 using Elf_Versym = typename ELFT::Versym; \
129 using Elf_Hash = typename ELFT::Hash; \
130 using Elf_GnuHash = typename ELFT::GnuHash; \
131 using Elf_Chdr = typename ELFT::Chdr; \
132 using Elf_Nhdr = typename ELFT::Nhdr; \
133 using Elf_Note = typename ELFT::Note; \
134 using Elf_Note_Iterator = typename ELFT::NoteIterator; \
135 using Elf_CGProfile = typename ELFT::CGProfile; \
136 using Elf_Dyn_Range = typename ELFT::DynRange; \
137 using Elf_Shdr_Range = typename ELFT::ShdrRange; \
138 using Elf_Sym_Range = typename ELFT::SymRange; \
139 using Elf_Rel_Range = typename ELFT::RelRange; \
140 using Elf_Rela_Range = typename ELFT::RelaRange; \
141 using Elf_Relr_Range = typename ELFT::RelrRange; \
142 using Elf_Phdr_Range = typename ELFT::PhdrRange;
143
144#define LLVM_ELF_COMMA ,
145#define LLVM_ELF_IMPORT_TYPES(E, W) \
146 LLVM_ELF_IMPORT_TYPES_ELFT(ELFType<E LLVM_ELF_COMMA W>)
147
148// Section header.
149template <class ELFT> struct Elf_Shdr_Base;
150
151template <endianness Endianness>
152struct Elf_Shdr_Base<ELFType<Endianness, false>> {
153 LLVM_ELF_IMPORT_TYPES(Endianness, false)
154 Elf_Word sh_name; // Section name (index into string table)
155 Elf_Word sh_type; // Section type (SHT_*)
156 Elf_Word sh_flags; // Section flags (SHF_*)
157 Elf_Addr sh_addr; // Address where section is to be loaded
158 Elf_Off sh_offset; // File offset of section data, in bytes
159 Elf_Word sh_size; // Size of section, in bytes
160 Elf_Word sh_link; // Section type-specific header table index link
161 Elf_Word sh_info; // Section type-specific extra information
162 Elf_Word sh_addralign; // Section address alignment
163 Elf_Word sh_entsize; // Size of records contained within the section
164};
165
166template <endianness Endianness>
167struct Elf_Shdr_Base<ELFType<Endianness, true>> {
168 LLVM_ELF_IMPORT_TYPES(Endianness, true)
169 Elf_Word sh_name; // Section name (index into string table)
170 Elf_Word sh_type; // Section type (SHT_*)
171 Elf_Xword sh_flags; // Section flags (SHF_*)
172 Elf_Addr sh_addr; // Address where section is to be loaded
173 Elf_Off sh_offset; // File offset of section data, in bytes
174 Elf_Xword sh_size; // Size of section, in bytes
175 Elf_Word sh_link; // Section type-specific header table index link
176 Elf_Word sh_info; // Section type-specific extra information
177 Elf_Xword sh_addralign; // Section address alignment
178 Elf_Xword sh_entsize; // Size of records contained within the section
179};
180
181template <class ELFT>
183 using Elf_Shdr_Base<ELFT>::sh_entsize;
184 using Elf_Shdr_Base<ELFT>::sh_size;
185
186 /// Get the number of entities this section contains if it has any.
187 unsigned getEntityCount() const {
188 if (sh_entsize == 0)
189 return 0;
190 return sh_size / sh_entsize;
191 }
192};
193
194template <class ELFT> struct Elf_Sym_Base;
195
196template <endianness Endianness>
197struct Elf_Sym_Base<ELFType<Endianness, false>> {
198 LLVM_ELF_IMPORT_TYPES(Endianness, false)
199 Elf_Word st_name; // Symbol name (index into string table)
200 Elf_Addr st_value; // Value or address associated with the symbol
201 Elf_Word st_size; // Size of the symbol
202 unsigned char st_info; // Symbol's type and binding attributes
203 unsigned char st_other; // Must be zero; reserved
204 Elf_Half st_shndx; // Which section (header table index) it's defined in
205};
206
207template <endianness Endianness>
208struct Elf_Sym_Base<ELFType<Endianness, true>> {
209 LLVM_ELF_IMPORT_TYPES(Endianness, true)
210 Elf_Word st_name; // Symbol name (index into string table)
211 unsigned char st_info; // Symbol's type and binding attributes
212 unsigned char st_other; // Must be zero; reserved
213 Elf_Half st_shndx; // Which section (header table index) it's defined in
214 Elf_Addr st_value; // Value or address associated with the symbol
215 Elf_Xword st_size; // Size of the symbol
216};
217
218template <class ELFT>
220 using Elf_Sym_Base<ELFT>::st_info;
221 using Elf_Sym_Base<ELFT>::st_shndx;
222 using Elf_Sym_Base<ELFT>::st_other;
223 using Elf_Sym_Base<ELFT>::st_value;
224
225 // These accessors and mutators correspond to the ELF32_ST_BIND,
226 // ELF32_ST_TYPE, and ELF32_ST_INFO macros defined in the ELF specification:
227 unsigned char getBinding() const { return st_info >> 4; }
228 unsigned char getType() const { return st_info & 0x0f; }
229 uint64_t getValue() const { return st_value; }
230 void setBinding(unsigned char b) { setBindingAndType(b, getType()); }
231 void setType(unsigned char t) { setBindingAndType(getBinding(), t); }
232
233 void setBindingAndType(unsigned char b, unsigned char t) {
234 st_info = (b << 4) + (t & 0x0f);
235 }
236
237 /// Access to the STV_xxx flag stored in the first two bits of st_other.
238 /// STV_DEFAULT: 0
239 /// STV_INTERNAL: 1
240 /// STV_HIDDEN: 2
241 /// STV_PROTECTED: 3
242 unsigned char getVisibility() const { return st_other & 0x3; }
243 void setVisibility(unsigned char v) {
244 assert(v < 4 && "Invalid value for visibility");
245 st_other = (st_other & ~0x3) | v;
246 }
247
248 bool isAbsolute() const { return st_shndx == ELF::SHN_ABS; }
249
250 bool isCommon() const {
251 return getType() == ELF::STT_COMMON || st_shndx == ELF::SHN_COMMON;
252 }
253
254 bool isDefined() const { return !isUndefined(); }
255
256 bool isProcessorSpecific() const {
257 return st_shndx >= ELF::SHN_LOPROC && st_shndx <= ELF::SHN_HIPROC;
258 }
259
260 bool isOSSpecific() const {
261 return st_shndx >= ELF::SHN_LOOS && st_shndx <= ELF::SHN_HIOS;
262 }
263
264 bool isReserved() const {
265 // ELF::SHN_HIRESERVE is 0xffff so st_shndx <= ELF::SHN_HIRESERVE is always
266 // true and some compilers warn about it.
267 return st_shndx >= ELF::SHN_LORESERVE;
268 }
269
270 bool isUndefined() const { return st_shndx == ELF::SHN_UNDEF; }
271
272 bool isExternal() const {
273 return getBinding() != ELF::STB_LOCAL;
274 }
275
277};
278
279template <class ELFT>
281 uint32_t Offset = this->st_name;
282 if (Offset >= StrTab.size())
283 return createStringError(object_error::parse_failed,
284 "st_name (0x%" PRIx32
285 ") is past the end of the string table"
286 " of size 0x%zx",
287 Offset, StrTab.size());
288 return StringRef(StrTab.data() + Offset);
289}
290
291/// Elf_Versym: This is the structure of entries in the SHT_GNU_versym section
292/// (.gnu.version). This structure is identical for ELF32 and ELF64.
293template <class ELFT>
296 Elf_Half vs_index; // Version index with flags (e.g. VERSYM_HIDDEN)
297};
298
299/// Elf_Verdef: This is the structure of entries in the SHT_GNU_verdef section
300/// (.gnu.version_d). This structure is identical for ELF32 and ELF64.
301template <class ELFT>
304 Elf_Half vd_version; // Version of this structure (e.g. VER_DEF_CURRENT)
305 Elf_Half vd_flags; // Bitwise flags (VER_DEF_*)
306 Elf_Half vd_ndx; // Version index, used in .gnu.version entries
307 Elf_Half vd_cnt; // Number of Verdaux entries
308 Elf_Word vd_hash; // Hash of name
309 Elf_Word vd_aux; // Offset to the first Verdaux entry (in bytes)
310 Elf_Word vd_next; // Offset to the next Verdef entry (in bytes)
311
312 /// Get the first Verdaux entry for this Verdef.
313 const Elf_Verdaux *getAux() const {
314 return reinterpret_cast<const Elf_Verdaux *>((const char *)this + vd_aux);
315 }
316};
317
318/// Elf_Verdaux: This is the structure of auxiliary data in the SHT_GNU_verdef
319/// section (.gnu.version_d). This structure is identical for ELF32 and ELF64.
320template <class ELFT>
323 Elf_Word vda_name; // Version name (offset in string table)
324 Elf_Word vda_next; // Offset to next Verdaux entry (in bytes)
325};
326
327/// Elf_Verneed: This is the structure of entries in the SHT_GNU_verneed
328/// section (.gnu.version_r). This structure is identical for ELF32 and ELF64.
329template <class ELFT>
332 Elf_Half vn_version; // Version of this structure (e.g. VER_NEED_CURRENT)
333 Elf_Half vn_cnt; // Number of associated Vernaux entries
334 Elf_Word vn_file; // Library name (string table offset)
335 Elf_Word vn_aux; // Offset to first Vernaux entry (in bytes)
336 Elf_Word vn_next; // Offset to next Verneed entry (in bytes)
337};
338
339/// Elf_Vernaux: This is the structure of auxiliary data in SHT_GNU_verneed
340/// section (.gnu.version_r). This structure is identical for ELF32 and ELF64.
341template <class ELFT>
344 Elf_Word vna_hash; // Hash of dependency name
345 Elf_Half vna_flags; // Bitwise Flags (VER_FLAG_*)
346 Elf_Half vna_other; // Version index, used in .gnu.version entries
347 Elf_Word vna_name; // Dependency name
348 Elf_Word vna_next; // Offset to next Vernaux entry (in bytes)
349};
350
351/// Elf_Dyn_Base: This structure matches the form of entries in the dynamic
352/// table section (.dynamic) look like.
353template <class ELFT> struct Elf_Dyn_Base;
354
355template <endianness Endianness>
356struct Elf_Dyn_Base<ELFType<Endianness, false>> {
357 LLVM_ELF_IMPORT_TYPES(Endianness, false)
358 Elf_Sword d_tag;
359 union {
360 Elf_Word d_val;
361 Elf_Addr d_ptr;
362 } d_un;
363};
364
365template <endianness Endianness>
366struct Elf_Dyn_Base<ELFType<Endianness, true>> {
367 LLVM_ELF_IMPORT_TYPES(Endianness, true)
368 Elf_Sxword d_tag;
369 union {
370 Elf_Xword d_val;
371 Elf_Addr d_ptr;
372 } d_un;
373};
374
375/// Elf_Dyn_Impl: This inherits from Elf_Dyn_Base, adding getters.
376template <class ELFT>
378 using Elf_Dyn_Base<ELFT>::d_tag;
379 using Elf_Dyn_Base<ELFT>::d_un;
380 using intX_t = std::conditional_t<ELFT::Is64Bits, int64_t, int32_t>;
381 using uintX_t = std::conditional_t<ELFT::Is64Bits, uint64_t, uint32_t>;
382 intX_t getTag() const { return d_tag; }
383 uintX_t getVal() const { return d_un.d_val; }
384 uintX_t getPtr() const { return d_un.d_ptr; }
385};
386
387template <endianness Endianness>
388struct Elf_Rel_Impl<ELFType<Endianness, false>, false> {
389 LLVM_ELF_IMPORT_TYPES(Endianness, false)
390 static const bool HasAddend = false;
391 static const bool IsCrel = false;
392 Elf_Addr r_offset; // Location (file byte offset, or program virtual addr)
393 Elf_Word r_info; // Symbol table index and type of relocation to apply
394
395 uint32_t getRInfo(bool isMips64EL) const {
397 return r_info;
398 }
399 void setRInfo(uint32_t R, bool IsMips64EL) {
400 assert(!IsMips64EL);
401 r_info = R;
402 }
403
404 // These accessors and mutators correspond to the ELF32_R_SYM, ELF32_R_TYPE,
405 // and ELF32_R_INFO macros defined in the ELF specification:
407 return this->getRInfo(isMips64EL) >> 8;
408 }
409 unsigned char getType(bool isMips64EL) const {
410 return (unsigned char)(this->getRInfo(isMips64EL) & 0x0ff);
411 }
412 void setSymbol(uint32_t s, bool IsMips64EL) {
413 setSymbolAndType(s, getType(IsMips64EL), IsMips64EL);
414 }
415 void setType(unsigned char t, bool IsMips64EL) {
416 setSymbolAndType(getSymbol(IsMips64EL), t, IsMips64EL);
417 }
418 void setSymbolAndType(uint32_t s, unsigned char t, bool IsMips64EL) {
419 this->setRInfo((s << 8) + t, IsMips64EL);
420 }
421};
422
423template <endianness Endianness>
424struct Elf_Rel_Impl<ELFType<Endianness, false>, true>
425 : public Elf_Rel_Impl<ELFType<Endianness, false>, false> {
426 LLVM_ELF_IMPORT_TYPES(Endianness, false)
427 static const bool HasAddend = true;
428 static const bool IsCrel = false;
429 Elf_Sword r_addend; // Compute value for relocatable field by adding this
430};
431
432template <endianness Endianness>
433struct Elf_Rel_Impl<ELFType<Endianness, true>, false> {
434 LLVM_ELF_IMPORT_TYPES(Endianness, true)
435 static const bool HasAddend = false;
436 static const bool IsCrel = false;
437 Elf_Addr r_offset; // Location (file byte offset, or program virtual addr)
438 Elf_Xword r_info; // Symbol table index and type of relocation to apply
439
440 uint64_t getRInfo(bool isMips64EL) const {
441 uint64_t t = r_info;
442 if (!isMips64EL)
443 return t;
444 // Mips64 little endian has a "special" encoding of r_info. Instead of one
445 // 64 bit little endian number, it is a little endian 32 bit number followed
446 // by a 32 bit big endian number.
447 return (t << 32) | ((t >> 8) & 0xff000000) | ((t >> 24) & 0x00ff0000) |
448 ((t >> 40) & 0x0000ff00) | ((t >> 56) & 0x000000ff);
449 }
450
451 void setRInfo(uint64_t R, bool IsMips64EL) {
452 if (IsMips64EL)
453 r_info = (R >> 32) | ((R & 0xff000000) << 8) | ((R & 0x00ff0000) << 24) |
454 ((R & 0x0000ff00) << 40) | ((R & 0x000000ff) << 56);
455 else
456 r_info = R;
457 }
458
459 // These accessors and mutators correspond to the ELF64_R_SYM, ELF64_R_TYPE,
460 // and ELF64_R_INFO macros defined in the ELF specification:
462 return (uint32_t)(this->getRInfo(isMips64EL) >> 32);
463 }
465 return (uint32_t)(this->getRInfo(isMips64EL) & 0xffffffffL);
466 }
467 void setSymbol(uint32_t s, bool IsMips64EL) {
468 setSymbolAndType(s, getType(IsMips64EL), IsMips64EL);
469 }
470 void setType(uint32_t t, bool IsMips64EL) {
471 setSymbolAndType(getSymbol(IsMips64EL), t, IsMips64EL);
472 }
473 void setSymbolAndType(uint32_t s, uint32_t t, bool IsMips64EL) {
474 this->setRInfo(((uint64_t)s << 32) + (t & 0xffffffffL), IsMips64EL);
475 }
476};
477
478template <endianness Endianness>
479struct Elf_Rel_Impl<ELFType<Endianness, true>, true>
480 : public Elf_Rel_Impl<ELFType<Endianness, true>, false> {
481 LLVM_ELF_IMPORT_TYPES(Endianness, true)
482 static const bool HasAddend = true;
483 static const bool IsCrel = false;
484 Elf_Sxword r_addend; // Compute value for relocatable field by adding this.
485};
486
487// In-memory representation. The serialized representation uses LEB128.
488template <bool Is64> struct Elf_Crel_Impl {
489 using uint = std::conditional_t<Is64, uint64_t, uint32_t>;
490 static const bool HasAddend = true;
491 static const bool IsCrel = true;
495 std::conditional_t<Is64, int64_t, int32_t> r_addend;
496
497 // Dummy bool parameter is for compatibility with Elf_Rel_Impl.
498 uint32_t getType(bool) const { return r_type; }
499 uint32_t getSymbol(bool) const { return r_symidx; }
500 void setSymbolAndType(uint32_t s, unsigned char t, bool) {
501 r_symidx = s;
502 r_type = t;
503 }
504};
505
506template <class ELFT>
509 unsigned char e_ident[ELF::EI_NIDENT]; // ELF Identification bytes
510 Elf_Half e_type; // Type of file (see ET_*)
511 Elf_Half e_machine; // Required architecture for this file (see EM_*)
512 Elf_Word e_version; // Must be equal to 1
513 Elf_Addr e_entry; // Address to jump to in order to start program
514 Elf_Off e_phoff; // Program header table's file offset, in bytes
515 Elf_Off e_shoff; // Section header table's file offset, in bytes
516 Elf_Word e_flags; // Processor-specific flags
517 Elf_Half e_ehsize; // Size of ELF header, in bytes
518 Elf_Half e_phentsize; // Size of an entry in the program header table
519 Elf_Half e_phnum; // Number of entries in the program header table
520 Elf_Half e_shentsize; // Size of an entry in the section header table
521 Elf_Half e_shnum; // Number of entries in the section header table
522 Elf_Half e_shstrndx; // Section header table index of section name
523 // string table
524
525 bool checkMagic() const {
526 return (memcmp(e_ident, ELF::ElfMagic, strlen(ELF::ElfMagic))) == 0;
527 }
528
529 unsigned char getFileClass() const { return e_ident[ELF::EI_CLASS]; }
530 unsigned char getDataEncoding() const { return e_ident[ELF::EI_DATA]; }
531};
532
533template <endianness Endianness>
534struct Elf_Phdr_Impl<ELFType<Endianness, false>> {
535 LLVM_ELF_IMPORT_TYPES(Endianness, false)
536 Elf_Word p_type; // Type of segment
537 Elf_Off p_offset; // FileOffset where segment is located, in bytes
538 Elf_Addr p_vaddr; // Virtual Address of beginning of segment
539 Elf_Addr p_paddr; // Physical address of beginning of segment (OS-specific)
540 Elf_Word p_filesz; // Num. of bytes in file image of segment (may be zero)
541 Elf_Word p_memsz; // Num. of bytes in mem image of segment (may be zero)
542 Elf_Word p_flags; // Segment flags
543 Elf_Word p_align; // Segment alignment constraint
544};
545
546template <endianness Endianness>
547struct Elf_Phdr_Impl<ELFType<Endianness, true>> {
548 LLVM_ELF_IMPORT_TYPES(Endianness, true)
549 Elf_Word p_type; // Type of segment
550 Elf_Word p_flags; // Segment flags
551 Elf_Off p_offset; // FileOffset where segment is located, in bytes
552 Elf_Addr p_vaddr; // Virtual Address of beginning of segment
553 Elf_Addr p_paddr; // Physical address of beginning of segment (OS-specific)
554 Elf_Xword p_filesz; // Num. of bytes in file image of segment (may be zero)
555 Elf_Xword p_memsz; // Num. of bytes in mem image of segment (may be zero)
556 Elf_Xword p_align; // Segment alignment constraint
557};
558
559// ELFT needed for endianness.
560template <class ELFT>
563 Elf_Word nbucket;
564 Elf_Word nchain;
565
566 ArrayRef<Elf_Word> buckets() const {
567 return ArrayRef<Elf_Word>(&nbucket + 2, &nbucket + 2 + nbucket);
568 }
569
571 return ArrayRef<Elf_Word>(&nbucket + 2 + nbucket,
572 &nbucket + 2 + nbucket + nchain);
573 }
574};
575
576// .gnu.hash section
577template <class ELFT>
580 Elf_Word nbuckets;
581 Elf_Word symndx;
582 Elf_Word maskwords;
583 Elf_Word shift2;
584
585 ArrayRef<Elf_Off> filter() const {
586 return ArrayRef<Elf_Off>(reinterpret_cast<const Elf_Off *>(&shift2 + 1),
587 maskwords);
588 }
589
591 return ArrayRef<Elf_Word>(
592 reinterpret_cast<const Elf_Word *>(filter().end()), nbuckets);
593 }
594
595 ArrayRef<Elf_Word> values(unsigned DynamicSymCount) const {
596 assert(DynamicSymCount >= symndx);
597 return ArrayRef<Elf_Word>(buckets().end(), DynamicSymCount - symndx);
598 }
599};
600
601// Compressed section headers.
602// http://www.sco.com/developers/gabi/latest/ch4.sheader.html#compression_header
603template <endianness Endianness>
604struct Elf_Chdr_Impl<ELFType<Endianness, false>> {
605 LLVM_ELF_IMPORT_TYPES(Endianness, false)
606 Elf_Word ch_type;
607 Elf_Word ch_size;
608 Elf_Word ch_addralign;
609};
610
611template <endianness Endianness>
612struct Elf_Chdr_Impl<ELFType<Endianness, true>> {
613 LLVM_ELF_IMPORT_TYPES(Endianness, true)
614 Elf_Word ch_type;
615 Elf_Word ch_reserved;
616 Elf_Xword ch_size;
617 Elf_Xword ch_addralign;
618};
619
620/// Note header
621template <class ELFT>
624 Elf_Word n_namesz;
625 Elf_Word n_descsz;
626 Elf_Word n_type;
627
628 /// Get the size of the note, including name, descriptor, and padding. Both
629 /// the start and the end of the descriptor are aligned by the section
630 /// alignment. In practice many 64-bit systems deviate from the generic ABI by
631 /// using sh_addralign=4.
632 size_t getSize(size_t Align) const {
633 return alignToPowerOf2(sizeof(*this) + n_namesz, Align) +
634 alignToPowerOf2(n_descsz, Align);
635 }
636};
637
638/// An ELF note.
639///
640/// Wraps a note header, providing methods for accessing the name and
641/// descriptor safely.
642template <class ELFT>
645
646 const Elf_Nhdr_Impl<ELFT> &Nhdr;
647
648 template <class NoteIteratorELFT> friend class Elf_Note_Iterator_Impl;
649
650public:
651 Elf_Note_Impl(const Elf_Nhdr_Impl<ELFT> &Nhdr) : Nhdr(Nhdr) {}
652
653 /// Get the note's name, excluding the terminating null byte.
655 if (!Nhdr.n_namesz)
656 return StringRef();
657 return StringRef(reinterpret_cast<const char *>(&Nhdr) + sizeof(Nhdr),
658 Nhdr.n_namesz - 1);
659 }
660
661 /// Get the note's descriptor.
663 if (!Nhdr.n_descsz)
664 return ArrayRef<uint8_t>();
665 return ArrayRef<uint8_t>(
666 reinterpret_cast<const uint8_t *>(&Nhdr) +
667 alignToPowerOf2(sizeof(Nhdr) + Nhdr.n_namesz, Align),
668 Nhdr.n_descsz);
669 }
670
671 /// Get the note's descriptor as StringRef
673 ArrayRef<uint8_t> Desc = getDesc(Align);
674 return StringRef(reinterpret_cast<const char *>(Desc.data()), Desc.size());
675 }
676
677 /// Get the note's type.
678 Elf_Word getType() const { return Nhdr.n_type; }
679};
680
681template <class ELFT> class Elf_Note_Iterator_Impl {
682public:
683 using iterator_category = std::forward_iterator_tag;
685 using difference_type = std::ptrdiff_t;
688
689private:
690 // Nhdr being a nullptr marks the end of iteration.
691 const Elf_Nhdr_Impl<ELFT> *Nhdr = nullptr;
692 size_t RemainingSize = 0u;
693 size_t Align = 0;
694 Error *Err = nullptr;
695
696 template <class ELFFileELFT> friend class ELFFile;
697
698 // Stop iteration and indicate an overflow.
699 void stopWithOverflowError() {
700 Nhdr = nullptr;
701 *Err = make_error<StringError>("ELF note overflows container",
702 object_error::parse_failed);
703 }
704
705 // Advance Nhdr by NoteSize bytes, starting from NhdrPos.
706 //
707 // Assumes NoteSize <= RemainingSize. Ensures Nhdr->getSize() <= RemainingSize
708 // upon returning. Handles stopping iteration when reaching the end of the
709 // container, either cleanly or with an overflow error.
710 void advanceNhdr(const uint8_t *NhdrPos, size_t NoteSize) {
711 RemainingSize -= NoteSize;
712 if (RemainingSize == 0u) {
713 // Ensure that if the iterator walks to the end, the error is checked
714 // afterwards.
715 *Err = Error::success();
716 Nhdr = nullptr;
717 } else if (sizeof(*Nhdr) > RemainingSize)
718 stopWithOverflowError();
719 else {
720 Nhdr = reinterpret_cast<const Elf_Nhdr_Impl<ELFT> *>(NhdrPos + NoteSize);
721 if (Nhdr->getSize(Align) > RemainingSize)
722 stopWithOverflowError();
723 else
724 *Err = Error::success();
725 }
726 }
727
728 Elf_Note_Iterator_Impl() = default;
729 explicit Elf_Note_Iterator_Impl(Error &Err) : Err(&Err) {}
730 Elf_Note_Iterator_Impl(const uint8_t *Start, size_t Size, size_t Align,
731 Error &Err)
732 : RemainingSize(Size), Align(Align), Err(&Err) {
733 consumeError(std::move(Err));
734 assert(Start && "ELF note iterator starting at NULL");
735 advanceNhdr(Start, 0u);
736 }
737
738public:
740 assert(Nhdr && "incremented ELF note end iterator");
741 const uint8_t *NhdrPos = reinterpret_cast<const uint8_t *>(Nhdr);
742 size_t NoteSize = Nhdr->getSize(Align);
743 advanceNhdr(NhdrPos, NoteSize);
744 return *this;
745 }
747 if (!Nhdr && Other.Err)
748 (void)(bool)(*Other.Err);
749 if (!Other.Nhdr && Err)
750 (void)(bool)(*Err);
751 return Nhdr == Other.Nhdr;
752 }
754 return !(*this == Other);
755 }
757 assert(Nhdr && "dereferenced ELF note end iterator");
758 return Elf_Note_Impl<ELFT>(*Nhdr);
759 }
760};
761
762template <class ELFT> struct Elf_CGProfile_Impl {
764 Elf_Xword cgp_weight;
765};
766
767// MIPS .reginfo section
768template <class ELFT>
770
771template <llvm::endianness Endianness>
772struct Elf_Mips_RegInfo<ELFType<Endianness, false>> {
773 LLVM_ELF_IMPORT_TYPES(Endianness, false)
774 Elf_Word ri_gprmask; // bit-mask of used general registers
775 Elf_Word ri_cprmask[4]; // bit-mask of used co-processor registers
776 Elf_Addr ri_gp_value; // gp register value
777};
778
779template <llvm::endianness Endianness>
780struct Elf_Mips_RegInfo<ELFType<Endianness, true>> {
781 LLVM_ELF_IMPORT_TYPES(Endianness, true)
782 Elf_Word ri_gprmask; // bit-mask of used general registers
783 Elf_Word ri_pad; // unused padding field
784 Elf_Word ri_cprmask[4]; // bit-mask of used co-processor registers
785 Elf_Addr ri_gp_value; // gp register value
786};
787
788// .MIPS.options section
789template <class ELFT> struct Elf_Mips_Options {
791 uint8_t kind; // Determines interpretation of variable part of descriptor
792 uint8_t size; // Byte size of descriptor, including this header
793 Elf_Half section; // Section header index of section affected,
794 // or 0 for global options
795 Elf_Word info; // Kind-specific information
796
797 Elf_Mips_RegInfo<ELFT> &getRegInfo() {
798 assert(kind == ELF::ODK_REGINFO);
799 return *reinterpret_cast<Elf_Mips_RegInfo<ELFT> *>(
800 (uint8_t *)this + sizeof(Elf_Mips_Options));
801 }
803 return const_cast<Elf_Mips_Options *>(this)->getRegInfo();
804 }
805};
806
807// .MIPS.abiflags section content
808template <class ELFT> struct Elf_Mips_ABIFlags {
810 Elf_Half version; // Version of the structure
811 uint8_t isa_level; // ISA level: 1-5, 32, and 64
812 uint8_t isa_rev; // ISA revision (0 for MIPS I - MIPS V)
813 uint8_t gpr_size; // General purpose registers size
814 uint8_t cpr1_size; // Co-processor 1 registers size
815 uint8_t cpr2_size; // Co-processor 2 registers size
816 uint8_t fp_abi; // Floating-point ABI flag
817 Elf_Word isa_ext; // Processor-specific extension
818 Elf_Word ases; // ASEs flags
819 Elf_Word flags1; // General flags
820 Elf_Word flags2; // General flags
821};
822
823// Struct representing the BBAddrMap for one function.
824struct BBAddrMap {
825
826 // Bitfield of optional features to control the extra information
827 // emitted/encoded in the the section.
828 struct Features {
830 bool BBFreq : 1;
831 bool BrProb : 1;
832 bool MultiBBRange : 1;
833
834 bool hasPGOAnalysis() const { return FuncEntryCount || BBFreq || BrProb; }
835
836 bool hasPGOAnalysisBBData() const { return BBFreq || BrProb; }
837
838 // Encodes to minimum bit width representation.
839 uint8_t encode() const {
840 return (static_cast<uint8_t>(FuncEntryCount) << 0) |
841 (static_cast<uint8_t>(BBFreq) << 1) |
842 (static_cast<uint8_t>(BrProb) << 2) |
843 (static_cast<uint8_t>(MultiBBRange) << 3);
844 }
845
846 // Decodes from minimum bit width representation and validates no
847 // unnecessary bits are used.
848 static Expected<Features> decode(uint8_t Val) {
849 Features Feat{
850 static_cast<bool>(Val & (1 << 0)), static_cast<bool>(Val & (1 << 1)),
851 static_cast<bool>(Val & (1 << 2)), static_cast<bool>(Val & (1 << 3))};
852 if (Feat.encode() != Val)
853 return createStringError(
854 std::error_code(), "invalid encoding for BBAddrMap::Features: 0x%x",
855 Val);
856 return Feat;
857 }
858
859 bool operator==(const Features &Other) const {
860 return std::tie(FuncEntryCount, BBFreq, BrProb, MultiBBRange) ==
861 std::tie(Other.FuncEntryCount, Other.BBFreq, Other.BrProb,
862 Other.MultiBBRange);
863 }
864 };
865
866 // Struct representing the BBAddrMap information for one basic block.
867 struct BBEntry {
868 struct Metadata {
869 bool HasReturn : 1; // If this block ends with a return (or tail
870 // call).
871 bool HasTailCall : 1; // If this block ends with a tail call.
872 bool IsEHPad : 1; // If this is an exception handling block.
873 bool CanFallThrough : 1; // If this block can fall through to its next.
874 bool HasIndirectBranch : 1; // If this block ends with an indirect branch
875 // (branch via a register).
876
877 bool operator==(const Metadata &Other) const {
878 return HasReturn == Other.HasReturn &&
879 HasTailCall == Other.HasTailCall && IsEHPad == Other.IsEHPad &&
880 CanFallThrough == Other.CanFallThrough &&
881 HasIndirectBranch == Other.HasIndirectBranch;
882 }
883
884 // Encodes this struct as a uint32_t value.
885 uint32_t encode() const {
886 return static_cast<uint32_t>(HasReturn) |
887 (static_cast<uint32_t>(HasTailCall) << 1) |
888 (static_cast<uint32_t>(IsEHPad) << 2) |
889 (static_cast<uint32_t>(CanFallThrough) << 3) |
890 (static_cast<uint32_t>(HasIndirectBranch) << 4);
891 }
892
893 // Decodes and returns a Metadata struct from a uint32_t value.
895 Metadata MD{/*HasReturn=*/static_cast<bool>(V & 1),
896 /*HasTailCall=*/static_cast<bool>(V & (1 << 1)),
897 /*IsEHPad=*/static_cast<bool>(V & (1 << 2)),
898 /*CanFallThrough=*/static_cast<bool>(V & (1 << 3)),
899 /*HasIndirectBranch=*/static_cast<bool>(V & (1 << 4))};
900 if (MD.encode() != V)
901 return createStringError(
902 std::error_code(), "invalid encoding for BBEntry::Metadata: 0x%x",
903 V);
904 return MD;
905 }
906 };
907
908 uint32_t ID = 0; // Unique ID of this basic block.
909 uint32_t Offset = 0; // Offset of basic block relative to the base address.
910 uint32_t Size = 0; // Size of the basic block.
911 Metadata MD = {false, false, false, false,
912 false}; // Metdata for this basic block.
913
915 : ID(ID), Offset(Offset), Size(Size), MD(MD){};
916
917 bool operator==(const BBEntry &Other) const {
918 return ID == Other.ID && Offset == Other.Offset && Size == Other.Size &&
919 MD == Other.MD;
920 }
921
922 bool hasReturn() const { return MD.HasReturn; }
923 bool hasTailCall() const { return MD.HasTailCall; }
924 bool isEHPad() const { return MD.IsEHPad; }
925 bool canFallThrough() const { return MD.CanFallThrough; }
926 bool hasIndirectBranch() const { return MD.HasIndirectBranch; }
927 };
928
929 // Struct representing the BBAddrMap information for a contiguous range of
930 // basic blocks (a function or a basic block section).
932 uint64_t BaseAddress = 0; // Base address of the range.
933 std::vector<BBEntry> BBEntries; // Basic block entries for this range.
934
935 // Equality operator for unit testing.
936 bool operator==(const BBRangeEntry &Other) const {
937 return BaseAddress == Other.BaseAddress &&
938 std::equal(BBEntries.begin(), BBEntries.end(),
939 Other.BBEntries.begin());
940 }
941 };
942
943 // All ranges for this function. Cannot be empty. The first range always
944 // corresponds to the function entry.
945 std::vector<BBRangeEntry> BBRanges;
946
947 // Returns the function address associated with this BBAddrMap, which is
948 // stored as the `BaseAddress` of its first BBRangeEntry.
950 assert(!BBRanges.empty());
951 return BBRanges.front().BaseAddress;
952 }
953
954 // Returns the total number of bb entries in all bb ranges.
955 size_t getNumBBEntries() const {
956 size_t NumBBEntries = 0;
957 for (const auto &BBR : BBRanges)
958 NumBBEntries += BBR.BBEntries.size();
959 return NumBBEntries;
960 }
961
962 // Returns the index of the bb range with the given base address, or
963 // `std::nullopt` if no such range exists.
964 std::optional<size_t>
966 for (size_t I = 0; I < BBRanges.size(); ++I)
967 if (BBRanges[I].BaseAddress == BaseAddress)
968 return I;
969 return {};
970 }
971
972 // Returns bb entries in the first range.
973 const std::vector<BBEntry> &getBBEntries() const {
974 return BBRanges.front().BBEntries;
975 }
976
977 const std::vector<BBRangeEntry> &getBBRanges() const { return BBRanges; }
978
979 // Equality operator for unit testing.
980 bool operator==(const BBAddrMap &Other) const {
981 return std::equal(BBRanges.begin(), BBRanges.end(), Other.BBRanges.begin());
982 }
983};
984
985/// A feature extension of BBAddrMap that holds information relevant to PGO.
987 /// Extra basic block data with fields for block frequency and branch
988 /// probability.
989 struct PGOBBEntry {
990 /// Single successor of a given basic block that contains the tag and branch
991 /// probability associated with it.
993 /// Unique ID of this successor basic block.
995 /// Branch Probability of the edge to this successor taken from MBPI.
997
998 bool operator==(const SuccessorEntry &Other) const {
999 return std::tie(ID, Prob) == std::tie(Other.ID, Other.Prob);
1000 }
1001 };
1002
1003 /// Block frequency taken from MBFI
1005 /// List of successors of the current block
1007
1008 bool operator==(const PGOBBEntry &Other) const {
1009 return std::tie(BlockFreq, Successors) ==
1010 std::tie(Other.BlockFreq, Other.Successors);
1011 }
1012 };
1013
1014 uint64_t FuncEntryCount; // Prof count from IR function
1015 std::vector<PGOBBEntry> BBEntries; // Extended basic block entries
1016
1017 // Flags to indicate if each PGO related info was enabled in this function
1019
1020 bool operator==(const PGOAnalysisMap &Other) const {
1021 return std::tie(FuncEntryCount, BBEntries, FeatEnable) ==
1022 std::tie(Other.FuncEntryCount, Other.BBEntries, Other.FeatEnable);
1023 }
1024};
1025
1026} // end namespace object.
1027} // end namespace llvm.
1028
1029#endif // LLVM_OBJECT_ELFTYPES_H
aarch64 promote const
basic Basic Alias true
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
static bool isMips64EL(const ELFYAML::Object &Obj)
uint64_t Align
uint64_t Size
#define LLVM_ELF_IMPORT_TYPES(E, W)
Definition: ELFTypes.h:145
#define LLVM_ELF_IMPORT_TYPES_ELFT(ELFT)
Definition: ELFTypes.h:106
std::optional< std::vector< StOtherPiece > > Other
Definition: ELFYAML.cpp:1309
uint64_t Offset
Definition: ELF_riscv.cpp:478
lazy value info
#define I(x, y, z)
Definition: MD5.cpp:58
Merge contiguous icmps into a memcmp
Definition: MergeICmps.cpp:911
static StringRef getName(Value *V)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static SymbolRef::Type getType(const Symbol *Sym)
Definition: TapiFile.cpp:40
static unsigned getSize(unsigned Kind)
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition: ArrayRef.h:41
Lightweight error class with error context and mandatory checking.
Definition: Error.h:160
Tagged union holding either a T or a Error.
Definition: Error.h:481
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1209
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:50
constexpr size_t size() const
size - Get the string size.
Definition: StringRef.h:137
constexpr const char * data() const
data - Get a pointer to the start of the string (which may not be null terminated).
Definition: StringRef.h:131
StringRef getDescAsStringRef(size_t Align) const
Get the note's descriptor as StringRef.
Definition: ELFTypes.h:672
Elf_Word getType() const
Get the note's type.
Definition: ELFTypes.h:678
Elf_Note_Impl(const Elf_Nhdr_Impl< ELFT > &Nhdr)
Definition: ELFTypes.h:651
StringRef getName() const
Get the note's name, excluding the terminating null byte.
Definition: ELFTypes.h:654
ArrayRef< uint8_t > getDesc(size_t Align) const
Get the note's descriptor.
Definition: ELFTypes.h:662
bool operator!=(Elf_Note_Iterator_Impl Other) const
Definition: ELFTypes.h:753
std::forward_iterator_tag iterator_category
Definition: ELFTypes.h:683
Elf_Note_Impl< ELFT > operator*() const
Definition: ELFTypes.h:756
Elf_Note_Iterator_Impl & operator++()
Definition: ELFTypes.h:739
bool operator==(Elf_Note_Iterator_Impl Other) const
Definition: ELFTypes.h:746
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
Error createStringError(std::error_code EC, char const *Fmt, const Ts &... Vals)
Create formatted StringError object.
Definition: Error.h:1286
constexpr T alignToPowerOf2(U Value, V Align)
Will overflow only if result is not representable in T.
Definition: MathExtras.h:502
endianness
Definition: bit.h:70
void consumeError(Error Err)
Consume a Error without doing anything.
Definition: Error.h:1069
This struct is a compact representation of a valid (non-zero power of two) alignment.
Definition: Alignment.h:39
Description of the encoding of one expression Op.
static Expected< Metadata > decode(uint32_t V)
Definition: ELFTypes.h:894
bool operator==(const Metadata &Other) const
Definition: ELFTypes.h:877
bool operator==(const BBEntry &Other) const
Definition: ELFTypes.h:917
BBEntry(uint32_t ID, uint32_t Offset, uint32_t Size, Metadata MD)
Definition: ELFTypes.h:914
bool operator==(const BBRangeEntry &Other) const
Definition: ELFTypes.h:936
std::vector< BBEntry > BBEntries
Definition: ELFTypes.h:933
bool operator==(const Features &Other) const
Definition: ELFTypes.h:859
static Expected< Features > decode(uint8_t Val)
Definition: ELFTypes.h:848
const std::vector< BBRangeEntry > & getBBRanges() const
Definition: ELFTypes.h:977
std::vector< BBRangeEntry > BBRanges
Definition: ELFTypes.h:945
size_t getNumBBEntries() const
Definition: ELFTypes.h:955
bool operator==(const BBAddrMap &Other) const
Definition: ELFTypes.h:980
const std::vector< BBEntry > & getBBEntries() const
Definition: ELFTypes.h:973
uint64_t getFunctionAddress() const
Definition: ELFTypes.h:949
std::optional< size_t > getBBRangeIndexForBaseAddress(uint64_t BaseAddress) const
Definition: ELFTypes.h:965
std::conditional_t< Is64, uint64_t, uint32_t > uint
Definition: ELFTypes.h:58
static const endianness Endianness
Definition: ELFTypes.h:55
static const bool Is64Bits
Definition: ELFTypes.h:56
uint32_t getType(bool) const
Definition: ELFTypes.h:498
std::conditional_t< Is64, uint64_t, uint32_t > uint
Definition: ELFTypes.h:489
uint32_t getSymbol(bool) const
Definition: ELFTypes.h:499
void setSymbolAndType(uint32_t s, unsigned char t, bool)
Definition: ELFTypes.h:500
std::conditional_t< Is64, int64_t, int32_t > r_addend
Definition: ELFTypes.h:495
Elf_Dyn_Base: This structure matches the form of entries in the dynamic table section (....
Definition: ELFTypes.h:353
Elf_Dyn_Impl: This inherits from Elf_Dyn_Base, adding getters.
Definition: ELFTypes.h:377
uintX_t getVal() const
Definition: ELFTypes.h:383
std::conditional_t< ELFT::Is64Bits, int64_t, int32_t > intX_t
Definition: ELFTypes.h:380
std::conditional_t< ELFT::Is64Bits, uint64_t, uint32_t > uintX_t
Definition: ELFTypes.h:381
uintX_t getPtr() const
Definition: ELFTypes.h:384
intX_t getTag() const
Definition: ELFTypes.h:382
unsigned char getFileClass() const
Definition: ELFTypes.h:529
unsigned char getDataEncoding() const
Definition: ELFTypes.h:530
ArrayRef< Elf_Word > values(unsigned DynamicSymCount) const
Definition: ELFTypes.h:595
ArrayRef< Elf_Word > buckets() const
Definition: ELFTypes.h:590
ArrayRef< Elf_Word > chains() const
Definition: ELFTypes.h:570
const Elf_Mips_RegInfo< ELFT > & getRegInfo() const
Definition: ELFTypes.h:802
size_t getSize(size_t Align) const
Get the size of the note, including name, descriptor, and padding.
Definition: ELFTypes.h:632
void setSymbolAndType(uint32_t s, unsigned char t, bool IsMips64EL)
Definition: ELFTypes.h:418
void setSymbolAndType(uint32_t s, uint32_t t, bool IsMips64EL)
Definition: ELFTypes.h:473
unsigned getEntityCount() const
Get the number of entities this section contains if it has any.
Definition: ELFTypes.h:187
void setBindingAndType(unsigned char b, unsigned char t)
Definition: ELFTypes.h:233
bool isProcessorSpecific() const
Definition: ELFTypes.h:256
void setBinding(unsigned char b)
Definition: ELFTypes.h:230
unsigned char getBinding() const
Definition: ELFTypes.h:227
bool isDefined() const
Definition: ELFTypes.h:254
bool isAbsolute() const
Definition: ELFTypes.h:248
bool isOSSpecific() const
Definition: ELFTypes.h:260
unsigned char getType() const
Definition: ELFTypes.h:228
uint64_t getValue() const
Definition: ELFTypes.h:229
void setVisibility(unsigned char v)
Definition: ELFTypes.h:243
bool isExternal() const
Definition: ELFTypes.h:272
void setType(unsigned char t)
Definition: ELFTypes.h:231
bool isUndefined() const
Definition: ELFTypes.h:270
bool isReserved() const
Definition: ELFTypes.h:264
unsigned char getVisibility() const
Access to the STV_xxx flag stored in the first two bits of st_other.
Definition: ELFTypes.h:242
Elf_Verdaux: This is the structure of auxiliary data in the SHT_GNU_verdef section (....
Definition: ELFTypes.h:321
Elf_Verdef: This is the structure of entries in the SHT_GNU_verdef section (.gnu.version_d).
Definition: ELFTypes.h:302
Elf_Vernaux: This is the structure of auxiliary data in SHT_GNU_verneed section (....
Definition: ELFTypes.h:342
Elf_Verneed: This is the structure of entries in the SHT_GNU_verneed section (.gnu....
Definition: ELFTypes.h:330
Elf_Versym: This is the structure of entries in the SHT_GNU_versym section (.gnu.version).
Definition: ELFTypes.h:294
Single successor of a given basic block that contains the tag and branch probability associated with ...
Definition: ELFTypes.h:992
uint32_t ID
Unique ID of this successor basic block.
Definition: ELFTypes.h:994
BranchProbability Prob
Branch Probability of the edge to this successor taken from MBPI.
Definition: ELFTypes.h:996
bool operator==(const SuccessorEntry &Other) const
Definition: ELFTypes.h:998
Extra basic block data with fields for block frequency and branch probability.
Definition: ELFTypes.h:989
bool operator==(const PGOBBEntry &Other) const
Definition: ELFTypes.h:1008
llvm::SmallVector< SuccessorEntry, 2 > Successors
List of successors of the current block.
Definition: ELFTypes.h:1006
BlockFrequency BlockFreq
Block frequency taken from MBFI.
Definition: ELFTypes.h:1004
A feature extension of BBAddrMap that holds information relevant to PGO.
Definition: ELFTypes.h:986
bool operator==(const PGOAnalysisMap &Other) const
Definition: ELFTypes.h:1020
std::vector< PGOBBEntry > BBEntries
Definition: ELFTypes.h:1015
BBAddrMap::Features FeatEnable
Definition: ELFTypes.h:1018