1 //===- bolt/Rewrite/DWARFRewriter.cpp -------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "bolt/Rewrite/DWARFRewriter.h"
10 #include "bolt/Core/BinaryContext.h"
11 #include "bolt/Core/BinaryFunction.h"
12 #include "bolt/Core/DebugData.h"
13 #include "bolt/Core/ParallelUtilities.h"
14 #include "bolt/Rewrite/RewriteInstance.h"
15 #include "bolt/Utils/Utils.h"
16 #include "llvm/ADT/STLExtras.h"
17 #include "llvm/BinaryFormat/Dwarf.h"
18 #include "llvm/DWP/DWP.h"
19 #include "llvm/DebugInfo/DWARF/DWARFContext.h"
20 #include "llvm/DebugInfo/DWARF/DWARFDebugLoc.h"
21 #include "llvm/DebugInfo/DWARF/DWARFExpression.h"
22 #include "llvm/DebugInfo/DWARF/DWARFFormValue.h"
23 #include "llvm/MC/MCAsmBackend.h"
24 #include "llvm/MC/MCAsmLayout.h"
25 #include "llvm/MC/MCContext.h"
26 #include "llvm/MC/MCObjectWriter.h"
27 #include "llvm/MC/MCStreamer.h"
28 #include "llvm/Object/ObjectFile.h"
29 #include "llvm/Support/Casting.h"
30 #include "llvm/Support/CommandLine.h"
31 #include "llvm/Support/Debug.h"
32 #include "llvm/Support/Endian.h"
33 #include "llvm/Support/Error.h"
34 #include "llvm/Support/FileSystem.h"
35 #include "llvm/Support/LEB128.h"
36 #include "llvm/Support/ThreadPool.h"
37 #include "llvm/Support/ToolOutputFile.h"
38 #include <algorithm>
39 #include <cstdint>
40 #include <string>
41 #include <unordered_map>
42 #include <utility>
43 #include <vector>
44 
45 #undef  DEBUG_TYPE
46 #define DEBUG_TYPE "bolt"
47 
48 LLVM_ATTRIBUTE_UNUSED
49 static void printDie(const DWARFDie &DIE) {
50   DIDumpOptions DumpOpts;
51   DumpOpts.ShowForm = true;
52   DumpOpts.Verbose = true;
53   DumpOpts.ChildRecurseDepth = 0;
54   DumpOpts.ShowChildren = 0;
55   DIE.dump(dbgs(), 0, DumpOpts);
56 }
57 
58 namespace llvm {
59 namespace bolt {
60 /// Finds attributes FormValue and Offset.
61 ///
62 /// \param DIE die to look up in.
63 /// \param Attrs finds the first attribute that matches and extracts it.
64 /// \return an optional AttrInfo with DWARFFormValue and Offset.
65 Optional<AttrInfo> findAttributeInfo(const DWARFDie DIE,
66                                      std::vector<dwarf::Attribute> Attrs) {
67   for (dwarf::Attribute &Attr : Attrs)
68     if (Optional<AttrInfo> Info = findAttributeInfo(DIE, Attr))
69       return Info;
70   return None;
71 }
72 } // namespace bolt
73 } // namespace llvm
74 
75 using namespace llvm;
76 using namespace llvm::support::endian;
77 using namespace object;
78 using namespace bolt;
79 
80 namespace opts {
81 
82 extern cl::OptionCategory BoltCategory;
83 extern cl::opt<unsigned> Verbosity;
84 extern cl::opt<std::string> OutputFilename;
85 
86 static cl::opt<bool> KeepARanges(
87     "keep-aranges",
88     cl::desc(
89         "keep or generate .debug_aranges section if .gdb_index is written"),
90     cl::Hidden, cl::cat(BoltCategory));
91 
92 static cl::opt<bool>
93 DeterministicDebugInfo("deterministic-debuginfo",
94   cl::desc("disables parallel execution of tasks that may produce"
95            "nondeterministic debug info"),
96   cl::init(true),
97   cl::cat(BoltCategory));
98 
99 static cl::opt<std::string> DwarfOutputPath(
100     "dwarf-output-path",
101     cl::desc("Path to where .dwo files or dwp file will be written out to."),
102     cl::init(""), cl::cat(BoltCategory));
103 
104 static cl::opt<bool>
105     WriteDWP("write-dwp",
106              cl::desc("output a single dwarf package file (dwp) instead of "
107                       "multiple non-relocatable dwarf object files (dwo)."),
108              cl::init(false), cl::cat(BoltCategory));
109 
110 static cl::opt<bool>
111     DebugSkeletonCu("debug-skeleton-cu",
112                     cl::desc("prints out offsetrs for abbrev and debu_info of "
113                              "Skeleton CUs that get patched."),
114                     cl::ZeroOrMore, cl::Hidden, cl::init(false),
115                     cl::cat(BoltCategory));
116 } // namespace opts
117 
118 /// Returns DWO Name to be used. Handles case where user specifies output DWO
119 /// directory, and there are duplicate names. Assumes DWO ID is unique.
120 static std::string
121 getDWOName(llvm::DWARFUnit &CU,
122            std::unordered_map<std::string, uint32_t> *NameToIndexMap,
123            std::unordered_map<uint64_t, std::string> &DWOIdToName) {
124   llvm::Optional<uint64_t> DWOId = CU.getDWOId();
125   assert(DWOId && "DWO ID not found.");
126   (void)DWOId;
127   auto NameIter = DWOIdToName.find(*DWOId);
128   if (NameIter != DWOIdToName.end())
129     return NameIter->second;
130 
131   std::string DWOName = dwarf::toString(
132       CU.getUnitDIE().find({dwarf::DW_AT_dwo_name, dwarf::DW_AT_GNU_dwo_name}),
133       "");
134   assert(!DWOName.empty() &&
135          "DW_AT_dwo_name/DW_AT_GNU_dwo_name does not exists.");
136   if (NameToIndexMap && !opts::DwarfOutputPath.empty()) {
137     auto Iter = NameToIndexMap->find(DWOName);
138     if (Iter == NameToIndexMap->end())
139       Iter = NameToIndexMap->insert({DWOName, 0}).first;
140     DWOName.append(std::to_string(Iter->second));
141     ++Iter->second;
142   }
143   DWOName.append(".dwo");
144   DWOIdToName[*DWOId] = DWOName;
145   return DWOName;
146 }
147 
148 void DWARFRewriter::addStringHelper(DebugInfoBinaryPatcher &DebugInfoPatcher,
149                                     const DWARFUnit &Unit,
150                                     const AttrInfo &AttrInfoVal,
151                                     StringRef Str) {
152   uint32_t NewOffset = StrWriter->addString(Str);
153   if (Unit.getVersion() == 5) {
154     StrOffstsWriter->updateAddressMap(AttrInfoVal.V.getRawUValue(), NewOffset);
155     return;
156   }
157   DebugInfoPatcher.addLE32Patch(AttrInfoVal.Offset, NewOffset,
158                                 AttrInfoVal.Size);
159 }
160 
161 void DWARFRewriter::updateDebugInfo() {
162   ErrorOr<BinarySection &> DebugInfo = BC.getUniqueSectionByName(".debug_info");
163   if (!DebugInfo)
164     return;
165 
166   auto *DebugInfoPatcher =
167       static_cast<DebugInfoBinaryPatcher *>(DebugInfo->getPatcher());
168 
169   ARangesSectionWriter = std::make_unique<DebugARangesSectionWriter>();
170   StrWriter = std::make_unique<DebugStrWriter>(BC);
171 
172   StrOffstsWriter = std::make_unique<DebugStrOffsetsWriter>();
173 
174   AbbrevWriter = std::make_unique<DebugAbbrevWriter>(*BC.DwCtx);
175 
176   if (!opts::DeterministicDebugInfo) {
177     opts::DeterministicDebugInfo = true;
178     errs() << "BOLT-WARNING: --deterministic-debuginfo is being deprecated\n";
179   }
180 
181   if (BC.isDWARF5Used()) {
182     AddrWriter = std::make_unique<DebugAddrWriterDwarf5>(&BC);
183     RangesSectionWriter = std::make_unique<DebugRangeListsSectionWriter>();
184     DebugRangeListsSectionWriter::setAddressWriter(AddrWriter.get());
185   } else {
186     AddrWriter = std::make_unique<DebugAddrWriter>(&BC);
187     RangesSectionWriter = std::make_unique<DebugRangesSectionWriter>();
188   }
189 
190   DebugLoclistWriter::setAddressWriter(AddrWriter.get());
191 
192   size_t CUIndex = 0;
193   for (std::unique_ptr<DWARFUnit> &CU : BC.DwCtx->compile_units()) {
194     const uint16_t DwarfVersion = CU->getVersion();
195     if (DwarfVersion >= 5) {
196       LocListWritersByCU[CUIndex] =
197           std::make_unique<DebugLoclistWriter>(*CU.get(), DwarfVersion, false);
198 
199       if (Optional<uint64_t> DWOId = CU->getDWOId()) {
200         assert(LocListWritersByCU.count(*DWOId) == 0 &&
201                "RangeLists writer for DWO unit already exists.");
202         auto RangeListsSectionWriter =
203             std::make_unique<DebugRangeListsSectionWriter>();
204         RangeListsSectionWriter->initSection(*CU.get());
205         RangeListsWritersByCU[*DWOId] = std::move(RangeListsSectionWriter);
206       }
207 
208     } else {
209       LocListWritersByCU[CUIndex] = std::make_unique<DebugLocWriter>();
210     }
211 
212     if (Optional<uint64_t> DWOId = CU->getDWOId()) {
213       assert(LocListWritersByCU.count(*DWOId) == 0 &&
214              "LocList writer for DWO unit already exists.");
215       // Work around some bug in llvm-15. If I pass in directly lld reports
216       // undefined symbol.
217       LocListWritersByCU[*DWOId] =
218           std::make_unique<DebugLoclistWriter>(*CU.get(), DwarfVersion, true);
219     }
220     ++CUIndex;
221   }
222 
223   // Unordered maps to handle name collision if output DWO directory is
224   // specified.
225   std::unordered_map<std::string, uint32_t> NameToIndexMap;
226   std::unordered_map<uint64_t, std::string> DWOIdToName;
227   std::mutex AccessMutex;
228 
229   auto updateDWONameCompDir = [&](DWARFUnit &Unit) -> void {
230     const DWARFDie &DIE = Unit.getUnitDIE();
231     Optional<AttrInfo> AttrInfoVal = findAttributeInfo(
232         DIE, {dwarf::DW_AT_dwo_name, dwarf::DW_AT_GNU_dwo_name});
233     (void)AttrInfoVal;
234     assert(AttrInfoVal && "Skeleton CU doesn't have dwo_name.");
235 
236     std::string ObjectName = "";
237 
238     {
239       std::lock_guard<std::mutex> Lock(AccessMutex);
240       ObjectName = getDWOName(Unit, &NameToIndexMap, DWOIdToName);
241     }
242     addStringHelper(*DebugInfoPatcher, Unit, *AttrInfoVal, ObjectName.c_str());
243 
244     AttrInfoVal = findAttributeInfo(DIE, dwarf::DW_AT_comp_dir);
245     (void)AttrInfoVal;
246     assert(AttrInfoVal && "DW_AT_comp_dir is not in Skeleton CU.");
247 
248     if (!opts::DwarfOutputPath.empty()) {
249       addStringHelper(*DebugInfoPatcher, Unit, *AttrInfoVal,
250                       opts::DwarfOutputPath.c_str());
251     }
252   };
253 
254   auto processUnitDIE = [&](size_t CUIndex, DWARFUnit *Unit) {
255     // Check if the unit is a skeleton and we need special updates for it and
256     // its matching split/DWO CU.
257     Optional<DWARFUnit *> SplitCU;
258     Optional<uint64_t> RangesBase;
259     llvm::Optional<uint64_t> DWOId = Unit->getDWOId();
260     StrOffstsWriter->initialize(Unit->getStringOffsetSection(),
261                                 Unit->getStringOffsetsTableContribution());
262     if (DWOId)
263       SplitCU = BC.getDWOCU(*DWOId);
264 
265     DebugLocWriter *DebugLocWriter = nullptr;
266     // Skipping CUs that failed to load.
267     if (SplitCU) {
268       updateDWONameCompDir(*Unit);
269 
270       DebugInfoBinaryPatcher *DwoDebugInfoPatcher =
271           llvm::cast<DebugInfoBinaryPatcher>(
272               getBinaryDWODebugInfoPatcher(*DWOId));
273       DWARFContext *DWOCtx = BC.getDWOContext();
274       // Setting this CU offset with DWP to normalize DIE offsets to uint32_t
275       if (DWOCtx && !DWOCtx->getCUIndex().getRows().empty())
276         DwoDebugInfoPatcher->setDWPOffset((*SplitCU)->getOffset());
277 
278       {
279         std::lock_guard<std::mutex> Lock(AccessMutex);
280         DebugLocWriter = LocListWritersByCU[*DWOId].get();
281       }
282       DebugRangesSectionWriter *TempRangesSectionWriter =
283           RangesSectionWriter.get();
284       if (Unit->getVersion() >= 5) {
285         TempRangesSectionWriter = RangeListsWritersByCU[*DWOId].get();
286       } else {
287         RangesBase = RangesSectionWriter->getSectionOffset();
288         // For DWARF5 there is now .debug_rnglists.dwo, so don't need to
289         // update rnglists base.
290         DwoDebugInfoPatcher->setRangeBase(*RangesBase);
291       }
292 
293       DwoDebugInfoPatcher->addUnitBaseOffsetLabel((*SplitCU)->getOffset());
294       DebugAbbrevWriter *DWOAbbrevWriter =
295           createBinaryDWOAbbrevWriter((*SplitCU)->getContext(), *DWOId);
296       updateUnitDebugInfo(*(*SplitCU), *DwoDebugInfoPatcher, *DWOAbbrevWriter,
297                           *DebugLocWriter, *TempRangesSectionWriter);
298       DebugLocWriter->finalize(*DwoDebugInfoPatcher, *DWOAbbrevWriter);
299       DwoDebugInfoPatcher->clearDestinationLabels();
300       if (!DwoDebugInfoPatcher->getWasRangBasedUsed())
301         RangesBase = None;
302       if (Unit->getVersion() >= 5)
303         TempRangesSectionWriter->finalizeSection();
304     }
305 
306     {
307       std::lock_guard<std::mutex> Lock(AccessMutex);
308       auto LocListWriterIter = LocListWritersByCU.find(CUIndex);
309       if (LocListWriterIter != LocListWritersByCU.end())
310         DebugLocWriter = LocListWriterIter->second.get();
311     }
312     if (Unit->getVersion() >= 5) {
313       RangesBase = RangesSectionWriter->getSectionOffset() +
314                    getDWARF5RngListLocListHeaderSize();
315       RangesSectionWriter.get()->initSection(*Unit);
316       StrOffstsWriter->finalizeSection();
317     }
318 
319     DebugInfoPatcher->addUnitBaseOffsetLabel(Unit->getOffset());
320     updateUnitDebugInfo(*Unit, *DebugInfoPatcher, *AbbrevWriter,
321                         *DebugLocWriter, *RangesSectionWriter, RangesBase);
322     DebugLocWriter->finalize(*DebugInfoPatcher, *AbbrevWriter);
323     if (Unit->getVersion() >= 5)
324       RangesSectionWriter.get()->finalizeSection();
325   };
326 
327   CUIndex = 0;
328   if (opts::NoThreads || opts::DeterministicDebugInfo) {
329     for (std::unique_ptr<DWARFUnit> &CU : BC.DwCtx->compile_units()) {
330       processUnitDIE(CUIndex, CU.get());
331       if (CU->getVersion() >= 5)
332         ++CUIndex;
333     }
334   } else {
335     // Update unit debug info in parallel
336     ThreadPool &ThreadPool = ParallelUtilities::getThreadPool();
337     for (std::unique_ptr<DWARFUnit> &CU : BC.DwCtx->compile_units()) {
338       ThreadPool.async(processUnitDIE, CUIndex, CU.get());
339       CUIndex++;
340     }
341     ThreadPool.wait();
342   }
343 
344   DebugInfoPatcher->clearDestinationLabels();
345   CUOffsetMap OffsetMap = finalizeDebugSections(*DebugInfoPatcher);
346 
347   if (opts::WriteDWP)
348     writeDWP(DWOIdToName);
349   else
350     writeDWOFiles(DWOIdToName);
351 
352   updateGdbIndexSection(OffsetMap);
353 }
354 
355 void DWARFRewriter::updateUnitDebugInfo(
356     DWARFUnit &Unit, DebugInfoBinaryPatcher &DebugInfoPatcher,
357     DebugAbbrevWriter &AbbrevWriter, DebugLocWriter &DebugLocWriter,
358     DebugRangesSectionWriter &RangesSectionWriter,
359     Optional<uint64_t> RangesBase) {
360   // Cache debug ranges so that the offset for identical ranges could be reused.
361   std::map<DebugAddressRangesVector, uint64_t> CachedRanges;
362 
363   uint64_t DIEOffset = Unit.getOffset() + Unit.getHeaderSize();
364   uint64_t NextCUOffset = Unit.getNextUnitOffset();
365   DWARFDebugInfoEntry Die;
366   DWARFDataExtractor DebugInfoData = Unit.getDebugInfoExtractor();
367   uint32_t Depth = 0;
368 
369   bool IsDWP = false;
370   if (DWARFContext *DWOCtx = BC.getDWOContext())
371     IsDWP = !DWOCtx->getCUIndex().getRows().empty();
372 
373   while (
374       DIEOffset < NextCUOffset &&
375       Die.extractFast(Unit, &DIEOffset, DebugInfoData, NextCUOffset, Depth)) {
376     if (const DWARFAbbreviationDeclaration *AbbrDecl =
377             Die.getAbbreviationDeclarationPtr()) {
378       if (AbbrDecl->hasChildren())
379         ++Depth;
380     } else {
381       // NULL entry.
382       if (Depth > 0)
383         --Depth;
384       if (Depth == 0)
385         break;
386     }
387 
388     DWARFDie DIE(&Unit, &Die);
389 
390     switch (DIE.getTag()) {
391     case dwarf::DW_TAG_compile_unit:
392     case dwarf::DW_TAG_skeleton_unit: {
393       // For dwarf5 section 3.1.3
394       // The following attributes are not part of a split full compilation unit
395       // entry but instead are inherited (if present) from the corresponding
396       // skeleton compilation unit: DW_AT_low_pc, DW_AT_high_pc, DW_AT_ranges,
397       // DW_AT_stmt_list, DW_AT_comp_dir, DW_AT_str_offsets_base,
398       // DW_AT_addr_base and DW_AT_rnglists_base.
399       if (Unit.getVersion() == 5 && Unit.isDWOUnit())
400         continue;
401       auto ModuleRangesOrError = DIE.getAddressRanges();
402       if (!ModuleRangesOrError) {
403         consumeError(ModuleRangesOrError.takeError());
404         break;
405       }
406       DWARFAddressRangesVector &ModuleRanges = *ModuleRangesOrError;
407       DebugAddressRangesVector OutputRanges =
408           BC.translateModuleAddressRanges(ModuleRanges);
409       const uint64_t RangesSectionOffset =
410           RangesSectionWriter.addRanges(OutputRanges);
411       if (!Unit.isDWOUnit())
412         ARangesSectionWriter->addCURanges(Unit.getOffset(),
413                                           std::move(OutputRanges));
414       updateDWARFObjectAddressRanges(DIE, RangesSectionOffset, DebugInfoPatcher,
415                                      AbbrevWriter, RangesBase);
416       break;
417     }
418     case dwarf::DW_TAG_subprogram: {
419       // Get function address either from ranges or [LowPC, HighPC) pair.
420       uint64_t Address;
421       uint64_t SectionIndex, HighPC;
422       if (!DIE.getLowAndHighPC(Address, HighPC, SectionIndex)) {
423         Expected<DWARFAddressRangesVector> RangesOrError =
424             DIE.getAddressRanges();
425         if (!RangesOrError) {
426           consumeError(RangesOrError.takeError());
427           break;
428         }
429         DWARFAddressRangesVector Ranges = *RangesOrError;
430         // Not a function definition.
431         if (Ranges.empty())
432           break;
433 
434         Address = Ranges.front().LowPC;
435       }
436 
437       // Clear cached ranges as the new function will have its own set.
438       CachedRanges.clear();
439 
440       DebugAddressRangesVector FunctionRanges;
441       if (const BinaryFunction *Function =
442               BC.getBinaryFunctionAtAddress(Address))
443         FunctionRanges = Function->getOutputAddressRanges();
444 
445       if (FunctionRanges.empty())
446         FunctionRanges.push_back({0, 0});
447 
448       updateDWARFObjectAddressRanges(
449           DIE, RangesSectionWriter.addRanges(FunctionRanges), DebugInfoPatcher,
450           AbbrevWriter);
451 
452       break;
453     }
454     case dwarf::DW_TAG_lexical_block:
455     case dwarf::DW_TAG_inlined_subroutine:
456     case dwarf::DW_TAG_try_block:
457     case dwarf::DW_TAG_catch_block: {
458       uint64_t RangesSectionOffset = RangesSectionWriter.getEmptyRangesOffset();
459       Expected<DWARFAddressRangesVector> RangesOrError = DIE.getAddressRanges();
460       const BinaryFunction *Function =
461           RangesOrError && !RangesOrError->empty()
462               ? BC.getBinaryFunctionContainingAddress(
463                     RangesOrError->front().LowPC)
464               : nullptr;
465       if (Function) {
466         DebugAddressRangesVector OutputRanges =
467             Function->translateInputToOutputRanges(*RangesOrError);
468         LLVM_DEBUG(if (OutputRanges.empty() != RangesOrError->empty()) {
469           dbgs() << "BOLT-DEBUG: problem with DIE at 0x"
470                  << Twine::utohexstr(DIE.getOffset()) << " in CU at 0x"
471                  << Twine::utohexstr(Unit.getOffset()) << '\n';
472         });
473         RangesSectionOffset = RangesSectionWriter.addRanges(
474             std::move(OutputRanges), CachedRanges);
475       } else if (!RangesOrError) {
476         consumeError(RangesOrError.takeError());
477       }
478       updateDWARFObjectAddressRanges(DIE, RangesSectionOffset, DebugInfoPatcher,
479                                      AbbrevWriter);
480       break;
481     }
482     default: {
483       // Handle any tag that can have DW_AT_location attribute.
484       DWARFFormValue Value;
485       uint64_t AttrOffset;
486       if (Optional<AttrInfo> AttrVal =
487               findAttributeInfo(DIE, dwarf::DW_AT_location)) {
488         AttrOffset = AttrVal->Offset;
489         Value = AttrVal->V;
490         if (Value.isFormClass(DWARFFormValue::FC_Constant) ||
491             Value.isFormClass(DWARFFormValue::FC_SectionOffset)) {
492           uint64_t Offset = Value.isFormClass(DWARFFormValue::FC_Constant)
493                                 ? Value.getAsUnsignedConstant().getValue()
494                                 : Value.getAsSectionOffset().getValue();
495           DebugLocationsVector InputLL;
496 
497           Optional<object::SectionedAddress> SectionAddress =
498               Unit.getBaseAddress();
499           uint64_t BaseAddress = 0;
500           if (SectionAddress)
501             BaseAddress = SectionAddress->Address;
502 
503           if (Unit.getVersion() >= 5 &&
504               AttrVal->V.getForm() == dwarf::DW_FORM_loclistx) {
505             Optional<uint64_t> LocOffset = Unit.getLoclistOffset(Offset);
506             assert(LocOffset && "Location Offset is invalid.");
507             Offset = *LocOffset;
508           }
509 
510           Error E = Unit.getLocationTable().visitLocationList(
511               &Offset, [&](const DWARFLocationEntry &Entry) {
512                 switch (Entry.Kind) {
513                 default:
514                   llvm_unreachable("Unsupported DWARFLocationEntry Kind.");
515                 case dwarf::DW_LLE_end_of_list:
516                   return false;
517                 case dwarf::DW_LLE_base_address: {
518                   assert(Entry.SectionIndex == SectionedAddress::UndefSection &&
519                          "absolute address expected");
520                   BaseAddress = Entry.Value0;
521                   break;
522                 }
523                 case dwarf::DW_LLE_offset_pair:
524                   assert(
525                       (Entry.SectionIndex == SectionedAddress::UndefSection &&
526                        (!Unit.isDWOUnit() || Unit.getVersion() == 5)) &&
527                       "absolute address expected");
528                   InputLL.emplace_back(DebugLocationEntry{
529                       BaseAddress + Entry.Value0, BaseAddress + Entry.Value1,
530                       Entry.Loc});
531                   break;
532                 case dwarf::DW_LLE_start_length:
533                   InputLL.emplace_back(DebugLocationEntry{
534                       Entry.Value0, Entry.Value0 + Entry.Value1, Entry.Loc});
535                   break;
536                 case dwarf::DW_LLE_base_addressx: {
537                   Optional<object::SectionedAddress> EntryAddress =
538                       Unit.getAddrOffsetSectionItem(Entry.Value0);
539                   assert(EntryAddress && "base Address not found.");
540                   BaseAddress = EntryAddress->Address;
541                   break;
542                 }
543                 case dwarf::DW_LLE_startx_length: {
544                   Optional<object::SectionedAddress> EntryAddress =
545                       Unit.getAddrOffsetSectionItem(Entry.Value0);
546                   assert(EntryAddress && "Address does not exist.");
547                   InputLL.emplace_back(DebugLocationEntry{
548                       EntryAddress->Address,
549                       EntryAddress->Address + Entry.Value1, Entry.Loc});
550                   break;
551                 }
552                 case dwarf::DW_LLE_startx_endx: {
553                   Optional<object::SectionedAddress> StartAddress =
554                       Unit.getAddrOffsetSectionItem(Entry.Value0);
555                   assert(StartAddress && "Start Address does not exist.");
556                   Optional<object::SectionedAddress> EndAddress =
557                       Unit.getAddrOffsetSectionItem(Entry.Value1);
558                   assert(EndAddress && "Start Address does not exist.");
559                   InputLL.emplace_back(DebugLocationEntry{
560                       StartAddress->Address, EndAddress->Address, Entry.Loc});
561                   break;
562                 }
563                 }
564                 return true;
565               });
566 
567           if (E || InputLL.empty()) {
568             consumeError(std::move(E));
569             errs() << "BOLT-WARNING: empty location list detected at 0x"
570                    << Twine::utohexstr(Offset) << " for DIE at 0x"
571                    << Twine::utohexstr(DIE.getOffset()) << " in CU at 0x"
572                    << Twine::utohexstr(Unit.getOffset()) << '\n';
573           } else {
574             const uint64_t Address = InputLL.front().LowPC;
575             DebugLocationsVector OutputLL;
576             if (const BinaryFunction *Function =
577                     BC.getBinaryFunctionContainingAddress(Address)) {
578               OutputLL = Function->translateInputToOutputLocationList(InputLL);
579               LLVM_DEBUG(if (OutputLL.empty()) {
580                 dbgs() << "BOLT-DEBUG: location list translated to an empty "
581                           "one at 0x"
582                        << Twine::utohexstr(DIE.getOffset()) << " in CU at 0x"
583                        << Twine::utohexstr(Unit.getOffset()) << '\n';
584               });
585             } else {
586               // It's possible for a subprogram to be removed and to have
587               // address of 0. Adding this entry to output to preserve debug
588               // information.
589               OutputLL = InputLL;
590             }
591             DebugLocWriter.addList(*AttrVal, OutputLL, DebugInfoPatcher,
592                                    AbbrevWriter);
593           }
594         } else {
595           assert((Value.isFormClass(DWARFFormValue::FC_Exprloc) ||
596                   Value.isFormClass(DWARFFormValue::FC_Block)) &&
597                  "unexpected DW_AT_location form");
598           if (Unit.isDWOUnit() || Unit.getVersion() >= 5) {
599             ArrayRef<uint8_t> Expr = *Value.getAsBlock();
600             DataExtractor Data(
601                 StringRef((const char *)Expr.data(), Expr.size()),
602                 Unit.getContext().isLittleEndian(), 0);
603             DWARFExpression LocExpr(Data, Unit.getAddressByteSize(),
604                                     Unit.getFormParams().Format);
605             uint32_t PrevOffset = 0;
606             constexpr uint32_t SizeOfOpcode = 1;
607             constexpr uint32_t SizeOfForm = 1;
608             for (auto &Expr : LocExpr) {
609               if (!(Expr.getCode() == dwarf::DW_OP_GNU_addr_index ||
610                     Expr.getCode() == dwarf::DW_OP_addrx))
611                 continue;
612 
613               const uint64_t Index = Expr.getRawOperand(0);
614               Optional<object::SectionedAddress> EntryAddress =
615                   Unit.getAddrOffsetSectionItem(Index);
616               assert(EntryAddress && "Address is not found.");
617               assert(Index <= std::numeric_limits<uint32_t>::max() &&
618                      "Invalid Operand Index.");
619               if (Expr.getCode() == dwarf::DW_OP_addrx) {
620                 const uint32_t EncodingSize =
621                     Expr.getOperandEndOffset(0) - PrevOffset - SizeOfOpcode;
622                 const uint32_t Index = AddrWriter->getIndexFromAddress(
623                     EntryAddress->Address, Unit);
624                 // Encoding new size.
625                 SmallString<8> Tmp;
626                 raw_svector_ostream OSE(Tmp);
627                 encodeULEB128(Index, OSE);
628                 DebugInfoPatcher.addUDataPatch(AttrOffset, Tmp.size() + 1, 1);
629                 DebugInfoPatcher.addUDataPatch(AttrOffset + PrevOffset +
630                                                    SizeOfOpcode + SizeOfForm,
631                                                Index, EncodingSize);
632               } else {
633                 // TODO: Re-do this as DWARF5.
634                 AddrWriter->addIndexAddress(EntryAddress->Address,
635                                             static_cast<uint32_t>(Index), Unit);
636               }
637               if (Expr.getDescription().Op[1] ==
638                   DWARFExpression::Operation::SizeNA)
639                 PrevOffset = Expr.getOperandEndOffset(0);
640               else
641                 PrevOffset = Expr.getOperandEndOffset(1);
642             }
643           }
644         }
645       } else if (Optional<AttrInfo> AttrVal =
646                      findAttributeInfo(DIE, dwarf::DW_AT_low_pc)) {
647         AttrOffset = AttrVal->Offset;
648         Value = AttrVal->V;
649         const Optional<uint64_t> Result = Value.getAsAddress();
650         if (Result.hasValue()) {
651           const uint64_t Address = Result.getValue();
652           uint64_t NewAddress = 0;
653           if (const BinaryFunction *Function =
654                   BC.getBinaryFunctionContainingAddress(Address)) {
655             NewAddress = Function->translateInputToOutputAddress(Address);
656             LLVM_DEBUG(dbgs()
657                        << "BOLT-DEBUG: Fixing low_pc 0x"
658                        << Twine::utohexstr(Address) << " for DIE with tag "
659                        << DIE.getTag() << " to 0x"
660                        << Twine::utohexstr(NewAddress) << '\n');
661           }
662 
663           dwarf::Form Form = Value.getForm();
664           assert(Form != dwarf::DW_FORM_LLVM_addrx_offset &&
665                  "DW_FORM_LLVM_addrx_offset is not supported");
666           std::lock_guard<std::mutex> Lock(DebugInfoPatcherMutex);
667           if (Form == dwarf::DW_FORM_GNU_addr_index) {
668             const uint64_t Index = Value.getRawUValue();
669             // If there is no new address, storing old address.
670             // Re-using Index to make implementation easier.
671             // DW_FORM_GNU_addr_index is variable lenght encoding
672             // so we either have to create indices of same sizes, or use same
673             // index.
674             // TODO: We can now re-write .debug_info. This can be simplified to
675             // just getting a new index and creating a patch.
676             AddrWriter->addIndexAddress(NewAddress ? NewAddress : Address,
677                                         Index, Unit);
678           } else if (Form == dwarf::DW_FORM_addrx) {
679             const uint32_t Index = AddrWriter->getIndexFromAddress(
680                 NewAddress ? NewAddress : Address, Unit);
681             DebugInfoPatcher.addUDataPatch(AttrOffset, Index, AttrVal->Size);
682           } else {
683             DebugInfoPatcher.addLE64Patch(AttrOffset, NewAddress);
684           }
685         } else if (opts::Verbosity >= 1) {
686           errs() << "BOLT-WARNING: unexpected form value for attribute at 0x"
687                  << Twine::utohexstr(AttrOffset);
688         }
689       } else if (IsDWP && Unit.isDWOUnit()) {
690         // Not a common path so don't want to search all DIEs all the time.
691         Optional<AttrInfo> SignatureAttrVal =
692             findAttributeInfo(DIE, dwarf::DW_AT_signature);
693         if (!SignatureAttrVal)
694           continue;
695         // If input is DWP file we need to keep track of which TU came from each
696         // CU, so we can write it out correctly.
697         if (Optional<uint64_t> Val = SignatureAttrVal->V.getAsReferenceUVal())
698           TypeSignaturesPerCU[*DIE.getDwarfUnit()->getDWOId()].insert(*Val);
699         else {
700           errs() << "BOT-ERROR: DW_AT_signature form is not supported.\n";
701           exit(1);
702         }
703       }
704     }
705     }
706 
707     // Handling references.
708     assert(DIE.isValid() && "Invalid DIE.");
709     const DWARFAbbreviationDeclaration *AbbrevDecl =
710         DIE.getAbbreviationDeclarationPtr();
711     if (!AbbrevDecl)
712       continue;
713     uint32_t Index = 0;
714     for (const DWARFAbbreviationDeclaration::AttributeSpec &Decl :
715          AbbrevDecl->attributes()) {
716       switch (Decl.Form) {
717       default:
718         break;
719       case dwarf::DW_FORM_ref1:
720       case dwarf::DW_FORM_ref2:
721       case dwarf::DW_FORM_ref4:
722       case dwarf::DW_FORM_ref8:
723       case dwarf::DW_FORM_ref_udata:
724       case dwarf::DW_FORM_ref_addr: {
725         Optional<AttrInfo> AttrVal = findAttributeInfo(DIE, AbbrevDecl, Index);
726         uint32_t DestinationAddress =
727             AttrVal->V.getRawUValue() +
728             (Decl.Form == dwarf::DW_FORM_ref_addr ? 0 : Unit.getOffset());
729         DebugInfoPatcher.addReferenceToPatch(
730             AttrVal->Offset, DestinationAddress, AttrVal->Size, Decl.Form);
731         // We can have only one reference, and it can be backward one.
732         DebugInfoPatcher.addDestinationReferenceLabel(DestinationAddress);
733         break;
734       }
735       }
736       ++Index;
737     }
738   }
739   if (DIEOffset > NextCUOffset)
740     errs() << "BOLT-WARNING: corrupt DWARF detected at 0x"
741            << Twine::utohexstr(Unit.getOffset()) << '\n';
742 }
743 
744 void DWARFRewriter::updateDWARFObjectAddressRanges(
745     const DWARFDie DIE, uint64_t DebugRangesOffset,
746     SimpleBinaryPatcher &DebugInfoPatcher, DebugAbbrevWriter &AbbrevWriter,
747     Optional<uint64_t> RangesBase) {
748 
749   // Some objects don't have an associated DIE and cannot be updated (such as
750   // compiler-generated functions).
751   if (!DIE)
752     return;
753 
754   const DWARFAbbreviationDeclaration *AbbreviationDecl =
755       DIE.getAbbreviationDeclarationPtr();
756   if (!AbbreviationDecl) {
757     if (opts::Verbosity >= 1)
758       errs() << "BOLT-WARNING: object's DIE doesn't have an abbreviation: "
759              << "skipping update. DIE at offset 0x"
760              << Twine::utohexstr(DIE.getOffset()) << '\n';
761     return;
762   }
763 
764   if (RangesBase) {
765     // If DW_AT_GNU_ranges_base is present, update it. No further modifications
766     // are needed for ranges base.
767     Optional<AttrInfo> RangesBaseAttrInfo =
768         findAttributeInfo(DIE, dwarf::DW_AT_GNU_ranges_base);
769     if (!RangesBaseAttrInfo)
770       RangesBaseAttrInfo = findAttributeInfo(DIE, dwarf::DW_AT_rnglists_base);
771 
772     if (RangesBaseAttrInfo) {
773       DebugInfoPatcher.addLE32Patch(RangesBaseAttrInfo->Offset,
774                                     static_cast<uint32_t>(*RangesBase),
775                                     RangesBaseAttrInfo->Size);
776       RangesBase = None;
777     }
778   }
779 
780   Optional<AttrInfo> LowPCAttrInfo =
781       findAttributeInfo(DIE, dwarf::DW_AT_low_pc);
782   if (Optional<AttrInfo> AttrVal =
783           findAttributeInfo(DIE, dwarf::DW_AT_ranges)) {
784     // Case 1: The object was already non-contiguous and had DW_AT_ranges.
785     // In this case we simply need to update the value of DW_AT_ranges
786     // and introduce DW_AT_GNU_ranges_base if required.
787     std::lock_guard<std::mutex> Lock(DebugInfoPatcherMutex);
788     // For DWARF5 converting all of DW_AT_ranges into DW_FORM_rnglistx
789     bool Converted = false;
790     if (DIE.getDwarfUnit()->getVersion() >= 5 &&
791         AttrVal->V.getForm() == dwarf::DW_FORM_sec_offset) {
792       AbbrevWriter.addAttributePatch(*DIE.getDwarfUnit(), AbbreviationDecl,
793                                      dwarf::DW_AT_ranges, dwarf::DW_AT_ranges,
794                                      dwarf::DW_FORM_rnglistx);
795       Converted = true;
796     }
797     if (Converted || AttrVal->V.getForm() == dwarf::DW_FORM_rnglistx)
798       DebugInfoPatcher.addUDataPatch(AttrVal->Offset, DebugRangesOffset,
799                                      AttrVal->Size);
800     else
801       DebugInfoPatcher.addLE32Patch(
802           AttrVal->Offset, DebugRangesOffset - DebugInfoPatcher.getRangeBase(),
803           AttrVal->Size);
804 
805     if (!RangesBase) {
806       if (LowPCAttrInfo &&
807           LowPCAttrInfo->V.getForm() != dwarf::DW_FORM_GNU_addr_index &&
808           LowPCAttrInfo->V.getForm() != dwarf::DW_FORM_addrx)
809         DebugInfoPatcher.addLE64Patch(LowPCAttrInfo->Offset, 0);
810       return;
811     }
812 
813     // Convert DW_AT_low_pc into DW_AT_GNU_ranges_base.
814     if (!LowPCAttrInfo) {
815       errs() << "BOLT-ERROR: skeleton CU at 0x"
816              << Twine::utohexstr(DIE.getOffset())
817              << " does not have DW_AT_GNU_ranges_base or DW_AT_low_pc to"
818                 " convert to update ranges base\n";
819       return;
820     }
821 
822     AbbrevWriter.addAttribute(*DIE.getDwarfUnit(), AbbreviationDecl,
823                               dwarf::DW_AT_GNU_ranges_base,
824                               dwarf::DW_FORM_sec_offset);
825     reinterpret_cast<DebugInfoBinaryPatcher &>(DebugInfoPatcher)
826         .insertNewEntry(DIE, *RangesBase);
827 
828     return;
829   }
830 
831   // Case 2: The object has both DW_AT_low_pc and DW_AT_high_pc emitted back
832   // to back. Replace with new attributes and patch the DIE.
833   Optional<AttrInfo> HighPCAttrInfo =
834       findAttributeInfo(DIE, dwarf::DW_AT_high_pc);
835   if (LowPCAttrInfo && HighPCAttrInfo) {
836     convertToRangesPatchAbbrev(*DIE.getDwarfUnit(), AbbreviationDecl,
837                                AbbrevWriter, RangesBase);
838     convertToRangesPatchDebugInfo(DIE, DebugRangesOffset, DebugInfoPatcher,
839                                   RangesBase);
840   } else {
841     if (opts::Verbosity >= 1)
842       errs() << "BOLT-ERROR: cannot update ranges for DIE at offset 0x"
843              << Twine::utohexstr(DIE.getOffset()) << '\n';
844   }
845 }
846 
847 void DWARFRewriter::updateLineTableOffsets(const MCAsmLayout &Layout) {
848   ErrorOr<BinarySection &> DbgInfoSection =
849       BC.getUniqueSectionByName(".debug_info");
850   ErrorOr<BinarySection &> TypeInfoSection =
851       BC.getUniqueSectionByName(".debug_types");
852   assert(((BC.DwCtx->getNumTypeUnits() > 0 && TypeInfoSection) ||
853           BC.DwCtx->getNumTypeUnits() == 0) &&
854          "Was not able to retrieve Debug Types section.");
855 
856   // We will be re-writing .debug_info so relocation mechanism doesn't work for
857   // Debug Info Patcher.
858   DebugInfoBinaryPatcher *DebugInfoPatcher = nullptr;
859   if (BC.DwCtx->getNumCompileUnits()) {
860     DbgInfoSection->registerPatcher(std::make_unique<DebugInfoBinaryPatcher>());
861     DebugInfoPatcher =
862         static_cast<DebugInfoBinaryPatcher *>(DbgInfoSection->getPatcher());
863   }
864 
865   // There is no direct connection between CU and TU, but same offsets,
866   // encoded in DW_AT_stmt_list, into .debug_line get modified.
867   // We take advantage of that to map original CU line table offsets to new
868   // ones.
869   std::unordered_map<uint64_t, uint64_t> DebugLineOffsetMap;
870 
871   auto GetStatementListValue = [](DWARFUnit *Unit) {
872     Optional<DWARFFormValue> StmtList =
873         Unit->getUnitDIE().find(dwarf::DW_AT_stmt_list);
874     Optional<uint64_t> Offset = dwarf::toSectionOffset(StmtList);
875     assert(Offset && "Was not able to retreive value of DW_AT_stmt_list.");
876     return *Offset;
877   };
878 
879   const uint64_t Reloc32Type = BC.isAArch64()
880                                    ? static_cast<uint64_t>(ELF::R_AARCH64_ABS32)
881                                    : static_cast<uint64_t>(ELF::R_X86_64_32);
882 
883   for (const std::unique_ptr<DWARFUnit> &CU : BC.DwCtx->compile_units()) {
884     const unsigned CUID = CU->getOffset();
885     MCSymbol *Label = BC.getDwarfLineTable(CUID).getLabel();
886     if (!Label)
887       continue;
888 
889     Optional<AttrInfo> AttrVal =
890         findAttributeInfo(CU.get()->getUnitDIE(), dwarf::DW_AT_stmt_list);
891     if (!AttrVal)
892       continue;
893 
894     const uint64_t AttributeOffset = AttrVal->Offset;
895     const uint64_t LineTableOffset = Layout.getSymbolOffset(*Label);
896     DebugLineOffsetMap[GetStatementListValue(CU.get())] = LineTableOffset;
897     assert(DbgInfoSection && ".debug_info section must exist");
898     DebugInfoPatcher->addLE32Patch(AttributeOffset, LineTableOffset);
899   }
900 
901   for (const std::unique_ptr<DWARFUnit> &TU : BC.DwCtx->types_section_units()) {
902     DWARFUnit *Unit = TU.get();
903     Optional<AttrInfo> AttrVal =
904         findAttributeInfo(TU.get()->getUnitDIE(), dwarf::DW_AT_stmt_list);
905     if (!AttrVal)
906       continue;
907     const uint64_t AttributeOffset = AttrVal->Offset;
908     auto Iter = DebugLineOffsetMap.find(GetStatementListValue(Unit));
909     assert(Iter != DebugLineOffsetMap.end() &&
910            "Type Unit Updated Line Number Entry does not exist.");
911     TypeInfoSection->addRelocation(AttributeOffset, nullptr, Reloc32Type,
912                                    Iter->second, 0, /*Pending=*/true);
913   }
914 
915   // Set .debug_info as finalized so it won't be skipped over when
916   // we process sections while writing out the new binary. This ensures
917   // that the pending relocations will be processed and not ignored.
918   if (DbgInfoSection)
919     DbgInfoSection->setIsFinalized();
920 
921   if (TypeInfoSection)
922     TypeInfoSection->setIsFinalized();
923 }
924 
925 CUOffsetMap
926 DWARFRewriter::finalizeDebugSections(DebugInfoBinaryPatcher &DebugInfoPatcher) {
927   if (StrWriter->isInitialized()) {
928     RewriteInstance::addToDebugSectionsToOverwrite(".debug_str");
929     std::unique_ptr<DebugStrBufferVector> DebugStrSectionContents =
930         StrWriter->releaseBuffer();
931     BC.registerOrUpdateNoteSection(".debug_str",
932                                    copyByteArray(*DebugStrSectionContents),
933                                    DebugStrSectionContents->size());
934   }
935 
936   if (StrOffstsWriter->isFinalized()) {
937     RewriteInstance::addToDebugSectionsToOverwrite(".debug_str_offsets");
938     std::unique_ptr<DebugStrOffsetsBufferVector>
939         DebugStrOffsetsSectionContents = StrOffstsWriter->releaseBuffer();
940     BC.registerOrUpdateNoteSection(
941         ".debug_str_offsets", copyByteArray(*DebugStrOffsetsSectionContents),
942         DebugStrOffsetsSectionContents->size());
943   }
944 
945   std::unique_ptr<DebugBufferVector> RangesSectionContents =
946       RangesSectionWriter->releaseBuffer();
947   BC.registerOrUpdateNoteSection(
948       llvm::isa<DebugRangeListsSectionWriter>(*RangesSectionWriter)
949           ? ".debug_rnglists"
950           : ".debug_ranges",
951       copyByteArray(*RangesSectionContents), RangesSectionContents->size());
952 
953   if (BC.isDWARF5Used()) {
954     std::unique_ptr<DebugBufferVector> LocationListSectionContents =
955         makeFinalLocListsSection(DebugInfoPatcher, DWARFVersion::DWARF5);
956     if (!LocationListSectionContents->empty())
957       BC.registerOrUpdateNoteSection(
958           ".debug_loclists", copyByteArray(*LocationListSectionContents),
959           LocationListSectionContents->size());
960   }
961 
962   if (BC.isDWARFLegacyUsed()) {
963     std::unique_ptr<DebugBufferVector> LocationListSectionContents =
964         makeFinalLocListsSection(DebugInfoPatcher, DWARFVersion::DWARFLegacy);
965     if (!LocationListSectionContents->empty())
966       BC.registerOrUpdateNoteSection(
967           ".debug_loc", copyByteArray(*LocationListSectionContents),
968           LocationListSectionContents->size());
969   }
970 
971   // AddrWriter should be finalized after debug_loc since more addresses can be
972   // added there.
973   if (AddrWriter->isInitialized()) {
974     AddressSectionBuffer AddressSectionContents = AddrWriter->finalize();
975     BC.registerOrUpdateNoteSection(".debug_addr",
976                                    copyByteArray(AddressSectionContents),
977                                    AddressSectionContents.size());
978     for (auto &CU : BC.DwCtx->compile_units()) {
979       DWARFDie DIE = CU->getUnitDIE();
980       uint64_t Offset = 0;
981       uint64_t AttrOffset = 0;
982       uint32_t Size = 0;
983       Optional<AttrInfo> AttrValGnu =
984           findAttributeInfo(DIE, dwarf::DW_AT_GNU_addr_base);
985       Optional<AttrInfo> AttrVal =
986           findAttributeInfo(DIE, dwarf::DW_AT_addr_base);
987 
988       // For cases where Skeleton CU does not have DW_AT_GNU_addr_base
989       if (!AttrValGnu && CU->getVersion() < 5)
990         continue;
991 
992       Offset = AddrWriter->getOffset(*CU);
993 
994       if (AttrValGnu) {
995         AttrOffset = AttrValGnu->Offset;
996         Size = AttrValGnu->Size;
997       }
998 
999       if (AttrVal) {
1000         AttrOffset = AttrVal->Offset;
1001         Size = AttrVal->Size;
1002       }
1003 
1004       if (AttrValGnu || AttrVal) {
1005         DebugInfoPatcher.addLE32Patch(AttrOffset, static_cast<int32_t>(Offset),
1006                                       Size);
1007       } else if (CU->getVersion() >= 5) {
1008         // A case where we were not using .debug_addr section, but after update
1009         // now using it.
1010         const DWARFAbbreviationDeclaration *Abbrev =
1011             DIE.getAbbreviationDeclarationPtr();
1012         AbbrevWriter->addAttribute(*CU, Abbrev, dwarf::DW_AT_addr_base,
1013                                    dwarf::DW_FORM_sec_offset);
1014         DebugInfoPatcher.insertNewEntry(DIE, static_cast<int32_t>(Offset));
1015       }
1016     }
1017   }
1018 
1019   std::unique_ptr<DebugBufferVector> AbbrevSectionContents =
1020       AbbrevWriter->finalize();
1021   BC.registerOrUpdateNoteSection(".debug_abbrev",
1022                                  copyByteArray(*AbbrevSectionContents),
1023                                  AbbrevSectionContents->size());
1024 
1025   // Update abbreviation offsets for CUs/TUs if they were changed.
1026   SimpleBinaryPatcher *DebugTypesPatcher = nullptr;
1027   for (auto &Unit : BC.DwCtx->normal_units()) {
1028     const uint64_t NewAbbrevOffset =
1029         AbbrevWriter->getAbbreviationsOffsetForUnit(*Unit);
1030     if (Unit->getAbbreviationsOffset() == NewAbbrevOffset)
1031       continue;
1032 
1033     // DWARFv4 or earlier
1034     // unit_length - 4 bytes
1035     // version - 2 bytes
1036     // So + 6 to patch debug_abbrev_offset
1037     constexpr uint64_t AbbrevFieldOffsetLegacy = 6;
1038     // DWARFv5
1039     // unit_length - 4 bytes
1040     // version - 2 bytes
1041     // unit_type - 1 byte
1042     // address_size - 1 byte
1043     // So + 8 to patch debug_abbrev_offset
1044     constexpr uint64_t AbbrevFieldOffsetV5 = 8;
1045     uint64_t AbbrevOffset =
1046         Unit->getVersion() >= 5 ? AbbrevFieldOffsetV5 : AbbrevFieldOffsetLegacy;
1047     if (!Unit->isTypeUnit() || Unit->getVersion() >= 5) {
1048       DebugInfoPatcher.addLE32Patch(Unit->getOffset() + AbbrevOffset,
1049                                     static_cast<uint32_t>(NewAbbrevOffset));
1050       continue;
1051     }
1052 
1053     if (!DebugTypesPatcher) {
1054       ErrorOr<BinarySection &> DebugTypes =
1055           BC.getUniqueSectionByName(".debug_types");
1056       DebugTypes->registerPatcher(std::make_unique<SimpleBinaryPatcher>());
1057       DebugTypesPatcher =
1058           static_cast<SimpleBinaryPatcher *>(DebugTypes->getPatcher());
1059     }
1060     DebugTypesPatcher->addLE32Patch(Unit->getOffset() + AbbrevOffset,
1061                                     static_cast<uint32_t>(NewAbbrevOffset));
1062   }
1063 
1064   // No more creating new DebugInfoPatches.
1065   CUOffsetMap CUMap =
1066       DebugInfoPatcher.computeNewOffsets(*BC.DwCtx.get(), false);
1067 
1068   // Skip .debug_aranges if we are re-generating .gdb_index.
1069   if (opts::KeepARanges || !BC.getGdbIndexSection()) {
1070     SmallVector<char, 16> ARangesBuffer;
1071     raw_svector_ostream OS(ARangesBuffer);
1072 
1073     auto MAB = std::unique_ptr<MCAsmBackend>(
1074         BC.TheTarget->createMCAsmBackend(*BC.STI, *BC.MRI, MCTargetOptions()));
1075 
1076     ARangesSectionWriter->writeARangesSection(OS, CUMap);
1077     const StringRef &ARangesContents = OS.str();
1078 
1079     BC.registerOrUpdateNoteSection(".debug_aranges",
1080                                    copyByteArray(ARangesContents),
1081                                    ARangesContents.size());
1082   }
1083   return CUMap;
1084 }
1085 
1086 // Creates all the data structures necessary for creating MCStreamer.
1087 // They are passed by reference because they need to be kept around.
1088 // Also creates known debug sections. These are sections handled by
1089 // handleDebugDataPatching.
1090 using KnownSectionsEntry = std::pair<MCSection *, DWARFSectionKind>;
1091 namespace {
1092 
1093 std::unique_ptr<BinaryContext>
1094 createDwarfOnlyBC(const object::ObjectFile &File) {
1095   return cantFail(BinaryContext::createBinaryContext(
1096       &File, false,
1097       DWARFContext::create(File, DWARFContext::ProcessDebugRelocations::Ignore,
1098                            nullptr, "", WithColor::defaultErrorHandler,
1099                            WithColor::defaultWarningHandler)));
1100 }
1101 
1102 StringMap<KnownSectionsEntry>
1103 createKnownSectionsMap(const MCObjectFileInfo &MCOFI) {
1104   StringMap<KnownSectionsEntry> KnownSectionsTemp = {
1105       {"debug_info.dwo", {MCOFI.getDwarfInfoDWOSection(), DW_SECT_INFO}},
1106       {"debug_types.dwo", {MCOFI.getDwarfTypesDWOSection(), DW_SECT_EXT_TYPES}},
1107       {"debug_str_offsets.dwo",
1108        {MCOFI.getDwarfStrOffDWOSection(), DW_SECT_STR_OFFSETS}},
1109       {"debug_str.dwo", {MCOFI.getDwarfStrDWOSection(), DW_SECT_EXT_unknown}},
1110       {"debug_loc.dwo", {MCOFI.getDwarfLocDWOSection(), DW_SECT_EXT_LOC}},
1111       {"debug_abbrev.dwo", {MCOFI.getDwarfAbbrevDWOSection(), DW_SECT_ABBREV}},
1112       {"debug_line.dwo", {MCOFI.getDwarfLineDWOSection(), DW_SECT_LINE}},
1113       {"debug_loclists.dwo",
1114        {MCOFI.getDwarfLoclistsDWOSection(), DW_SECT_LOCLISTS}},
1115       {"debug_rnglists.dwo",
1116        {MCOFI.getDwarfRnglistsDWOSection(), DW_SECT_RNGLISTS}}};
1117   return KnownSectionsTemp;
1118 }
1119 
1120 StringRef getSectionName(const SectionRef &Section) {
1121   Expected<StringRef> SectionName = Section.getName();
1122   assert(SectionName && "Invalid section name.");
1123   StringRef Name = *SectionName;
1124   Name = Name.substr(Name.find_first_not_of("._"));
1125   return Name;
1126 }
1127 
1128 // Exctracts an appropriate slice if input is DWP.
1129 // Applies patches or overwrites the section.
1130 Optional<StringRef>
1131 updateDebugData(DWARFContext &DWCtx, std::string &Storage,
1132                 StringRef SectionName, StringRef SectionContents,
1133                 const StringMap<KnownSectionsEntry> &KnownSections,
1134                 MCStreamer &Streamer, DWARFRewriter &Writer,
1135                 const DWARFUnitIndex::Entry *CUDWOEntry, uint64_t DWOId,
1136                 std::unique_ptr<DebugBufferVector> &OutputBuffer,
1137                 DebugRangeListsSectionWriter *RangeListsWriter) {
1138   auto applyPatch = [&](DebugInfoBinaryPatcher *Patcher,
1139                         StringRef Data) -> StringRef {
1140     Patcher->computeNewOffsets(DWCtx, true);
1141     Storage = Patcher->patchBinary(Data);
1142     return StringRef(Storage.c_str(), Storage.size());
1143   };
1144 
1145   using DWOSectionContribution =
1146       const DWARFUnitIndex::Entry::SectionContribution;
1147   auto getSliceData = [&](const DWARFUnitIndex::Entry *DWOEntry,
1148                           StringRef OutData, DWARFSectionKind Sec,
1149                           uint32_t &DWPOffset) -> StringRef {
1150     if (DWOEntry) {
1151       DWOSectionContribution *DWOContrubution = DWOEntry->getContribution(Sec);
1152       DWPOffset = DWOContrubution->Offset;
1153       OutData = OutData.substr(DWPOffset, DWOContrubution->Length);
1154     }
1155     return OutData;
1156   };
1157 
1158   auto SectionIter = KnownSections.find(SectionName);
1159   if (SectionIter == KnownSections.end())
1160     return None;
1161 
1162   Streamer.switchSection(SectionIter->second.first);
1163   StringRef OutData = SectionContents;
1164   uint32_t DWPOffset = 0;
1165 
1166   switch (SectionIter->second.second) {
1167   default: {
1168     if (!SectionName.equals("debug_str.dwo"))
1169       errs() << "BOLT-WARNING: unsupported debug section: " << SectionName
1170              << "\n";
1171     return OutData;
1172   }
1173   case DWARFSectionKind::DW_SECT_INFO: {
1174     OutData = getSliceData(CUDWOEntry, OutData, DWARFSectionKind::DW_SECT_INFO,
1175                            DWPOffset);
1176     DebugInfoBinaryPatcher *Patcher = llvm::cast<DebugInfoBinaryPatcher>(
1177         Writer.getBinaryDWODebugInfoPatcher(DWOId));
1178     return applyPatch(Patcher, OutData);
1179   }
1180   case DWARFSectionKind::DW_SECT_EXT_TYPES: {
1181     return getSliceData(nullptr, OutData, DWARFSectionKind::DW_SECT_EXT_TYPES,
1182                         DWPOffset);
1183   }
1184   case DWARFSectionKind::DW_SECT_STR_OFFSETS: {
1185     return getSliceData(CUDWOEntry, OutData,
1186                         DWARFSectionKind::DW_SECT_STR_OFFSETS, DWPOffset);
1187   }
1188   case DWARFSectionKind::DW_SECT_ABBREV: {
1189     DebugAbbrevWriter *AbbrevWriter = Writer.getBinaryDWOAbbrevWriter(DWOId);
1190     OutputBuffer = AbbrevWriter->finalize();
1191     // Creating explicit StringRef here, otherwise
1192     // with impicit conversion it will take null byte as end of
1193     // string.
1194     return StringRef(reinterpret_cast<const char *>(OutputBuffer->data()),
1195                      OutputBuffer->size());
1196   }
1197   case DWARFSectionKind::DW_SECT_EXT_LOC:
1198   case DWARFSectionKind::DW_SECT_LOCLISTS: {
1199     DebugLocWriter *LocWriter = Writer.getDebugLocWriter(DWOId);
1200     OutputBuffer = LocWriter->getBuffer();
1201     // Creating explicit StringRef here, otherwise
1202     // with impicit conversion it will take null byte as end of
1203     // string.
1204     return StringRef(reinterpret_cast<const char *>(OutputBuffer->data()),
1205                      OutputBuffer->size());
1206   }
1207   case DWARFSectionKind::DW_SECT_LINE: {
1208     return getSliceData(CUDWOEntry, OutData, DWARFSectionKind::DW_SECT_LINE,
1209                         DWPOffset);
1210   }
1211   case DWARFSectionKind::DW_SECT_RNGLISTS: {
1212     OutputBuffer = RangeListsWriter->releaseBuffer();
1213     return StringRef(reinterpret_cast<const char *>(OutputBuffer->data()),
1214                      OutputBuffer->size());
1215   }
1216   }
1217 }
1218 
1219 } // namespace
1220 
1221 struct TUContribution {
1222   uint64_t Signature{0};
1223   uint32_t Length{0};
1224 };
1225 using TUContributionVector = std::vector<TUContribution>;
1226 /// Iterates over all the signatures used in this CU, and
1227 /// uses TU Index to extract their contributions from the DWP file.
1228 /// It stores them in DWOTUSection.
1229 static std::string extractDWOTUFromDWP(
1230     const DWARFRewriter::DebugTypesSignaturesPerCUMap &TypeSignaturesPerCU,
1231     const DWARFUnitIndex &TUIndex, StringRef Contents,
1232     TUContributionVector &TUContributionsToCU, uint64_t DWOId) {
1233   std::string DWOTUSection;
1234   using TUEntry =
1235       std::pair<uint64_t, const DWARFUnitIndex::Entry::SectionContribution *>;
1236   std::vector<TUEntry> TUContributions;
1237   for (const uint64_t TUSignature : TypeSignaturesPerCU.at(DWOId)) {
1238     const DWARFUnitIndex::Entry *TUDWOEntry = TUIndex.getFromHash(TUSignature);
1239     const DWARFUnitIndex::Entry::SectionContribution *C =
1240         TUDWOEntry->getContribution(DW_SECT_EXT_TYPES);
1241     TUContributions.emplace_back(TUSignature, C);
1242   }
1243 
1244   // Sorting so it's easy to compare output.
1245   // They should be sharing the same Abbrev.
1246   std::sort(TUContributions.begin(), TUContributions.end(),
1247             [](const TUEntry &V1, const TUEntry &V2) -> bool {
1248               return V1.second->Offset < V2.second->Offset;
1249             });
1250 
1251   for (auto &PairEntry : TUContributions) {
1252     const DWARFUnitIndex::Entry::SectionContribution *C = PairEntry.second;
1253     const uint64_t TUSignature = PairEntry.first;
1254     DWOTUSection.append(Contents.slice(C->Offset, C->Offset + C->Length).str());
1255     TUContributionsToCU.push_back({TUSignature, C->Length});
1256   }
1257   return DWOTUSection;
1258 }
1259 
1260 static void extractDWOTUFromDWO(StringRef Contents,
1261                                 TUContributionVector &TUContributionsToCU) {
1262   uint64_t Offset = 0;
1263   DataExtractor Data(Contents, true, 0);
1264   while (Data.isValidOffset(Offset)) {
1265     auto PrevOffset = Offset;
1266     // Length of the unit, including the 4 byte length field.
1267     const uint32_t Length = Data.getU32(&Offset) + 4;
1268 
1269     Data.getU16(&Offset); // Version
1270     Data.getU32(&Offset); // Abbrev offset
1271     Data.getU8(&Offset);  // Address size
1272     const auto TUSignature = Data.getU64(&Offset);
1273     Offset = PrevOffset + Length;
1274     TUContributionsToCU.push_back({TUSignature, Length});
1275   }
1276 }
1277 
1278 static void extractTypesFromDWPDWARF5(
1279     const MCObjectFileInfo &MCOFI, const DWARFUnitIndex &TUIndex,
1280     const DWARFRewriter::DebugTypesSignaturesPerCUMap &TypeSignaturesPerCU,
1281     MCStreamer &Streamer, StringRef Contents, uint64_t DWOId) {
1282   std::vector<const DWARFUnitIndex::Entry::SectionContribution *>
1283       TUContributions;
1284   for (const uint64_t Val : TypeSignaturesPerCU.at(DWOId)) {
1285     const DWARFUnitIndex::Entry *TUE = TUIndex.getFromHash(Val);
1286     const DWARFUnitIndex::Entry::SectionContribution *C =
1287         TUE->getContribution(DWARFSectionKind::DW_SECT_INFO);
1288     TUContributions.push_back(C);
1289   }
1290   // Sorting so it's easy to compare output.
1291   // They should be sharing the same Abbrev.
1292   std::sort(TUContributions.begin(), TUContributions.end(),
1293             [](const DWARFUnitIndex::Entry::SectionContribution *V1,
1294                const DWARFUnitIndex::Entry::SectionContribution *V2) -> bool {
1295               return V1->Offset < V2->Offset;
1296             });
1297   Streamer.switchSection(MCOFI.getDwarfInfoDWOSection());
1298   for (const auto *C : TUContributions)
1299     Streamer.emitBytes(Contents.slice(C->Offset, C->Offset + C->Length));
1300 }
1301 
1302 void DWARFRewriter::writeDWP(
1303     std::unordered_map<uint64_t, std::string> &DWOIdToName) {
1304   SmallString<0> OutputNameStr;
1305   StringRef OutputName;
1306   if (opts::DwarfOutputPath.empty()) {
1307     OutputName =
1308         Twine(opts::OutputFilename).concat(".dwp").toStringRef(OutputNameStr);
1309   } else {
1310     StringRef ExeFileName = llvm::sys::path::filename(opts::OutputFilename);
1311     OutputName = Twine(opts::DwarfOutputPath)
1312                      .concat("/")
1313                      .concat(ExeFileName)
1314                      .concat(".dwp")
1315                      .toStringRef(OutputNameStr);
1316     errs() << "BOLT-WARNING: dwarf-output-path is in effect and .dwp file will "
1317               "possibly be written to another location that is not the same as "
1318               "the executable\n";
1319   }
1320   std::error_code EC;
1321   std::unique_ptr<ToolOutputFile> Out =
1322       std::make_unique<ToolOutputFile>(OutputName, EC, sys::fs::OF_None);
1323 
1324   const object::ObjectFile *File = BC.DwCtx->getDWARFObj().getFile();
1325   std::unique_ptr<BinaryContext> TmpBC = createDwarfOnlyBC(*File);
1326   std::unique_ptr<MCStreamer> Streamer = TmpBC->createStreamer(Out->os());
1327   const MCObjectFileInfo &MCOFI = *Streamer->getContext().getObjectFileInfo();
1328   StringMap<KnownSectionsEntry> KnownSections = createKnownSectionsMap(MCOFI);
1329   MCSection *const StrSection = MCOFI.getDwarfStrDWOSection();
1330   MCSection *const StrOffsetSection = MCOFI.getDwarfStrOffDWOSection();
1331 
1332   // Data Structures for DWP book keeping
1333   // Size of array corresponds to the number of sections supported by DWO format
1334   // in DWARF4/5.
1335   uint32_t ContributionOffsets[8] = {};
1336   std::deque<SmallString<32>> UncompressedSections;
1337   DWPStringPool Strings(*Streamer, StrSection);
1338   MapVector<uint64_t, UnitIndexEntry> IndexEntries;
1339   MapVector<uint64_t, UnitIndexEntry> TypeIndexEntries;
1340   uint16_t Version = 0;
1341   uint32_t IndexVersion = 2;
1342 
1343   // Setup DWP code once.
1344   DWARFContext *DWOCtx = BC.getDWOContext();
1345   const DWARFUnitIndex *CUIndex = nullptr;
1346   const DWARFUnitIndex *TUIndex = nullptr;
1347   bool IsDWP = false;
1348   if (DWOCtx) {
1349     CUIndex = &DWOCtx->getCUIndex();
1350     TUIndex = &DWOCtx->getTUIndex();
1351     IsDWP = !CUIndex->getRows().empty();
1352   }
1353 
1354   for (const std::unique_ptr<DWARFUnit> &CU : BC.DwCtx->compile_units()) {
1355     Optional<uint64_t> DWOId = CU->getDWOId();
1356     if (!DWOId)
1357       continue;
1358 
1359     // Skipping CUs that we failed to load.
1360     Optional<DWARFUnit *> DWOCU = BC.getDWOCU(*DWOId);
1361     if (!DWOCU)
1362       continue;
1363 
1364     if (Version == 0) {
1365       Version = CU->getVersion();
1366       IndexVersion = Version < 5 ? 2 : 5;
1367     } else if (Version != CU->getVersion()) {
1368       errs() << "BOLT-ERROR: Incompatible DWARF compile unit versions.\n";
1369       exit(1);
1370     }
1371 
1372     UnitIndexEntry CurEntry = {};
1373     CurEntry.DWOName =
1374         dwarf::toString(CU->getUnitDIE().find(
1375                             {dwarf::DW_AT_dwo_name, dwarf::DW_AT_GNU_dwo_name}),
1376                         "");
1377     const char *Name = CU->getUnitDIE().getShortName();
1378     if (Name)
1379       CurEntry.Name = Name;
1380     StringRef CurStrSection;
1381     StringRef CurStrOffsetSection;
1382 
1383     // This maps each section contained in this file to its length.
1384     // This information is later on used to calculate the contributions,
1385     // i.e. offset and length, of each compile/type unit to a section.
1386     std::vector<std::pair<DWARFSectionKind, uint32_t>> SectionLength;
1387 
1388     const DWARFUnitIndex::Entry *CUDWOEntry = nullptr;
1389     if (IsDWP)
1390       CUDWOEntry = CUIndex->getFromHash(*DWOId);
1391 
1392     bool StrSectionWrittenOut = false;
1393     const object::ObjectFile *DWOFile =
1394         (*DWOCU)->getContext().getDWARFObj().getFile();
1395 
1396     DebugRangeListsSectionWriter *RangeListssWriter = nullptr;
1397     if (CU->getVersion() == 5) {
1398       assert(RangeListsWritersByCU.count(*DWOId) != 0 &&
1399              "No RangeListsWriter for DWO ID.");
1400       RangeListssWriter = RangeListsWritersByCU[*DWOId].get();
1401     }
1402     std::string DWOTUSection;
1403     TUContributionVector TUContributionsToCU;
1404     for (const SectionRef &Section : DWOFile->sections()) {
1405       std::string DWOTUSection;
1406       std::string Storage = "";
1407       std::unique_ptr<DebugBufferVector> OutputData;
1408       StringRef SectionName = getSectionName(Section);
1409       Expected<StringRef> ContentsExp = Section.getContents();
1410       assert(ContentsExp && "Invalid contents.");
1411       StringRef Contents = *ContentsExp;
1412       const bool IsTypesDWO = SectionName == "debug_types.dwo";
1413       if (IsDWP && IsTypesDWO) {
1414         assert(TUIndex &&
1415                "DWP Input with .debug_types.dwo section with TU Index.");
1416         DWOTUSection =
1417             extractDWOTUFromDWP(TypeSignaturesPerCU, *TUIndex, Contents,
1418                                 TUContributionsToCU, *DWOId);
1419         Contents = DWOTUSection;
1420       } else if (IsTypesDWO) {
1421         extractDWOTUFromDWO(Contents, TUContributionsToCU);
1422       }
1423 
1424       Optional<StringRef> TOutData = updateDebugData(
1425           (*DWOCU)->getContext(), Storage, SectionName, Contents, KnownSections,
1426           *Streamer, *this, CUDWOEntry, *DWOId, OutputData, RangeListssWriter);
1427       if (!TOutData)
1428         continue;
1429 
1430       StringRef OutData = *TOutData;
1431       if (IsTypesDWO) {
1432         Streamer->emitBytes(OutData);
1433         continue;
1434       }
1435 
1436       if (SectionName.equals("debug_str.dwo")) {
1437         CurStrSection = OutData;
1438       } else {
1439         // Since handleDebugDataPatching returned true, we already know this is
1440         // a known section.
1441         auto SectionIter = KnownSections.find(SectionName);
1442         if (SectionIter->second.second == DWARFSectionKind::DW_SECT_STR_OFFSETS)
1443           CurStrOffsetSection = OutData;
1444         else
1445           Streamer->emitBytes(OutData);
1446         auto Index =
1447             getContributionIndex(SectionIter->second.second, IndexVersion);
1448         CurEntry.Contributions[Index].Offset = ContributionOffsets[Index];
1449         CurEntry.Contributions[Index].Length = OutData.size();
1450         ContributionOffsets[Index] += CurEntry.Contributions[Index].Length;
1451       }
1452 
1453       // Strings are combined in to a new string section, and de-duplicated
1454       // based on hash.
1455       if (!StrSectionWrittenOut && !CurStrOffsetSection.empty() &&
1456           !CurStrSection.empty()) {
1457         writeStringsAndOffsets(*Streamer.get(), Strings, StrOffsetSection,
1458                                CurStrSection, CurStrOffsetSection,
1459                                CU->getVersion());
1460         StrSectionWrittenOut = true;
1461       }
1462     }
1463     CompileUnitIdentifiers CUI{*DWOId, CurEntry.Name.c_str(),
1464                                CurEntry.DWOName.c_str()};
1465     auto P = IndexEntries.insert(std::make_pair(CUI.Signature, CurEntry));
1466     if (!P.second) {
1467       Error Err = buildDuplicateError(*P.first, CUI, "");
1468       errs() << "BOLT-ERROR: " << toString(std::move(Err)) << "\n";
1469       return;
1470     }
1471 
1472     // Handling TU
1473     if (!TUContributionsToCU.empty()) {
1474       const unsigned Index =
1475           getContributionIndex(DW_SECT_EXT_TYPES, IndexVersion);
1476       for (const TUContribution &TUC : TUContributionsToCU) {
1477         UnitIndexEntry TUEntry = CurEntry;
1478         TUEntry.Contributions[0] = {};
1479         TUEntry.Contributions[Index].Offset = ContributionOffsets[Index];
1480         TUEntry.Contributions[Index].Length = TUC.Length;
1481         ContributionOffsets[Index] += TUEntry.Contributions[Index].Length;
1482         TypeIndexEntries.insert(std::make_pair(TUC.Signature, TUEntry));
1483       }
1484     }
1485   }
1486 
1487   if (Version < 5) {
1488     // Lie about there being no info contributions so the TU index only includes
1489     // the type unit contribution for DWARF < 5. In DWARFv5 the TU index has a
1490     // contribution to the info section, so we do not want to lie about it.
1491     ContributionOffsets[0] = 0;
1492   }
1493   writeIndex(*Streamer.get(), MCOFI.getDwarfTUIndexSection(),
1494              ContributionOffsets, TypeIndexEntries, IndexVersion);
1495 
1496   if (Version < 5) {
1497     // Lie about the type contribution for DWARF < 5. In DWARFv5 the type
1498     // section does not exist, so no need to do anything about this.
1499     ContributionOffsets[getContributionIndex(DW_SECT_EXT_TYPES, 2)] = 0;
1500     // Unlie about the info contribution
1501     ContributionOffsets[0] = 1;
1502   }
1503   writeIndex(*Streamer.get(), MCOFI.getDwarfCUIndexSection(),
1504              ContributionOffsets, IndexEntries, IndexVersion);
1505 
1506   Streamer->finish();
1507   Out->keep();
1508 }
1509 
1510 void DWARFRewriter::writeDWOFiles(
1511     std::unordered_map<uint64_t, std::string> &DWOIdToName) {
1512   // Setup DWP code once.
1513   DWARFContext *DWOCtx = BC.getDWOContext();
1514   const DWARFUnitIndex *CUIndex = nullptr;
1515   const DWARFUnitIndex *TUIndex = nullptr;
1516   bool IsDWP = false;
1517   if (DWOCtx) {
1518     CUIndex = &DWOCtx->getCUIndex();
1519     TUIndex = &DWOCtx->getTUIndex();
1520     IsDWP = !CUIndex->getRows().empty();
1521   }
1522 
1523   for (const std::unique_ptr<DWARFUnit> &CU : BC.DwCtx->compile_units()) {
1524     Optional<uint64_t> DWOId = CU->getDWOId();
1525     if (!DWOId)
1526       continue;
1527 
1528     // Skipping CUs that we failed to load.
1529     Optional<DWARFUnit *> DWOCU = BC.getDWOCU(*DWOId);
1530     if (!DWOCU)
1531       continue;
1532 
1533     std::string CompDir = opts::DwarfOutputPath.empty()
1534                               ? CU->getCompilationDir()
1535                               : opts::DwarfOutputPath.c_str();
1536     std::string ObjectName = getDWOName(*CU.get(), nullptr, DWOIdToName);
1537     auto FullPath = CompDir.append("/").append(ObjectName);
1538 
1539     std::error_code EC;
1540     std::unique_ptr<ToolOutputFile> TempOut =
1541         std::make_unique<ToolOutputFile>(FullPath, EC, sys::fs::OF_None);
1542 
1543     const DWARFUnitIndex::Entry *CUDWOEntry = nullptr;
1544     if (IsDWP)
1545       CUDWOEntry = CUIndex->getFromHash(*DWOId);
1546 
1547     const object::ObjectFile *File =
1548         (*DWOCU)->getContext().getDWARFObj().getFile();
1549     std::unique_ptr<BinaryContext> TmpBC = createDwarfOnlyBC(*File);
1550     std::unique_ptr<MCStreamer> Streamer = TmpBC->createStreamer(TempOut->os());
1551     const MCObjectFileInfo &MCOFI = *Streamer->getContext().getObjectFileInfo();
1552     StringMap<KnownSectionsEntry> KnownSections = createKnownSectionsMap(MCOFI);
1553 
1554     DebugRangeListsSectionWriter *RangeListssWriter = nullptr;
1555     if (CU->getVersion() == 5) {
1556       assert(RangeListsWritersByCU.count(*DWOId) != 0 &&
1557              "No RangeListsWriter for DWO ID.");
1558       RangeListssWriter = RangeListsWritersByCU[*DWOId].get();
1559 
1560       // Handling .debug_rnglists.dwo seperatly. The original .o/.dwo might not
1561       // have .debug_rnglists so won't be part of the loop below.
1562       if (!RangeListssWriter->empty()) {
1563         std::string Storage = "";
1564         std::unique_ptr<DebugBufferVector> OutputData;
1565         if (Optional<StringRef> OutData = updateDebugData(
1566                 (*DWOCU)->getContext(), Storage, "debug_rnglists.dwo", "",
1567                 KnownSections, *Streamer, *this, CUDWOEntry, *DWOId, OutputData,
1568                 RangeListssWriter))
1569           Streamer->emitBytes(*OutData);
1570       }
1571     }
1572 
1573     TUContributionVector TUContributionsToCU;
1574     for (const SectionRef &Section : File->sections()) {
1575       std::string Storage = "";
1576       std::string DWOTUSection;
1577       std::unique_ptr<DebugBufferVector> OutputData;
1578       StringRef SectionName = getSectionName(Section);
1579       if (SectionName == "debug_rnglists.dwo")
1580         continue;
1581       Expected<StringRef> ContentsExp = Section.getContents();
1582       assert(ContentsExp && "Invalid contents.");
1583       StringRef Contents = *ContentsExp;
1584       if (IsDWP && SectionName == "debug_types.dwo") {
1585         assert(TUIndex &&
1586                "DWP Input with .debug_types.dwo section with TU Index.");
1587         DWOTUSection =
1588             extractDWOTUFromDWP(TypeSignaturesPerCU, *TUIndex, Contents,
1589                                 TUContributionsToCU, *DWOId);
1590         Contents = DWOTUSection;
1591       } else if (IsDWP && CU->getVersion() >= 5 &&
1592                  SectionName == "debug_info.dwo") {
1593         assert(TUIndex &&
1594                "DWP Input with .debug_types.dwo section with TU Index.");
1595         extractTypesFromDWPDWARF5(MCOFI, *TUIndex, TypeSignaturesPerCU,
1596                                   *Streamer, Contents, *DWOId);
1597       }
1598 
1599       if (Optional<StringRef> OutData = updateDebugData(
1600               (*DWOCU)->getContext(), Storage, SectionName, Contents,
1601               KnownSections, *Streamer, *this, CUDWOEntry, *DWOId, OutputData,
1602               RangeListssWriter))
1603         Streamer->emitBytes(*OutData);
1604     }
1605     Streamer->finish();
1606     TempOut->keep();
1607   }
1608 }
1609 
1610 void DWARFRewriter::updateGdbIndexSection(CUOffsetMap &CUMap) {
1611   if (!BC.getGdbIndexSection())
1612     return;
1613 
1614   // See https://sourceware.org/gdb/onlinedocs/gdb/Index-Section-Format.html
1615   // for .gdb_index section format.
1616 
1617   StringRef GdbIndexContents = BC.getGdbIndexSection()->getContents();
1618 
1619   const char *Data = GdbIndexContents.data();
1620 
1621   // Parse the header.
1622   const uint32_t Version = read32le(Data);
1623   if (Version != 7 && Version != 8) {
1624     errs() << "BOLT-ERROR: can only process .gdb_index versions 7 and 8\n";
1625     exit(1);
1626   }
1627 
1628   // Some .gdb_index generators use file offsets while others use section
1629   // offsets. Hence we can only rely on offsets relative to each other,
1630   // and ignore their absolute values.
1631   const uint32_t CUListOffset = read32le(Data + 4);
1632   const uint32_t CUTypesOffset = read32le(Data + 8);
1633   const uint32_t AddressTableOffset = read32le(Data + 12);
1634   const uint32_t SymbolTableOffset = read32le(Data + 16);
1635   const uint32_t ConstantPoolOffset = read32le(Data + 20);
1636   Data += 24;
1637 
1638   // Map CUs offsets to indices and verify existing index table.
1639   std::map<uint32_t, uint32_t> OffsetToIndexMap;
1640   const uint32_t CUListSize = CUTypesOffset - CUListOffset;
1641   const unsigned NumCUs = BC.DwCtx->getNumCompileUnits();
1642   if (CUListSize != NumCUs * 16) {
1643     errs() << "BOLT-ERROR: .gdb_index: CU count mismatch\n";
1644     exit(1);
1645   }
1646   for (unsigned Index = 0; Index < NumCUs; ++Index, Data += 16) {
1647     const DWARFUnit *CU = BC.DwCtx->getUnitAtIndex(Index);
1648     const uint64_t Offset = read64le(Data);
1649     if (CU->getOffset() != Offset) {
1650       errs() << "BOLT-ERROR: .gdb_index CU offset mismatch\n";
1651       exit(1);
1652     }
1653 
1654     OffsetToIndexMap[Offset] = Index;
1655   }
1656 
1657   // Ignore old address table.
1658   const uint32_t OldAddressTableSize = SymbolTableOffset - AddressTableOffset;
1659   // Move Data to the beginning of symbol table.
1660   Data += SymbolTableOffset - CUTypesOffset;
1661 
1662   // Calculate the size of the new address table.
1663   uint32_t NewAddressTableSize = 0;
1664   for (const auto &CURangesPair : ARangesSectionWriter->getCUAddressRanges()) {
1665     const SmallVector<DebugAddressRange, 2> &Ranges = CURangesPair.second;
1666     NewAddressTableSize += Ranges.size() * 20;
1667   }
1668 
1669   // Difference between old and new table (and section) sizes.
1670   // Could be negative.
1671   int32_t Delta = NewAddressTableSize - OldAddressTableSize;
1672 
1673   size_t NewGdbIndexSize = GdbIndexContents.size() + Delta;
1674 
1675   // Free'd by ExecutableFileMemoryManager.
1676   auto *NewGdbIndexContents = new uint8_t[NewGdbIndexSize];
1677   uint8_t *Buffer = NewGdbIndexContents;
1678 
1679   write32le(Buffer, Version);
1680   write32le(Buffer + 4, CUListOffset);
1681   write32le(Buffer + 8, CUTypesOffset);
1682   write32le(Buffer + 12, AddressTableOffset);
1683   write32le(Buffer + 16, SymbolTableOffset + Delta);
1684   write32le(Buffer + 20, ConstantPoolOffset + Delta);
1685   Buffer += 24;
1686 
1687   // Writing out CU List <Offset, Size>
1688   for (auto &CUInfo : CUMap) {
1689     write64le(Buffer, CUInfo.second.Offset);
1690     // Length encoded in CU doesn't contain first 4 bytes that encode length.
1691     write64le(Buffer + 8, CUInfo.second.Length + 4);
1692     Buffer += 16;
1693   }
1694 
1695   // Copy over types CU list
1696   // Spec says " triplet, the first value is the CU offset, the second value is
1697   // the type offset in the CU, and the third value is the type signature"
1698   // Looking at what is being generated by gdb-add-index. The first entry is TU
1699   // offset, second entry is offset from it, and third entry is the type
1700   // signature.
1701   memcpy(Buffer, GdbIndexContents.data() + CUTypesOffset,
1702          AddressTableOffset - CUTypesOffset);
1703   Buffer += AddressTableOffset - CUTypesOffset;
1704 
1705   // Generate new address table.
1706   for (const std::pair<const uint64_t, DebugAddressRangesVector> &CURangesPair :
1707        ARangesSectionWriter->getCUAddressRanges()) {
1708     const uint32_t CUIndex = OffsetToIndexMap[CURangesPair.first];
1709     const DebugAddressRangesVector &Ranges = CURangesPair.second;
1710     for (const DebugAddressRange &Range : Ranges) {
1711       write64le(Buffer, Range.LowPC);
1712       write64le(Buffer + 8, Range.HighPC);
1713       write32le(Buffer + 16, CUIndex);
1714       Buffer += 20;
1715     }
1716   }
1717 
1718   const size_t TrailingSize =
1719       GdbIndexContents.data() + GdbIndexContents.size() - Data;
1720   assert(Buffer + TrailingSize == NewGdbIndexContents + NewGdbIndexSize &&
1721          "size calculation error");
1722 
1723   // Copy over the rest of the original data.
1724   memcpy(Buffer, Data, TrailingSize);
1725 
1726   // Register the new section.
1727   BC.registerOrUpdateNoteSection(".gdb_index", NewGdbIndexContents,
1728                                  NewGdbIndexSize);
1729 }
1730 
1731 std::unique_ptr<DebugBufferVector> DWARFRewriter::makeFinalLocListsSection(
1732     DebugInfoBinaryPatcher &DebugInfoPatcher, DWARFVersion Version) {
1733   auto LocBuffer = std::make_unique<DebugBufferVector>();
1734   auto LocStream = std::make_unique<raw_svector_ostream>(*LocBuffer);
1735   auto Writer =
1736       std::unique_ptr<MCObjectWriter>(BC.createObjectWriter(*LocStream));
1737 
1738   for (std::pair<const uint64_t, std::unique_ptr<DebugLocWriter>> &Loc :
1739        LocListWritersByCU) {
1740     DebugLocWriter *LocWriter = Loc.second.get();
1741     auto *LocListWriter = llvm::dyn_cast<DebugLoclistWriter>(LocWriter);
1742 
1743     // Filter out DWARF4, writing out DWARF5
1744     if (Version == DWARFVersion::DWARF5 &&
1745         (!LocListWriter || LocListWriter->getDwarfVersion() <= 4))
1746       continue;
1747 
1748     // Filter out DWARF5, writing out DWARF4
1749     if (Version == DWARFVersion::DWARFLegacy &&
1750         (LocListWriter && LocListWriter->getDwarfVersion() >= 5))
1751       continue;
1752 
1753     // Skipping DWARF4/5 split dwarf.
1754     if (LocListWriter && (LocListWriter->getDwarfVersion() <= 4 ||
1755                           (LocListWriter->getDwarfVersion() >= 5 &&
1756                            LocListWriter->isSplitDwarf()))) {
1757       continue;
1758     }
1759     std::unique_ptr<DebugBufferVector> CurrCULocationLists =
1760         LocWriter->getBuffer();
1761     *LocStream << *CurrCULocationLists;
1762   }
1763 
1764   return LocBuffer;
1765 }
1766 
1767 namespace {
1768 
1769 void getRangeAttrData(DWARFDie DIE, Optional<AttrInfo> &LowPCVal,
1770                       Optional<AttrInfo> &HighPCVal) {
1771   LowPCVal = findAttributeInfo(DIE, dwarf::DW_AT_low_pc);
1772   HighPCVal = findAttributeInfo(DIE, dwarf::DW_AT_high_pc);
1773   uint64_t LowPCOffset = LowPCVal->Offset;
1774   uint64_t HighPCOffset = HighPCVal->Offset;
1775   dwarf::Form LowPCForm = LowPCVal->V.getForm();
1776   dwarf::Form HighPCForm = HighPCVal->V.getForm();
1777 
1778   if (LowPCForm != dwarf::DW_FORM_addr &&
1779       LowPCForm != dwarf::DW_FORM_GNU_addr_index &&
1780       LowPCForm != dwarf::DW_FORM_addrx) {
1781     errs() << "BOLT-WARNING: unexpected low_pc form value. Cannot update DIE "
1782            << "at offset 0x" << Twine::utohexstr(DIE.getOffset()) << "\n";
1783     return;
1784   }
1785   if (HighPCForm != dwarf::DW_FORM_addr && HighPCForm != dwarf::DW_FORM_data8 &&
1786       HighPCForm != dwarf::DW_FORM_data4 &&
1787       HighPCForm != dwarf::DW_FORM_data2 &&
1788       HighPCForm != dwarf::DW_FORM_data1 &&
1789       HighPCForm != dwarf::DW_FORM_udata) {
1790     errs() << "BOLT-WARNING: unexpected high_pc form value. Cannot update DIE "
1791            << "at offset 0x" << Twine::utohexstr(DIE.getOffset()) << "\n";
1792     return;
1793   }
1794   if ((LowPCOffset == -1U || (LowPCOffset + 8 != HighPCOffset)) &&
1795       LowPCForm != dwarf::DW_FORM_GNU_addr_index &&
1796       LowPCForm != dwarf::DW_FORM_addrx) {
1797     errs() << "BOLT-WARNING: high_pc expected immediately after low_pc. "
1798            << "Cannot update DIE at offset 0x"
1799            << Twine::utohexstr(DIE.getOffset()) << '\n';
1800     return;
1801   }
1802 }
1803 
1804 } // namespace
1805 
1806 void DWARFRewriter::convertToRangesPatchAbbrev(
1807     const DWARFUnit &Unit, const DWARFAbbreviationDeclaration *Abbrev,
1808     DebugAbbrevWriter &AbbrevWriter, Optional<uint64_t> RangesBase) {
1809 
1810   dwarf::Attribute RangeBaseAttribute = dwarf::DW_AT_GNU_ranges_base;
1811   dwarf::Form RangesForm = dwarf::DW_FORM_sec_offset;
1812 
1813   if (Unit.getVersion() >= 5) {
1814     RangeBaseAttribute = dwarf::DW_AT_rnglists_base;
1815     RangesForm = dwarf::DW_FORM_rnglistx;
1816   }
1817   // If we hit this point it means we converted subprogram DIEs from
1818   // low_pc/high_pc into ranges. The CU originally didn't have DW_AT_*_base, so
1819   // we are adding it here.
1820   if (RangesBase)
1821     AbbrevWriter.addAttribute(Unit, Abbrev, RangeBaseAttribute,
1822                               dwarf::DW_FORM_sec_offset);
1823 
1824   // Converting DW_AT_high_pc into DW_AT_ranges.
1825   // For DWARF4 it's DW_FORM_sec_offset.
1826   // For DWARF5 it can be either DW_FORM_sec_offset or DW_FORM_rnglistx.
1827   // For consistency for DWARF5 we always use DW_FORM_rnglistx.
1828   AbbrevWriter.addAttributePatch(Unit, Abbrev, dwarf::DW_AT_high_pc,
1829                                  dwarf::DW_AT_ranges, RangesForm);
1830 }
1831 
1832 void DWARFRewriter::convertToRangesPatchDebugInfo(
1833     DWARFDie DIE, uint64_t RangesSectionOffset,
1834     SimpleBinaryPatcher &DebugInfoPatcher, Optional<uint64_t> RangesBase) {
1835   Optional<AttrInfo> LowPCVal = None;
1836   Optional<AttrInfo> HighPCVal = None;
1837   getRangeAttrData(DIE, LowPCVal, HighPCVal);
1838   uint64_t LowPCOffset = LowPCVal->Offset;
1839   uint64_t HighPCOffset = HighPCVal->Offset;
1840 
1841   std::lock_guard<std::mutex> Lock(DebugInfoPatcherMutex);
1842   uint32_t BaseOffset = 0;
1843   dwarf::Form LowForm = LowPCVal->V.getForm();
1844 
1845   // In DWARF4 for DW_AT_low_pc in binary DW_FORM_addr is used. In the DWO
1846   // section DW_FORM_GNU_addr_index is used. So for if we are converting
1847   // DW_AT_low_pc/DW_AT_high_pc and see DW_FORM_GNU_addr_index. We are
1848   // converting in DWO section, and DW_AT_ranges [DW_FORM_sec_offset] is
1849   // relative to DW_AT_GNU_ranges_base.
1850   if (LowForm == dwarf::DW_FORM_GNU_addr_index) {
1851     // Use ULEB128 for the value.
1852     DebugInfoPatcher.addUDataPatch(LowPCOffset, 0, LowPCVal->Size);
1853     // Ranges are relative to DW_AT_GNU_ranges_base.
1854     BaseOffset = DebugInfoPatcher.getRangeBase();
1855   } else {
1856     // In DWARF 5 we can have DW_AT_low_pc either as DW_FORM_addr, or
1857     // DW_FORM_addrx. Former is when DW_AT_rnglists_base is present. Latter is
1858     // when it's absent.
1859     if (LowForm == dwarf::DW_FORM_addrx) {
1860       const uint32_t Index =
1861           AddrWriter->getIndexFromAddress(0, *DIE.getDwarfUnit());
1862       DebugInfoPatcher.addUDataPatch(LowPCOffset, Index, LowPCVal->Size);
1863     } else
1864       DebugInfoPatcher.addLE64Patch(LowPCOffset, 0);
1865 
1866     // Original CU didn't have DW_AT_*_base. We converted it's children (or
1867     // dwo), so need to insert it into CU.
1868     if (RangesBase)
1869       reinterpret_cast<DebugInfoBinaryPatcher &>(DebugInfoPatcher)
1870           .insertNewEntry(DIE, *RangesBase);
1871   }
1872 
1873   // HighPC was conveted into DW_AT_ranges.
1874   // For DWARF5 we only access ranges throught index.
1875   if (DIE.getDwarfUnit()->getVersion() >= 5)
1876     DebugInfoPatcher.addUDataPatch(HighPCOffset, RangesSectionOffset,
1877                                    HighPCVal->Size);
1878   else
1879     DebugInfoPatcher.addLE32Patch(
1880         HighPCOffset, RangesSectionOffset - BaseOffset, HighPCVal->Size);
1881 }
1882