diff options
-rw-r--r-- | lld/ELF/InputFiles.cpp | 56 | ||||
-rw-r--r-- | lld/ELF/InputFiles.h | 30 | ||||
-rw-r--r-- | lld/ELF/Relocations.cpp | 2 |
3 files changed, 31 insertions, 57 deletions
diff --git a/lld/ELF/InputFiles.cpp b/lld/ELF/InputFiles.cpp index 5bbea4f4c96..a1ebf748a1e 100644 --- a/lld/ELF/InputFiles.cpp +++ b/lld/ELF/InputFiles.cpp @@ -35,7 +35,6 @@ using namespace llvm::sys::fs; using namespace lld; using namespace lld::elf; - namespace { // In ELF object file all section addresses are zero. If we have multiple // .text sections (when using -ffunction-section or comdat group) then @@ -53,11 +52,10 @@ public: }; } -template <class ELFT> DIHelper<ELFT>::DIHelper(InputFile *F) { - Expected<std::unique_ptr<object::ObjectFile>> Obj = - object::ObjectFile::createObjectFile(F->MB); - if (!Obj) - return; +template <class ELFT> void ObjectFile<ELFT>::initializeDwarfLine() { + std::unique_ptr<object::ObjectFile> Obj = + check(object::ObjectFile::createObjectFile(this->MB), + "createObjectFile failed"); ObjectInfo ObjInfo; DWARFContextInMemory Dwarf(*Obj.get(), &ObjInfo); @@ -65,35 +63,35 @@ template <class ELFT> DIHelper<ELFT>::DIHelper(InputFile *F) { DataExtractor LineData(Dwarf.getLineSection().Data, ELFT::TargetEndianness == support::little, ELFT::Is64Bits ? 8 : 4); + // The second parameter is offset in .debug_line section // for compilation unit (CU) of interest. We have only one // CU (object file), so offset is always 0. DwarfLine->getOrParseLineTable(LineData, 0); } -template <class ELFT> DIHelper<ELFT>::~DIHelper() {} - +// Returns source line information for a given offset +// using DWARF debug info. template <class ELFT> -std::string DIHelper<ELFT>::getLineInfo(InputSectionBase<ELFT> *S, - uintX_t Offset) { +std::string ObjectFile<ELFT>::getLineInfo(InputSectionBase<ELFT> *S, + uintX_t Offset) { if (!DwarfLine) - return ""; + initializeDwarfLine(); - DILineInfo LineInfo; - DILineInfoSpecifier Spec; - // The offset to CU is 0 (see DIHelper constructor). - const DWARFDebugLine::LineTable *LineTbl = DwarfLine->getLineTable(0); - if (!LineTbl) + // The offset to CU is 0. + const DWARFDebugLine::LineTable *Tbl = DwarfLine->getLineTable(0); + if (!Tbl) return ""; // Use fake address calcuated by adding section file offset and offset in - // section. - // See comments for ObjectInfo class - LineTbl->getFileLineInfoForAddress(S->Offset + Offset, nullptr, Spec.FLIKind, - LineInfo); - return LineInfo.Line != 0 - ? LineInfo.FileName + " (" + std::to_string(LineInfo.Line) + ")" - : ""; + // section. See comments for ObjectInfo class. + DILineInfo Info; + DILineInfoSpecifier Spec; + Tbl->getFileLineInfoForAddress(S->Offset + Offset, nullptr, Spec.FLIKind, + Info); + if (Info.Line == 0) + return ""; + return Info.FileName + " (" + std::to_string(Info.Line) + ")"; } // Returns "(internal)", "foo.a(bar.o)" or "baz.o". @@ -185,13 +183,6 @@ ArrayRef<SymbolBody *> elf::ObjectFile<ELFT>::getSymbols() { return makeArrayRef(this->SymbolBodies).slice(1); } -template <class ELFT> DIHelper<ELFT> *elf::ObjectFile<ELFT>::getDIHelper() { - if (!DIH) - DIH.reset(new DIHelper<ELFT>(this)); - - return DIH.get(); -} - template <class ELFT> uint32_t elf::ObjectFile<ELFT>::getMipsGp0() const { if (ELFT::Is64Bits && MipsOptions && MipsOptions->Reginfo) return MipsOptions->Reginfo->ri_gp_value; @@ -968,8 +959,3 @@ template void BinaryFile::parse<ELF32LE>(); template void BinaryFile::parse<ELF32BE>(); template void BinaryFile::parse<ELF64LE>(); template void BinaryFile::parse<ELF64BE>(); - -template class elf::DIHelper<ELF32LE>; -template class elf::DIHelper<ELF32BE>; -template class elf::DIHelper<ELF64LE>; -template class elf::DIHelper<ELF64BE>; diff --git a/lld/ELF/InputFiles.h b/lld/ELF/InputFiles.h index ac9134aa96a..d9f996aa2aa 100644 --- a/lld/ELF/InputFiles.h +++ b/lld/ELF/InputFiles.h @@ -43,23 +43,6 @@ class InputFile; class Lazy; class SymbolBody; -// Debugging information helper class. The main purpose is to -// retrieve source file and line for error reporting. Linker may -// find reasonable number of errors in a single object file, so -// we cache debugging information in order to parse it only once -// for each object file we link. -template <class ELFT> class DIHelper { - typedef typename ELFT::uint uintX_t; - -public: - DIHelper(InputFile *F); - ~DIHelper(); - std::string getLineInfo(InputSectionBase<ELFT> *S, uintX_t Offset); - -private: - std::unique_ptr<llvm::DWARFDebugLine> DwarfLine; -}; - // The root class of input files. class InputFile { public: @@ -175,9 +158,9 @@ public: const Elf_Shdr *getSymbolTable() const { return this->Symtab; }; - // DI helper allows manipilating debugging information for this - // object file. Used for error reporting. - DIHelper<ELFT> *getDIHelper(); + // Returns source line information for a given offset. + // If no information is available, returns "". + std::string getLineInfo(InputSectionBase<ELFT> *S, uintX_t Offset); // Get MIPS GP0 value defined by this file. This value represents the gp value // used to create the relocatable object and required to support @@ -198,6 +181,7 @@ private: initializeSections(llvm::DenseSet<llvm::CachedHashStringRef> &ComdatGroups); void initializeSymbols(); void initializeReverseDependencies(); + void initializeDwarfLine(); InputSectionBase<ELFT> *getRelocTarget(const Elf_Shdr &Sec); InputSectionBase<ELFT> *createInputSection(const Elf_Shdr &Sec, StringRef SectionStringTable); @@ -218,7 +202,11 @@ private: // MIPS .MIPS.abiflags section defined by this file. std::unique_ptr<MipsAbiFlagsInputSection<ELFT>> MipsAbiFlags; - std::unique_ptr<DIHelper<ELFT>> DIH; + // Debugging information to retrieve source file and line for error + // reporting. Linker may find reasonable number of errors in a + // single object file, so we cache debugging information in order to + // parse it only once for each object file we link. + std::unique_ptr<llvm::DWARFDebugLine> DwarfLine; }; // LazyObjectFile is analogous to ArchiveFile in the sense that diff --git a/lld/ELF/Relocations.cpp b/lld/ELF/Relocations.cpp index 7273f67c3dd..0b8343baac4 100644 --- a/lld/ELF/Relocations.cpp +++ b/lld/ELF/Relocations.cpp @@ -544,7 +544,7 @@ static std::string getLocation(SymbolBody &Sym, InputSectionBase<ELFT> &S, ObjectFile<ELFT> *File = S.getFile(); // First check if we can get desired values from debugging information. - std::string LineInfo = File->getDIHelper()->getLineInfo(&S, Offset); + std::string LineInfo = File->getLineInfo(&S, Offset); if (!LineInfo.empty()) return LineInfo; |