xref: /freebsd/contrib/llvm-project/llvm/include/llvm/DWARFLinker/Classic/DWARFLinker.h (revision 700637cbb5e582861067a11aaca4d053546871d2)
1 //===- DWARFLinker.h --------------------------------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #ifndef LLVM_DWARFLINKER_CLASSIC_DWARFLINKER_H
10 #define LLVM_DWARFLINKER_CLASSIC_DWARFLINKER_H
11 
12 #include "llvm/ADT/AddressRanges.h"
13 #include "llvm/ADT/DenseMap.h"
14 #include "llvm/CodeGen/AccelTable.h"
15 #include "llvm/CodeGen/NonRelocatableStringpool.h"
16 #include "llvm/DWARFLinker/Classic/DWARFLinkerCompileUnit.h"
17 #include "llvm/DWARFLinker/DWARFLinkerBase.h"
18 #include "llvm/DWARFLinker/IndexedValuesMap.h"
19 #include "llvm/DebugInfo/DWARF/DWARFContext.h"
20 #include "llvm/DebugInfo/DWARF/DWARFDebugLine.h"
21 #include "llvm/DebugInfo/DWARF/DWARFDebugRangeList.h"
22 #include "llvm/DebugInfo/DWARF/DWARFDie.h"
23 #include "llvm/DebugInfo/DWARF/LowLevel/DWARFExpression.h"
24 #include "llvm/Support/Compiler.h"
25 #include <map>
26 
27 namespace llvm {
28 class DWARFExpression;
29 class DWARFUnit;
30 class DataExtractor;
31 template <typename T> class SmallVectorImpl;
32 
33 namespace dwarf_linker {
34 namespace classic {
35 class DeclContextTree;
36 
37 using Offset2UnitMap = DenseMap<uint64_t, CompileUnit *>;
38 using DebugDieValuePool = IndexedValuesMap<uint64_t>;
39 
40 /// DwarfEmitter presents interface to generate all debug info tables.
41 class DwarfEmitter {
42 public:
43   virtual ~DwarfEmitter() = default;
44 
45   /// Emit section named SecName with data SecData.
46   virtual void emitSectionContents(StringRef SecData,
47                                    DebugSectionKind SecKind) = 0;
48 
49   /// Emit the abbreviation table \p Abbrevs to the .debug_abbrev section.
50   virtual void
51   emitAbbrevs(const std::vector<std::unique_ptr<DIEAbbrev>> &Abbrevs,
52               unsigned DwarfVersion) = 0;
53 
54   /// Emit the string table described by \p Pool into .debug_str table.
55   virtual void emitStrings(const NonRelocatableStringpool &Pool) = 0;
56 
57   /// Emit the debug string offset table described by \p StringOffsets into the
58   /// .debug_str_offsets table.
59   virtual void emitStringOffsets(const SmallVector<uint64_t> &StringOffsets,
60                                  uint16_t TargetDWARFVersion) = 0;
61 
62   /// Emit the string table described by \p Pool into .debug_line_str table.
63   virtual void emitLineStrings(const NonRelocatableStringpool &Pool) = 0;
64 
65   /// Emit DWARF debug names.
66   virtual void emitDebugNames(DWARF5AccelTable &Table) = 0;
67 
68   /// Emit Apple namespaces accelerator table.
69   virtual void
70   emitAppleNamespaces(AccelTable<AppleAccelTableStaticOffsetData> &Table) = 0;
71 
72   /// Emit Apple names accelerator table.
73   virtual void
74   emitAppleNames(AccelTable<AppleAccelTableStaticOffsetData> &Table) = 0;
75 
76   /// Emit Apple Objective-C accelerator table.
77   virtual void
78   emitAppleObjc(AccelTable<AppleAccelTableStaticOffsetData> &Table) = 0;
79 
80   /// Emit Apple type accelerator table.
81   virtual void
82   emitAppleTypes(AccelTable<AppleAccelTableStaticTypeData> &Table) = 0;
83 
84   /// Emit debug ranges (.debug_ranges, .debug_rnglists) header.
85   virtual MCSymbol *emitDwarfDebugRangeListHeader(const CompileUnit &Unit) = 0;
86 
87   /// Emit debug ranges (.debug_ranges, .debug_rnglists) fragment.
88   virtual void emitDwarfDebugRangeListFragment(
89       const CompileUnit &Unit, const AddressRanges &LinkedRanges,
90       PatchLocation Patch, DebugDieValuePool &AddrPool) = 0;
91 
92   /// Emit debug ranges (.debug_ranges, .debug_rnglists) footer.
93   virtual void emitDwarfDebugRangeListFooter(const CompileUnit &Unit,
94                                              MCSymbol *EndLabel) = 0;
95 
96   /// Emit debug locations (.debug_loc, .debug_loclists) header.
97   virtual MCSymbol *emitDwarfDebugLocListHeader(const CompileUnit &Unit) = 0;
98 
99   /// Emit debug locations (.debug_loc, .debug_loclists) fragment.
100   virtual void emitDwarfDebugLocListFragment(
101       const CompileUnit &Unit,
102       const DWARFLocationExpressionsVector &LinkedLocationExpression,
103       PatchLocation Patch, DebugDieValuePool &AddrPool) = 0;
104 
105   /// Emit debug locations (.debug_loc, .debug_loclists) footer.
106   virtual void emitDwarfDebugLocListFooter(const CompileUnit &Unit,
107                                            MCSymbol *EndLabel) = 0;
108 
109   /// Emit .debug_addr header.
110   virtual MCSymbol *emitDwarfDebugAddrsHeader(const CompileUnit &Unit) = 0;
111 
112   /// Emit the addresses described by \p Addrs into the .debug_addr section.
113   virtual void emitDwarfDebugAddrs(const SmallVector<uint64_t> &Addrs,
114                                    uint8_t AddrSize) = 0;
115 
116   /// Emit .debug_addr footer.
117   virtual void emitDwarfDebugAddrsFooter(const CompileUnit &Unit,
118                                          MCSymbol *EndLabel) = 0;
119 
120   /// Emit .debug_aranges entries for \p Unit
121   virtual void
122   emitDwarfDebugArangesTable(const CompileUnit &Unit,
123                              const AddressRanges &LinkedRanges) = 0;
124 
125   /// Emit specified \p LineTable into .debug_line table.
126   /// The optional parameter RowOffsets, if provided, will be populated with the
127   /// offsets of each line table row in the output .debug_line section.
128   virtual void
129   emitLineTableForUnit(const DWARFDebugLine::LineTable &LineTable,
130                        const CompileUnit &Unit, OffsetsStringPool &DebugStrPool,
131                        OffsetsStringPool &DebugLineStrPool,
132                        std::vector<uint64_t> *RowOffsets = nullptr) = 0;
133 
134   /// Emit the .debug_pubnames contribution for \p Unit.
135   virtual void emitPubNamesForUnit(const CompileUnit &Unit) = 0;
136 
137   /// Emit the .debug_pubtypes contribution for \p Unit.
138   virtual void emitPubTypesForUnit(const CompileUnit &Unit) = 0;
139 
140   /// Emit a CIE.
141   virtual void emitCIE(StringRef CIEBytes) = 0;
142 
143   /// Emit an FDE with data \p Bytes.
144   virtual void emitFDE(uint32_t CIEOffset, uint32_t AddreSize, uint64_t Address,
145                        StringRef Bytes) = 0;
146 
147   /// Emit the compilation unit header for \p Unit in the
148   /// .debug_info section.
149   ///
150   /// As a side effect, this also switches the current Dwarf version
151   /// of the MC layer to the one of U.getOrigUnit().
152   virtual void emitCompileUnitHeader(CompileUnit &Unit,
153                                      unsigned DwarfVersion) = 0;
154 
155   /// Recursively emit the DIE tree rooted at \p Die.
156   virtual void emitDIE(DIE &Die) = 0;
157 
158   /// Emit all available macro tables(DWARFv4 and DWARFv5).
159   /// Use \p UnitMacroMap to get compilation unit by macro table offset.
160   /// Side effects: Fill \p StringPool with macro strings, update
161   /// DW_AT_macro_info, DW_AT_macros attributes for corresponding compile
162   /// units.
163   virtual void emitMacroTables(DWARFContext *Context,
164                                const Offset2UnitMap &UnitMacroMap,
165                                OffsetsStringPool &StringPool) = 0;
166 
167   /// Returns size of generated .debug_line section.
168   virtual uint64_t getLineSectionSize() const = 0;
169 
170   /// Returns size of generated .debug_frame section.
171   virtual uint64_t getFrameSectionSize() const = 0;
172 
173   /// Returns size of generated .debug_ranges section.
174   virtual uint64_t getRangesSectionSize() const = 0;
175 
176   /// Returns size of generated .debug_rnglists section.
177   virtual uint64_t getRngListsSectionSize() const = 0;
178 
179   /// Returns size of generated .debug_info section.
180   virtual uint64_t getDebugInfoSectionSize() const = 0;
181 
182   /// Returns size of generated .debug_macinfo section.
183   virtual uint64_t getDebugMacInfoSectionSize() const = 0;
184 
185   /// Returns size of generated .debug_macro section.
186   virtual uint64_t getDebugMacroSectionSize() const = 0;
187 
188   /// Returns size of generated .debug_loclists section.
189   virtual uint64_t getLocListsSectionSize() const = 0;
190 
191   /// Returns size of generated .debug_addr section.
192   virtual uint64_t getDebugAddrSectionSize() const = 0;
193 
194   /// Dump the file to the disk.
195   virtual void finish() = 0;
196 };
197 
198 class DwarfStreamer;
199 using UnitListTy = std::vector<std::unique_ptr<CompileUnit>>;
200 
201 /// The core of the Dwarf linking logic.
202 ///
203 /// The generation of the dwarf information from the object files will be
204 /// driven by the selection of 'root DIEs', which are DIEs that
205 /// describe variables or functions that resolves to the corresponding
206 /// code section(and thus have entries in the Addresses map). All the debug
207 /// information that will be generated(the DIEs, but also the line
208 /// tables, ranges, ...) is derived from that set of root DIEs.
209 ///
210 /// The root DIEs are identified because they contain relocations that
211 /// points to code section(the low_pc for a function, the location for
212 /// a variable). These relocations are called ValidRelocs in the
213 /// AddressesInfo and are gathered as a very first step when we start
214 /// processing a object file.
215 class LLVM_ABI DWARFLinker : public DWARFLinkerBase {
216 public:
DWARFLinker(MessageHandlerTy ErrorHandler,MessageHandlerTy WarningHandler,std::function<StringRef (StringRef)> StringsTranslator)217   DWARFLinker(MessageHandlerTy ErrorHandler, MessageHandlerTy WarningHandler,
218               std::function<StringRef(StringRef)> StringsTranslator)
219       : StringsTranslator(StringsTranslator), ErrorHandler(ErrorHandler),
220         WarningHandler(WarningHandler) {}
221 
222   static std::unique_ptr<DWARFLinker> createLinker(
223       MessageHandlerTy ErrorHandler, MessageHandlerTy WarningHandler,
224       std::function<StringRef(StringRef)> StringsTranslator = nullptr) {
225     return std::make_unique<DWARFLinker>(ErrorHandler, WarningHandler,
226                                          StringsTranslator);
227   }
228 
229   /// Set output DWARF emitter.
setOutputDWARFEmitter(DwarfEmitter * Emitter)230   void setOutputDWARFEmitter(DwarfEmitter *Emitter) {
231     TheDwarfEmitter = Emitter;
232   }
233 
234   /// Add object file to be linked. Pre-load compile unit die. Call
235   /// \p OnCUDieLoaded for each compile unit die. If specified \p File
236   /// has reference to the Clang module then such module would be
237   /// pre-loaded by \p Loader for !Update case.
238   ///
239   /// \pre NoODR, Update options should be set before call to addObjectFile.
240   void addObjectFile(
241       DWARFFile &File, ObjFileLoaderTy Loader = nullptr,
242       CompileUnitHandlerTy OnCUDieLoaded = [](const DWARFUnit &) {}) override;
243 
244   /// Link debug info for added objFiles. Object files are linked all together.
245   Error link() override;
246 
247   /// A number of methods setting various linking options:
248 
249   /// Allows to generate log of linking process to the standard output.
setVerbosity(bool Verbose)250   void setVerbosity(bool Verbose) override { Options.Verbose = Verbose; }
251 
252   /// Print statistics to standard output.
setStatistics(bool Statistics)253   void setStatistics(bool Statistics) override {
254     Options.Statistics = Statistics;
255   }
256 
257   /// Verify the input DWARF.
setVerifyInputDWARF(bool Verify)258   void setVerifyInputDWARF(bool Verify) override {
259     Options.VerifyInputDWARF = Verify;
260   }
261 
262   /// Do not unique types according to ODR.
setNoODR(bool NoODR)263   void setNoODR(bool NoODR) override { Options.NoODR = NoODR; }
264 
265   /// Update index tables only(do not modify rest of DWARF).
setUpdateIndexTablesOnly(bool Update)266   void setUpdateIndexTablesOnly(bool Update) override {
267     Options.Update = Update;
268   }
269 
270   /// Allow generating valid, but non-deterministic output.
setAllowNonDeterministicOutput(bool)271   void setAllowNonDeterministicOutput(bool) override { /* Nothing to do. */
272   }
273 
274   /// Set whether to keep the enclosing function for a static variable.
setKeepFunctionForStatic(bool KeepFunctionForStatic)275   void setKeepFunctionForStatic(bool KeepFunctionForStatic) override {
276     Options.KeepFunctionForStatic = KeepFunctionForStatic;
277   }
278 
279   /// Use specified number of threads for parallel files linking.
setNumThreads(unsigned NumThreads)280   void setNumThreads(unsigned NumThreads) override {
281     Options.Threads = NumThreads;
282   }
283 
284   /// Add kind of accelerator tables to be generated.
addAccelTableKind(AccelTableKind Kind)285   void addAccelTableKind(AccelTableKind Kind) override {
286     assert(!llvm::is_contained(Options.AccelTables, Kind));
287     Options.AccelTables.emplace_back(Kind);
288   }
289 
290   /// Set prepend path for clang modules.
setPrependPath(StringRef Ppath)291   void setPrependPath(StringRef Ppath) override { Options.PrependPath = Ppath; }
292 
293   /// Set estimated objects files amount, for preliminary data allocation.
setEstimatedObjfilesAmount(unsigned ObjFilesNum)294   void setEstimatedObjfilesAmount(unsigned ObjFilesNum) override {
295     ObjectContexts.reserve(ObjFilesNum);
296   }
297 
298   /// Set verification handler which would be used to report verification
299   /// errors.
300   void
setInputVerificationHandler(InputVerificationHandlerTy Handler)301   setInputVerificationHandler(InputVerificationHandlerTy Handler) override {
302     Options.InputVerificationHandler = Handler;
303   }
304 
305   /// Set map for Swift interfaces.
setSwiftInterfacesMap(SwiftInterfacesMapTy * Map)306   void setSwiftInterfacesMap(SwiftInterfacesMapTy *Map) override {
307     Options.ParseableSwiftInterfaces = Map;
308   }
309 
310   /// Set prefix map for objects.
setObjectPrefixMap(ObjectPrefixMapTy * Map)311   void setObjectPrefixMap(ObjectPrefixMapTy *Map) override {
312     Options.ObjectPrefixMap = Map;
313   }
314 
315   /// Set target DWARF version.
setTargetDWARFVersion(uint16_t TargetDWARFVersion)316   Error setTargetDWARFVersion(uint16_t TargetDWARFVersion) override {
317     if ((TargetDWARFVersion < 1) || (TargetDWARFVersion > 5))
318       return createStringError(std::errc::invalid_argument,
319                                "unsupported DWARF version: %d",
320                                TargetDWARFVersion);
321 
322     Options.TargetDWARFVersion = TargetDWARFVersion;
323     return Error::success();
324   }
325 
326 private:
327   /// Flags passed to DwarfLinker::lookForDIEsToKeep
328   enum TraversalFlags {
329     TF_Keep = 1 << 0,            ///< Mark the traversed DIEs as kept.
330     TF_InFunctionScope = 1 << 1, ///< Current scope is a function scope.
331     TF_DependencyWalk = 1 << 2,  ///< Walking the dependencies of a kept DIE.
332     TF_ParentWalk = 1 << 3,      ///< Walking up the parents of a kept DIE.
333     TF_ODR = 1 << 4,             ///< Use the ODR while keeping dependents.
334     TF_SkipPC = 1 << 5,          ///< Skip all location attributes.
335   };
336 
337   /// The  distinct types of work performed by the work loop.
338   enum class WorklistItemType {
339     /// Given a DIE, look for DIEs to be kept.
340     LookForDIEsToKeep,
341     /// Given a DIE, look for children of this DIE to be kept.
342     LookForChildDIEsToKeep,
343     /// Given a DIE, look for DIEs referencing this DIE to be kept.
344     LookForRefDIEsToKeep,
345     /// Given a DIE, look for parent DIEs to be kept.
346     LookForParentDIEsToKeep,
347     /// Given a DIE, update its incompleteness based on whether its children are
348     /// incomplete.
349     UpdateChildIncompleteness,
350     /// Given a DIE, update its incompleteness based on whether the DIEs it
351     /// references are incomplete.
352     UpdateRefIncompleteness,
353     /// Given a DIE, mark it as ODR Canonical if applicable.
354     MarkODRCanonicalDie,
355   };
356 
357   /// This class represents an item in the work list. The type defines what kind
358   /// of work needs to be performed when processing the current item. The flags
359   /// and info fields are optional based on the type.
360   struct WorklistItem {
361     DWARFDie Die;
362     WorklistItemType Type;
363     CompileUnit &CU;
364     unsigned Flags;
365     union {
366       const unsigned AncestorIdx;
367       CompileUnit::DIEInfo *OtherInfo;
368     };
369 
370     WorklistItem(DWARFDie Die, CompileUnit &CU, unsigned Flags,
371                  WorklistItemType T = WorklistItemType::LookForDIEsToKeep)
DieWorklistItem372         : Die(Die), Type(T), CU(CU), Flags(Flags), AncestorIdx(0) {}
373 
374     WorklistItem(DWARFDie Die, CompileUnit &CU, WorklistItemType T,
375                  CompileUnit::DIEInfo *OtherInfo = nullptr)
DieWorklistItem376         : Die(Die), Type(T), CU(CU), Flags(0), OtherInfo(OtherInfo) {}
377 
WorklistItemWorklistItem378     WorklistItem(unsigned AncestorIdx, CompileUnit &CU, unsigned Flags)
379         : Type(WorklistItemType::LookForParentDIEsToKeep), CU(CU), Flags(Flags),
380           AncestorIdx(AncestorIdx) {}
381   };
382 
383   /// Verify the given DWARF file.
384   void verifyInput(const DWARFFile &File);
385 
386   /// returns true if we need to translate strings.
needToTranslateStrings()387   bool needToTranslateStrings() { return StringsTranslator != nullptr; }
388 
389   void reportWarning(const Twine &Warning, const DWARFFile &File,
390                      const DWARFDie *DIE = nullptr) const {
391     if (WarningHandler != nullptr)
392       WarningHandler(Warning, File.FileName, DIE);
393   }
394 
395   void reportError(const Twine &Warning, const DWARFFile &File,
396                    const DWARFDie *DIE = nullptr) const {
397     if (ErrorHandler != nullptr)
398       ErrorHandler(Warning, File.FileName, DIE);
399   }
400 
401   void copyInvariantDebugSection(DWARFContext &Dwarf);
402 
403   /// Keep information for referenced clang module: already loaded DWARF info
404   /// of the clang module and a CompileUnit of the module.
405   struct RefModuleUnit {
RefModuleUnitRefModuleUnit406     RefModuleUnit(DWARFFile &File, std::unique_ptr<CompileUnit> Unit)
407         : File(File), Unit(std::move(Unit)) {}
RefModuleUnitRefModuleUnit408     RefModuleUnit(RefModuleUnit &&Other)
409         : File(Other.File), Unit(std::move(Other.Unit)) {}
410     RefModuleUnit(const RefModuleUnit &) = delete;
411 
412     DWARFFile &File;
413     std::unique_ptr<CompileUnit> Unit;
414   };
415   using ModuleUnitListTy = std::vector<RefModuleUnit>;
416 
417   /// Keeps track of data associated with one object during linking.
418   struct LinkContext {
419     DWARFFile &File;
420     UnitListTy CompileUnits;
421     ModuleUnitListTy ModuleUnits;
422     bool Skip = false;
423 
LinkContextLinkContext424     LinkContext(DWARFFile &File) : File(File) {}
425 
426     /// Clear part of the context that's no longer needed when we're done with
427     /// the debug object.
clearLinkContext428     void clear() {
429       CompileUnits.clear();
430       ModuleUnits.clear();
431       File.unload();
432     }
433   };
434 
435   /// Called before emitting object data
436   void cleanupAuxiliarryData(LinkContext &Context);
437 
438   /// Look at the parent of the given DIE and decide whether they should be
439   /// kept.
440   void lookForParentDIEsToKeep(unsigned AncestorIdx, CompileUnit &CU,
441                                unsigned Flags,
442                                SmallVectorImpl<WorklistItem> &Worklist);
443 
444   /// Look at the children of the given DIE and decide whether they should be
445   /// kept.
446   void lookForChildDIEsToKeep(const DWARFDie &Die, CompileUnit &CU,
447                               unsigned Flags,
448                               SmallVectorImpl<WorklistItem> &Worklist);
449 
450   /// Look at DIEs referenced by the given DIE and decide whether they should be
451   /// kept. All DIEs referenced though attributes should be kept.
452   void lookForRefDIEsToKeep(const DWARFDie &Die, CompileUnit &CU,
453                             unsigned Flags, const UnitListTy &Units,
454                             const DWARFFile &File,
455                             SmallVectorImpl<WorklistItem> &Worklist);
456 
457   /// Mark context corresponding to the specified \p Die as having canonical
458   /// die, if applicable.
459   void markODRCanonicalDie(const DWARFDie &Die, CompileUnit &CU);
460 
461   /// \defgroup FindRootDIEs Find DIEs corresponding to Address map entries.
462   ///
463   /// @{
464   /// Recursively walk the \p DIE tree and look for DIEs to
465   /// keep. Store that information in \p CU's DIEInfo.
466   ///
467   /// The return value indicates whether the DIE is incomplete.
468   void lookForDIEsToKeep(AddressesMap &RelocMgr, const UnitListTy &Units,
469                          const DWARFDie &DIE, const DWARFFile &File,
470                          CompileUnit &CU, unsigned Flags);
471 
472   /// Check whether specified \p CUDie is a Clang module reference.
473   /// if \p Quiet is false then display error messages.
474   /// \return first == true if CUDie is a Clang module reference.
475   ///         second == true if module is already loaded.
476   std::pair<bool, bool> isClangModuleRef(const DWARFDie &CUDie,
477                                          std::string &PCMFile,
478                                          LinkContext &Context, unsigned Indent,
479                                          bool Quiet);
480 
481   /// If this compile unit is really a skeleton CU that points to a
482   /// clang module, register it in ClangModules and return true.
483   ///
484   /// A skeleton CU is a CU without children, a DW_AT_gnu_dwo_name
485   /// pointing to the module, and a DW_AT_gnu_dwo_id with the module
486   /// hash.
487   bool registerModuleReference(const DWARFDie &CUDie, LinkContext &Context,
488                                ObjFileLoaderTy Loader,
489                                CompileUnitHandlerTy OnCUDieLoaded,
490                                unsigned Indent = 0);
491 
492   /// Recursively add the debug info in this clang module .pcm
493   /// file (and all the modules imported by it in a bottom-up fashion)
494   /// to ModuleUnits.
495   Error loadClangModule(ObjFileLoaderTy Loader, const DWARFDie &CUDie,
496                         const std::string &PCMFile, LinkContext &Context,
497                         CompileUnitHandlerTy OnCUDieLoaded,
498                         unsigned Indent = 0);
499 
500   /// Clone specified Clang module unit \p Unit.
501   Error cloneModuleUnit(LinkContext &Context, RefModuleUnit &Unit,
502                         DeclContextTree &ODRContexts,
503                         OffsetsStringPool &DebugStrPool,
504                         OffsetsStringPool &DebugLineStrPool,
505                         DebugDieValuePool &StringOffsetPool,
506                         unsigned Indent = 0);
507 
508   unsigned shouldKeepDIE(AddressesMap &RelocMgr, const DWARFDie &DIE,
509                          const DWARFFile &File, CompileUnit &Unit,
510                          CompileUnit::DIEInfo &MyInfo, unsigned Flags);
511 
512   /// This function checks whether variable has DWARF expression containing
513   /// operation referencing live address(f.e. DW_OP_addr, DW_OP_addrx...).
514   /// \returns first is true if the expression has an operation referencing an
515   /// address.
516   ///          second is the relocation adjustment value if the live address is
517   ///          referenced.
518   std::pair<bool, std::optional<int64_t>>
519   getVariableRelocAdjustment(AddressesMap &RelocMgr, const DWARFDie &DIE);
520 
521   /// Check if a variable describing DIE should be kept.
522   /// \returns updated TraversalFlags.
523   unsigned shouldKeepVariableDIE(AddressesMap &RelocMgr, const DWARFDie &DIE,
524                                  CompileUnit::DIEInfo &MyInfo, unsigned Flags);
525 
526   unsigned shouldKeepSubprogramDIE(AddressesMap &RelocMgr, const DWARFDie &DIE,
527                                    const DWARFFile &File, CompileUnit &Unit,
528                                    CompileUnit::DIEInfo &MyInfo,
529                                    unsigned Flags);
530 
531   /// Resolve the DIE attribute reference that has been extracted in \p
532   /// RefValue. The resulting DIE might be in another CompileUnit which is
533   /// stored into \p ReferencedCU. \returns null if resolving fails for any
534   /// reason.
535   DWARFDie resolveDIEReference(const DWARFFile &File, const UnitListTy &Units,
536                                const DWARFFormValue &RefValue,
537                                const DWARFDie &DIE, CompileUnit *&RefCU);
538 
539   /// @}
540 
541   /// \defgroup Methods used to link the debug information
542   ///
543   /// @{
544 
545   struct DWARFLinkerOptions;
546 
547   class DIECloner {
548     DWARFLinker &Linker;
549     DwarfEmitter *Emitter;
550     DWARFFile &ObjFile;
551     OffsetsStringPool &DebugStrPool;
552     OffsetsStringPool &DebugLineStrPool;
553     DebugDieValuePool &StringOffsetPool;
554     DebugDieValuePool AddrPool;
555 
556     /// Allocator used for all the DIEValue objects.
557     BumpPtrAllocator &DIEAlloc;
558 
559     std::vector<std::unique_ptr<CompileUnit>> &CompileUnits;
560 
561     /// Keeps mapping from offset of the macro table to corresponding
562     /// compile unit.
563     Offset2UnitMap UnitMacroMap;
564 
565     bool Update;
566 
567   public:
DIECloner(DWARFLinker & Linker,DwarfEmitter * Emitter,DWARFFile & ObjFile,BumpPtrAllocator & DIEAlloc,std::vector<std::unique_ptr<CompileUnit>> & CompileUnits,bool Update,OffsetsStringPool & DebugStrPool,OffsetsStringPool & DebugLineStrPool,DebugDieValuePool & StringOffsetPool)568     DIECloner(DWARFLinker &Linker, DwarfEmitter *Emitter, DWARFFile &ObjFile,
569               BumpPtrAllocator &DIEAlloc,
570               std::vector<std::unique_ptr<CompileUnit>> &CompileUnits,
571               bool Update, OffsetsStringPool &DebugStrPool,
572               OffsetsStringPool &DebugLineStrPool,
573               DebugDieValuePool &StringOffsetPool)
574         : Linker(Linker), Emitter(Emitter), ObjFile(ObjFile),
575           DebugStrPool(DebugStrPool), DebugLineStrPool(DebugLineStrPool),
576           StringOffsetPool(StringOffsetPool), DIEAlloc(DIEAlloc),
577           CompileUnits(CompileUnits), Update(Update) {}
578 
579     /// Recursively clone \p InputDIE into an tree of DIE objects
580     /// where useless (as decided by lookForDIEsToKeep()) bits have been
581     /// stripped out and addresses have been rewritten according to the
582     /// address map.
583     ///
584     /// \param OutOffset is the offset the cloned DIE in the output
585     /// compile unit.
586     /// \param PCOffset (while cloning a function scope) is the offset
587     /// applied to the entry point of the function to get the linked address.
588     /// \param Die the output DIE to use, pass NULL to create one.
589     /// \returns the root of the cloned tree or null if nothing was selected.
590     LLVM_ABI DIE *cloneDIE(const DWARFDie &InputDIE, const DWARFFile &File,
591                            CompileUnit &U, int64_t PCOffset, uint32_t OutOffset,
592                            unsigned Flags, bool IsLittleEndian,
593                            DIE *Die = nullptr);
594 
595     /// Construct the output DIE tree by cloning the DIEs we
596     /// chose to keep above. If there are no valid relocs, then there's
597     /// nothing to clone/emit.
598     LLVM_ABI uint64_t cloneAllCompileUnits(DWARFContext &DwarfContext,
599                                            const DWARFFile &File,
600                                            bool IsLittleEndian);
601 
602     /// Emit the .debug_addr section for the \p Unit.
603     LLVM_ABI void emitDebugAddrSection(CompileUnit &Unit,
604                                        const uint16_t DwarfVersion) const;
605 
606     using ExpressionHandlerRef = function_ref<void(
607         SmallVectorImpl<uint8_t> &, SmallVectorImpl<uint8_t> &,
608         int64_t AddrRelocAdjustment)>;
609 
610     /// Compute and emit debug locations (.debug_loc, .debug_loclists)
611     /// for \p Unit, patch the attributes referencing it.
612     LLVM_ABI void generateUnitLocations(CompileUnit &Unit,
613                                         const DWARFFile &File,
614                                         ExpressionHandlerRef ExprHandler);
615 
616   private:
617     using AttributeSpec = DWARFAbbreviationDeclaration::AttributeSpec;
618 
619     /// Information gathered and exchanged between the various
620     /// clone*Attributes helpers about the attributes of a particular DIE.
621     struct AttributesInfo {
622       /// Names.
623       DwarfStringPoolEntryRef Name, MangledName, NameWithoutTemplate;
624 
625       /// Offsets in the string pool.
626       uint32_t NameOffset = 0;
627       uint32_t MangledNameOffset = 0;
628 
629       /// Offset to apply to PC addresses inside a function.
630       int64_t PCOffset = 0;
631 
632       /// Does the DIE have a low_pc attribute?
633       bool HasLowPc = false;
634 
635       /// Does the DIE have a ranges attribute?
636       bool HasRanges = false;
637 
638       /// Is this DIE only a declaration?
639       bool IsDeclaration = false;
640 
641       /// Is there a DW_AT_str_offsets_base in the CU?
642       bool AttrStrOffsetBaseSeen = false;
643 
644       /// Is there a DW_AT_APPLE_origin in the CU?
645       bool HasAppleOrigin = false;
646 
647       AttributesInfo() = default;
648     };
649 
650     /// Helper for cloneDIE.
651     unsigned cloneAttribute(DIE &Die, const DWARFDie &InputDIE,
652                             const DWARFFile &File, CompileUnit &U,
653                             const DWARFFormValue &Val,
654                             const AttributeSpec AttrSpec, unsigned AttrSize,
655                             AttributesInfo &AttrInfo, bool IsLittleEndian);
656 
657     /// Clone a string attribute described by \p AttrSpec and add
658     /// it to \p Die.
659     /// \returns the size of the new attribute.
660     unsigned cloneStringAttribute(DIE &Die, AttributeSpec AttrSpec,
661                                   const DWARFFormValue &Val, const DWARFUnit &U,
662                                   AttributesInfo &Info);
663 
664     /// Clone an attribute referencing another DIE and add
665     /// it to \p Die.
666     /// \returns the size of the new attribute.
667     unsigned cloneDieReferenceAttribute(DIE &Die, const DWARFDie &InputDIE,
668                                         AttributeSpec AttrSpec,
669                                         unsigned AttrSize,
670                                         const DWARFFormValue &Val,
671                                         const DWARFFile &File,
672                                         CompileUnit &Unit);
673 
674     /// Clone a DWARF expression that may be referencing another DIE.
675     void cloneExpression(DataExtractor &Data, DWARFExpression Expression,
676                          const DWARFFile &File, CompileUnit &Unit,
677                          SmallVectorImpl<uint8_t> &OutputBuffer,
678                          int64_t AddrRelocAdjustment, bool IsLittleEndian);
679 
680     /// Clone an attribute referencing another DIE and add
681     /// it to \p Die.
682     /// \returns the size of the new attribute.
683     unsigned cloneBlockAttribute(DIE &Die, const DWARFDie &InputDIE,
684                                  const DWARFFile &File, CompileUnit &Unit,
685                                  AttributeSpec AttrSpec,
686                                  const DWARFFormValue &Val,
687                                  bool IsLittleEndian);
688 
689     /// Clone an attribute referencing another DIE and add
690     /// it to \p Die.
691     /// \returns the size of the new attribute.
692     unsigned cloneAddressAttribute(DIE &Die, const DWARFDie &InputDIE,
693                                    AttributeSpec AttrSpec, unsigned AttrSize,
694                                    const DWARFFormValue &Val,
695                                    const CompileUnit &Unit,
696                                    AttributesInfo &Info);
697 
698     /// Clone a scalar attribute  and add it to \p Die.
699     /// \returns the size of the new attribute.
700     unsigned cloneScalarAttribute(DIE &Die, const DWARFDie &InputDIE,
701                                   const DWARFFile &File, CompileUnit &U,
702                                   AttributeSpec AttrSpec,
703                                   const DWARFFormValue &Val, unsigned AttrSize,
704                                   AttributesInfo &Info);
705 
706     /// Get the potential name and mangled name for the entity
707     /// described by \p Die and store them in \Info if they are not
708     /// already there.
709     /// \returns is a name was found.
710     bool getDIENames(const DWARFDie &Die, AttributesInfo &Info,
711                      OffsetsStringPool &StringPool, bool StripTemplate = false);
712 
713     uint32_t hashFullyQualifiedName(DWARFDie DIE, CompileUnit &U,
714                                     const DWARFFile &File,
715                                     int RecurseDepth = 0);
716 
717     /// Helper for cloneDIE.
718     void addObjCAccelerator(CompileUnit &Unit, const DIE *Die,
719                             DwarfStringPoolEntryRef Name,
720                             OffsetsStringPool &StringPool, bool SkipPubSection);
721 
722     void rememberUnitForMacroOffset(CompileUnit &Unit);
723 
724     /// Clone and emit the line table for the specified \p Unit.
725     /// Translate directories and file names if necessary.
726     /// Relocate address ranges.
727     void generateLineTableForUnit(CompileUnit &Unit);
728   };
729 
730   /// Assign an abbreviation number to \p Abbrev
731   void assignAbbrev(DIEAbbrev &Abbrev);
732 
733   /// Compute and emit debug ranges(.debug_aranges, .debug_ranges,
734   /// .debug_rnglists) for \p Unit, patch the attributes referencing it.
735   void generateUnitRanges(CompileUnit &Unit, const DWARFFile &File,
736                           DebugDieValuePool &AddrPool) const;
737 
738   /// Emit the accelerator entries for \p Unit.
739   void emitAcceleratorEntriesForUnit(CompileUnit &Unit);
740 
741   /// Patch the frame info for an object file and emit it.
742   void patchFrameInfoForObject(LinkContext &Context);
743 
744   /// FoldingSet that uniques the abbreviations.
745   FoldingSet<DIEAbbrev> AbbreviationsSet;
746 
747   /// Storage for the unique Abbreviations.
748   /// This is passed to AsmPrinter::emitDwarfAbbrevs(), thus it cannot be
749   /// changed to a vector of unique_ptrs.
750   std::vector<std::unique_ptr<DIEAbbrev>> Abbreviations;
751 
752   /// DIELoc objects that need to be destructed (but not freed!).
753   std::vector<DIELoc *> DIELocs;
754 
755   /// DIEBlock objects that need to be destructed (but not freed!).
756   std::vector<DIEBlock *> DIEBlocks;
757 
758   /// Allocator used for all the DIEValue objects.
759   BumpPtrAllocator DIEAlloc;
760   /// @}
761 
762   DwarfEmitter *TheDwarfEmitter = nullptr;
763   std::vector<LinkContext> ObjectContexts;
764 
765   /// The CIEs that have been emitted in the output section. The actual CIE
766   /// data serves a the key to this StringMap, this takes care of comparing the
767   /// semantics of CIEs defined in different object files.
768   StringMap<uint32_t> EmittedCIEs;
769 
770   /// Offset of the last CIE that has been emitted in the output
771   /// .debug_frame section.
772   uint32_t LastCIEOffset = 0;
773 
774   /// Apple accelerator tables.
775   DWARF5AccelTable DebugNames;
776   AccelTable<AppleAccelTableStaticOffsetData> AppleNames;
777   AccelTable<AppleAccelTableStaticOffsetData> AppleNamespaces;
778   AccelTable<AppleAccelTableStaticOffsetData> AppleObjc;
779   AccelTable<AppleAccelTableStaticTypeData> AppleTypes;
780 
781   /// Mapping the PCM filename to the DwoId.
782   StringMap<uint64_t> ClangModules;
783 
784   std::function<StringRef(StringRef)> StringsTranslator = nullptr;
785 
786   /// A unique ID that identifies each compile unit.
787   unsigned UniqueUnitID = 0;
788 
789   // error handler
790   MessageHandlerTy ErrorHandler = nullptr;
791 
792   // warning handler
793   MessageHandlerTy WarningHandler = nullptr;
794 
795   /// linking options
796   struct DWARFLinkerOptions {
797     /// DWARF version for the output.
798     uint16_t TargetDWARFVersion = 0;
799 
800     /// Generate processing log to the standard output.
801     bool Verbose = false;
802 
803     /// Print statistics.
804     bool Statistics = false;
805 
806     /// Verify the input DWARF.
807     bool VerifyInputDWARF = false;
808 
809     /// Do not unique types according to ODR
810     bool NoODR = false;
811 
812     /// Update
813     bool Update = false;
814 
815     /// Whether we want a static variable to force us to keep its enclosing
816     /// function.
817     bool KeepFunctionForStatic = false;
818 
819     /// Number of threads.
820     unsigned Threads = 1;
821 
822     /// The accelerator table kinds
823     SmallVector<AccelTableKind, 1> AccelTables;
824 
825     /// Prepend path for the clang modules.
826     std::string PrependPath;
827 
828     // input verification handler
829     InputVerificationHandlerTy InputVerificationHandler = nullptr;
830 
831     /// A list of all .swiftinterface files referenced by the debug
832     /// info, mapping Module name to path on disk. The entries need to
833     /// be uniqued and sorted and there are only few entries expected
834     /// per compile unit, which is why this is a std::map.
835     /// this is dsymutil specific fag.
836     SwiftInterfacesMapTy *ParseableSwiftInterfaces = nullptr;
837 
838     /// A list of remappings to apply to file paths.
839     ObjectPrefixMapTy *ObjectPrefixMap = nullptr;
840   } Options;
841 };
842 
843 } // end of namespace classic
844 } // end of namespace dwarf_linker
845 } // end of namespace llvm
846 
847 #endif // LLVM_DWARFLINKER_CLASSIC_DWARFLINKER_H
848