1313#include " llvm/CodeGen/AccelTable.h"
1414#include " DwarfCompileUnit.h"
1515#include " llvm/ADT/STLExtras.h"
16+ #include " llvm/ADT/StringMap.h"
1617#include " llvm/ADT/Twine.h"
1718#include " llvm/BinaryFormat/Dwarf.h"
1819#include " llvm/CodeGen/AsmPrinter.h"
@@ -199,30 +200,32 @@ class Dwarf5AccelTableWriter : public AccelTableWriter {
199200 uint32_t AugmentationStringSize = sizeof (AugmentationString);
200201 char AugmentationString[8 ] = {' L' , ' L' , ' V' , ' M' , ' 0' , ' 7' , ' 0' , ' 0' };
201202
202- Header (uint32_t CompUnitCount, uint32_t LocalTypeUnitCount,
203- uint32_t BucketCount, uint32_t NameCount)
204- : CompUnitCount(CompUnitCount), LocalTypeUnitCount(LocalTypeUnitCount),
205- BucketCount (BucketCount), NameCount(NameCount) {}
203+ Header (uint32_t CompUnitCount, uint32_t BucketCount, uint32_t NameCount)
204+ : CompUnitCount(CompUnitCount), BucketCount(BucketCount),
205+ NameCount (NameCount) {}
206206
207207 void emit (Dwarf5AccelTableWriter &Ctx);
208208 };
209+ struct AttributeEncoding {
210+ dwarf::Index Index;
211+ dwarf::Form Form;
212+ };
209213
210214 Header Header;
211- DenseMap<uint32_t , SmallVector<DWARF5AccelTableData::AttributeEncoding, 2 >>
212- Abbreviations;
215+ DenseMap<uint32_t , SmallVector<AttributeEncoding, 2 >> Abbreviations;
213216 ArrayRef<std::variant<MCSymbol *, uint64_t >> CompUnits;
214- ArrayRef<std::variant<MCSymbol *, uint64_t >> TypeUnits;
215- llvm::function_ref<GetIndexForEntryReturnType(const DataT &)>
216- getIndexForEntry;
217+ llvm::function_ref<unsigned (const DataT &)> getCUIndexForEntry;
217218 MCSymbol *ContributionEnd = nullptr ;
218219 MCSymbol *AbbrevStart = Asm->createTempSymbol (" names_abbrev_start" );
219220 MCSymbol *AbbrevEnd = Asm->createTempSymbol (" names_abbrev_end" );
220221 MCSymbol *EntryPool = Asm->createTempSymbol (" names_entries" );
221222
222- void populateAbbrevsMap ();
223+ DenseSet<uint32_t > getUniqueTags () const ;
224+
225+ // Right now, we emit uniform attributes for all tags.
226+ SmallVector<AttributeEncoding, 2 > getUniformAttributes () const ;
223227
224228 void emitCUList () const ;
225- void emitTUList () const ;
226229 void emitBuckets () const ;
227230 void emitStringOffsets () const ;
228231 void emitAbbrevs () const ;
@@ -233,9 +236,7 @@ class Dwarf5AccelTableWriter : public AccelTableWriter {
233236 Dwarf5AccelTableWriter (
234237 AsmPrinter *Asm, const AccelTableBase &Contents,
235238 ArrayRef<std::variant<MCSymbol *, uint64_t >> CompUnits,
236- ArrayRef<std::variant<MCSymbol *, uint64_t >> TypeUnits,
237- llvm::function_ref<GetIndexForEntryReturnType(const DataT &)>
238- getIndexForEntry);
239+ llvm::function_ref<unsigned (const DataT &)> GetCUIndexForEntry);
239240
240241 void emit ();
241242};
@@ -387,39 +388,31 @@ void Dwarf5AccelTableWriter<DataT>::Header::emit(Dwarf5AccelTableWriter &Ctx) {
387388 Asm->OutStreamer ->emitBytes ({AugmentationString, AugmentationStringSize});
388389}
389390
390- static uint32_t constexpr LowerBitSize = dwarf::DW_IDX_type_hash;
391- static uint32_t getTagFromAbbreviationTag (const uint32_t AbbrvTag) {
392- return AbbrvTag >> LowerBitSize;
393- }
394- static uint32_t
395- constructAbbreviationTag (const unsigned Tag,
396- const GetIndexForEntryReturnType &EntryRet) {
397- uint32_t AbbrvTag = 0 ;
398- if (EntryRet)
399- AbbrvTag |= 1 << EntryRet->second .Index ;
400- AbbrvTag |= 1 << dwarf::DW_IDX_die_offset;
401- AbbrvTag |= Tag << LowerBitSize;
402- return AbbrvTag;
403- }
404391template <typename DataT>
405- void Dwarf5AccelTableWriter<DataT>::populateAbbrevsMap() {
392+ DenseSet<uint32_t > Dwarf5AccelTableWriter<DataT>::getUniqueTags() const {
393+ DenseSet<uint32_t > UniqueTags;
406394 for (auto &Bucket : Contents.getBuckets ()) {
407395 for (auto *Hash : Bucket) {
408396 for (auto *Value : Hash->Values ) {
409- GetIndexForEntryReturnType EntryRet =
410- getIndexForEntry (*static_cast <const DataT *>(Value));
411397 unsigned Tag = static_cast <const DataT *>(Value)->getDieTag ();
412- uint32_t AbbrvTag = constructAbbreviationTag (Tag, EntryRet);
413- if (Abbreviations.count (AbbrvTag) == 0 ) {
414- SmallVector<DWARF5AccelTableData::AttributeEncoding, 2 > UA;
415- if (EntryRet)
416- UA.push_back (EntryRet->second );
417- UA.push_back ({dwarf::DW_IDX_die_offset, dwarf::DW_FORM_ref4});
418- Abbreviations.try_emplace (AbbrvTag, UA);
419- }
398+ UniqueTags.insert (Tag);
420399 }
421400 }
422401 }
402+ return UniqueTags;
403+ }
404+
405+ template <typename DataT>
406+ SmallVector<typename Dwarf5AccelTableWriter<DataT>::AttributeEncoding, 2 >
407+ Dwarf5AccelTableWriter<DataT>::getUniformAttributes() const {
408+ SmallVector<AttributeEncoding, 2 > UA;
409+ if (CompUnits.size () > 1 ) {
410+ size_t LargestCUIndex = CompUnits.size () - 1 ;
411+ dwarf::Form Form = DIEInteger::BestForm (/* IsSigned*/ false , LargestCUIndex);
412+ UA.push_back ({dwarf::DW_IDX_compile_unit, Form});
413+ }
414+ UA.push_back ({dwarf::DW_IDX_die_offset, dwarf::DW_FORM_ref4});
415+ return UA;
423416}
424417
425418template <typename DataT>
@@ -433,17 +426,6 @@ void Dwarf5AccelTableWriter<DataT>::emitCUList() const {
433426 }
434427}
435428
436- template <typename DataT>
437- void Dwarf5AccelTableWriter<DataT>::emitTUList() const {
438- for (const auto &TU : enumerate(TypeUnits)) {
439- Asm->OutStreamer ->AddComment (" Type unit " + Twine (TU.index ()));
440- if (std::holds_alternative<MCSymbol *>(TU.value ()))
441- Asm->emitDwarfSymbolReference (std::get<MCSymbol *>(TU.value ()));
442- else
443- Asm->emitDwarfLengthOrOffset (std::get<uint64_t >(TU.value ()));
444- }
445- }
446-
447429template <typename DataT>
448430void Dwarf5AccelTableWriter<DataT>::emitBuckets() const {
449431 uint32_t Index = 1 ;
@@ -471,11 +453,10 @@ void Dwarf5AccelTableWriter<DataT>::emitAbbrevs() const {
471453 Asm->OutStreamer ->emitLabel (AbbrevStart);
472454 for (const auto &Abbrev : Abbreviations) {
473455 Asm->OutStreamer ->AddComment (" Abbrev code" );
474- uint32_t Tag = getTagFromAbbreviationTag (Abbrev.first );
475- assert (Tag != 0 );
456+ assert (Abbrev.first != 0 );
457+ Asm->emitULEB128 (Abbrev.first );
458+ Asm->OutStreamer ->AddComment (dwarf::TagString (Abbrev.first ));
476459 Asm->emitULEB128 (Abbrev.first );
477- Asm->OutStreamer ->AddComment (dwarf::TagString (Tag));
478- Asm->emitULEB128 (Tag);
479460 for (const auto &AttrEnc : Abbrev.second ) {
480461 Asm->emitULEB128 (AttrEnc.Index , dwarf::IndexString (AttrEnc.Index ).data ());
481462 Asm->emitULEB128 (AttrEnc.Form ,
@@ -490,21 +471,16 @@ void Dwarf5AccelTableWriter<DataT>::emitAbbrevs() const {
490471
491472template <typename DataT>
492473void Dwarf5AccelTableWriter<DataT>::emitEntry(const DataT &Entry) const {
493- GetIndexForEntryReturnType EntryRet = getIndexForEntry (Entry);
494- uint32_t AbbrvTag = constructAbbreviationTag (Entry.getDieTag (), EntryRet);
495- auto AbbrevIt = Abbreviations.find (AbbrvTag);
474+ auto AbbrevIt = Abbreviations.find (Entry.getDieTag ());
496475 assert (AbbrevIt != Abbreviations.end () &&
497476 " Why wasn't this abbrev generated?" );
498- assert (getTagFromAbbreviationTag (AbbrevIt->first ) == Entry.getDieTag () &&
499- " Invalid Tag" );
500- Asm->emitULEB128 (AbbrevIt->first , " Abbreviation code" );
501477
478+ Asm->emitULEB128 (AbbrevIt->first , " Abbreviation code" );
502479 for (const auto &AttrEnc : AbbrevIt->second ) {
503480 Asm->OutStreamer ->AddComment (dwarf::IndexString (AttrEnc.Index ));
504481 switch (AttrEnc.Index ) {
505- case dwarf::DW_IDX_compile_unit:
506- case dwarf::DW_IDX_type_unit: {
507- DIEInteger ID (EntryRet->first );
482+ case dwarf::DW_IDX_compile_unit: {
483+ DIEInteger ID (getCUIndexForEntry (Entry));
508484 ID.emitValue (Asm, AttrEnc.Form );
509485 break ;
510486 }
@@ -536,21 +512,22 @@ template <typename DataT>
536512Dwarf5AccelTableWriter<DataT>::Dwarf5AccelTableWriter(
537513 AsmPrinter *Asm, const AccelTableBase &Contents,
538514 ArrayRef<std::variant<MCSymbol *, uint64_t >> CompUnits,
539- ArrayRef<std::variant<MCSymbol *, uint64_t >> TypeUnits,
540- llvm::function_ref<GetIndexForEntryReturnType(const DataT &)>
541- getIndexForEntry)
515+ llvm::function_ref<unsigned (const DataT &)> getCUIndexForEntry)
542516 : AccelTableWriter(Asm, Contents, false ),
543- Header (CompUnits.size(), TypeUnits.size(), Contents.getBucketCount(),
517+ Header (CompUnits.size(), Contents.getBucketCount(),
544518 Contents.getUniqueNameCount()),
545- CompUnits(CompUnits), TypeUnits(TypeUnits),
546- getIndexForEntry(std::move(getIndexForEntry)) {
547- populateAbbrevsMap ();
519+ CompUnits(CompUnits), getCUIndexForEntry(std::move(getCUIndexForEntry)) {
520+ DenseSet<uint32_t > UniqueTags = getUniqueTags ();
521+ SmallVector<AttributeEncoding, 2 > UniformAttributes = getUniformAttributes ();
522+
523+ Abbreviations.reserve (UniqueTags.size ());
524+ for (uint32_t Tag : UniqueTags)
525+ Abbreviations.try_emplace (Tag, UniformAttributes);
548526}
549527
550528template <typename DataT> void Dwarf5AccelTableWriter<DataT>::emit() {
551529 Header.emit (*this );
552530 emitCUList ();
553- emitTUList ();
554531 emitBuckets ();
555532 emitHashes ();
556533 emitStringOffsets ();
@@ -568,17 +545,12 @@ void llvm::emitAppleAccelTableImpl(AsmPrinter *Asm, AccelTableBase &Contents,
568545 AppleAccelTableWriter (Asm, Contents, Atoms, SecBegin).emit ();
569546}
570547
571- void llvm::emitDWARF5AccelTable (AsmPrinter *Asm,
572- AccelTable<DWARF5AccelTableData> &Contents,
573- const DwarfDebug &DD,
574- ArrayRef<std::unique_ptr<DwarfCompileUnit>> CUs,
575- ArrayRef<std::unique_ptr<DwarfTypeUnit>> TUs) {
548+ void llvm::emitDWARF5AccelTable (
549+ AsmPrinter *Asm, AccelTable<DWARF5AccelTableData> &Contents,
550+ const DwarfDebug &DD, ArrayRef<std::unique_ptr<DwarfCompileUnit>> CUs) {
576551 std::vector<std::variant<MCSymbol *, uint64_t >> CompUnits;
577- std::vector<std::variant<MCSymbol *, uint64_t >> TypeUnits;
578552 SmallVector<unsigned , 1 > CUIndex (CUs.size ());
579- DenseMap<const DIE *, unsigned > TUIndex (TUs.size ());
580- int CUCount = 0 ;
581- int TUCount = 0 ;
553+ int Count = 0 ;
582554 for (const auto &CU : enumerate(CUs)) {
583555 switch (CU.value ()->getCUNode ()->getNameTableKind ()) {
584556 case DICompileUnit::DebugNameTableKind::Default:
@@ -587,61 +559,37 @@ void llvm::emitDWARF5AccelTable(AsmPrinter *Asm,
587559 default :
588560 continue ;
589561 }
590- CUIndex[CU.index ()] = CUCount ++;
562+ CUIndex[CU.index ()] = Count ++;
591563 assert (CU.index () == CU.value ()->getUniqueID ());
592564 const DwarfCompileUnit *MainCU =
593565 DD.useSplitDwarf () ? CU.value ()->getSkeleton () : CU.value ().get ();
594566 CompUnits.push_back (MainCU->getLabelBegin ());
595567 }
596568
597- for (const auto &TU : enumerate(TUs)) {
598- switch (TU.value ()->getCUNode ()->getNameTableKind ()) {
599- case DICompileUnit::DebugNameTableKind::Default:
600- break ;
601- default :
602- continue ;
603- }
604- TUIndex[&TU.value ()->getUnitDie ()] = TUCount++;
605- const DwarfTypeUnit *MainTU = TU.value ().get ();
606- TypeUnits.push_back (MainTU->getLabelBegin ());
607- }
608-
609569 if (CompUnits.empty ())
610570 return ;
611571
612572 Asm->OutStreamer ->switchSection (
613573 Asm->getObjFileLowering ().getDwarfDebugNamesSection ());
614574
615575 Contents.finalize (Asm, " names" );
616- dwarf::Form CUIndexForm =
617- DIEInteger::BestForm (/* IsSigned*/ false , CompUnits.size () - 1 );
618- dwarf::Form TUIndexForm =
619- DIEInteger::BestForm (/* IsSigned*/ false , TypeUnits.size () - 1 );
620576 Dwarf5AccelTableWriter<DWARF5AccelTableData>(
621- Asm, Contents, CompUnits, TypeUnits,
622- [&](const DWARF5AccelTableData &Entry) -> GetIndexForEntryReturnType {
577+ Asm, Contents, CompUnits,
578+ [&](const DWARF5AccelTableData &Entry) {
623579 const DIE *CUDie = Entry.getDie ().getUnitDie ();
624- GetIndexForEntryReturnType Index = std::nullopt ;
625- if (CUDie->getTag () == dwarf::DW_TAG_type_unit)
626- Index = {TUIndex[CUDie], {dwarf::DW_IDX_type_unit, TUIndexForm}};
627- else if (CUIndex.size () > 1 )
628- Index = {CUIndex[DD.lookupCU (CUDie)->getUniqueID ()],
629- {dwarf::DW_IDX_compile_unit, CUIndexForm}};
630- return Index;
580+ return CUIndex[DD.lookupCU (CUDie)->getUniqueID ()];
631581 })
632582 .emit ();
633583}
634584
635585void llvm::emitDWARF5AccelTable (
636586 AsmPrinter *Asm, AccelTable<DWARF5AccelTableStaticData> &Contents,
637587 ArrayRef<std::variant<MCSymbol *, uint64_t >> CUs,
638- llvm::function_ref<
639- GetIndexForEntryReturnType (const DWARF5AccelTableStaticData &)>
640- getIndexForEntry) {
641- std::vector<std::variant<MCSymbol *, uint64_t >> TypeUnits;
588+ llvm::function_ref<unsigned (const DWARF5AccelTableStaticData &)>
589+ getCUIndexForEntry) {
642590 Contents.finalize (Asm, " names" );
643- Dwarf5AccelTableWriter<DWARF5AccelTableStaticData>(
644- Asm, Contents, CUs, TypeUnits, getIndexForEntry )
591+ Dwarf5AccelTableWriter<DWARF5AccelTableStaticData>(Asm, Contents, CUs,
592+ getCUIndexForEntry )
645593 .emit ();
646594}
647595
0 commit comments