23enum class DWARFSectionKindV2 {
29 DW_SECT_STR_OFFSETS = 6,
38 return ID >= DW_SECT_INFO &&
ID <= DW_SECT_RNGLISTS &&
43 unsigned IndexVersion) {
44 if (IndexVersion == 5) {
52 return static_cast<uint32_t>(DWARFSectionKindV2::DW_SECT_##T)
58 CASE(STR_OFFSETS, STR_OFFSETS);
59 CASE(EXT_MACINFO, MACINFO);
69 unsigned IndexVersion) {
70 if (IndexVersion == 5)
75 switch (
static_cast<DWARFSectionKindV2
>(
Value)) {
77 case DWARFSectionKindV2::DW_SECT_##S: \
84 CASE(STR_OFFSETS, STR_OFFSETS);
85 CASE(MACINFO, EXT_MACINFO);
94 const uint64_t BeginOffset = *OffsetPtr;
101 Version = IndexData.
getU32(OffsetPtr);
103 *OffsetPtr = BeginOffset;
104 Version = IndexData.
getU16(OffsetPtr);
109 NumColumns = IndexData.
getU32(OffsetPtr);
110 NumUnits = IndexData.
getU32(OffsetPtr);
111 NumBuckets = IndexData.
getU32(OffsetPtr);
115void DWARFUnitIndex::Header::dump(raw_ostream &OS)
const {
116 OS <<
format(
"version = %u, units = %u, slots = %u\n\n",
Version, NumUnits, NumBuckets);
120 bool b = parseImpl(IndexData);
123 Header.NumBuckets = 0;
133 if (!Header.parse(IndexData, &
Offset))
137 if (Header.Version == 5)
138 InfoColumnKind = DW_SECT_INFO;
141 Offset, Header.NumBuckets * (8 + 4) +
142 (2 * Header.NumUnits + 1) * 4 * Header.NumColumns))
145 Rows = std::make_unique<Entry[]>(Header.NumBuckets);
147 std::make_unique<Entry::SectionContribution *[]>(Header.NumUnits);
148 ColumnKinds = std::make_unique<DWARFSectionKind[]>(Header.NumColumns);
149 RawSectionIds = std::make_unique<uint32_t[]>(Header.NumColumns);
152 for (
unsigned i = 0; i != Header.NumBuckets; ++i)
156 for (
unsigned i = 0; i != Header.NumBuckets; ++i) {
160 Rows[i].Index =
this;
161 Rows[i].Contributions =
162 std::make_unique<Entry::SectionContribution[]>(Header.NumColumns);
163 Contribs[Index - 1] = Rows[i].Contributions.get();
167 for (
unsigned i = 0; i != Header.NumColumns; ++i) {
170 if (ColumnKinds[i] == InfoColumnKind) {
171 if (InfoColumn != -1)
177 if (InfoColumn == -1)
181 for (
unsigned i = 0; i != Header.NumUnits; ++i) {
182 auto *Contrib = Contribs[i];
183 for (
unsigned i = 0; i != Header.NumColumns; ++i)
188 for (
unsigned i = 0; i != Header.NumUnits; ++i) {
189 auto *Contrib = Contribs[i];
190 for (
unsigned i = 0; i != Header.NumColumns; ++i)
199#define HANDLE_DW_SECT(ID, NAME) \
200 case DW_SECT_##NAME: \
202#include "llvm/BinaryFormat/Dwarf.def"
220 OS <<
"Index Signature ";
221 for (
unsigned i = 0; i != Header.NumColumns; ++i) {
227 Kind == DWARFSectionKind::DW_SECT_INFO ? 40 : 24);
229 OS <<
format(
" Unknown: %-15" PRIu32, RawSectionIds[i]);
231 OS <<
"\n----- ------------------";
232 for (
unsigned i = 0; i != Header.NumColumns; ++i) {
234 if (Kind == DWARFSectionKind::DW_SECT_INFO ||
236 OS <<
" ----------------------------------------";
238 OS <<
" ------------------------";
241 for (
unsigned i = 0; i != Header.NumBuckets; ++i) {
243 if (
auto *Contribs = Row.Contributions.get()) {
244 OS <<
format(
"%5u 0x%016" PRIx64
" ", i + 1, Row.Signature);
245 for (
unsigned i = 0; i != Header.NumColumns; ++i) {
246 auto &Contrib = Contribs[i];
248 if (Kind == DWARFSectionKind::DW_SECT_INFO ||
250 OS <<
format(
"[0x%016" PRIx64
", 0x%016" PRIx64
") ",
252 Contrib.getOffset() + Contrib.getLength());
254 OS <<
format(
"[0x%08" PRIx32
", 0x%08" PRIx32
") ",
255 Contrib.getOffset32(),
256 Contrib.getOffset32() + Contrib.getLength32());
266 for (; i != Index->Header.NumColumns; ++i)
267 if (Index->ColumnKinds[i] == Sec)
268 return &Contributions[i];
274 return Contributions[Index->InfoColumn];
279 return &Contributions[Index->InfoColumn];
284 if (OffsetLookup.empty()) {
285 for (
uint32_t i = 0; i != Header.NumBuckets; ++i)
286 if (Rows[i].Contributions)
287 OffsetLookup.push_back(&Rows[i]);
289 return E1->Contributions[InfoColumn].getOffset() <
290 E2->Contributions[InfoColumn].getOffset();
294 return E2->Contributions[InfoColumn].getOffset() <=
Offset;
296 if (
I == OffsetLookup.begin())
300 const auto &InfoContrib = E->Contributions[InfoColumn];
301 if ((InfoContrib.getOffset() + InfoContrib.getLength()) <=
Offset)
307 uint64_t Mask = Header.NumBuckets - 1;
310 auto HP = ((S >> 32) & Mask) | 1;
318 if (Rows[
H].Index ==
nullptr)
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
constexpr bool isKnownV5SectionID(uint32_t ID)
static std::string getSignature(FunctionType *FTy)
LLVM_ABI const SectionContribution * getContribution() const
LLVM_ABI void dump(raw_ostream &OS) const
LLVM_ABI bool parse(DataExtractor IndexData)
LLVM_ABI const Entry * getFromHash(uint64_t Offset) const
LLVM_ABI const Entry * getFromOffset(uint64_t Offset) const
StringRef - Represent a constant reference to a string, i.e.
LLVM Value Representation.
This class implements an extremely fast bulk output stream that can only output to a stream.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
This is an optimization pass for GlobalISel generic memory operations.
auto partition_point(R &&Range, Predicate P)
Binary search for the first iterator in a range where a predicate is false.
LLVM_ABI DWARFSectionKind deserializeSectionKind(uint32_t Value, unsigned IndexVersion)
Convert a value read from an index section to the internal representation.
DWARFSectionKind
The enum of section identifiers to be used in internal interfaces.
@ DW_SECT_EXT_unknown
Denotes a value read from an index section that does not correspond to any of the supported standards...
LLVM_ABI uint32_t serializeSectionKind(DWARFSectionKind Kind, unsigned IndexVersion)
Convert the internal value for a section kind to an on-disk value.
FunctionAddr VTableAddr uintptr_t uintptr_t Version
void sort(IteratorTy Start, IteratorTy End)
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.
FormattedString left_justify(StringRef Str, unsigned Width)
left_justify - append spaces after string so total output is Width characters.