forked from OSchip/llvm-project
[ELF] Convert GdbIndexSection to input section
Differential revision: https://reviews.llvm.org/D26854 llvm-svn: 287526
This commit is contained in:
parent
1f0236d8e5
commit
a113a4194c
|
@ -10,7 +10,6 @@
|
||||||
#include "OutputSections.h"
|
#include "OutputSections.h"
|
||||||
#include "Config.h"
|
#include "Config.h"
|
||||||
#include "EhFrame.h"
|
#include "EhFrame.h"
|
||||||
#include "GdbIndex.h"
|
|
||||||
#include "LinkerScript.h"
|
#include "LinkerScript.h"
|
||||||
#include "Memory.h"
|
#include "Memory.h"
|
||||||
#include "Strings.h"
|
#include "Strings.h"
|
||||||
|
@ -63,50 +62,6 @@ void OutputSectionBase::writeHeaderTo(typename ELFT::Shdr *Shdr) {
|
||||||
Shdr->sh_name = ShName;
|
Shdr->sh_name = ShName;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class ELFT>
|
|
||||||
GdbIndexSection<ELFT>::GdbIndexSection()
|
|
||||||
: OutputSectionBase(".gdb_index", SHT_PROGBITS, 0) {}
|
|
||||||
|
|
||||||
template <class ELFT> void GdbIndexSection<ELFT>::parseDebugSections() {
|
|
||||||
std::vector<InputSection<ELFT> *> &IS =
|
|
||||||
static_cast<OutputSection<ELFT> *>(Out<ELFT>::DebugInfo)->Sections;
|
|
||||||
|
|
||||||
for (InputSection<ELFT> *I : IS)
|
|
||||||
readDwarf(I);
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class ELFT>
|
|
||||||
void GdbIndexSection<ELFT>::readDwarf(InputSection<ELFT> *I) {
|
|
||||||
std::vector<std::pair<uintX_t, uintX_t>> CuList = readCuList(I);
|
|
||||||
CompilationUnits.insert(CompilationUnits.end(), CuList.begin(), CuList.end());
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class ELFT> void GdbIndexSection<ELFT>::finalize() {
|
|
||||||
parseDebugSections();
|
|
||||||
|
|
||||||
// GdbIndex header consist from version fields
|
|
||||||
// and 5 more fields with different kinds of offsets.
|
|
||||||
CuTypesOffset = CuListOffset + CompilationUnits.size() * CompilationUnitSize;
|
|
||||||
this->Size = CuTypesOffset;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class ELFT> void GdbIndexSection<ELFT>::writeTo(uint8_t *Buf) {
|
|
||||||
write32le(Buf, 7); // Write Version
|
|
||||||
write32le(Buf + 4, CuListOffset); // CU list offset
|
|
||||||
write32le(Buf + 8, CuTypesOffset); // Types CU list offset
|
|
||||||
write32le(Buf + 12, CuTypesOffset); // Address area offset
|
|
||||||
write32le(Buf + 16, CuTypesOffset); // Symbol table offset
|
|
||||||
write32le(Buf + 20, CuTypesOffset); // Constant pool offset
|
|
||||||
Buf += 24;
|
|
||||||
|
|
||||||
// Write the CU list.
|
|
||||||
for (std::pair<uintX_t, uintX_t> CU : CompilationUnits) {
|
|
||||||
write64le(Buf, CU.first);
|
|
||||||
write64le(Buf + 8, CU.second);
|
|
||||||
Buf += 16;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Returns the number of version definition entries. Because the first entry
|
// Returns the number of version definition entries. Because the first entry
|
||||||
// is for the version definition itself, it is the number of versioned symbols
|
// is for the version definition itself, it is the number of versioned symbols
|
||||||
// plus one. Note that we don't support multiple versions yet.
|
// plus one. Note that we don't support multiple versions yet.
|
||||||
|
@ -908,11 +863,6 @@ template class VersionDefinitionSection<ELF32BE>;
|
||||||
template class VersionDefinitionSection<ELF64LE>;
|
template class VersionDefinitionSection<ELF64LE>;
|
||||||
template class VersionDefinitionSection<ELF64BE>;
|
template class VersionDefinitionSection<ELF64BE>;
|
||||||
|
|
||||||
template class GdbIndexSection<ELF32LE>;
|
|
||||||
template class GdbIndexSection<ELF32BE>;
|
|
||||||
template class GdbIndexSection<ELF64LE>;
|
|
||||||
template class GdbIndexSection<ELF64BE>;
|
|
||||||
|
|
||||||
template class OutputSectionFactory<ELF32LE>;
|
template class OutputSectionFactory<ELF32LE>;
|
||||||
template class OutputSectionFactory<ELF32BE>;
|
template class OutputSectionFactory<ELF32BE>;
|
||||||
template class OutputSectionFactory<ELF64LE>;
|
template class OutputSectionFactory<ELF64LE>;
|
||||||
|
|
|
@ -11,7 +11,6 @@
|
||||||
#define LLD_ELF_OUTPUT_SECTIONS_H
|
#define LLD_ELF_OUTPUT_SECTIONS_H
|
||||||
|
|
||||||
#include "Config.h"
|
#include "Config.h"
|
||||||
#include "GdbIndex.h"
|
|
||||||
#include "Relocations.h"
|
#include "Relocations.h"
|
||||||
|
|
||||||
#include "lld/Core/LLVM.h"
|
#include "lld/Core/LLVM.h"
|
||||||
|
@ -105,30 +104,6 @@ public:
|
||||||
uint32_t Link = 0;
|
uint32_t Link = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class ELFT> class GdbIndexSection final : public OutputSectionBase {
|
|
||||||
typedef typename ELFT::uint uintX_t;
|
|
||||||
|
|
||||||
const unsigned OffsetTypeSize = 4;
|
|
||||||
const unsigned CuListOffset = 6 * OffsetTypeSize;
|
|
||||||
const unsigned CompilationUnitSize = 16;
|
|
||||||
const unsigned AddressEntrySize = 16 + OffsetTypeSize;
|
|
||||||
const unsigned SymTabEntrySize = 2 * OffsetTypeSize;
|
|
||||||
|
|
||||||
public:
|
|
||||||
GdbIndexSection();
|
|
||||||
void finalize() override;
|
|
||||||
void writeTo(uint8_t *Buf) override;
|
|
||||||
|
|
||||||
// Pairs of [CU Offset, CU length].
|
|
||||||
std::vector<std::pair<uintX_t, uintX_t>> CompilationUnits;
|
|
||||||
|
|
||||||
private:
|
|
||||||
void parseDebugSections();
|
|
||||||
void readDwarf(InputSection<ELFT> *I);
|
|
||||||
|
|
||||||
uint32_t CuTypesOffset;
|
|
||||||
};
|
|
||||||
|
|
||||||
// For more information about .gnu.version and .gnu.version_r see:
|
// For more information about .gnu.version and .gnu.version_r see:
|
||||||
// https://www.akkadia.org/drepper/symbol-versioning
|
// https://www.akkadia.org/drepper/symbol-versioning
|
||||||
|
|
||||||
|
@ -338,7 +313,6 @@ template <class ELFT> struct Out {
|
||||||
static uint8_t First;
|
static uint8_t First;
|
||||||
static EhFrameHeader<ELFT> *EhFrameHdr;
|
static EhFrameHeader<ELFT> *EhFrameHdr;
|
||||||
static EhOutputSection<ELFT> *EhFrame;
|
static EhOutputSection<ELFT> *EhFrame;
|
||||||
static GdbIndexSection<ELFT> *GdbIndex;
|
|
||||||
static OutputSection<ELFT> *Bss;
|
static OutputSection<ELFT> *Bss;
|
||||||
static OutputSection<ELFT> *MipsRldMap;
|
static OutputSection<ELFT> *MipsRldMap;
|
||||||
static OutputSectionBase *Opd;
|
static OutputSectionBase *Opd;
|
||||||
|
@ -391,7 +365,6 @@ template <class ELFT> uint64_t getHeaderSize() {
|
||||||
template <class ELFT> uint8_t Out<ELFT>::First;
|
template <class ELFT> uint8_t Out<ELFT>::First;
|
||||||
template <class ELFT> EhFrameHeader<ELFT> *Out<ELFT>::EhFrameHdr;
|
template <class ELFT> EhFrameHeader<ELFT> *Out<ELFT>::EhFrameHdr;
|
||||||
template <class ELFT> EhOutputSection<ELFT> *Out<ELFT>::EhFrame;
|
template <class ELFT> EhOutputSection<ELFT> *Out<ELFT>::EhFrame;
|
||||||
template <class ELFT> GdbIndexSection<ELFT> *Out<ELFT>::GdbIndex;
|
|
||||||
template <class ELFT> OutputSection<ELFT> *Out<ELFT>::Bss;
|
template <class ELFT> OutputSection<ELFT> *Out<ELFT>::Bss;
|
||||||
template <class ELFT> OutputSection<ELFT> *Out<ELFT>::MipsRldMap;
|
template <class ELFT> OutputSection<ELFT> *Out<ELFT>::MipsRldMap;
|
||||||
template <class ELFT> OutputSectionBase *Out<ELFT>::Opd;
|
template <class ELFT> OutputSectionBase *Out<ELFT>::Opd;
|
||||||
|
|
|
@ -1360,6 +1360,49 @@ template <class ELFT> size_t PltSection<ELFT>::getSize() const {
|
||||||
return Target->PltHeaderSize + Entries.size() * Target->PltEntrySize;
|
return Target->PltHeaderSize + Entries.size() * Target->PltEntrySize;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template <class ELFT>
|
||||||
|
GdbIndexSection<ELFT>::GdbIndexSection()
|
||||||
|
: SyntheticSection<ELFT>(0, SHT_PROGBITS, 1, ".gdb_index") {}
|
||||||
|
|
||||||
|
template <class ELFT> void GdbIndexSection<ELFT>::parseDebugSections() {
|
||||||
|
std::vector<InputSection<ELFT> *> &IS =
|
||||||
|
static_cast<OutputSection<ELFT> *>(Out<ELFT>::DebugInfo)->Sections;
|
||||||
|
|
||||||
|
for (InputSection<ELFT> *I : IS)
|
||||||
|
readDwarf(I);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class ELFT>
|
||||||
|
void GdbIndexSection<ELFT>::readDwarf(InputSection<ELFT> *I) {
|
||||||
|
std::vector<std::pair<uintX_t, uintX_t>> CuList = readCuList(I);
|
||||||
|
CompilationUnits.insert(CompilationUnits.end(), CuList.begin(), CuList.end());
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class ELFT> void GdbIndexSection<ELFT>::finalize() {
|
||||||
|
parseDebugSections();
|
||||||
|
|
||||||
|
// GdbIndex header consist from version fields
|
||||||
|
// and 5 more fields with different kinds of offsets.
|
||||||
|
CuTypesOffset = CuListOffset + CompilationUnits.size() * CompilationUnitSize;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class ELFT> void GdbIndexSection<ELFT>::writeTo(uint8_t *Buf) {
|
||||||
|
write32le(Buf, 7); // Write Version
|
||||||
|
write32le(Buf + 4, CuListOffset); // CU list offset
|
||||||
|
write32le(Buf + 8, CuTypesOffset); // Types CU list offset
|
||||||
|
write32le(Buf + 12, CuTypesOffset); // Address area offset
|
||||||
|
write32le(Buf + 16, CuTypesOffset); // Symbol table offset
|
||||||
|
write32le(Buf + 20, CuTypesOffset); // Constant pool offset
|
||||||
|
Buf += 24;
|
||||||
|
|
||||||
|
// Write the CU list.
|
||||||
|
for (std::pair<uintX_t, uintX_t> CU : CompilationUnits) {
|
||||||
|
write64le(Buf, CU.first);
|
||||||
|
write64le(Buf + 8, CU.second);
|
||||||
|
Buf += 16;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
template InputSection<ELF32LE> *elf::createCommonSection();
|
template InputSection<ELF32LE> *elf::createCommonSection();
|
||||||
template InputSection<ELF32BE> *elf::createCommonSection();
|
template InputSection<ELF32BE> *elf::createCommonSection();
|
||||||
template InputSection<ELF64LE> *elf::createCommonSection();
|
template InputSection<ELF64LE> *elf::createCommonSection();
|
||||||
|
@ -1469,3 +1512,8 @@ template class elf::PltSection<ELF32LE>;
|
||||||
template class elf::PltSection<ELF32BE>;
|
template class elf::PltSection<ELF32BE>;
|
||||||
template class elf::PltSection<ELF64LE>;
|
template class elf::PltSection<ELF64LE>;
|
||||||
template class elf::PltSection<ELF64BE>;
|
template class elf::PltSection<ELF64BE>;
|
||||||
|
|
||||||
|
template class elf::GdbIndexSection<ELF32LE>;
|
||||||
|
template class elf::GdbIndexSection<ELF32BE>;
|
||||||
|
template class elf::GdbIndexSection<ELF64LE>;
|
||||||
|
template class elf::GdbIndexSection<ELF64BE>;
|
||||||
|
|
|
@ -10,6 +10,7 @@
|
||||||
#ifndef LLD_ELF_SYNTHETIC_SECTION_H
|
#ifndef LLD_ELF_SYNTHETIC_SECTION_H
|
||||||
#define LLD_ELF_SYNTHETIC_SECTION_H
|
#define LLD_ELF_SYNTHETIC_SECTION_H
|
||||||
|
|
||||||
|
#include "GdbIndex.h"
|
||||||
#include "InputSection.h"
|
#include "InputSection.h"
|
||||||
#include "llvm/ADT/SmallPtrSet.h"
|
#include "llvm/ADT/SmallPtrSet.h"
|
||||||
|
|
||||||
|
@ -502,6 +503,32 @@ private:
|
||||||
std::vector<std::pair<const SymbolBody *, unsigned>> Entries;
|
std::vector<std::pair<const SymbolBody *, unsigned>> Entries;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <class ELFT>
|
||||||
|
class GdbIndexSection final : public SyntheticSection<ELFT> {
|
||||||
|
typedef typename ELFT::uint uintX_t;
|
||||||
|
|
||||||
|
const unsigned OffsetTypeSize = 4;
|
||||||
|
const unsigned CuListOffset = 6 * OffsetTypeSize;
|
||||||
|
const unsigned CompilationUnitSize = 16;
|
||||||
|
const unsigned AddressEntrySize = 16 + OffsetTypeSize;
|
||||||
|
const unsigned SymTabEntrySize = 2 * OffsetTypeSize;
|
||||||
|
|
||||||
|
public:
|
||||||
|
GdbIndexSection();
|
||||||
|
void finalize() override;
|
||||||
|
void writeTo(uint8_t *Buf) override;
|
||||||
|
size_t getSize() const override { return CuTypesOffset; }
|
||||||
|
|
||||||
|
// Pairs of [CU Offset, CU length].
|
||||||
|
std::vector<std::pair<uintX_t, uintX_t>> CompilationUnits;
|
||||||
|
|
||||||
|
private:
|
||||||
|
void parseDebugSections();
|
||||||
|
void readDwarf(InputSection<ELFT> *I);
|
||||||
|
|
||||||
|
uint32_t CuTypesOffset;
|
||||||
|
};
|
||||||
|
|
||||||
template <class ELFT> InputSection<ELFT> *createCommonSection();
|
template <class ELFT> InputSection<ELFT> *createCommonSection();
|
||||||
template <class ELFT> InputSection<ELFT> *createInterpSection();
|
template <class ELFT> InputSection<ELFT> *createInterpSection();
|
||||||
template <class ELFT> MergeInputSection<ELFT> *createCommentSection();
|
template <class ELFT> MergeInputSection<ELFT> *createCommentSection();
|
||||||
|
@ -514,6 +541,7 @@ template <class ELFT> struct In {
|
||||||
static StringTableSection<ELFT> *DynStrTab;
|
static StringTableSection<ELFT> *DynStrTab;
|
||||||
static SymbolTableSection<ELFT> *DynSymTab;
|
static SymbolTableSection<ELFT> *DynSymTab;
|
||||||
static GnuHashTableSection<ELFT> *GnuHashTab;
|
static GnuHashTableSection<ELFT> *GnuHashTab;
|
||||||
|
static GdbIndexSection<ELFT> *GdbIndex;
|
||||||
static GotSection<ELFT> *Got;
|
static GotSection<ELFT> *Got;
|
||||||
static MipsGotSection<ELFT> *MipsGot;
|
static MipsGotSection<ELFT> *MipsGot;
|
||||||
static GotPltSection<ELFT> *GotPlt;
|
static GotPltSection<ELFT> *GotPlt;
|
||||||
|
@ -535,6 +563,7 @@ template <class ELFT> InputSection<ELFT> *In<ELFT>::Common;
|
||||||
template <class ELFT> DynamicSection<ELFT> *In<ELFT>::Dynamic;
|
template <class ELFT> DynamicSection<ELFT> *In<ELFT>::Dynamic;
|
||||||
template <class ELFT> StringTableSection<ELFT> *In<ELFT>::DynStrTab;
|
template <class ELFT> StringTableSection<ELFT> *In<ELFT>::DynStrTab;
|
||||||
template <class ELFT> SymbolTableSection<ELFT> *In<ELFT>::DynSymTab;
|
template <class ELFT> SymbolTableSection<ELFT> *In<ELFT>::DynSymTab;
|
||||||
|
template <class ELFT> GdbIndexSection<ELFT> *In<ELFT>::GdbIndex;
|
||||||
template <class ELFT> GnuHashTableSection<ELFT> *In<ELFT>::GnuHashTab;
|
template <class ELFT> GnuHashTableSection<ELFT> *In<ELFT>::GnuHashTab;
|
||||||
template <class ELFT> GotSection<ELFT> *In<ELFT>::Got;
|
template <class ELFT> GotSection<ELFT> *In<ELFT>::Got;
|
||||||
template <class ELFT> MipsGotSection<ELFT> *In<ELFT>::MipsGot;
|
template <class ELFT> MipsGotSection<ELFT> *In<ELFT>::MipsGot;
|
||||||
|
|
|
@ -268,7 +268,7 @@ template <class ELFT> void Writer<ELFT>::createSyntheticSections() {
|
||||||
if (Config->SysvHash)
|
if (Config->SysvHash)
|
||||||
In<ELFT>::HashTab = make<HashTableSection<ELFT>>();
|
In<ELFT>::HashTab = make<HashTableSection<ELFT>>();
|
||||||
if (Config->GdbIndex)
|
if (Config->GdbIndex)
|
||||||
Out<ELFT>::GdbIndex = make<GdbIndexSection<ELFT>>();
|
In<ELFT>::GdbIndex = make<GdbIndexSection<ELFT>>();
|
||||||
|
|
||||||
In<ELFT>::RelaPlt = make<RelocationSection<ELFT>>(
|
In<ELFT>::RelaPlt = make<RelocationSection<ELFT>>(
|
||||||
Config->Rela ? ".rela.plt" : ".rel.plt", false /*Sort*/);
|
Config->Rela ? ".rela.plt" : ".rel.plt", false /*Sort*/);
|
||||||
|
@ -979,8 +979,9 @@ template <class ELFT> void Writer<ELFT>::finalizeSections() {
|
||||||
finalizeSynthetic<ELFT>(
|
finalizeSynthetic<ELFT>(
|
||||||
{In<ELFT>::DynSymTab, In<ELFT>::GnuHashTab, In<ELFT>::HashTab,
|
{In<ELFT>::DynSymTab, In<ELFT>::GnuHashTab, In<ELFT>::HashTab,
|
||||||
In<ELFT>::SymTab, In<ELFT>::ShStrTab, In<ELFT>::StrTab,
|
In<ELFT>::SymTab, In<ELFT>::ShStrTab, In<ELFT>::StrTab,
|
||||||
In<ELFT>::DynStrTab, In<ELFT>::Got, In<ELFT>::MipsGot, In<ELFT>::GotPlt,
|
In<ELFT>::DynStrTab, In<ELFT>::GdbIndex, In<ELFT>::Got,
|
||||||
In<ELFT>::RelaDyn, In<ELFT>::RelaPlt, In<ELFT>::Plt, In<ELFT>::Dynamic});
|
In<ELFT>::MipsGot, In<ELFT>::GotPlt, In<ELFT>::RelaDyn,
|
||||||
|
In<ELFT>::RelaPlt, In<ELFT>::Plt, In<ELFT>::Dynamic});
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class ELFT> bool Writer<ELFT>::needsGot() {
|
template <class ELFT> bool Writer<ELFT>::needsGot() {
|
||||||
|
@ -1006,8 +1007,8 @@ template <class ELFT> void Writer<ELFT>::addPredefinedSections() {
|
||||||
|
|
||||||
// This order is not the same as the final output order
|
// This order is not the same as the final output order
|
||||||
// because we sort the sections using their attributes below.
|
// because we sort the sections using their attributes below.
|
||||||
if (Out<ELFT>::GdbIndex && Out<ELFT>::DebugInfo)
|
if (In<ELFT>::GdbIndex && Out<ELFT>::DebugInfo)
|
||||||
Add(Out<ELFT>::GdbIndex);
|
addInputSec(In<ELFT>::GdbIndex);
|
||||||
addInputSec(In<ELFT>::SymTab);
|
addInputSec(In<ELFT>::SymTab);
|
||||||
addInputSec(In<ELFT>::ShStrTab);
|
addInputSec(In<ELFT>::ShStrTab);
|
||||||
addInputSec(In<ELFT>::StrTab);
|
addInputSec(In<ELFT>::StrTab);
|
||||||
|
|
Loading…
Reference in New Issue