LLVM  15.0.0git
DWP.cpp
Go to the documentation of this file.
1 //===-- llvm-dwp.cpp - Split DWARF merging tool for llvm ------------------===//
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 // A utility for merging DWARF 5 Split DWARF .dwo files into .dwp (DWARF
10 // package files).
11 //
12 //===----------------------------------------------------------------------===//
13 #include "llvm/DWP/DWP.h"
14 #include "llvm/DWP/DWPError.h"
15 #include "llvm/MC/MCContext.h"
20 
21 using namespace llvm;
22 using namespace llvm::object;
23 
25 
26 // Returns the size of debug_str_offsets section headers in bytes.
28  uint16_t DwarfVersion) {
29  if (DwarfVersion <= 4)
30  return 0; // There is no header before dwarf 5.
31  uint64_t Offset = 0;
32  uint64_t Length = StrOffsetsData.getU32(&Offset);
33  if (Length == llvm::dwarf::DW_LENGTH_DWARF64)
34  return 16; // unit length: 12 bytes, version: 2 bytes, padding: 2 bytes.
35  return 8; // unit length: 4 bytes, version: 2 bytes, padding: 2 bytes.
36 }
37 
38 static uint64_t getCUAbbrev(StringRef Abbrev, uint64_t AbbrCode) {
39  uint64_t Offset = 0;
40  DataExtractor AbbrevData(Abbrev, true, 0);
41  while (AbbrevData.getULEB128(&Offset) != AbbrCode) {
42  // Tag
43  AbbrevData.getULEB128(&Offset);
44  // DW_CHILDREN
45  AbbrevData.getU8(&Offset);
46  // Attributes
47  while (AbbrevData.getULEB128(&Offset) | AbbrevData.getULEB128(&Offset))
48  ;
49  }
50  return Offset;
51 }
52 
55  StringRef StrOffsets, StringRef Str, uint16_t Version) {
56  if (Form == dwarf::DW_FORM_string)
57  return InfoData.getCStr(&InfoOffset);
58  uint64_t StrIndex;
59  switch (Form) {
60  case dwarf::DW_FORM_strx1:
61  StrIndex = InfoData.getU8(&InfoOffset);
62  break;
63  case dwarf::DW_FORM_strx2:
64  StrIndex = InfoData.getU16(&InfoOffset);
65  break;
66  case dwarf::DW_FORM_strx3:
67  StrIndex = InfoData.getU24(&InfoOffset);
68  break;
69  case dwarf::DW_FORM_strx4:
70  StrIndex = InfoData.getU32(&InfoOffset);
71  break;
72  case dwarf::DW_FORM_strx:
73  case dwarf::DW_FORM_GNU_str_index:
74  StrIndex = InfoData.getULEB128(&InfoOffset);
75  break;
76  default:
77  return make_error<DWPError>(
78  "string field must be encoded with one of the following: "
79  "DW_FORM_string, DW_FORM_strx, DW_FORM_strx1, DW_FORM_strx2, "
80  "DW_FORM_strx3, DW_FORM_strx4, or DW_FORM_GNU_str_index.");
81  }
82  DataExtractor StrOffsetsData(StrOffsets, true, 0);
83  uint64_t StrOffsetsOffset = 4 * StrIndex;
84  StrOffsetsOffset += debugStrOffsetsHeaderSize(StrOffsetsData, Version);
85 
86  uint64_t StrOffset = StrOffsetsData.getU32(&StrOffsetsOffset);
87  DataExtractor StrData(Str, true, 0);
88  return StrData.getCStr(&StrOffset);
89 }
90 
93  StringRef Info, StringRef StrOffsets, StringRef Str) {
94  DataExtractor InfoData(Info, true, 0);
95  uint64_t Offset = Header.HeaderSize;
96  if (Header.Version >= 5 && Header.UnitType != dwarf::DW_UT_split_compile)
97  return make_error<DWPError>(
98  std::string("unit type DW_UT_split_compile type not found in "
99  "debug_info header. Unexpected unit type 0x" +
100  utostr(Header.UnitType) + " found"));
101 
103 
104  uint32_t AbbrCode = InfoData.getULEB128(&Offset);
105  DataExtractor AbbrevData(Abbrev, true, 0);
106  uint64_t AbbrevOffset = getCUAbbrev(Abbrev, AbbrCode);
107  auto Tag = static_cast<dwarf::Tag>(AbbrevData.getULEB128(&AbbrevOffset));
108  if (Tag != dwarf::DW_TAG_compile_unit)
109  return make_error<DWPError>("top level DIE is not a compile unit");
110  // DW_CHILDREN
111  AbbrevData.getU8(&AbbrevOffset);
112  uint32_t Name;
114  while ((Name = AbbrevData.getULEB128(&AbbrevOffset)) |
115  (Form = static_cast<dwarf::Form>(
116  AbbrevData.getULEB128(&AbbrevOffset))) &&
117  (Name != 0 || Form != 0)) {
118  switch (Name) {
119  case dwarf::DW_AT_name: {
121  Form, InfoData, Offset, StrOffsets, Str, Header.Version);
122  if (!EName)
123  return EName.takeError();
124  ID.Name = *EName;
125  break;
126  }
127  case dwarf::DW_AT_GNU_dwo_name:
128  case dwarf::DW_AT_dwo_name: {
130  Form, InfoData, Offset, StrOffsets, Str, Header.Version);
131  if (!EName)
132  return EName.takeError();
133  ID.DWOName = *EName;
134  break;
135  }
136  case dwarf::DW_AT_GNU_dwo_id:
137  Header.Signature = InfoData.getU64(&Offset);
138  break;
139  default:
141  Form, InfoData, &Offset,
142  dwarf::FormParams({Header.Version, Header.AddrSize, Header.Format}));
143  }
144  }
145  if (!Header.Signature)
146  return make_error<DWPError>("compile unit missing dwo_id");
147  ID.Signature = *Header.Signature;
148  return ID;
149 }
150 
152  return Kind != DW_SECT_EXT_unknown;
153 }
154 
155 namespace llvm {
156 // Convert an internal section identifier into the index to use with
157 // UnitIndexEntry::Contributions.
159  assert(serializeSectionKind(Kind, IndexVersion) >= DW_SECT_INFO);
160  return serializeSectionKind(Kind, IndexVersion) - DW_SECT_INFO;
161 }
162 } // namespace llvm
163 
164 // Convert a UnitIndexEntry::Contributions index to the corresponding on-disk
165 // value of the section identifier.
166 static unsigned getOnDiskSectionId(unsigned Index) {
167  return Index + DW_SECT_INFO;
168 }
169 
171  const DWARFUnitIndex::Entry &Entry,
173  const auto *Off = Entry.getContribution(Kind);
174  if (!Off)
175  return StringRef();
176  return Section.substr(Off->Offset, Off->Length);
177 }
178 
179 static void
181  MapVector<uint64_t, UnitIndexEntry> &TypeIndexEntries,
182  const DWARFUnitIndex &TUIndex, MCSection *OutputTypes,
183  StringRef Types, const UnitIndexEntry &TUEntry,
184  uint32_t &TypesOffset, unsigned TypesContributionIndex) {
185  Out.SwitchSection(OutputTypes);
186  for (const DWARFUnitIndex::Entry &E : TUIndex.getRows()) {
187  auto *I = E.getContributions();
188  if (!I)
189  continue;
190  auto P = TypeIndexEntries.insert(std::make_pair(E.getSignature(), TUEntry));
191  if (!P.second)
192  continue;
193  auto &Entry = P.first->second;
194  // Zero out the debug_info contribution
195  Entry.Contributions[0] = {};
196  for (auto Kind : TUIndex.getColumnKinds()) {
198  continue;
199  auto &C =
200  Entry.Contributions[getContributionIndex(Kind, TUIndex.getVersion())];
201  C.Offset += I->Offset;
202  C.Length = I->Length;
203  ++I;
204  }
205  auto &C = Entry.Contributions[TypesContributionIndex];
206  Out.emitBytes(Types.substr(
207  C.Offset - TUEntry.Contributions[TypesContributionIndex].Offset,
208  C.Length));
209  C.Offset = TypesOffset;
210  TypesOffset += C.Length;
211  }
212 }
213 
215  MCStreamer &Out, MapVector<uint64_t, UnitIndexEntry> &TypeIndexEntries,
216  MCSection *OutputTypes, const std::vector<StringRef> &TypesSections,
217  const UnitIndexEntry &CUEntry, uint32_t &TypesOffset) {
218  for (StringRef Types : TypesSections) {
219  Out.SwitchSection(OutputTypes);
220  uint64_t Offset = 0;
221  DataExtractor Data(Types, true, 0);
222  while (Data.isValidOffset(Offset)) {
223  UnitIndexEntry Entry = CUEntry;
224  // Zero out the debug_info contribution
225  Entry.Contributions[0] = {};
226  auto &C = Entry.Contributions[getContributionIndex(DW_SECT_EXT_TYPES, 2)];
227  C.Offset = TypesOffset;
228  auto PrevOffset = Offset;
229  // Length of the unit, including the 4 byte length field.
230  C.Length = Data.getU32(&Offset) + 4;
231 
232  Data.getU16(&Offset); // Version
233  Data.getU32(&Offset); // Abbrev offset
234  Data.getU8(&Offset); // Address size
235  auto Signature = Data.getU64(&Offset);
236  Offset = PrevOffset + C.Length;
237 
238  auto P = TypeIndexEntries.insert(std::make_pair(Signature, Entry));
239  if (!P.second)
240  continue;
241 
242  Out.emitBytes(Types.substr(PrevOffset, C.Length));
243  TypesOffset += C.Length;
244  }
245  }
246 }
247 
248 static std::string buildDWODescription(StringRef Name, StringRef DWPName,
249  StringRef DWOName) {
250  std::string Text = "\'";
251  Text += Name;
252  Text += '\'';
253  if (!DWPName.empty()) {
254  Text += " (from ";
255  if (!DWOName.empty()) {
256  Text += '\'';
257  Text += DWOName;
258  Text += "' in ";
259  }
260  Text += '\'';
261  Text += DWPName;
262  Text += "')";
263  }
264  return Text;
265 }
266 
268  return make_error<DWPError>(
269  ("failure while decompressing compressed section: '" + Name + "', " +
271  .str());
272 }
273 
274 static Error
275 handleCompressedSection(std::deque<SmallString<32>> &UncompressedSections,
276  StringRef &Name, StringRef &Contents) {
278  return Error::success();
279 
281  Decompressor::create(Name, Contents, false /*IsLE*/, false /*Is64Bit*/);
282  if (!Dec)
283  return createError(Name, Dec.takeError());
284 
285  UncompressedSections.emplace_back();
286  if (Error E = Dec->resizeAndDecompress(UncompressedSections.back()))
287  return createError(Name, std::move(E));
288 
289  Name = Name.substr(2); // Drop ".z"
290  Contents = UncompressedSections.back();
291  return Error::success();
292 }
293 
294 namespace llvm {
295 // Parse and return the header of an info section compile/type unit.
297  InfoSectionUnitHeader Header;
298  Error Err = Error::success();
299  uint64_t Offset = 0;
300  DWARFDataExtractor InfoData(Info, true, 0);
301  std::tie(Header.Length, Header.Format) =
302  InfoData.getInitialLength(&Offset, &Err);
303  if (Err)
304  return make_error<DWPError>("cannot parse compile unit length: " +
305  llvm::toString(std::move(Err)));
306 
307  if (!InfoData.isValidOffset(Offset + (Header.Length - 1))) {
308  return make_error<DWPError>(
309  "compile unit exceeds .debug_info section range: " +
310  utostr(Offset + Header.Length) + " >= " + utostr(InfoData.size()));
311  }
312 
313  Header.Version = InfoData.getU16(&Offset, &Err);
314  if (Err)
315  return make_error<DWPError>("cannot parse compile unit version: " +
316  llvm::toString(std::move(Err)));
317 
318  uint64_t MinHeaderLength;
319  if (Header.Version >= 5) {
320  // Size: Version (2), UnitType (1), AddrSize (1), DebugAbbrevOffset (4),
321  // Signature (8)
322  MinHeaderLength = 16;
323  } else {
324  // Size: Version (2), DebugAbbrevOffset (4), AddrSize (1)
325  MinHeaderLength = 7;
326  }
327  if (Header.Length < MinHeaderLength) {
328  return make_error<DWPError>("unit length is too small: expected at least " +
329  utostr(MinHeaderLength) + " got " +
330  utostr(Header.Length) + ".");
331  }
332  if (Header.Version >= 5) {
333  Header.UnitType = InfoData.getU8(&Offset);
334  Header.AddrSize = InfoData.getU8(&Offset);
335  Header.DebugAbbrevOffset = InfoData.getU32(&Offset);
336  Header.Signature = InfoData.getU64(&Offset);
337  if (Header.UnitType == dwarf::DW_UT_split_type) {
338  // Type offset.
339  MinHeaderLength += 4;
340  if (Header.Length < MinHeaderLength)
341  return make_error<DWPError>("type unit is missing type offset");
342  InfoData.getU32(&Offset);
343  }
344  } else {
345  // Note that, address_size and debug_abbrev_offset fields have switched
346  // places between dwarf version 4 and 5.
347  Header.DebugAbbrevOffset = InfoData.getU32(&Offset);
348  Header.AddrSize = InfoData.getU8(&Offset);
349  }
350 
351  Header.HeaderSize = Offset;
352  return Header;
353 }
354 
356  MCSection *StrOffsetSection,
357  StringRef CurStrSection,
358  StringRef CurStrOffsetSection, uint16_t Version) {
359  // Could possibly produce an error or warning if one of these was non-null but
360  // the other was null.
361  if (CurStrSection.empty() || CurStrOffsetSection.empty())
362  return;
363 
364  DenseMap<uint64_t, uint32_t> OffsetRemapping;
365 
366  DataExtractor Data(CurStrSection, true, 0);
367  uint64_t LocalOffset = 0;
368  uint64_t PrevOffset = 0;
369  while (const char *S = Data.getCStr(&LocalOffset)) {
370  OffsetRemapping[PrevOffset] =
371  Strings.getOffset(S, LocalOffset - PrevOffset);
372  PrevOffset = LocalOffset;
373  }
374 
375  Data = DataExtractor(CurStrOffsetSection, true, 0);
376 
377  Out.SwitchSection(StrOffsetSection);
378 
380  uint64_t Offset = 0;
381  uint64_t Size = CurStrOffsetSection.size();
382  // FIXME: This can be caused by bad input and should be handled as such.
383  assert(HeaderSize <= Size && "StrOffsetSection size is less than its header");
384  // Copy the header to the output.
385  Out.emitBytes(Data.getBytes(&Offset, HeaderSize));
386  while (Offset < Size) {
387  auto OldOffset = Data.getU32(&Offset);
388  auto NewOffset = OffsetRemapping[OldOffset];
389  Out.emitIntValue(NewOffset, 4);
390  }
391 }
392 
394  MCStreamer &Out, ArrayRef<unsigned> ContributionOffsets,
395  const MapVector<uint64_t, UnitIndexEntry> &IndexEntries,
397  for (const auto &E : IndexEntries)
398  for (size_t I = 0; I != array_lengthof(E.second.Contributions); ++I)
399  if (ContributionOffsets[I])
400  Out.emitIntValue(E.second.Contributions[I].*Field, 4);
401 }
402 
403 void writeIndex(MCStreamer &Out, MCSection *Section,
404  ArrayRef<unsigned> ContributionOffsets,
405  const MapVector<uint64_t, UnitIndexEntry> &IndexEntries,
406  uint32_t IndexVersion) {
407  if (IndexEntries.empty())
408  return;
409 
410  unsigned Columns = 0;
411  for (auto &C : ContributionOffsets)
412  if (C)
413  ++Columns;
414 
415  std::vector<unsigned> Buckets(NextPowerOf2(3 * IndexEntries.size() / 2));
416  uint64_t Mask = Buckets.size() - 1;
417  size_t I = 0;
418  for (const auto &P : IndexEntries) {
419  auto S = P.first;
420  auto H = S & Mask;
421  auto HP = ((S >> 32) & Mask) | 1;
422  while (Buckets[H]) {
423  assert(S != IndexEntries.begin()[Buckets[H] - 1].first &&
424  "Duplicate unit");
425  H = (H + HP) & Mask;
426  }
427  Buckets[H] = I + 1;
428  ++I;
429  }
430 
431  Out.SwitchSection(Section);
432  Out.emitIntValue(IndexVersion, 4); // Version
433  Out.emitIntValue(Columns, 4); // Columns
434  Out.emitIntValue(IndexEntries.size(), 4); // Num Units
435  Out.emitIntValue(Buckets.size(), 4); // Num Buckets
436 
437  // Write the signatures.
438  for (const auto &I : Buckets)
439  Out.emitIntValue(I ? IndexEntries.begin()[I - 1].first : 0, 8);
440 
441  // Write the indexes.
442  for (const auto &I : Buckets)
443  Out.emitIntValue(I, 4);
444 
445  // Write the column headers (which sections will appear in the table)
446  for (size_t I = 0; I != ContributionOffsets.size(); ++I)
447  if (ContributionOffsets[I])
449 
450  // Write the offsets.
451  writeIndexTable(Out, ContributionOffsets, IndexEntries,
453 
454  // Write the lengths.
455  writeIndexTable(Out, ContributionOffsets, IndexEntries,
457 }
458 
459 Error buildDuplicateError(const std::pair<uint64_t, UnitIndexEntry> &PrevE,
460  const CompileUnitIdentifiers &ID, StringRef DWPName) {
461  return make_error<DWPError>(
462  std::string("duplicate DWO ID (") + utohexstr(PrevE.first) + ") in " +
463  buildDWODescription(PrevE.second.Name, PrevE.second.DWPName,
464  PrevE.second.DWOName) +
465  " and " + buildDWODescription(ID.Name, DWPName, ID.DWOName));
466 }
467 
469  const StringMap<std::pair<MCSection *, DWARFSectionKind>> &KnownSections,
470  const MCSection *StrSection, const MCSection *StrOffsetSection,
471  const MCSection *TypesSection, const MCSection *CUIndexSection,
472  const MCSection *TUIndexSection, const MCSection *InfoSection,
473  const SectionRef &Section, MCStreamer &Out,
474  std::deque<SmallString<32>> &UncompressedSections,
475  uint32_t (&ContributionOffsets)[8], UnitIndexEntry &CurEntry,
476  StringRef &CurStrSection, StringRef &CurStrOffsetSection,
477  std::vector<StringRef> &CurTypesSection,
478  std::vector<StringRef> &CurInfoSection, StringRef &AbbrevSection,
479  StringRef &CurCUIndexSection, StringRef &CurTUIndexSection,
480  std::vector<std::pair<DWARFSectionKind, uint32_t>> &SectionLength) {
481  if (Section.isBSS())
482  return Error::success();
483 
484  if (Section.isVirtual())
485  return Error::success();
486 
487  Expected<StringRef> NameOrErr = Section.getName();
488  if (!NameOrErr)
489  return NameOrErr.takeError();
490  StringRef Name = *NameOrErr;
491 
492  Expected<StringRef> ContentsOrErr = Section.getContents();
493  if (!ContentsOrErr)
494  return ContentsOrErr.takeError();
495  StringRef Contents = *ContentsOrErr;
496 
497  if (auto Err = handleCompressedSection(UncompressedSections, Name, Contents))
498  return Err;
499 
500  Name = Name.substr(Name.find_first_not_of("._"));
501 
502  auto SectionPair = KnownSections.find(Name);
503  if (SectionPair == KnownSections.end())
504  return Error::success();
505 
506  if (DWARFSectionKind Kind = SectionPair->second.second) {
507  if (Kind != DW_SECT_EXT_TYPES && Kind != DW_SECT_INFO) {
508  SectionLength.push_back(std::make_pair(Kind, Contents.size()));
509  }
510 
511  if (Kind == DW_SECT_ABBREV) {
512  AbbrevSection = Contents;
513  }
514  }
515 
516  MCSection *OutSection = SectionPair->second.first;
517  if (OutSection == StrOffsetSection)
518  CurStrOffsetSection = Contents;
519  else if (OutSection == StrSection)
520  CurStrSection = Contents;
521  else if (OutSection == TypesSection)
522  CurTypesSection.push_back(Contents);
523  else if (OutSection == CUIndexSection)
524  CurCUIndexSection = Contents;
525  else if (OutSection == TUIndexSection)
526  CurTUIndexSection = Contents;
527  else if (OutSection == InfoSection)
528  CurInfoSection.push_back(Contents);
529  else {
530  Out.SwitchSection(OutSection);
531  Out.emitBytes(Contents);
532  }
533  return Error::success();
534 }
535 
537  const auto &MCOFI = *Out.getContext().getObjectFileInfo();
538  MCSection *const StrSection = MCOFI.getDwarfStrDWOSection();
539  MCSection *const StrOffsetSection = MCOFI.getDwarfStrOffDWOSection();
540  MCSection *const TypesSection = MCOFI.getDwarfTypesDWOSection();
541  MCSection *const CUIndexSection = MCOFI.getDwarfCUIndexSection();
542  MCSection *const TUIndexSection = MCOFI.getDwarfTUIndexSection();
543  MCSection *const InfoSection = MCOFI.getDwarfInfoDWOSection();
545  {"debug_info.dwo", {InfoSection, DW_SECT_INFO}},
546  {"debug_types.dwo", {MCOFI.getDwarfTypesDWOSection(), DW_SECT_EXT_TYPES}},
547  {"debug_str_offsets.dwo", {StrOffsetSection, DW_SECT_STR_OFFSETS}},
548  {"debug_str.dwo", {StrSection, static_cast<DWARFSectionKind>(0)}},
549  {"debug_loc.dwo", {MCOFI.getDwarfLocDWOSection(), DW_SECT_EXT_LOC}},
550  {"debug_line.dwo", {MCOFI.getDwarfLineDWOSection(), DW_SECT_LINE}},
551  {"debug_macro.dwo", {MCOFI.getDwarfMacroDWOSection(), DW_SECT_MACRO}},
552  {"debug_abbrev.dwo", {MCOFI.getDwarfAbbrevDWOSection(), DW_SECT_ABBREV}},
553  {"debug_loclists.dwo",
554  {MCOFI.getDwarfLoclistsDWOSection(), DW_SECT_LOCLISTS}},
555  {"debug_rnglists.dwo",
556  {MCOFI.getDwarfRnglistsDWOSection(), DW_SECT_RNGLISTS}},
557  {"debug_cu_index", {CUIndexSection, static_cast<DWARFSectionKind>(0)}},
558  {"debug_tu_index", {TUIndexSection, static_cast<DWARFSectionKind>(0)}}};
559 
561  MapVector<uint64_t, UnitIndexEntry> TypeIndexEntries;
562 
563  uint32_t ContributionOffsets[8] = {};
564  uint16_t Version = 0;
565  uint32_t IndexVersion = 0;
566 
567  DWPStringPool Strings(Out, StrSection);
568 
570  Objects.reserve(Inputs.size());
571 
572  std::deque<SmallString<32>> UncompressedSections;
573 
574  for (const auto &Input : Inputs) {
575  auto ErrOrObj = object::ObjectFile::createObjectFile(Input);
576  if (!ErrOrObj)
577  return ErrOrObj.takeError();
578 
579  auto &Obj = *ErrOrObj->getBinary();
580  Objects.push_back(std::move(*ErrOrObj));
581 
582  UnitIndexEntry CurEntry = {};
583 
584  StringRef CurStrSection;
585  StringRef CurStrOffsetSection;
586  std::vector<StringRef> CurTypesSection;
587  std::vector<StringRef> CurInfoSection;
588  StringRef AbbrevSection;
589  StringRef CurCUIndexSection;
590  StringRef CurTUIndexSection;
591 
592  // This maps each section contained in this file to its length.
593  // This information is later on used to calculate the contributions,
594  // i.e. offset and length, of each compile/type unit to a section.
595  std::vector<std::pair<DWARFSectionKind, uint32_t>> SectionLength;
596 
597  for (const auto &Section : Obj.sections())
598  if (auto Err = handleSection(
599  KnownSections, StrSection, StrOffsetSection, TypesSection,
600  CUIndexSection, TUIndexSection, InfoSection, Section, Out,
601  UncompressedSections, ContributionOffsets, CurEntry,
602  CurStrSection, CurStrOffsetSection, CurTypesSection,
603  CurInfoSection, AbbrevSection, CurCUIndexSection,
604  CurTUIndexSection, SectionLength))
605  return Err;
606 
607  if (CurInfoSection.empty())
608  continue;
609 
610  Expected<InfoSectionUnitHeader> HeaderOrErr =
611  parseInfoSectionUnitHeader(CurInfoSection.front());
612  if (!HeaderOrErr)
613  return HeaderOrErr.takeError();
614  InfoSectionUnitHeader &Header = *HeaderOrErr;
615 
616  if (Version == 0) {
617  Version = Header.Version;
618  IndexVersion = Version < 5 ? 2 : 5;
619  } else if (Version != Header.Version) {
620  return make_error<DWPError>("incompatible DWARF compile unit versions.");
621  }
622 
623  writeStringsAndOffsets(Out, Strings, StrOffsetSection, CurStrSection,
624  CurStrOffsetSection, Header.Version);
625 
626  for (auto Pair : SectionLength) {
627  auto Index = getContributionIndex(Pair.first, IndexVersion);
628  CurEntry.Contributions[Index].Offset = ContributionOffsets[Index];
629  ContributionOffsets[Index] +=
630  (CurEntry.Contributions[Index].Length = Pair.second);
631  }
632 
633  uint32_t &InfoSectionOffset =
634  ContributionOffsets[getContributionIndex(DW_SECT_INFO, IndexVersion)];
635  if (CurCUIndexSection.empty()) {
636  bool FoundCUUnit = false;
637  Out.SwitchSection(InfoSection);
638  for (StringRef Info : CurInfoSection) {
639  uint64_t UnitOffset = 0;
640  while (Info.size() > UnitOffset) {
641  Expected<InfoSectionUnitHeader> HeaderOrError =
642  parseInfoSectionUnitHeader(Info.substr(UnitOffset, Info.size()));
643  if (!HeaderOrError)
644  return HeaderOrError.takeError();
645  InfoSectionUnitHeader &Header = *HeaderOrError;
646 
647  UnitIndexEntry Entry = CurEntry;
648  auto &C = Entry.Contributions[getContributionIndex(DW_SECT_INFO,
649  IndexVersion)];
650  C.Offset = InfoSectionOffset;
651  C.Length = Header.Length + 4;
652  UnitOffset += C.Length;
653  if (Header.Version < 5 ||
654  Header.UnitType == dwarf::DW_UT_split_compile) {
656  getCUIdentifiers(Header, AbbrevSection,
657  Info.substr(UnitOffset - C.Length, C.Length),
658  CurStrOffsetSection, CurStrSection);
659 
660  if (!EID)
661  return createFileError(Input, EID.takeError());
662  const auto &ID = *EID;
663  auto P = IndexEntries.insert(std::make_pair(ID.Signature, Entry));
664  if (!P.second)
665  return buildDuplicateError(*P.first, ID, "");
666  P.first->second.Name = ID.Name;
667  P.first->second.DWOName = ID.DWOName;
668 
669  FoundCUUnit = true;
670  } else if (Header.UnitType == dwarf::DW_UT_split_type) {
671  auto P = TypeIndexEntries.insert(
672  std::make_pair(Header.Signature.getValue(), Entry));
673  if (!P.second)
674  continue;
675  }
676  Out.emitBytes(Info.substr(UnitOffset - C.Length, C.Length));
677  InfoSectionOffset += C.Length;
678  }
679  }
680 
681  if (!FoundCUUnit)
682  return make_error<DWPError>("no compile unit found in file: " + Input);
683 
684  if (IndexVersion == 2) {
685  // Add types from the .debug_types section from DWARF < 5.
687  Out, TypeIndexEntries, TypesSection, CurTypesSection, CurEntry,
688  ContributionOffsets[getContributionIndex(DW_SECT_EXT_TYPES, 2)]);
689  }
690  continue;
691  }
692 
693  if (CurInfoSection.size() != 1)
694  return make_error<DWPError>("expected exactly one occurrence of a debug "
695  "info section in a .dwp file");
696  StringRef DwpSingleInfoSection = CurInfoSection.front();
697 
698  DWARFUnitIndex CUIndex(DW_SECT_INFO);
699  DataExtractor CUIndexData(CurCUIndexSection, Obj.isLittleEndian(), 0);
700  if (!CUIndex.parse(CUIndexData))
701  return make_error<DWPError>("failed to parse cu_index");
702  if (CUIndex.getVersion() != IndexVersion)
703  return make_error<DWPError>("incompatible cu_index versions, found " +
704  utostr(CUIndex.getVersion()) +
705  " and expecting " + utostr(IndexVersion));
706 
707  Out.SwitchSection(InfoSection);
708  for (const DWARFUnitIndex::Entry &E : CUIndex.getRows()) {
709  auto *I = E.getContributions();
710  if (!I)
711  continue;
712  auto P = IndexEntries.insert(std::make_pair(E.getSignature(), CurEntry));
713  StringRef CUInfoSection =
714  getSubsection(DwpSingleInfoSection, E, DW_SECT_INFO);
715  Expected<InfoSectionUnitHeader> HeaderOrError =
716  parseInfoSectionUnitHeader(CUInfoSection);
717  if (!HeaderOrError)
718  return HeaderOrError.takeError();
719  InfoSectionUnitHeader &Header = *HeaderOrError;
720 
722  Header, getSubsection(AbbrevSection, E, DW_SECT_ABBREV),
723  CUInfoSection,
724  getSubsection(CurStrOffsetSection, E, DW_SECT_STR_OFFSETS),
725  CurStrSection);
726  if (!EID)
727  return createFileError(Input, EID.takeError());
728  const auto &ID = *EID;
729  if (!P.second)
730  return buildDuplicateError(*P.first, ID, Input);
731  auto &NewEntry = P.first->second;
732  NewEntry.Name = ID.Name;
733  NewEntry.DWOName = ID.DWOName;
734  NewEntry.DWPName = Input;
735  for (auto Kind : CUIndex.getColumnKinds()) {
737  continue;
738  auto &C =
739  NewEntry.Contributions[getContributionIndex(Kind, IndexVersion)];
740  C.Offset += I->Offset;
741  C.Length = I->Length;
742  ++I;
743  }
744  unsigned Index = getContributionIndex(DW_SECT_INFO, IndexVersion);
745  auto &C = NewEntry.Contributions[Index];
746  Out.emitBytes(CUInfoSection);
747  C.Offset = InfoSectionOffset;
748  InfoSectionOffset += C.Length;
749  }
750 
751  if (!CurTUIndexSection.empty()) {
752  llvm::DWARFSectionKind TUSectionKind;
753  MCSection *OutSection;
754  StringRef TypeInputSection;
755  // Write type units into debug info section for DWARFv5.
756  if (Version >= 5) {
757  TUSectionKind = DW_SECT_INFO;
758  OutSection = InfoSection;
759  TypeInputSection = DwpSingleInfoSection;
760  } else {
761  // Write type units into debug types section for DWARF < 5.
762  if (CurTypesSection.size() != 1)
763  return make_error<DWPError>(
764  "multiple type unit sections in .dwp file");
765 
766  TUSectionKind = DW_SECT_EXT_TYPES;
767  OutSection = TypesSection;
768  TypeInputSection = CurTypesSection.front();
769  }
770 
771  DWARFUnitIndex TUIndex(TUSectionKind);
772  DataExtractor TUIndexData(CurTUIndexSection, Obj.isLittleEndian(), 0);
773  if (!TUIndex.parse(TUIndexData))
774  return make_error<DWPError>("failed to parse tu_index");
775  if (TUIndex.getVersion() != IndexVersion)
776  return make_error<DWPError>("incompatible tu_index versions, found " +
777  utostr(TUIndex.getVersion()) +
778  " and expecting " + utostr(IndexVersion));
779 
780  unsigned TypesContributionIndex =
781  getContributionIndex(TUSectionKind, IndexVersion);
782  addAllTypesFromDWP(Out, TypeIndexEntries, TUIndex, OutSection,
783  TypeInputSection, CurEntry,
784  ContributionOffsets[TypesContributionIndex],
785  TypesContributionIndex);
786  }
787  }
788 
789  if (Version < 5) {
790  // Lie about there being no info contributions so the TU index only includes
791  // the type unit contribution for DWARF < 5. In DWARFv5 the TU index has a
792  // contribution to the info section, so we do not want to lie about it.
793  ContributionOffsets[0] = 0;
794  }
795  writeIndex(Out, MCOFI.getDwarfTUIndexSection(), ContributionOffsets,
796  TypeIndexEntries, IndexVersion);
797 
798  if (Version < 5) {
799  // Lie about the type contribution for DWARF < 5. In DWARFv5 the type
800  // section does not exist, so no need to do anything about this.
801  ContributionOffsets[getContributionIndex(DW_SECT_EXT_TYPES, 2)] = 0;
802  // Unlie about the info contribution
803  ContributionOffsets[0] = 1;
804  }
805 
806  writeIndex(Out, MCOFI.getDwarfCUIndexSection(), ContributionOffsets,
807  IndexEntries, IndexVersion);
808 
809  return Error::success();
810 }
811 } // namespace llvm
MemoryBuffer.h
llvm::InfoSectionUnitHeader::UnitType
uint8_t UnitType
Definition: DWP.h:36
llvm::StringRef::back
LLVM_NODISCARD char back() const
back - Get the last character in the string.
Definition: StringRef.h:168
llvm::MCContext::getObjectFileInfo
const MCObjectFileInfo * getObjectFileInfo() const
Definition: MCContext.h:443
llvm::InfoSectionUnitHeader::Version
uint16_t Version
Definition: DWP.h:33
getCUAbbrev
static uint64_t getCUAbbrev(StringRef Abbrev, uint64_t AbbrCode)
Definition: DWP.cpp:38
llvm::object::Kind
Kind
Definition: COFFModuleDefinition.cpp:31
llvm
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:17
llvm::handleSection
Error handleSection(const StringMap< std::pair< MCSection *, DWARFSectionKind >> &KnownSections, const MCSection *StrSection, const MCSection *StrOffsetSection, const MCSection *TypesSection, const MCSection *CUIndexSection, const MCSection *TUIndexSection, const MCSection *InfoSection, const object::SectionRef &Section, MCStreamer &Out, std::deque< SmallString< 32 >> &UncompressedSections, uint32_t(&ContributionOffsets)[8], UnitIndexEntry &CurEntry, StringRef &CurStrSection, StringRef &CurStrOffsetSection, std::vector< StringRef > &CurTypesSection, std::vector< StringRef > &CurInfoSection, StringRef &AbbrevSection, StringRef &CurCUIndexSection, StringRef &CurTUIndexSection, std::vector< std::pair< DWARFSectionKind, uint32_t >> &SectionLength)
Definition: DWP.cpp:468
P
This currently compiles esp xmm0 movsd esp eax eax esp ret We should use not the dag combiner This is because dagcombine2 needs to be able to see through the X86ISD::Wrapper which DAGCombine can t really do The code for turning x load into a single vector load is target independent and should be moved to the dag combiner The code for turning x load into a vector load can only handle a direct load from a global or a direct load from the stack It should be generalized to handle any load from P
Definition: README-SSE.txt:411
llvm::write
Error write(MCStreamer &Out, ArrayRef< std::string > Inputs)
Definition: DWP.cpp:536
llvm::writeIndexTable
void writeIndexTable(MCStreamer &Out, ArrayRef< unsigned > ContributionOffsets, const MapVector< uint64_t, UnitIndexEntry > &IndexEntries, uint32_t DWARFUnitIndex::Entry::SectionContribution::*Field)
Definition: DWP.cpp:393
llvm::SmallVector
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1185
llvm::DWARFUnitIndex::Entry::SectionContribution
Definition: DWARFUnitIndex.h:113
MCTargetOptionsFlags
static mc::RegisterMCTargetOptionsFlags MCTargetOptionsFlags
Definition: DWP.cpp:24
getSubsection
static StringRef getSubsection(StringRef Section, const DWARFUnitIndex::Entry &Entry, DWARFSectionKind Kind)
Definition: DWP.cpp:170
llvm::dwarf::Form
Form
Definition: Dwarf.h:132
llvm::DW_SECT_EXT_unknown
@ DW_SECT_EXT_unknown
Denotes a value read from an index section that does not correspond to any of the supported standards...
Definition: DWARFUnitIndex.h:59
llvm::Error::success
static ErrorSuccess success()
Create a success value.
Definition: Error.h:329
llvm::DWPStringPool
Definition: DWPStringPool.h:10
MCTargetOptionsCommandFlags.h
llvm::dwarf::DW_LENGTH_DWARF64
@ DW_LENGTH_DWARF64
Indicator of 64-bit DWARF format.
Definition: Dwarf.h:57
MCObjectFileInfo.h
llvm::DWARFUnitIndex::Entry
Definition: DWARFUnitIndex.h:111
llvm::MapVector
This class implements a map that also provides access to all stored values in a deterministic order.
Definition: MapVector.h:37
llvm::InfoSectionUnitHeader::AddrSize
uint8_t AddrSize
Definition: DWP.h:39
llvm::Expected
Tagged union holding either a T or a Error.
Definition: APFloat.h:41
llvm::DataExtractor::getU64
uint64_t getU64(uint64_t *offset_ptr, Error *Err=nullptr) const
Extract a uint64_t value from *offset_ptr.
Definition: DataExtractor.cpp:116
llvm::DWARFDataExtractor
A DataExtractor (typically for an in-memory copy of an object-file section) plus a relocation map for...
Definition: DWARFDataExtractor.h:21
llvm::dwarf::Tag
Tag
Definition: Dwarf.h:105
llvm::Data
@ Data
Definition: SIMachineScheduler.h:55
llvm::StringRef::substr
LLVM_NODISCARD StringRef substr(size_t Start, size_t N=npos) const
Return a reference to the substring from [Start, Start + N).
Definition: StringRef.h:611
llvm::InfoSectionUnitHeader::Signature
Optional< uint64_t > Signature
Definition: DWP.h:47
llvm::BitmaskEnumDetail::Mask
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
Definition: BitmaskEnum.h:80
llvm::serializeSectionKind
uint32_t serializeSectionKind(DWARFSectionKind Kind, unsigned IndexVersion)
Convert the internal value for a section kind to an on-disk value.
Definition: DWARFUnitIndex.cpp:42
llvm::MCStreamer
Streaming machine code generation interface.
Definition: MCStreamer.h:201
llvm::DataExtractor::getULEB128
uint64_t getULEB128(uint64_t *offset_ptr, llvm::Error *Err=nullptr) const
Extract a unsigned LEB128 value from *offset_ptr.
Definition: DataExtractor.cpp:220
llvm::BTF::HeaderSize
@ HeaderSize
Definition: BTF.h:58
llvm::object
Definition: DWARFDebugLoc.h:25
handleCompressedSection
static Error handleCompressedSection(std::deque< SmallString< 32 >> &UncompressedSections, StringRef &Name, StringRef &Contents)
Definition: DWP.cpp:275
llvm::createFileError
Error createFileError(const Twine &F, Error E)
Concatenate a source file path and/or name with an Error.
Definition: Error.h:1320
E
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
C
(vector float) vec_cmpeq(*A, *B) C
Definition: README_ALTIVEC.txt:86
debugStrOffsetsHeaderSize
static uint64_t debugStrOffsetsHeaderSize(DataExtractor StrOffsetsData, uint16_t DwarfVersion)
Definition: DWP.cpp:27
MCContext.h
llvm::DWARFSectionKind
DWARFSectionKind
The enum of section identifiers to be used in internal interfaces.
Definition: DWARFUnitIndex.h:56
llvm::writeIndex
void writeIndex(MCStreamer &Out, MCSection *Section, ArrayRef< unsigned > ContributionOffsets, const MapVector< uint64_t, UnitIndexEntry > &IndexEntries, uint32_t IndexVersion)
Definition: DWP.cpp:403
getCUIdentifiers
static Expected< CompileUnitIdentifiers > getCUIdentifiers(InfoSectionUnitHeader &Header, StringRef Abbrev, StringRef Info, StringRef StrOffsets, StringRef Str)
Definition: DWP.cpp:92
llvm::DWARFUnitIndex
Definition: DWARFUnitIndex.h:99
llvm::InfoSectionUnitHeader::HeaderSize
uint8_t HeaderSize
Definition: DWP.h:54
llvm::NextPowerOf2
constexpr uint64_t NextPowerOf2(uint64_t A)
Returns the next power of two (in 64-bits) that is strictly greater than A.
Definition: MathExtras.h:710
llvm::DWARFUnitIndex::parse
bool parse(DataExtractor IndexData)
Definition: DWARFUnitIndex.cpp:119
getIndexedString
static Expected< const char * > getIndexedString(dwarf::Form Form, DataExtractor InfoData, uint64_t &InfoOffset, StringRef StrOffsets, StringRef Str, uint16_t Version)
Definition: DWP.cpp:54
llvm::DW_SECT_EXT_TYPES
@ DW_SECT_EXT_TYPES
Definition: DWARFUnitIndex.h:62
llvm::InfoSectionUnitHeader::DebugAbbrevOffset
uint64_t DebugAbbrevOffset
Definition: DWP.h:43
isSupportedSectionKind
static bool isSupportedSectionKind(DWARFSectionKind Kind)
Definition: DWP.cpp:151
Info
Analysis containing CSE Info
Definition: CSEInfo.cpp:27
llvm::array_lengthof
constexpr size_t array_lengthof(T(&)[N])
Find the length of an array.
Definition: STLArrayExtras.h:29
llvm::CallingConv::ID
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
Definition: CallingConv.h:24
llvm::StringMap
StringMap - This is an unconventional map that is specialized for handling keys that are "strings",...
Definition: StringMap.h:110
llvm::SmallString< 32 >
llvm::InfoSectionUnitHeader::Format
dwarf::DwarfFormat Format
Definition: DWP.h:50
llvm::DWARFFormValue::skipValue
bool skipValue(DataExtractor DebugInfoData, uint64_t *OffsetPtr, const dwarf::FormParams Params) const
Skip a form's value in DebugInfoData at the offset specified by OffsetPtr.
Definition: DWARFFormValue.h:147
llvm::object::SectionRef
This is a value type class that represents a single section in the list of sections in the object fil...
Definition: ObjectFile.h:80
llvm::DataExtractor::size
size_t size() const
Return the number of bytes in the underlying buffer.
Definition: DataExtractor.h:688
llvm::UnitIndexEntry::Contributions
DWARFUnitIndex::Entry::SectionContribution Contributions[8]
Definition: DWP.h:19
llvm::StringRef::empty
constexpr LLVM_NODISCARD bool empty() const
empty - Check if the string is empty.
Definition: StringRef.h:153
uint64_t
llvm::DW_SECT_EXT_LOC
@ DW_SECT_EXT_LOC
Definition: DWARFUnitIndex.h:63
move
compiles ldr LCPI1_0 ldr ldr mov lsr tst moveq r1 ldr LCPI1_1 and r0 bx lr It would be better to do something like to fold the shift into the conditional move
Definition: README.txt:546
llvm::object::Decompressor::create
static Expected< Decompressor > create(StringRef Name, StringRef Data, bool IsLE, bool Is64Bit)
Create decompressor object.
Definition: Decompressor.cpp:20
llvm::DenseMap
Definition: DenseMap.h:716
llvm::StringRef::front
LLVM_NODISCARD char front() const
front - Get the first character in the string.
Definition: StringRef.h:161
llvm::getContributionIndex
unsigned getContributionIndex(DWARFSectionKind Kind, uint32_t IndexVersion)
Definition: DWP.cpp:158
llvm::object::Decompressor::isGnuStyle
static bool isGnuStyle(StringRef Name)
Return true if section name matches gnu style compressed one.
Definition: Decompressor.cpp:75
I
#define I(x, y, z)
Definition: MD5.cpp:58
llvm::InfoSectionUnitHeader
Definition: DWP.h:28
llvm::dwarf::FormParams
A helper struct providing information about the byte size of DW_FORM values that vary in size dependi...
Definition: Dwarf.h:653
llvm::DataExtractor::isValidOffset
bool isValidOffset(uint64_t offset) const
Test the validity of offset.
Definition: DataExtractor.h:665
llvm::object::ObjectFile::createObjectFile
static Expected< OwningBinary< ObjectFile > > createObjectFile(StringRef ObjectPath)
Definition: ObjectFile.cpp:187
assert
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
llvm::DWARFDataExtractor::getInitialLength
std::pair< uint64_t, dwarf::DwarfFormat > getInitialLength(uint64_t *Off, Error *Err=nullptr) const
Extracts the DWARF "initial length" field, which can either be a 32-bit value smaller than 0xfffffff0...
Definition: DWARFDataExtractor.cpp:17
llvm::Optional::getValue
constexpr const T & getValue() const &
Definition: Optional.h:279
llvm::DWARFUnitIndex::Entry::SectionContribution::Length
uint32_t Length
Definition: DWARFUnitIndex.h:115
llvm::MCStreamer::emitIntValue
virtual void emitIntValue(uint64_t Value, unsigned Size)
Special case of EmitValue that avoids the client having to pass in a MCExpr for constant integers.
Definition: MCStreamer.cpp:134
DWP.h
llvm::InfoSectionUnitHeader::Length
uint64_t Length
Definition: DWP.h:30
buildDWODescription
static std::string buildDWODescription(StringRef Name, StringRef DWPName, StringRef DWOName)
Definition: DWP.cpp:248
llvm::DataExtractor::getU32
uint32_t getU32(uint64_t *offset_ptr, Error *Err=nullptr) const
Extract a uint32_t value from *offset_ptr.
Definition: DataExtractor.cpp:107
llvm::parseInfoSectionUnitHeader
Expected< InfoSectionUnitHeader > parseInfoSectionUnitHeader(StringRef Info)
Definition: DWP.cpp:296
llvm::DataExtractor::getCStr
const char * getCStr(uint64_t *OffsetPtr, Error *Err=nullptr) const
Extract a C string from *offset_ptr.
Definition: DataExtractor.h:129
llvm::ArrayRef< unsigned >
llvm::MapVector::insert
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Definition: MapVector.h:118
llvm::StringRef
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:58
DWPError.h
uint32_t
llvm::MCSection
Instances of this class represent a uniqued identifier for a section in the current translation unit.
Definition: MCSection.h:39
S
add sub stmia L5 ldr r0 bl L_printf $stub Instead of a and a wouldn t it be better to do three moves *Return an aggregate type is even return S
Definition: README.txt:210
llvm::DataExtractor::getU24
uint32_t getU24(uint64_t *OffsetPtr, Error *Err=nullptr) const
Extract a 24-bit unsigned value from *offset_ptr and return it in a uint32_t.
Definition: DataExtractor.cpp:101
llvm::DataExtractor::getU8
uint8_t getU8(uint64_t *offset_ptr, Error *Err=nullptr) const
Extract a uint8_t value from *offset_ptr.
Definition: DataExtractor.cpp:79
Decompressor.h
llvm::StringRef::size
constexpr LLVM_NODISCARD size_t size() const
size - Get the string size.
Definition: StringRef.h:157
llvm::mc::RegisterMCTargetOptionsFlags
Create this object with static storage to register mc-related command line options.
Definition: MCTargetOptionsCommandFlags.h:49
llvm::MapVector::empty
bool empty() const
Definition: MapVector.h:80
llvm::GraphProgram::Name
Name
Definition: GraphWriter.h:50
H
#define H(x, y, z)
Definition: MD5.cpp:57
uint16_t
llvm::toString
const char * toString(DWARFSectionKind Kind)
Definition: DWARFUnitIndex.h:67
llvm::Error
Lightweight error class with error context and mandatory checking.
Definition: Error.h:155
llvm::MapVector::size
size_type size() const
Definition: MapVector.h:61
llvm::DWARFUnitIndex::getColumnKinds
ArrayRef< DWARFSectionKind > getColumnKinds() const
Definition: DWARFUnitIndex.h:166
addAllTypesFromDWP
static void addAllTypesFromDWP(MCStreamer &Out, MapVector< uint64_t, UnitIndexEntry > &TypeIndexEntries, const DWARFUnitIndex &TUIndex, MCSection *OutputTypes, StringRef Types, const UnitIndexEntry &TUEntry, uint32_t &TypesOffset, unsigned TypesContributionIndex)
Definition: DWP.cpp:180
llvm::DWARFUnitIndex::Entry::SectionContribution::Offset
uint32_t Offset
Definition: DWARFUnitIndex.h:114
llvm::Expected::takeError
Error takeError()
Take ownership of the stored error.
Definition: Error.h:597
llvm::DWARFUnitIndex::getRows
ArrayRef< Entry > getRows() const
Definition: DWARFUnitIndex.h:170
llvm::DataExtractor
Definition: DataExtractor.h:41
llvm::MCStreamer::getContext
MCContext & getContext() const
Definition: MCStreamer.h:282
Version
uint64_t Version
Definition: RawMemProfReader.cpp:40
llvm::DWARFUnitIndex::getVersion
uint32_t getVersion() const
Definition: DWARFUnitIndex.h:161
llvm::writeStringsAndOffsets
void writeStringsAndOffsets(MCStreamer &Out, DWPStringPool &Strings, MCSection *StrOffsetSection, StringRef CurStrSection, StringRef CurStrOffsetSection, uint16_t Version)
Definition: DWP.cpp:355
llvm::ArrayRef::size
size_t size() const
size - Get the array size.
Definition: ArrayRef.h:164
llvm::MCStreamer::emitBytes
virtual void emitBytes(StringRef Data)
Emit the bytes in Data into the output.
Definition: MCStreamer.cpp:1197
llvm::object::createError
Error createError(const Twine &Err)
Definition: Error.h:83
llvm::UnitIndexEntry
Definition: DWP.h:18
getOnDiskSectionId
static unsigned getOnDiskSectionId(unsigned Index)
Definition: DWP.cpp:166
llvm::OptimizedStructLayoutField
A field in a structure.
Definition: OptimizedStructLayout.h:45
llvm::SmallVectorImpl::reserve
void reserve(size_type N)
Definition: SmallVector.h:644
llvm::MCStreamer::SwitchSection
virtual void SwitchSection(MCSection *Section, const MCExpr *Subsection=nullptr)
Set the current section where code is being emitted to Section.
Definition: MCStreamer.cpp:1220
addAllTypesFromTypesSection
static void addAllTypesFromTypesSection(MCStreamer &Out, MapVector< uint64_t, UnitIndexEntry > &TypeIndexEntries, MCSection *OutputTypes, const std::vector< StringRef > &TypesSections, const UnitIndexEntry &CUEntry, uint32_t &TypesOffset)
Definition: DWP.cpp:214
llvm::CompileUnitIdentifiers
Definition: DWP.h:57
llvm::DataExtractor::getU16
uint16_t getU16(uint64_t *offset_ptr, Error *Err=nullptr) const
Extract a uint16_t value from *offset_ptr.
Definition: DataExtractor.cpp:92
llvm::Intrinsic::ID
unsigned ID
Definition: TargetTransformInfo.h:37
llvm::buildDuplicateError
Error buildDuplicateError(const std::pair< uint64_t, UnitIndexEntry > &PrevE, const CompileUnitIdentifiers &ID, StringRef DWPName)
Definition: DWP.cpp:459