Coverage Report

Created: 2018-08-19 14:04

/Users/buildslave/jenkins/workspace/clang-stage2-coverage-R/llvm/tools/lld/ELF/SyntheticSections.cpp
Line
Count
Source (jump to first uncovered line)
1
//===- SyntheticSections.cpp ----------------------------------------------===//
2
//
3
//                             The LLVM Linker
4
//
5
// This file is distributed under the University of Illinois Open Source
6
// License. See LICENSE.TXT for details.
7
//
8
//===----------------------------------------------------------------------===//
9
//
10
// This file contains linker-synthesized sections. Currently,
11
// synthetic sections are created either output sections or input sections,
12
// but we are rewriting code so that all synthetic sections are created as
13
// input sections.
14
//
15
//===----------------------------------------------------------------------===//
16
17
#include "SyntheticSections.h"
18
#include "Bits.h"
19
#include "Config.h"
20
#include "InputFiles.h"
21
#include "LinkerScript.h"
22
#include "OutputSections.h"
23
#include "SymbolTable.h"
24
#include "Symbols.h"
25
#include "Target.h"
26
#include "Writer.h"
27
#include "lld/Common/ErrorHandler.h"
28
#include "lld/Common/Memory.h"
29
#include "lld/Common/Strings.h"
30
#include "lld/Common/Threads.h"
31
#include "lld/Common/Version.h"
32
#include "llvm/ADT/SetOperations.h"
33
#include "llvm/BinaryFormat/Dwarf.h"
34
#include "llvm/DebugInfo/DWARF/DWARFDebugPubTable.h"
35
#include "llvm/Object/Decompressor.h"
36
#include "llvm/Object/ELFObjectFile.h"
37
#include "llvm/Support/Endian.h"
38
#include "llvm/Support/LEB128.h"
39
#include "llvm/Support/MD5.h"
40
#include "llvm/Support/RandomNumberGenerator.h"
41
#include "llvm/Support/SHA1.h"
42
#include "llvm/Support/xxhash.h"
43
#include <cstdlib>
44
#include <thread>
45
46
using namespace llvm;
47
using namespace llvm::dwarf;
48
using namespace llvm::ELF;
49
using namespace llvm::object;
50
using namespace llvm::support;
51
52
using namespace lld;
53
using namespace lld::elf;
54
55
using llvm::support::endian::read32le;
56
using llvm::support::endian::write32le;
57
using llvm::support::endian::write64le;
58
59
constexpr size_t MergeNoTailSection::NumShards;
60
61
// Returns an LLD version string.
62
2.16k
static ArrayRef<uint8_t> getVersion() {
63
2.16k
  // Check LLD_VERSION first for ease of testing.
64
2.16k
  // You can get consistent output by using the environment variable.
65
2.16k
  // This is only for testing.
66
2.16k
  StringRef S = getenv("LLD_VERSION");
67
2.16k
  if (S.empty())
68
0
    S = Saver.save(Twine("Linker: ") + getLLDVersion());
69
2.16k
70
2.16k
  // +1 to include the terminating '\0'.
71
2.16k
  return {(const uint8_t *)S.data(), S.size() + 1};
72
2.16k
}
73
74
// Creates a .comment section containing LLD version info.
75
// With this feature, you can identify LLD-generated binaries easily
76
// by "readelf --string-dump .comment <file>".
77
// The returned object is a mergeable string section.
78
2.16k
MergeInputSection *elf::createCommentSection() {
79
2.16k
  return make<MergeInputSection>(SHF_MERGE | SHF_STRINGS, SHT_PROGBITS, 1,
80
2.16k
                                 getVersion(), ".comment");
81
2.16k
}
82
83
// .MIPS.abiflags section.
84
template <class ELFT>
85
MipsAbiFlagsSection<ELFT>::MipsAbiFlagsSection(Elf_Mips_ABIFlags Flags)
86
    : SyntheticSection(SHF_ALLOC, SHT_MIPS_ABIFLAGS, 8, ".MIPS.abiflags"),
87
173
      Flags(Flags) {
88
173
  this->Entsize = sizeof(Elf_Mips_ABIFlags);
89
173
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::MipsAbiFlagsSection(llvm::object::Elf_Mips_ABIFlags<llvm::object::ELFType<(llvm::support::endianness)1, false> >)
Line
Count
Source
87
16
      Flags(Flags) {
88
16
  this->Entsize = sizeof(Elf_Mips_ABIFlags);
89
16
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::MipsAbiFlagsSection(llvm::object::Elf_Mips_ABIFlags<llvm::object::ELFType<(llvm::support::endianness)0, false> >)
Line
Count
Source
87
113
      Flags(Flags) {
88
113
  this->Entsize = sizeof(Elf_Mips_ABIFlags);
89
113
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::MipsAbiFlagsSection(llvm::object::Elf_Mips_ABIFlags<llvm::object::ELFType<(llvm::support::endianness)1, true> >)
Line
Count
Source
87
2
      Flags(Flags) {
88
2
  this->Entsize = sizeof(Elf_Mips_ABIFlags);
89
2
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::MipsAbiFlagsSection(llvm::object::Elf_Mips_ABIFlags<llvm::object::ELFType<(llvm::support::endianness)0, true> >)
Line
Count
Source
87
42
      Flags(Flags) {
88
42
  this->Entsize = sizeof(Elf_Mips_ABIFlags);
89
42
}
90
91
167
template <class ELFT> void MipsAbiFlagsSection<ELFT>::writeTo(uint8_t *Buf) {
92
167
  memcpy(Buf, &Flags, sizeof(Flags));
93
167
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::writeTo(unsigned char*)
Line
Count
Source
91
16
template <class ELFT> void MipsAbiFlagsSection<ELFT>::writeTo(uint8_t *Buf) {
92
16
  memcpy(Buf, &Flags, sizeof(Flags));
93
16
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::writeTo(unsigned char*)
Line
Count
Source
91
112
template <class ELFT> void MipsAbiFlagsSection<ELFT>::writeTo(uint8_t *Buf) {
92
112
  memcpy(Buf, &Flags, sizeof(Flags));
93
112
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::writeTo(unsigned char*)
Line
Count
Source
91
2
template <class ELFT> void MipsAbiFlagsSection<ELFT>::writeTo(uint8_t *Buf) {
92
2
  memcpy(Buf, &Flags, sizeof(Flags));
93
2
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::writeTo(unsigned char*)
Line
Count
Source
91
37
template <class ELFT> void MipsAbiFlagsSection<ELFT>::writeTo(uint8_t *Buf) {
92
37
  memcpy(Buf, &Flags, sizeof(Flags));
93
37
}
94
95
template <class ELFT>
96
179
MipsAbiFlagsSection<ELFT> *MipsAbiFlagsSection<ELFT>::create() {
97
179
  Elf_Mips_ABIFlags Flags = {};
98
179
  bool Create = false;
99
179
100
1.73k
  for (InputSectionBase *Sec : InputSections) {
101
1.73k
    if (Sec->Type != SHT_MIPS_ABIFLAGS)
102
1.50k
      continue;
103
226
    Sec->Live = false;
104
226
    Create = true;
105
226
106
226
    std::string Filename = toString(Sec->File);
107
226
    const size_t Size = Sec->Data.size();
108
226
    // Older version of BFD (such as the default FreeBSD linker) concatenate
109
226
    // .MIPS.abiflags instead of merging. To allow for this case (or potential
110
226
    // zero padding) we ignore everything after the first Elf_Mips_ABIFlags
111
226
    if (Size < sizeof(Elf_Mips_ABIFlags)) {
112
0
      error(Filename + ": invalid size of .MIPS.abiflags section: got " +
113
0
            Twine(Size) + " instead of " + Twine(sizeof(Elf_Mips_ABIFlags)));
114
0
      return nullptr;
115
0
    }
116
226
    auto *S = reinterpret_cast<const Elf_Mips_ABIFlags *>(Sec->Data.data());
117
226
    if (S->version != 0) {
118
0
      error(Filename + ": unexpected .MIPS.abiflags version " +
119
0
            Twine(S->version));
120
0
      return nullptr;
121
0
    }
122
226
123
226
    // LLD checks ISA compatibility in calcMipsEFlags(). Here we just
124
226
    // select the highest number of ISA/Rev/Ext.
125
226
    Flags.isa_level = std::max(Flags.isa_level, S->isa_level);
126
226
    Flags.isa_rev = std::max(Flags.isa_rev, S->isa_rev);
127
226
    Flags.isa_ext = std::max(Flags.isa_ext, S->isa_ext);
128
226
    Flags.gpr_size = std::max(Flags.gpr_size, S->gpr_size);
129
226
    Flags.cpr1_size = std::max(Flags.cpr1_size, S->cpr1_size);
130
226
    Flags.cpr2_size = std::max(Flags.cpr2_size, S->cpr2_size);
131
226
    Flags.ases |= S->ases;
132
226
    Flags.flags1 |= S->flags1;
133
226
    Flags.flags2 |= S->flags2;
134
226
    Flags.fp_abi = elf::getMipsFpAbiFlag(Flags.fp_abi, S->fp_abi, Filename);
135
226
  };
136
179
137
179
  if (Create)
138
173
    return make<MipsAbiFlagsSection<ELFT>>(Flags);
139
6
  return nullptr;
140
6
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::create()
Line
Count
Source
96
17
MipsAbiFlagsSection<ELFT> *MipsAbiFlagsSection<ELFT>::create() {
97
17
  Elf_Mips_ABIFlags Flags = {};
98
17
  bool Create = false;
99
17
100
154
  for (InputSectionBase *Sec : InputSections) {
101
154
    if (Sec->Type != SHT_MIPS_ABIFLAGS)
102
134
      continue;
103
20
    Sec->Live = false;
104
20
    Create = true;
105
20
106
20
    std::string Filename = toString(Sec->File);
107
20
    const size_t Size = Sec->Data.size();
108
20
    // Older version of BFD (such as the default FreeBSD linker) concatenate
109
20
    // .MIPS.abiflags instead of merging. To allow for this case (or potential
110
20
    // zero padding) we ignore everything after the first Elf_Mips_ABIFlags
111
20
    if (Size < sizeof(Elf_Mips_ABIFlags)) {
112
0
      error(Filename + ": invalid size of .MIPS.abiflags section: got " +
113
0
            Twine(Size) + " instead of " + Twine(sizeof(Elf_Mips_ABIFlags)));
114
0
      return nullptr;
115
0
    }
116
20
    auto *S = reinterpret_cast<const Elf_Mips_ABIFlags *>(Sec->Data.data());
117
20
    if (S->version != 0) {
118
0
      error(Filename + ": unexpected .MIPS.abiflags version " +
119
0
            Twine(S->version));
120
0
      return nullptr;
121
0
    }
122
20
123
20
    // LLD checks ISA compatibility in calcMipsEFlags(). Here we just
124
20
    // select the highest number of ISA/Rev/Ext.
125
20
    Flags.isa_level = std::max(Flags.isa_level, S->isa_level);
126
20
    Flags.isa_rev = std::max(Flags.isa_rev, S->isa_rev);
127
20
    Flags.isa_ext = std::max(Flags.isa_ext, S->isa_ext);
128
20
    Flags.gpr_size = std::max(Flags.gpr_size, S->gpr_size);
129
20
    Flags.cpr1_size = std::max(Flags.cpr1_size, S->cpr1_size);
130
20
    Flags.cpr2_size = std::max(Flags.cpr2_size, S->cpr2_size);
131
20
    Flags.ases |= S->ases;
132
20
    Flags.flags1 |= S->flags1;
133
20
    Flags.flags2 |= S->flags2;
134
20
    Flags.fp_abi = elf::getMipsFpAbiFlag(Flags.fp_abi, S->fp_abi, Filename);
135
20
  };
136
17
137
17
  if (Create)
138
16
    return make<MipsAbiFlagsSection<ELFT>>(Flags);
139
1
  return nullptr;
140
1
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::create()
Line
Count
Source
96
116
MipsAbiFlagsSection<ELFT> *MipsAbiFlagsSection<ELFT>::create() {
97
116
  Elf_Mips_ABIFlags Flags = {};
98
116
  bool Create = false;
99
116
100
1.16k
  for (InputSectionBase *Sec : InputSections) {
101
1.16k
    if (Sec->Type != SHT_MIPS_ABIFLAGS)
102
1.01k
      continue;
103
150
    Sec->Live = false;
104
150
    Create = true;
105
150
106
150
    std::string Filename = toString(Sec->File);
107
150
    const size_t Size = Sec->Data.size();
108
150
    // Older version of BFD (such as the default FreeBSD linker) concatenate
109
150
    // .MIPS.abiflags instead of merging. To allow for this case (or potential
110
150
    // zero padding) we ignore everything after the first Elf_Mips_ABIFlags
111
150
    if (Size < sizeof(Elf_Mips_ABIFlags)) {
112
0
      error(Filename + ": invalid size of .MIPS.abiflags section: got " +
113
0
            Twine(Size) + " instead of " + Twine(sizeof(Elf_Mips_ABIFlags)));
114
0
      return nullptr;
115
0
    }
116
150
    auto *S = reinterpret_cast<const Elf_Mips_ABIFlags *>(Sec->Data.data());
117
150
    if (S->version != 0) {
118
0
      error(Filename + ": unexpected .MIPS.abiflags version " +
119
0
            Twine(S->version));
120
0
      return nullptr;
121
0
    }
122
150
123
150
    // LLD checks ISA compatibility in calcMipsEFlags(). Here we just
124
150
    // select the highest number of ISA/Rev/Ext.
125
150
    Flags.isa_level = std::max(Flags.isa_level, S->isa_level);
126
150
    Flags.isa_rev = std::max(Flags.isa_rev, S->isa_rev);
127
150
    Flags.isa_ext = std::max(Flags.isa_ext, S->isa_ext);
128
150
    Flags.gpr_size = std::max(Flags.gpr_size, S->gpr_size);
129
150
    Flags.cpr1_size = std::max(Flags.cpr1_size, S->cpr1_size);
130
150
    Flags.cpr2_size = std::max(Flags.cpr2_size, S->cpr2_size);
131
150
    Flags.ases |= S->ases;
132
150
    Flags.flags1 |= S->flags1;
133
150
    Flags.flags2 |= S->flags2;
134
150
    Flags.fp_abi = elf::getMipsFpAbiFlag(Flags.fp_abi, S->fp_abi, Filename);
135
150
  };
136
116
137
116
  if (Create)
138
113
    return make<MipsAbiFlagsSection<ELFT>>(Flags);
139
3
  return nullptr;
140
3
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::create()
Line
Count
Source
96
2
MipsAbiFlagsSection<ELFT> *MipsAbiFlagsSection<ELFT>::create() {
97
2
  Elf_Mips_ABIFlags Flags = {};
98
2
  bool Create = false;
99
2
100
16
  for (InputSectionBase *Sec : InputSections) {
101
16
    if (Sec->Type != SHT_MIPS_ABIFLAGS)
102
14
      continue;
103
2
    Sec->Live = false;
104
2
    Create = true;
105
2
106
2
    std::string Filename = toString(Sec->File);
107
2
    const size_t Size = Sec->Data.size();
108
2
    // Older version of BFD (such as the default FreeBSD linker) concatenate
109
2
    // .MIPS.abiflags instead of merging. To allow for this case (or potential
110
2
    // zero padding) we ignore everything after the first Elf_Mips_ABIFlags
111
2
    if (Size < sizeof(Elf_Mips_ABIFlags)) {
112
0
      error(Filename + ": invalid size of .MIPS.abiflags section: got " +
113
0
            Twine(Size) + " instead of " + Twine(sizeof(Elf_Mips_ABIFlags)));
114
0
      return nullptr;
115
0
    }
116
2
    auto *S = reinterpret_cast<const Elf_Mips_ABIFlags *>(Sec->Data.data());
117
2
    if (S->version != 0) {
118
0
      error(Filename + ": unexpected .MIPS.abiflags version " +
119
0
            Twine(S->version));
120
0
      return nullptr;
121
0
    }
122
2
123
2
    // LLD checks ISA compatibility in calcMipsEFlags(). Here we just
124
2
    // select the highest number of ISA/Rev/Ext.
125
2
    Flags.isa_level = std::max(Flags.isa_level, S->isa_level);
126
2
    Flags.isa_rev = std::max(Flags.isa_rev, S->isa_rev);
127
2
    Flags.isa_ext = std::max(Flags.isa_ext, S->isa_ext);
128
2
    Flags.gpr_size = std::max(Flags.gpr_size, S->gpr_size);
129
2
    Flags.cpr1_size = std::max(Flags.cpr1_size, S->cpr1_size);
130
2
    Flags.cpr2_size = std::max(Flags.cpr2_size, S->cpr2_size);
131
2
    Flags.ases |= S->ases;
132
2
    Flags.flags1 |= S->flags1;
133
2
    Flags.flags2 |= S->flags2;
134
2
    Flags.fp_abi = elf::getMipsFpAbiFlag(Flags.fp_abi, S->fp_abi, Filename);
135
2
  };
136
2
137
2
  if (Create)
138
2
    return make<MipsAbiFlagsSection<ELFT>>(Flags);
139
0
  return nullptr;
140
0
}
lld::elf::MipsAbiFlagsSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::create()
Line
Count
Source
96
44
MipsAbiFlagsSection<ELFT> *MipsAbiFlagsSection<ELFT>::create() {
97
44
  Elf_Mips_ABIFlags Flags = {};
98
44
  bool Create = false;
99
44
100
401
  for (InputSectionBase *Sec : InputSections) {
101
401
    if (Sec->Type != SHT_MIPS_ABIFLAGS)
102
347
      continue;
103
54
    Sec->Live = false;
104
54
    Create = true;
105
54
106
54
    std::string Filename = toString(Sec->File);
107
54
    const size_t Size = Sec->Data.size();
108
54
    // Older version of BFD (such as the default FreeBSD linker) concatenate
109
54
    // .MIPS.abiflags instead of merging. To allow for this case (or potential
110
54
    // zero padding) we ignore everything after the first Elf_Mips_ABIFlags
111
54
    if (Size < sizeof(Elf_Mips_ABIFlags)) {
112
0
      error(Filename + ": invalid size of .MIPS.abiflags section: got " +
113
0
            Twine(Size) + " instead of " + Twine(sizeof(Elf_Mips_ABIFlags)));
114
0
      return nullptr;
115
0
    }
116
54
    auto *S = reinterpret_cast<const Elf_Mips_ABIFlags *>(Sec->Data.data());
117
54
    if (S->version != 0) {
118
0
      error(Filename + ": unexpected .MIPS.abiflags version " +
119
0
            Twine(S->version));
120
0
      return nullptr;
121
0
    }
122
54
123
54
    // LLD checks ISA compatibility in calcMipsEFlags(). Here we just
124
54
    // select the highest number of ISA/Rev/Ext.
125
54
    Flags.isa_level = std::max(Flags.isa_level, S->isa_level);
126
54
    Flags.isa_rev = std::max(Flags.isa_rev, S->isa_rev);
127
54
    Flags.isa_ext = std::max(Flags.isa_ext, S->isa_ext);
128
54
    Flags.gpr_size = std::max(Flags.gpr_size, S->gpr_size);
129
54
    Flags.cpr1_size = std::max(Flags.cpr1_size, S->cpr1_size);
130
54
    Flags.cpr2_size = std::max(Flags.cpr2_size, S->cpr2_size);
131
54
    Flags.ases |= S->ases;
132
54
    Flags.flags1 |= S->flags1;
133
54
    Flags.flags2 |= S->flags2;
134
54
    Flags.fp_abi = elf::getMipsFpAbiFlag(Flags.fp_abi, S->fp_abi, Filename);
135
54
  };
136
44
137
44
  if (Create)
138
42
    return make<MipsAbiFlagsSection<ELFT>>(Flags);
139
2
  return nullptr;
140
2
}
141
142
// .MIPS.options section.
143
template <class ELFT>
144
MipsOptionsSection<ELFT>::MipsOptionsSection(Elf_Mips_RegInfo Reginfo)
145
    : SyntheticSection(SHF_ALLOC, SHT_MIPS_OPTIONS, 8, ".MIPS.options"),
146
40
      Reginfo(Reginfo) {
147
40
  this->Entsize = sizeof(Elf_Mips_Options) + sizeof(Elf_Mips_RegInfo);
148
40
}
Unexecuted instantiation: lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::MipsOptionsSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)1, false> >)
Unexecuted instantiation: lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::MipsOptionsSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)0, false> >)
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::MipsOptionsSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)1, true> >)
Line
Count
Source
146
2
      Reginfo(Reginfo) {
147
2
  this->Entsize = sizeof(Elf_Mips_Options) + sizeof(Elf_Mips_RegInfo);
148
2
}
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::MipsOptionsSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)0, true> >)
Line
Count
Source
146
38
      Reginfo(Reginfo) {
147
38
  this->Entsize = sizeof(Elf_Mips_Options) + sizeof(Elf_Mips_RegInfo);
148
38
}
149
150
39
template <class ELFT> void MipsOptionsSection<ELFT>::writeTo(uint8_t *Buf) {
151
39
  auto *Options = reinterpret_cast<Elf_Mips_Options *>(Buf);
152
39
  Options->kind = ODK_REGINFO;
153
39
  Options->size = getSize();
154
39
155
39
  if (!Config->Relocatable)
156
37
    Reginfo.ri_gp_value = InX::MipsGot->getGp();
157
39
  memcpy(Buf + sizeof(Elf_Mips_Options), &Reginfo, sizeof(Reginfo));
158
39
}
Unexecuted instantiation: lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::writeTo(unsigned char*)
Unexecuted instantiation: lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::writeTo(unsigned char*)
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::writeTo(unsigned char*)
Line
Count
Source
150
2
template <class ELFT> void MipsOptionsSection<ELFT>::writeTo(uint8_t *Buf) {
151
2
  auto *Options = reinterpret_cast<Elf_Mips_Options *>(Buf);
152
2
  Options->kind = ODK_REGINFO;
153
2
  Options->size = getSize();
154
2
155
2
  if (!Config->Relocatable)
156
2
    Reginfo.ri_gp_value = InX::MipsGot->getGp();
157
2
  memcpy(Buf + sizeof(Elf_Mips_Options), &Reginfo, sizeof(Reginfo));
158
2
}
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::writeTo(unsigned char*)
Line
Count
Source
150
37
template <class ELFT> void MipsOptionsSection<ELFT>::writeTo(uint8_t *Buf) {
151
37
  auto *Options = reinterpret_cast<Elf_Mips_Options *>(Buf);
152
37
  Options->kind = ODK_REGINFO;
153
37
  Options->size = getSize();
154
37
155
37
  if (!Config->Relocatable)
156
35
    Reginfo.ri_gp_value = InX::MipsGot->getGp();
157
37
  memcpy(Buf + sizeof(Elf_Mips_Options), &Reginfo, sizeof(Reginfo));
158
37
}
159
160
template <class ELFT>
161
179
MipsOptionsSection<ELFT> *MipsOptionsSection<ELFT>::create() {
162
179
  // N64 ABI only.
163
179
  if (!ELFT::Is64Bits)
164
133
    return nullptr;
165
46
166
46
  std::vector<InputSectionBase *> Sections;
167
46
  for (InputSectionBase *Sec : InputSections)
168
461
    if (Sec->Type == SHT_MIPS_OPTIONS)
169
48
      Sections.push_back(Sec);
170
46
171
46
  if (Sections.empty())
172
6
    return nullptr;
173
40
174
40
  Elf_Mips_RegInfo Reginfo = {};
175
48
  for (InputSectionBase *Sec : Sections) {
176
48
    Sec->Live = false;
177
48
178
48
    std::string Filename = toString(Sec->File);
179
48
    ArrayRef<uint8_t> D = Sec->Data;
180
48
181
48
    while (!D.empty()) {
182
48
      if (D.size() < sizeof(Elf_Mips_Options)) {
183
0
        error(Filename + ": invalid size of .MIPS.options section");
184
0
        break;
185
0
      }
186
48
187
48
      auto *Opt = reinterpret_cast<const Elf_Mips_Options *>(D.data());
188
48
      if (Opt->kind == ODK_REGINFO) {
189
48
        Reginfo.ri_gprmask |= Opt->getRegInfo().ri_gprmask;
190
48
        Sec->getFile<ELFT>()->MipsGp0 = Opt->getRegInfo().ri_gp_value;
191
48
        break;
192
48
      }
193
0
194
0
      if (!Opt->size)
195
0
        fatal(Filename + ": zero option descriptor size");
196
0
      D = D.slice(Opt->size);
197
0
    }
198
48
  };
199
40
200
40
  return make<MipsOptionsSection<ELFT>>(Reginfo);
201
40
}
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::create()
Line
Count
Source
161
17
MipsOptionsSection<ELFT> *MipsOptionsSection<ELFT>::create() {
162
17
  // N64 ABI only.
163
17
  if (!ELFT::Is64Bits)
164
17
    return nullptr;
165
0
166
0
  std::vector<InputSectionBase *> Sections;
167
0
  for (InputSectionBase *Sec : InputSections)
168
0
    if (Sec->Type == SHT_MIPS_OPTIONS)
169
0
      Sections.push_back(Sec);
170
0
171
0
  if (Sections.empty())
172
0
    return nullptr;
173
0
174
0
  Elf_Mips_RegInfo Reginfo = {};
175
0
  for (InputSectionBase *Sec : Sections) {
176
0
    Sec->Live = false;
177
0
178
0
    std::string Filename = toString(Sec->File);
179
0
    ArrayRef<uint8_t> D = Sec->Data;
180
0
181
0
    while (!D.empty()) {
182
0
      if (D.size() < sizeof(Elf_Mips_Options)) {
183
0
        error(Filename + ": invalid size of .MIPS.options section");
184
0
        break;
185
0
      }
186
0
187
0
      auto *Opt = reinterpret_cast<const Elf_Mips_Options *>(D.data());
188
0
      if (Opt->kind == ODK_REGINFO) {
189
0
        Reginfo.ri_gprmask |= Opt->getRegInfo().ri_gprmask;
190
0
        Sec->getFile<ELFT>()->MipsGp0 = Opt->getRegInfo().ri_gp_value;
191
0
        break;
192
0
      }
193
0
194
0
      if (!Opt->size)
195
0
        fatal(Filename + ": zero option descriptor size");
196
0
      D = D.slice(Opt->size);
197
0
    }
198
0
  };
199
0
200
0
  return make<MipsOptionsSection<ELFT>>(Reginfo);
201
0
}
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::create()
Line
Count
Source
161
116
MipsOptionsSection<ELFT> *MipsOptionsSection<ELFT>::create() {
162
116
  // N64 ABI only.
163
116
  if (!ELFT::Is64Bits)
164
116
    return nullptr;
165
0
166
0
  std::vector<InputSectionBase *> Sections;
167
0
  for (InputSectionBase *Sec : InputSections)
168
0
    if (Sec->Type == SHT_MIPS_OPTIONS)
169
0
      Sections.push_back(Sec);
170
0
171
0
  if (Sections.empty())
172
0
    return nullptr;
173
0
174
0
  Elf_Mips_RegInfo Reginfo = {};
175
0
  for (InputSectionBase *Sec : Sections) {
176
0
    Sec->Live = false;
177
0
178
0
    std::string Filename = toString(Sec->File);
179
0
    ArrayRef<uint8_t> D = Sec->Data;
180
0
181
0
    while (!D.empty()) {
182
0
      if (D.size() < sizeof(Elf_Mips_Options)) {
183
0
        error(Filename + ": invalid size of .MIPS.options section");
184
0
        break;
185
0
      }
186
0
187
0
      auto *Opt = reinterpret_cast<const Elf_Mips_Options *>(D.data());
188
0
      if (Opt->kind == ODK_REGINFO) {
189
0
        Reginfo.ri_gprmask |= Opt->getRegInfo().ri_gprmask;
190
0
        Sec->getFile<ELFT>()->MipsGp0 = Opt->getRegInfo().ri_gp_value;
191
0
        break;
192
0
      }
193
0
194
0
      if (!Opt->size)
195
0
        fatal(Filename + ": zero option descriptor size");
196
0
      D = D.slice(Opt->size);
197
0
    }
198
0
  };
199
0
200
0
  return make<MipsOptionsSection<ELFT>>(Reginfo);
201
0
}
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::create()
Line
Count
Source
161
2
MipsOptionsSection<ELFT> *MipsOptionsSection<ELFT>::create() {
162
2
  // N64 ABI only.
163
2
  if (!ELFT::Is64Bits)
164
0
    return nullptr;
165
2
166
2
  std::vector<InputSectionBase *> Sections;
167
2
  for (InputSectionBase *Sec : InputSections)
168
18
    if (Sec->Type == SHT_MIPS_OPTIONS)
169
2
      Sections.push_back(Sec);
170
2
171
2
  if (Sections.empty())
172
0
    return nullptr;
173
2
174
2
  Elf_Mips_RegInfo Reginfo = {};
175
2
  for (InputSectionBase *Sec : Sections) {
176
2
    Sec->Live = false;
177
2
178
2
    std::string Filename = toString(Sec->File);
179
2
    ArrayRef<uint8_t> D = Sec->Data;
180
2
181
2
    while (!D.empty()) {
182
2
      if (D.size() < sizeof(Elf_Mips_Options)) {
183
0
        error(Filename + ": invalid size of .MIPS.options section");
184
0
        break;
185
0
      }
186
2
187
2
      auto *Opt = reinterpret_cast<const Elf_Mips_Options *>(D.data());
188
2
      if (Opt->kind == ODK_REGINFO) {
189
2
        Reginfo.ri_gprmask |= Opt->getRegInfo().ri_gprmask;
190
2
        Sec->getFile<ELFT>()->MipsGp0 = Opt->getRegInfo().ri_gp_value;
191
2
        break;
192
2
      }
193
0
194
0
      if (!Opt->size)
195
0
        fatal(Filename + ": zero option descriptor size");
196
0
      D = D.slice(Opt->size);
197
0
    }
198
2
  };
199
2
200
2
  return make<MipsOptionsSection<ELFT>>(Reginfo);
201
2
}
lld::elf::MipsOptionsSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::create()
Line
Count
Source
161
44
MipsOptionsSection<ELFT> *MipsOptionsSection<ELFT>::create() {
162
44
  // N64 ABI only.
163
44
  if (!ELFT::Is64Bits)
164
0
    return nullptr;
165
44
166
44
  std::vector<InputSectionBase *> Sections;
167
44
  for (InputSectionBase *Sec : InputSections)
168
443
    if (Sec->Type == SHT_MIPS_OPTIONS)
169
46
      Sections.push_back(Sec);
170
44
171
44
  if (Sections.empty())
172
6
    return nullptr;
173
38
174
38
  Elf_Mips_RegInfo Reginfo = {};
175
46
  for (InputSectionBase *Sec : Sections) {
176
46
    Sec->Live = false;
177
46
178
46
    std::string Filename = toString(Sec->File);
179
46
    ArrayRef<uint8_t> D = Sec->Data;
180
46
181
46
    while (!D.empty()) {
182
46
      if (D.size() < sizeof(Elf_Mips_Options)) {
183
0
        error(Filename + ": invalid size of .MIPS.options section");
184
0
        break;
185
0
      }
186
46
187
46
      auto *Opt = reinterpret_cast<const Elf_Mips_Options *>(D.data());
188
46
      if (Opt->kind == ODK_REGINFO) {
189
46
        Reginfo.ri_gprmask |= Opt->getRegInfo().ri_gprmask;
190
46
        Sec->getFile<ELFT>()->MipsGp0 = Opt->getRegInfo().ri_gp_value;
191
46
        break;
192
46
      }
193
0
194
0
      if (!Opt->size)
195
0
        fatal(Filename + ": zero option descriptor size");
196
0
      D = D.slice(Opt->size);
197
0
    }
198
46
  };
199
38
200
38
  return make<MipsOptionsSection<ELFT>>(Reginfo);
201
38
}
202
203
// MIPS .reginfo section.
204
template <class ELFT>
205
MipsReginfoSection<ELFT>::MipsReginfoSection(Elf_Mips_RegInfo Reginfo)
206
    : SyntheticSection(SHF_ALLOC, SHT_MIPS_REGINFO, 4, ".reginfo"),
207
129
      Reginfo(Reginfo) {
208
129
  this->Entsize = sizeof(Elf_Mips_RegInfo);
209
129
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::MipsReginfoSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)1, false> >)
Line
Count
Source
207
16
      Reginfo(Reginfo) {
208
16
  this->Entsize = sizeof(Elf_Mips_RegInfo);
209
16
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::MipsReginfoSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)0, false> >)
Line
Count
Source
207
113
      Reginfo(Reginfo) {
208
113
  this->Entsize = sizeof(Elf_Mips_RegInfo);
209
113
}
Unexecuted instantiation: lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::MipsReginfoSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)1, true> >)
Unexecuted instantiation: lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::MipsReginfoSection(llvm::object::Elf_Mips_RegInfo<llvm::object::ELFType<(llvm::support::endianness)0, true> >)
210
211
128
template <class ELFT> void MipsReginfoSection<ELFT>::writeTo(uint8_t *Buf) {
212
128
  if (!Config->Relocatable)
213
119
    Reginfo.ri_gp_value = InX::MipsGot->getGp();
214
128
  memcpy(Buf, &Reginfo, sizeof(Reginfo));
215
128
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::writeTo(unsigned char*)
Line
Count
Source
211
16
template <class ELFT> void MipsReginfoSection<ELFT>::writeTo(uint8_t *Buf) {
212
16
  if (!Config->Relocatable)
213
16
    Reginfo.ri_gp_value = InX::MipsGot->getGp();
214
16
  memcpy(Buf, &Reginfo, sizeof(Reginfo));
215
16
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::writeTo(unsigned char*)
Line
Count
Source
211
112
template <class ELFT> void MipsReginfoSection<ELFT>::writeTo(uint8_t *Buf) {
212
112
  if (!Config->Relocatable)
213
103
    Reginfo.ri_gp_value = InX::MipsGot->getGp();
214
112
  memcpy(Buf, &Reginfo, sizeof(Reginfo));
215
112
}
Unexecuted instantiation: lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::writeTo(unsigned char*)
Unexecuted instantiation: lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::writeTo(unsigned char*)
216
217
template <class ELFT>
218
179
MipsReginfoSection<ELFT> *MipsReginfoSection<ELFT>::create() {
219
179
  // Section should be alive for O32 and N32 ABIs only.
220
179
  if (ELFT::Is64Bits)
221
46
    return nullptr;
222
133
223
133
  std::vector<InputSectionBase *> Sections;
224
133
  for (InputSectionBase *Sec : InputSections)
225
1.44k
    if (Sec->Type == SHT_MIPS_REGINFO)
226
170
      Sections.push_back(Sec);
227
133
228
133
  if (Sections.empty())
229
4
    return nullptr;
230
129
231
129
  Elf_Mips_RegInfo Reginfo = {};
232
170
  for (InputSectionBase *Sec : Sections) {
233
170
    Sec->Live = false;
234
170
235
170
    if (Sec->Data.size() != sizeof(Elf_Mips_RegInfo)) {
236
0
      error(toString(Sec->File) + ": invalid size of .reginfo section");
237
0
      return nullptr;
238
0
    }
239
170
240
170
    auto *R = reinterpret_cast<const Elf_Mips_RegInfo *>(Sec->Data.data());
241
170
    Reginfo.ri_gprmask |= R->ri_gprmask;
242
170
    Sec->getFile<ELFT>()->MipsGp0 = R->ri_gp_value;
243
170
  };
244
129
245
129
  return make<MipsReginfoSection<ELFT>>(Reginfo);
246
129
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::create()
Line
Count
Source
218
17
MipsReginfoSection<ELFT> *MipsReginfoSection<ELFT>::create() {
219
17
  // Section should be alive for O32 and N32 ABIs only.
220
17
  if (ELFT::Is64Bits)
221
0
    return nullptr;
222
17
223
17
  std::vector<InputSectionBase *> Sections;
224
17
  for (InputSectionBase *Sec : InputSections)
225
170
    if (Sec->Type == SHT_MIPS_REGINFO)
226
20
      Sections.push_back(Sec);
227
17
228
17
  if (Sections.empty())
229
1
    return nullptr;
230
16
231
16
  Elf_Mips_RegInfo Reginfo = {};
232
20
  for (InputSectionBase *Sec : Sections) {
233
20
    Sec->Live = false;
234
20
235
20
    if (Sec->Data.size() != sizeof(Elf_Mips_RegInfo)) {
236
0
      error(toString(Sec->File) + ": invalid size of .reginfo section");
237
0
      return nullptr;
238
0
    }
239
20
240
20
    auto *R = reinterpret_cast<const Elf_Mips_RegInfo *>(Sec->Data.data());
241
20
    Reginfo.ri_gprmask |= R->ri_gprmask;
242
20
    Sec->getFile<ELFT>()->MipsGp0 = R->ri_gp_value;
243
20
  };
244
16
245
16
  return make<MipsReginfoSection<ELFT>>(Reginfo);
246
16
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::create()
Line
Count
Source
218
116
MipsReginfoSection<ELFT> *MipsReginfoSection<ELFT>::create() {
219
116
  // Section should be alive for O32 and N32 ABIs only.
220
116
  if (ELFT::Is64Bits)
221
0
    return nullptr;
222
116
223
116
  std::vector<InputSectionBase *> Sections;
224
116
  for (InputSectionBase *Sec : InputSections)
225
1.27k
    if (Sec->Type == SHT_MIPS_REGINFO)
226
150
      Sections.push_back(Sec);
227
116
228
116
  if (Sections.empty())
229
3
    return nullptr;
230
113
231
113
  Elf_Mips_RegInfo Reginfo = {};
232
150
  for (InputSectionBase *Sec : Sections) {
233
150
    Sec->Live = false;
234
150
235
150
    if (Sec->Data.size() != sizeof(Elf_Mips_RegInfo)) {
236
0
      error(toString(Sec->File) + ": invalid size of .reginfo section");
237
0
      return nullptr;
238
0
    }
239
150
240
150
    auto *R = reinterpret_cast<const Elf_Mips_RegInfo *>(Sec->Data.data());
241
150
    Reginfo.ri_gprmask |= R->ri_gprmask;
242
150
    Sec->getFile<ELFT>()->MipsGp0 = R->ri_gp_value;
243
150
  };
244
113
245
113
  return make<MipsReginfoSection<ELFT>>(Reginfo);
246
113
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::create()
Line
Count
Source
218
2
MipsReginfoSection<ELFT> *MipsReginfoSection<ELFT>::create() {
219
2
  // Section should be alive for O32 and N32 ABIs only.
220
2
  if (ELFT::Is64Bits)
221
2
    return nullptr;
222
0
223
0
  std::vector<InputSectionBase *> Sections;
224
0
  for (InputSectionBase *Sec : InputSections)
225
0
    if (Sec->Type == SHT_MIPS_REGINFO)
226
0
      Sections.push_back(Sec);
227
0
228
0
  if (Sections.empty())
229
0
    return nullptr;
230
0
231
0
  Elf_Mips_RegInfo Reginfo = {};
232
0
  for (InputSectionBase *Sec : Sections) {
233
0
    Sec->Live = false;
234
0
235
0
    if (Sec->Data.size() != sizeof(Elf_Mips_RegInfo)) {
236
0
      error(toString(Sec->File) + ": invalid size of .reginfo section");
237
0
      return nullptr;
238
0
    }
239
0
240
0
    auto *R = reinterpret_cast<const Elf_Mips_RegInfo *>(Sec->Data.data());
241
0
    Reginfo.ri_gprmask |= R->ri_gprmask;
242
0
    Sec->getFile<ELFT>()->MipsGp0 = R->ri_gp_value;
243
0
  };
244
0
245
0
  return make<MipsReginfoSection<ELFT>>(Reginfo);
246
0
}
lld::elf::MipsReginfoSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::create()
Line
Count
Source
218
44
MipsReginfoSection<ELFT> *MipsReginfoSection<ELFT>::create() {
219
44
  // Section should be alive for O32 and N32 ABIs only.
220
44
  if (ELFT::Is64Bits)
221
44
    return nullptr;
222
0
223
0
  std::vector<InputSectionBase *> Sections;
224
0
  for (InputSectionBase *Sec : InputSections)
225
0
    if (Sec->Type == SHT_MIPS_REGINFO)
226
0
      Sections.push_back(Sec);
227
0
228
0
  if (Sections.empty())
229
0
    return nullptr;
230
0
231
0
  Elf_Mips_RegInfo Reginfo = {};
232
0
  for (InputSectionBase *Sec : Sections) {
233
0
    Sec->Live = false;
234
0
235
0
    if (Sec->Data.size() != sizeof(Elf_Mips_RegInfo)) {
236
0
      error(toString(Sec->File) + ": invalid size of .reginfo section");
237
0
      return nullptr;
238
0
    }
239
0
240
0
    auto *R = reinterpret_cast<const Elf_Mips_RegInfo *>(Sec->Data.data());
241
0
    Reginfo.ri_gprmask |= R->ri_gprmask;
242
0
    Sec->getFile<ELFT>()->MipsGp0 = R->ri_gp_value;
243
0
  };
244
0
245
0
  return make<MipsReginfoSection<ELFT>>(Reginfo);
246
0
}
247
248
10
InputSection *elf::createInterpSection() {
249
10
  // StringSaver guarantees that the returned string ends with '\0'.
250
10
  StringRef S = Saver.save(Config->DynamicLinker);
251
10
  ArrayRef<uint8_t> Contents = {(const uint8_t *)S.data(), S.size() + 1};
252
10
253
10
  auto *Sec = make<InputSection>(nullptr, SHF_ALLOC, SHT_PROGBITS, 1, Contents,
254
10
                                 ".interp");
255
10
  Sec->Live = true;
256
10
  return Sec;
257
10
}
258
259
Defined *elf::addSyntheticLocal(StringRef Name, uint8_t Type, uint64_t Value,
260
459
                                uint64_t Size, InputSectionBase &Section) {
261
459
  auto *S = make<Defined>(Section.File, Name, STB_LOCAL, STV_DEFAULT, Type,
262
459
                          Value, Size, &Section);
263
459
  if (InX::SymTab)
264
459
    InX::SymTab->addSymbol(S);
265
459
  return S;
266
459
}
267
268
16
static size_t getHashSize() {
269
16
  switch (Config->BuildId) {
270
16
  case BuildIdKind::Fast:
271
6
    return 8;
272
16
  case BuildIdKind::Md5:
273
3
  case BuildIdKind::Uuid:
274
3
    return 16;
275
4
  case BuildIdKind::Sha1:
276
4
    return 20;
277
3
  case BuildIdKind::Hexstring:
278
3
    return Config->BuildIdVector.size();
279
3
  default:
280
0
    llvm_unreachable("unknown BuildIdKind");
281
16
  }
282
16
}
283
284
BuildIdSection::BuildIdSection()
285
    : SyntheticSection(SHF_ALLOC, SHT_NOTE, 4, ".note.gnu.build-id"),
286
16
      HashSize(getHashSize()) {}
287
288
16
void BuildIdSection::writeTo(uint8_t *Buf) {
289
16
  write32(Buf, 4);                      // Name size
290
16
  write32(Buf + 4, HashSize);           // Content size
291
16
  write32(Buf + 8, NT_GNU_BUILD_ID);    // Type
292
16
  memcpy(Buf + 12, "GNU", 4);           // Name string
293
16
  HashBuf = Buf + 16;
294
16
}
295
296
// Split one uint8 array into small pieces of uint8 arrays.
297
static std::vector<ArrayRef<uint8_t>> split(ArrayRef<uint8_t> Arr,
298
12
                                            size_t ChunkSize) {
299
12
  std::vector<ArrayRef<uint8_t>> Ret;
300
12
  while (Arr.size() > ChunkSize) {
301
0
    Ret.push_back(Arr.take_front(ChunkSize));
302
0
    Arr = Arr.drop_front(ChunkSize);
303
0
  }
304
12
  if (!Arr.empty())
305
12
    Ret.push_back(Arr);
306
12
  return Ret;
307
12
}
308
309
// Computes a hash value of Data using a given hash function.
310
// In order to utilize multiple cores, we first split data into 1MB
311
// chunks, compute a hash for each chunk, and then compute a hash value
312
// of the hash values.
313
void BuildIdSection::computeHash(
314
    llvm::ArrayRef<uint8_t> Data,
315
12
    std::function<void(uint8_t *Dest, ArrayRef<uint8_t> Arr)> HashFn) {
316
12
  std::vector<ArrayRef<uint8_t>> Chunks = split(Data, 1024 * 1024);
317
12
  std::vector<uint8_t> Hashes(Chunks.size() * HashSize);
318
12
319
12
  // Compute hash values.
320
12
  parallelForEachN(0, Chunks.size(), [&](size_t I) {
321
12
    HashFn(Hashes.data() + I * HashSize, Chunks[I]);
322
12
  });
323
12
324
12
  // Write to the final output buffer.
325
12
  HashFn(HashBuf, Hashes);
326
12
}
327
328
BssSection::BssSection(StringRef Name, uint64_t Size, uint32_t Alignment)
329
4.61k
    : SyntheticSection(SHF_ALLOC | SHF_WRITE, SHT_NOBITS, Alignment, Name) {
330
4.61k
  this->Bss = true;
331
4.61k
  this->Size = Size;
332
4.61k
}
333
334
16
void BuildIdSection::writeBuildId(ArrayRef<uint8_t> Buf) {
335
16
  switch (Config->BuildId) {
336
16
  case BuildIdKind::Fast:
337
12
    computeHash(Buf, [](uint8_t *Dest, ArrayRef<uint8_t> Arr) {
338
12
      write64le(Dest, xxHash64(Arr));
339
12
    });
340
6
    break;
341
16
  case BuildIdKind::Md5:
342
4
    computeHash(Buf, [](uint8_t *Dest, ArrayRef<uint8_t> Arr) {
343
4
      memcpy(Dest, MD5::hash(Arr).data(), 16);
344
4
    });
345
2
    break;
346
16
  case BuildIdKind::Sha1:
347
8
    computeHash(Buf, [](uint8_t *Dest, ArrayRef<uint8_t> Arr) {
348
8
      memcpy(Dest, SHA1::hash(Arr).data(), 20);
349
8
    });
350
4
    break;
351
16
  case BuildIdKind::Uuid:
352
1
    if (auto EC = getRandomBytes(HashBuf, HashSize))
353
0
      error("entropy source failure: " + EC.message());
354
1
    break;
355
16
  case BuildIdKind::Hexstring:
356
3
    memcpy(HashBuf, Config->BuildIdVector.data(), Config->BuildIdVector.size());
357
3
    break;
358
16
  default:
359
0
    llvm_unreachable("unknown BuildIdKind");
360
16
  }
361
16
}
362
363
EhFrameSection::EhFrameSection()
364
2.16k
    : SyntheticSection(SHF_ALLOC, SHT_PROGBITS, 1, ".eh_frame") {}
365
366
// Search for an existing CIE record or create a new one.
367
// CIE records from input object files are uniquified by their contents
368
// and where their relocations point to.
369
template <class ELFT, class RelTy>
370
104
CieRecord *EhFrameSection::addCie(EhSectionPiece &Cie, ArrayRef<RelTy> Rels) {
371
104
  Symbol *Personality = nullptr;
372
104
  unsigned FirstRelI = Cie.FirstRelocation;
373
104
  if (FirstRelI != (unsigned)-1)
374
11
    Personality =
375
11
        &Cie.Sec->template getFile<ELFT>()->getRelocTargetSym(Rels[FirstRelI]);
376
104
377
104
  // Search for an existing CIE by CIE contents/relocation target pair.
378
104
  CieRecord *&Rec = CieMap[{Cie.data(), Personality}];
379
104
380
104
  // If not found, create a new one.
381
104
  if (!Rec) {
382
90
    Rec = make<CieRecord>();
383
90
    Rec->Cie = &Cie;
384
90
    CieRecords.push_back(Rec);
385
90
  }
386
104
  return Rec;
387
104
}
Unexecuted instantiation: lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)1, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> >)
lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)1, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> >)
Line
Count
Source
370
4
CieRecord *EhFrameSection::addCie(EhSectionPiece &Cie, ArrayRef<RelTy> Rels) {
371
4
  Symbol *Personality = nullptr;
372
4
  unsigned FirstRelI = Cie.FirstRelocation;
373
4
  if (FirstRelI != (unsigned)-1)
374
2
    Personality =
375
2
        &Cie.Sec->template getFile<ELFT>()->getRelocTargetSym(Rels[FirstRelI]);
376
4
377
4
  // Search for an existing CIE by CIE contents/relocation target pair.
378
4
  CieRecord *&Rec = CieMap[{Cie.data(), Personality}];
379
4
380
4
  // If not found, create a new one.
381
4
  if (!Rec) {
382
3
    Rec = make<CieRecord>();
383
3
    Rec->Cie = &Cie;
384
3
    CieRecords.push_back(Rec);
385
3
  }
386
4
  return Rec;
387
4
}
Unexecuted instantiation: lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)0, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> >)
lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)0, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> >)
Line
Count
Source
370
1
CieRecord *EhFrameSection::addCie(EhSectionPiece &Cie, ArrayRef<RelTy> Rels) {
371
1
  Symbol *Personality = nullptr;
372
1
  unsigned FirstRelI = Cie.FirstRelocation;
373
1
  if (FirstRelI != (unsigned)-1)
374
0
    Personality =
375
0
        &Cie.Sec->template getFile<ELFT>()->getRelocTargetSym(Rels[FirstRelI]);
376
1
377
1
  // Search for an existing CIE by CIE contents/relocation target pair.
378
1
  CieRecord *&Rec = CieMap[{Cie.data(), Personality}];
379
1
380
1
  // If not found, create a new one.
381
1
  if (!Rec) {
382
1
    Rec = make<CieRecord>();
383
1
    Rec->Cie = &Cie;
384
1
    CieRecords.push_back(Rec);
385
1
  }
386
1
  return Rec;
387
1
}
lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)1, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> >)
Line
Count
Source
370
88
CieRecord *EhFrameSection::addCie(EhSectionPiece &Cie, ArrayRef<RelTy> Rels) {
371
88
  Symbol *Personality = nullptr;
372
88
  unsigned FirstRelI = Cie.FirstRelocation;
373
88
  if (FirstRelI != (unsigned)-1)
374
8
    Personality =
375
8
        &Cie.Sec->template getFile<ELFT>()->getRelocTargetSym(Rels[FirstRelI]);
376
88
377
88
  // Search for an existing CIE by CIE contents/relocation target pair.
378
88
  CieRecord *&Rec = CieMap[{Cie.data(), Personality}];
379
88
380
88
  // If not found, create a new one.
381
88
  if (!Rec) {
382
75
    Rec = make<CieRecord>();
383
75
    Rec->Cie = &Cie;
384
75
    CieRecords.push_back(Rec);
385
75
  }
386
88
  return Rec;
387
88
}
lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)1, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> >)
Line
Count
Source
370
7
CieRecord *EhFrameSection::addCie(EhSectionPiece &Cie, ArrayRef<RelTy> Rels) {
371
7
  Symbol *Personality = nullptr;
372
7
  unsigned FirstRelI = Cie.FirstRelocation;
373
7
  if (FirstRelI != (unsigned)-1)
374
0
    Personality =
375
0
        &Cie.Sec->template getFile<ELFT>()->getRelocTargetSym(Rels[FirstRelI]);
376
7
377
7
  // Search for an existing CIE by CIE contents/relocation target pair.
378
7
  CieRecord *&Rec = CieMap[{Cie.data(), Personality}];
379
7
380
7
  // If not found, create a new one.
381
7
  if (!Rec) {
382
7
    Rec = make<CieRecord>();
383
7
    Rec->Cie = &Cie;
384
7
    CieRecords.push_back(Rec);
385
7
  }
386
7
  return Rec;
387
7
}
lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)0, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> >)
Line
Count
Source
370
3
CieRecord *EhFrameSection::addCie(EhSectionPiece &Cie, ArrayRef<RelTy> Rels) {
371
3
  Symbol *Personality = nullptr;
372
3
  unsigned FirstRelI = Cie.FirstRelocation;
373
3
  if (FirstRelI != (unsigned)-1)
374
1
    Personality =
375
1
        &Cie.Sec->template getFile<ELFT>()->getRelocTargetSym(Rels[FirstRelI]);
376
3
377
3
  // Search for an existing CIE by CIE contents/relocation target pair.
378
3
  CieRecord *&Rec = CieMap[{Cie.data(), Personality}];
379
3
380
3
  // If not found, create a new one.
381
3
  if (!Rec) {
382
3
    Rec = make<CieRecord>();
383
3
    Rec->Cie = &Cie;
384
3
    CieRecords.push_back(Rec);
385
3
  }
386
3
  return Rec;
387
3
}
lld::elf::CieRecord* lld::elf::EhFrameSection::addCie<llvm::object::ELFType<(llvm::support::endianness)0, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> >)
Line
Count
Source
370
1
CieRecord *EhFrameSection::addCie(EhSectionPiece &Cie, ArrayRef<RelTy> Rels) {
371
1
  Symbol *Personality = nullptr;
372
1
  unsigned FirstRelI = Cie.FirstRelocation;
373
1
  if (FirstRelI != (unsigned)-1)
374
0
    Personality =
375
0
        &Cie.Sec->template getFile<ELFT>()->getRelocTargetSym(Rels[FirstRelI]);
376
1
377
1
  // Search for an existing CIE by CIE contents/relocation target pair.
378
1
  CieRecord *&Rec = CieMap[{Cie.data(), Personality}];
379
1
380
1
  // If not found, create a new one.
381
1
  if (!Rec) {
382
1
    Rec = make<CieRecord>();
383
1
    Rec->Cie = &Cie;
384
1
    CieRecords.push_back(Rec);
385
1
  }
386
1
  return Rec;
387
1
}
388
389
// There is one FDE per function. Returns true if a given FDE
390
// points to a live function.
391
template <class ELFT, class RelTy>
392
128
bool EhFrameSection::isFdeLive(EhSectionPiece &Fde, ArrayRef<RelTy> Rels) {
393
128
  auto *Sec = cast<EhInputSection>(Fde.Sec);
394
128
  unsigned FirstRelI = Fde.FirstRelocation;
395
128
396
128
  // An FDE should point to some function because FDEs are to describe
397
128
  // functions. That's however not always the case due to an issue of
398
128
  // ld.gold with -r. ld.gold may discard only functions and leave their
399
128
  // corresponding FDEs, which results in creating bad .eh_frame sections.
400
128
  // To deal with that, we ignore such FDEs.
401
128
  if (FirstRelI == (unsigned)-1)
402
1
    return false;
403
127
404
127
  const RelTy &Rel = Rels[FirstRelI];
405
127
  Symbol &B = Sec->template getFile<ELFT>()->getRelocTargetSym(Rel);
406
127
407
127
  // FDEs for garbage-collected or merged-by-ICF sections are dead.
408
127
  if (auto *D = dyn_cast<Defined>(&B))
409
126
    if (SectionBase *Sec = D->Section)
410
126
      return Sec->Live;
411
1
  return false;
412
1
}
Unexecuted instantiation: bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)1, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> >)
bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)1, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> >)
Line
Count
Source
392
4
bool EhFrameSection::isFdeLive(EhSectionPiece &Fde, ArrayRef<RelTy> Rels) {
393
4
  auto *Sec = cast<EhInputSection>(Fde.Sec);
394
4
  unsigned FirstRelI = Fde.FirstRelocation;
395
4
396
4
  // An FDE should point to some function because FDEs are to describe
397
4
  // functions. That's however not always the case due to an issue of
398
4
  // ld.gold with -r. ld.gold may discard only functions and leave their
399
4
  // corresponding FDEs, which results in creating bad .eh_frame sections.
400
4
  // To deal with that, we ignore such FDEs.
401
4
  if (FirstRelI == (unsigned)-1)
402
0
    return false;
403
4
404
4
  const RelTy &Rel = Rels[FirstRelI];
405
4
  Symbol &B = Sec->template getFile<ELFT>()->getRelocTargetSym(Rel);
406
4
407
4
  // FDEs for garbage-collected or merged-by-ICF sections are dead.
408
4
  if (auto *D = dyn_cast<Defined>(&B))
409
4
    if (SectionBase *Sec = D->Section)
410
4
      return Sec->Live;
411
0
  return false;
412
0
}
Unexecuted instantiation: bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)0, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> >)
bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)0, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> >)
Line
Count
Source
392
1
bool EhFrameSection::isFdeLive(EhSectionPiece &Fde, ArrayRef<RelTy> Rels) {
393
1
  auto *Sec = cast<EhInputSection>(Fde.Sec);
394
1
  unsigned FirstRelI = Fde.FirstRelocation;
395
1
396
1
  // An FDE should point to some function because FDEs are to describe
397
1
  // functions. That's however not always the case due to an issue of
398
1
  // ld.gold with -r. ld.gold may discard only functions and leave their
399
1
  // corresponding FDEs, which results in creating bad .eh_frame sections.
400
1
  // To deal with that, we ignore such FDEs.
401
1
  if (FirstRelI == (unsigned)-1)
402
0
    return false;
403
1
404
1
  const RelTy &Rel = Rels[FirstRelI];
405
1
  Symbol &B = Sec->template getFile<ELFT>()->getRelocTargetSym(Rel);
406
1
407
1
  // FDEs for garbage-collected or merged-by-ICF sections are dead.
408
1
  if (auto *D = dyn_cast<Defined>(&B))
409
1
    if (SectionBase *Sec = D->Section)
410
1
      return Sec->Live;
411
0
  return false;
412
0
}
bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)1, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> >)
Line
Count
Source
392
119
bool EhFrameSection::isFdeLive(EhSectionPiece &Fde, ArrayRef<RelTy> Rels) {
393
119
  auto *Sec = cast<EhInputSection>(Fde.Sec);
394
119
  unsigned FirstRelI = Fde.FirstRelocation;
395
119
396
119
  // An FDE should point to some function because FDEs are to describe
397
119
  // functions. That's however not always the case due to an issue of
398
119
  // ld.gold with -r. ld.gold may discard only functions and leave their
399
119
  // corresponding FDEs, which results in creating bad .eh_frame sections.
400
119
  // To deal with that, we ignore such FDEs.
401
119
  if (FirstRelI == (unsigned)-1)
402
0
    return false;
403
119
404
119
  const RelTy &Rel = Rels[FirstRelI];
405
119
  Symbol &B = Sec->template getFile<ELFT>()->getRelocTargetSym(Rel);
406
119
407
119
  // FDEs for garbage-collected or merged-by-ICF sections are dead.
408
119
  if (auto *D = dyn_cast<Defined>(&B))
409
118
    if (SectionBase *Sec = D->Section)
410
118
      return Sec->Live;
411
1
  return false;
412
1
}
bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)1, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> >)
Line
Count
Source
392
1
bool EhFrameSection::isFdeLive(EhSectionPiece &Fde, ArrayRef<RelTy> Rels) {
393
1
  auto *Sec = cast<EhInputSection>(Fde.Sec);
394
1
  unsigned FirstRelI = Fde.FirstRelocation;
395
1
396
1
  // An FDE should point to some function because FDEs are to describe
397
1
  // functions. That's however not always the case due to an issue of
398
1
  // ld.gold with -r. ld.gold may discard only functions and leave their
399
1
  // corresponding FDEs, which results in creating bad .eh_frame sections.
400
1
  // To deal with that, we ignore such FDEs.
401
1
  if (FirstRelI == (unsigned)-1)
402
1
    return false;
403
0
404
0
  const RelTy &Rel = Rels[FirstRelI];
405
0
  Symbol &B = Sec->template getFile<ELFT>()->getRelocTargetSym(Rel);
406
0
407
0
  // FDEs for garbage-collected or merged-by-ICF sections are dead.
408
0
  if (auto *D = dyn_cast<Defined>(&B))
409
0
    if (SectionBase *Sec = D->Section)
410
0
      return Sec->Live;
411
0
  return false;
412
0
}
bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)0, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> >)
Line
Count
Source
392
3
bool EhFrameSection::isFdeLive(EhSectionPiece &Fde, ArrayRef<RelTy> Rels) {
393
3
  auto *Sec = cast<EhInputSection>(Fde.Sec);
394
3
  unsigned FirstRelI = Fde.FirstRelocation;
395
3
396
3
  // An FDE should point to some function because FDEs are to describe
397
3
  // functions. That's however not always the case due to an issue of
398
3
  // ld.gold with -r. ld.gold may discard only functions and leave their
399
3
  // corresponding FDEs, which results in creating bad .eh_frame sections.
400
3
  // To deal with that, we ignore such FDEs.
401
3
  if (FirstRelI == (unsigned)-1)
402
0
    return false;
403
3
404
3
  const RelTy &Rel = Rels[FirstRelI];
405
3
  Symbol &B = Sec->template getFile<ELFT>()->getRelocTargetSym(Rel);
406
3
407
3
  // FDEs for garbage-collected or merged-by-ICF sections are dead.
408
3
  if (auto *D = dyn_cast<Defined>(&B))
409
3
    if (SectionBase *Sec = D->Section)
410
3
      return Sec->Live;
411
0
  return false;
412
0
}
Unexecuted instantiation: bool lld::elf::EhFrameSection::isFdeLive<llvm::object::ELFType<(llvm::support::endianness)0, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> >(lld::elf::EhSectionPiece&, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> >)
413
414
// .eh_frame is a sequence of CIE or FDE records. In general, there
415
// is one CIE record per input object file which is followed by
416
// a list of FDEs. This function searches an existing CIE or create a new
417
// one and associates FDEs to the CIE.
418
template <class ELFT, class RelTy>
419
108
void EhFrameSection::addSectionAux(EhInputSection *Sec, ArrayRef<RelTy> Rels) {
420
108
  OffsetToCie.clear();
421
238
  for (EhSectionPiece &Piece : Sec->Pieces) {
422
238
    // The empty record is the end marker.
423
238
    if (Piece.Size == 4)
424
6
      return;
425
232
426
232
    size_t Offset = Piece.InputOff;
427
232
    uint32_t ID = read32(Piece.data().data() + 4);
428
232
    if (ID == 0) {
429
104
      OffsetToCie[Offset] = addCie<ELFT>(Piece, Rels);
430
104
      continue;
431
104
    }
432
128
433
128
    uint32_t CieOffset = Offset + 4 - ID;
434
128
    CieRecord *Rec = OffsetToCie[CieOffset];
435
128
    if (!Rec)
436
0
      fatal(toString(Sec) + ": invalid CIE reference");
437
128
438
128
    if (!isFdeLive<ELFT>(Piece, Rels))
439
10
      continue;
440
118
    Rec->Fdes.push_back(&Piece);
441
118
    NumFdes++;
442
118
  }
443
108
}
Unexecuted instantiation: void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)1, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> >)
void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)1, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> >)
Line
Count
Source
419
4
void EhFrameSection::addSectionAux(EhInputSection *Sec, ArrayRef<RelTy> Rels) {
420
4
  OffsetToCie.clear();
421
8
  for (EhSectionPiece &Piece : Sec->Pieces) {
422
8
    // The empty record is the end marker.
423
8
    if (Piece.Size == 4)
424
0
      return;
425
8
426
8
    size_t Offset = Piece.InputOff;
427
8
    uint32_t ID = read32(Piece.data().data() + 4);
428
8
    if (ID == 0) {
429
4
      OffsetToCie[Offset] = addCie<ELFT>(Piece, Rels);
430
4
      continue;
431
4
    }
432
4
433
4
    uint32_t CieOffset = Offset + 4 - ID;
434
4
    CieRecord *Rec = OffsetToCie[CieOffset];
435
4
    if (!Rec)
436
0
      fatal(toString(Sec) + ": invalid CIE reference");
437
4
438
4
    if (!isFdeLive<ELFT>(Piece, Rels))
439
0
      continue;
440
4
    Rec->Fdes.push_back(&Piece);
441
4
    NumFdes++;
442
4
  }
443
4
}
Unexecuted instantiation: void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)0, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> >)
void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)0, false>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> >)
Line
Count
Source
419
1
void EhFrameSection::addSectionAux(EhInputSection *Sec, ArrayRef<RelTy> Rels) {
420
1
  OffsetToCie.clear();
421
2
  for (EhSectionPiece &Piece : Sec->Pieces) {
422
2
    // The empty record is the end marker.
423
2
    if (Piece.Size == 4)
424
0
      return;
425
2
426
2
    size_t Offset = Piece.InputOff;
427
2
    uint32_t ID = read32(Piece.data().data() + 4);
428
2
    if (ID == 0) {
429
1
      OffsetToCie[Offset] = addCie<ELFT>(Piece, Rels);
430
1
      continue;
431
1
    }
432
1
433
1
    uint32_t CieOffset = Offset + 4 - ID;
434
1
    CieRecord *Rec = OffsetToCie[CieOffset];
435
1
    if (!Rec)
436
0
      fatal(toString(Sec) + ": invalid CIE reference");
437
1
438
1
    if (!isFdeLive<ELFT>(Piece, Rels))
439
0
      continue;
440
1
    Rec->Fdes.push_back(&Piece);
441
1
    NumFdes++;
442
1
  }
443
1
}
void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)1, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> >)
Line
Count
Source
419
86
void EhFrameSection::addSectionAux(EhInputSection *Sec, ArrayRef<RelTy> Rels) {
420
86
  OffsetToCie.clear();
421
207
  for (EhSectionPiece &Piece : Sec->Pieces) {
422
207
    // The empty record is the end marker.
423
207
    if (Piece.Size == 4)
424
0
      return;
425
207
426
207
    size_t Offset = Piece.InputOff;
427
207
    uint32_t ID = read32(Piece.data().data() + 4);
428
207
    if (ID == 0) {
429
88
      OffsetToCie[Offset] = addCie<ELFT>(Piece, Rels);
430
88
      continue;
431
88
    }
432
119
433
119
    uint32_t CieOffset = Offset + 4 - ID;
434
119
    CieRecord *Rec = OffsetToCie[CieOffset];
435
119
    if (!Rec)
436
0
      fatal(toString(Sec) + ": invalid CIE reference");
437
119
438
119
    if (!isFdeLive<ELFT>(Piece, Rels))
439
9
      continue;
440
110
    Rec->Fdes.push_back(&Piece);
441
110
    NumFdes++;
442
110
  }
443
86
}
void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)1, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> >)
Line
Count
Source
419
13
void EhFrameSection::addSectionAux(EhInputSection *Sec, ArrayRef<RelTy> Rels) {
420
13
  OffsetToCie.clear();
421
14
  for (EhSectionPiece &Piece : Sec->Pieces) {
422
14
    // The empty record is the end marker.
423
14
    if (Piece.Size == 4)
424
6
      return;
425
8
426
8
    size_t Offset = Piece.InputOff;
427
8
    uint32_t ID = read32(Piece.data().data() + 4);
428
8
    if (ID == 0) {
429
7
      OffsetToCie[Offset] = addCie<ELFT>(Piece, Rels);
430
7
      continue;
431
7
    }
432
1
433
1
    uint32_t CieOffset = Offset + 4 - ID;
434
1
    CieRecord *Rec = OffsetToCie[CieOffset];
435
1
    if (!Rec)
436
0
      fatal(toString(Sec) + ": invalid CIE reference");
437
1
438
1
    if (!isFdeLive<ELFT>(Piece, Rels))
439
1
      continue;
440
0
    Rec->Fdes.push_back(&Piece);
441
0
    NumFdes++;
442
0
  }
443
13
}
void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)0, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> >)
Line
Count
Source
419
3
void EhFrameSection::addSectionAux(EhInputSection *Sec, ArrayRef<RelTy> Rels) {
420
3
  OffsetToCie.clear();
421
6
  for (EhSectionPiece &Piece : Sec->Pieces) {
422
6
    // The empty record is the end marker.
423
6
    if (Piece.Size == 4)
424
0
      return;
425
6
426
6
    size_t Offset = Piece.InputOff;
427
6
    uint32_t ID = read32(Piece.data().data() + 4);
428
6
    if (ID == 0) {
429
3
      OffsetToCie[Offset] = addCie<ELFT>(Piece, Rels);
430
3
      continue;
431
3
    }
432
3
433
3
    uint32_t CieOffset = Offset + 4 - ID;
434
3
    CieRecord *Rec = OffsetToCie[CieOffset];
435
3
    if (!Rec)
436
0
      fatal(toString(Sec) + ": invalid CIE reference");
437
3
438
3
    if (!isFdeLive<ELFT>(Piece, Rels))
439
0
      continue;
440
3
    Rec->Fdes.push_back(&Piece);
441
3
    NumFdes++;
442
3
  }
443
3
}
void lld::elf::EhFrameSection::addSectionAux<llvm::object::ELFType<(llvm::support::endianness)0, true>, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> >(lld::elf::EhInputSection*, llvm::ArrayRef<llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> >)
Line
Count
Source
419
1
void EhFrameSection::addSectionAux(EhInputSection *Sec, ArrayRef<RelTy> Rels) {
420
1
  OffsetToCie.clear();
421
1
  for (EhSectionPiece &Piece : Sec->Pieces) {
422
1
    // The empty record is the end marker.
423
1
    if (Piece.Size == 4)
424
0
      return;
425
1
426
1
    size_t Offset = Piece.InputOff;
427
1
    uint32_t ID = read32(Piece.data().data() + 4);
428
1
    if (ID == 0) {
429
1
      OffsetToCie[Offset] = addCie<ELFT>(Piece, Rels);
430
1
      continue;
431
1
    }
432
0
433
0
    uint32_t CieOffset = Offset + 4 - ID;
434
0
    CieRecord *Rec = OffsetToCie[CieOffset];
435
0
    if (!Rec)
436
0
      fatal(toString(Sec) + ": invalid CIE reference");
437
0
438
0
    if (!isFdeLive<ELFT>(Piece, Rels))
439
0
      continue;
440
0
    Rec->Fdes.push_back(&Piece);
441
0
    NumFdes++;
442
0
  }
443
1
}
444
445
111
template <class ELFT> void EhFrameSection::addSection(InputSectionBase *C) {
446
111
  auto *Sec = cast<EhInputSection>(C);
447
111
  Sec->Parent = this;
448
111
449
111
  Alignment = std::max(Alignment, Sec->Alignment);
450
111
  Sections.push_back(Sec);
451
111
452
111
  for (auto *DS : Sec->DependentSections)
453
3
    DependentSections.push_back(DS);
454
111
455
111
  if (Sec->Pieces.empty())
456
3
    return;
457
108
458
108
  if (Sec->AreRelocsRela)
459
89
    addSectionAux<ELFT>(Sec, Sec->template relas<ELFT>());
460
19
  else
461
19
    addSectionAux<ELFT>(Sec, Sec->template rels<ELFT>());
462
108
}
void lld::elf::EhFrameSection::addSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >(lld::elf::InputSectionBase*)
Line
Count
Source
445
4
template <class ELFT> void EhFrameSection::addSection(InputSectionBase *C) {
446
4
  auto *Sec = cast<EhInputSection>(C);
447
4
  Sec->Parent = this;
448
4
449
4
  Alignment = std::max(Alignment, Sec->Alignment);
450
4
  Sections.push_back(Sec);
451
4
452
4
  for (auto *DS : Sec->DependentSections)
453
0
    DependentSections.push_back(DS);
454
4
455
4
  if (Sec->Pieces.empty())
456
0
    return;
457
4
458
4
  if (Sec->AreRelocsRela)
459
0
    addSectionAux<ELFT>(Sec, Sec->template relas<ELFT>());
460
4
  else
461
4
    addSectionAux<ELFT>(Sec, Sec->template rels<ELFT>());
462
4
}
void lld::elf::EhFrameSection::addSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >(lld::elf::InputSectionBase*)
Line
Count
Source
445
1
template <class ELFT> void EhFrameSection::addSection(InputSectionBase *C) {
446
1
  auto *Sec = cast<EhInputSection>(C);
447
1
  Sec->Parent = this;
448
1
449
1
  Alignment = std::max(Alignment, Sec->Alignment);
450
1
  Sections.push_back(Sec);
451
1
452
1
  for (auto *DS : Sec->DependentSections)
453
0
    DependentSections.push_back(DS);
454
1
455
1
  if (Sec->Pieces.empty())
456
0
    return;
457
1
458
1
  if (Sec->AreRelocsRela)
459
0
    addSectionAux<ELFT>(Sec, Sec->template relas<ELFT>());
460
1
  else
461
1
    addSectionAux<ELFT>(Sec, Sec->template rels<ELFT>());
462
1
}
void lld::elf::EhFrameSection::addSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >(lld::elf::InputSectionBase*)
Line
Count
Source
445
102
template <class ELFT> void EhFrameSection::addSection(InputSectionBase *C) {
446
102
  auto *Sec = cast<EhInputSection>(C);
447
102
  Sec->Parent = this;
448
102
449
102
  Alignment = std::max(Alignment, Sec->Alignment);
450
102
  Sections.push_back(Sec);
451
102
452
102
  for (auto *DS : Sec->DependentSections)
453
3
    DependentSections.push_back(DS);
454
102
455
102
  if (Sec->Pieces.empty())
456
3
    return;
457
99
458
99
  if (Sec->AreRelocsRela)
459
86
    addSectionAux<ELFT>(Sec, Sec->template relas<ELFT>());
460
13
  else
461
13
    addSectionAux<ELFT>(Sec, Sec->template rels<ELFT>());
462
99
}
void lld::elf::EhFrameSection::addSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >(lld::elf::InputSectionBase*)
Line
Count
Source
445
4
template <class ELFT> void EhFrameSection::addSection(InputSectionBase *C) {
446
4
  auto *Sec = cast<EhInputSection>(C);
447
4
  Sec->Parent = this;
448
4
449
4
  Alignment = std::max(Alignment, Sec->Alignment);
450
4
  Sections.push_back(Sec);
451
4
452
4
  for (auto *DS : Sec->DependentSections)
453
0
    DependentSections.push_back(DS);
454
4
455
4
  if (Sec->Pieces.empty())
456
0
    return;
457
4
458
4
  if (Sec->AreRelocsRela)
459
3
    addSectionAux<ELFT>(Sec, Sec->template relas<ELFT>());
460
1
  else
461
1
    addSectionAux<ELFT>(Sec, Sec->template rels<ELFT>());
462
4
}
463
464
200
static void writeCieFde(uint8_t *Buf, ArrayRef<uint8_t> D) {
465
200
  memcpy(Buf, D.data(), D.size());
466
200
467
200
  size_t Aligned = alignTo(D.size(), Config->Wordsize);
468
200
469
200
  // Zero-clear trailing padding if it exists.
470
200
  memset(Buf + D.size(), 0, Aligned - D.size());
471
200
472
200
  // Fix the size field. -4 since size does not include the size field itself.
473
200
  write32(Buf, Aligned - 4);
474
200
}
475
476
94
void EhFrameSection::finalizeContents() {
477
94
  assert(!this->Size); // Not finalized.
478
94
  size_t Off = 0;
479
94
  for (CieRecord *Rec : CieRecords) {
480
88
    Rec->Cie->OutputOff = Off;
481
88
    Off += alignTo(Rec->Cie->Size, Config->Wordsize);
482
88
483
116
    for (EhSectionPiece *Fde : Rec->Fdes) {
484
116
      Fde->OutputOff = Off;
485
116
      Off += alignTo(Fde->Size, Config->Wordsize);
486
116
    }
487
88
  }
488
94
489
94
  // The LSB standard does not allow a .eh_frame section with zero
490
94
  // Call Frame Information records. glibc unwind-dw2-fde.c
491
94
  // classify_object_over_fdes expects there is a CIE record length 0 as a
492
94
  // terminator. Thus we add one unconditionally.
493
94
  Off += 4;
494
94
495
94
  this->Size = Off;
496
94
}
497
498
// Returns data for .eh_frame_hdr. .eh_frame_hdr is a binary search table
499
// to get an FDE from an address to which FDE is applied. This function
500
// returns a list of such pairs.
501
27
std::vector<EhFrameSection::FdeData> EhFrameSection::getFdeData() const {
502
27
  uint8_t *Buf = getParent()->Loc + OutSecOff;
503
27
  std::vector<FdeData> Ret;
504
27
505
27
  uint64_t VA = InX::EhFrameHdr->getVA();
506
27
  for (CieRecord *Rec : CieRecords) {
507
27
    uint8_t Enc = getFdeEncoding(Rec->Cie);
508
27
    for (EhSectionPiece *Fde : Rec->Fdes) {
509
23
      uint64_t Pc = getFdePc(Buf, Fde->OutputOff, Enc);
510
23
      uint64_t FdeVA = getParent()->Addr + Fde->OutputOff;
511
23
      if (!isInt<32>(Pc - VA))
512
0
        fatal(toString(Fde->Sec) + ": PC offset is too large: 0x" +
513
0
              Twine::utohexstr(Pc - VA));
514
23
      Ret.push_back({uint32_t(Pc - VA), uint32_t(FdeVA - VA)});
515
23
    }
516
27
  }
517
27
518
27
  // Sort the FDE list by their PC and uniqueify. Usually there is only
519
27
  // one FDE for a PC (i.e. function), but if ICF merges two functions
520
27
  // into one, there can be more than one FDEs pointing to the address.
521
27
  auto Less = [](const FdeData &A, const FdeData &B) {
522
4
    return A.PcRel < B.PcRel;
523
4
  };
524
27
  std::stable_sort(Ret.begin(), Ret.end(), Less);
525
27
  auto Eq = [](const FdeData &A, const FdeData &B) {
526
4
    return A.PcRel == B.PcRel;
527
4
  };
528
27
  Ret.erase(std::unique(Ret.begin(), Ret.end(), Eq), Ret.end());
529
27
530
27
  return Ret;
531
27
}
532
533
23
static uint64_t readFdeAddr(uint8_t *Buf, int Size) {
534
23
  switch (Size) {
535
23
  case DW_EH_PE_udata2:
536
1
    return read16(Buf);
537
23
  case DW_EH_PE_sdata2:
538
1
    return (int16_t)read16(Buf);
539
23
  case DW_EH_PE_udata4:
540
0
    return read32(Buf);
541
23
  case DW_EH_PE_sdata4:
542
16
    return (int32_t)read32(Buf);
543
23
  case DW_EH_PE_udata8:
544
3
  case DW_EH_PE_sdata8:
545
3
    return read64(Buf);
546
3
  case DW_EH_PE_absptr:
547
2
    return readUint(Buf);
548
0
  }
549
0
  fatal("unknown FDE size encoding");
550
0
}
551
552
// Returns the VA to which a given FDE (on a mmap'ed buffer) is applied to.
553
// We need it to create .eh_frame_hdr section.
554
uint64_t EhFrameSection::getFdePc(uint8_t *Buf, size_t FdeOff,
555
23
                                  uint8_t Enc) const {
556
23
  // The starting address to which this FDE applies is
557
23
  // stored at FDE + 8 byte.
558
23
  size_t Off = FdeOff + 8;
559
23
  uint64_t Addr = readFdeAddr(Buf + Off, Enc & 0xf);
560
23
  if ((Enc & 0x70) == DW_EH_PE_absptr)
561
6
    return Addr;
562
17
  if ((Enc & 0x70) == DW_EH_PE_pcrel)
563
17
    return Addr + getParent()->Addr + Off;
564
0
  fatal("unknown FDE size relative encoding");
565
0
}
566
567
92
void EhFrameSection::writeTo(uint8_t *Buf) {
568
92
  // Write CIE and FDE records.
569
92
  for (CieRecord *Rec : CieRecords) {
570
86
    size_t CieOffset = Rec->Cie->OutputOff;
571
86
    writeCieFde(Buf + CieOffset, Rec->Cie->data());
572
86
573
114
    for (EhSectionPiece *Fde : Rec->Fdes) {
574
114
      size_t Off = Fde->OutputOff;
575
114
      writeCieFde(Buf + Off, Fde->data());
576
114
577
114
      // FDE's second word should have the offset to an associated CIE.
578
114
      // Write it.
579
114
      write32(Buf + Off + 4, Off + 4 - CieOffset);
580
114
    }
581
86
  }
582
92
583
92
  // Apply relocations. .eh_frame section contents are not contiguous
584
92
  // in the output buffer, but relocateAlloc() still works because
585
92
  // getOffset() takes care of discontiguous section pieces.
586
92
  for (EhInputSection *S : Sections)
587
106
    S->relocateAlloc(Buf, nullptr);
588
92
}
589
590
GotSection::GotSection()
591
    : SyntheticSection(SHF_ALLOC | SHF_WRITE, SHT_PROGBITS,
592
2.05k
                       Target->GotEntrySize, ".got") {
593
2.05k
  // PPC64 saves the ElfSym::GlobalOffsetTable .TOC. as the first entry in the
594
2.05k
  // .got. If there are no references to .TOC. in the symbol table,
595
2.05k
  // ElfSym::GlobalOffsetTable will not be defined and we won't need to save
596
2.05k
  // .TOC. in the .got. When it is defined, we increase NumEntries by the number
597
2.05k
  // of entries used to emit ElfSym::GlobalOffsetTable.
598
2.05k
  if (ElfSym::GlobalOffsetTable && 
!Target->GotBaseSymInGotPlt64
)
599
33
    NumEntries += Target->GotHeaderEntriesNum;
600
2.05k
}
601
602
140
void GotSection::addEntry(Symbol &Sym) {
603
140
  Sym.GotIndex = NumEntries;
604
140
  ++NumEntries;
605
140
}
606
607
48
bool GotSection::addDynTlsEntry(Symbol &Sym) {
608
48
  if (Sym.GlobalDynIndex != -1U)
609
17
    return false;
610
31
  Sym.GlobalDynIndex = NumEntries;
611
31
  // Global Dynamic TLS entries take two GOT slots.
612
31
  NumEntries += 2;
613
31
  return true;
614
31
}
615
616
// Reserves TLS entries for a TLS module ID and a TLS block offset.
617
// In total it takes two GOT slots.
618
27
bool GotSection::addTlsIndex() {
619
27
  if (TlsIndexOff != uint32_t(-1))
620
18
    return false;
621
9
  TlsIndexOff = NumEntries * Config->Wordsize;
622
9
  NumEntries += 2;
623
9
  return true;
624
9
}
625
626
31
uint64_t GotSection::getGlobalDynAddr(const Symbol &B) const {
627
31
  return this->getVA() + B.GlobalDynIndex * Config->Wordsize;
628
31
}
629
630
41
uint64_t GotSection::getGlobalDynOffset(const Symbol &B) const {
631
41
  return B.GlobalDynIndex * Config->Wordsize;
632
41
}
633
634
135
void GotSection::finalizeContents() {
635
135
  Size = NumEntries * Config->Wordsize;
636
135
}
637
638
3.91k
bool GotSection::empty() const {
639
3.91k
  // We need to emit a GOT even if it's empty if there's a relocation that is
640
3.91k
  // relative to GOT(such as GOTOFFREL) or there's a symbol that points to a GOT
641
3.91k
  // (i.e. _GLOBAL_OFFSET_TABLE_) that the target defines relative to the .got.
642
3.91k
  return NumEntries == 0 && 
!HasGotOffRel3.66k
&&
643
3.91k
         
!(3.64k
ElfSym::GlobalOffsetTable3.64k
&&
!Target->GotBaseSymInGotPlt42
);
644
3.91k
}
645
646
134
void GotSection::writeTo(uint8_t *Buf) {
647
134
  // Buf points to the start of this section's buffer,
648
134
  // whereas InputSectionBase::relocateAlloc() expects its argument
649
134
  // to point to the start of the output section.
650
134
  Target->writeGotHeader(Buf);
651
134
  relocateAlloc(Buf - OutSecOff, Buf - OutSecOff + Size);
652
134
}
653
654
71
static uint64_t getMipsPageAddr(uint64_t Addr) {
655
71
  return (Addr + 0x8000) & ~0xffff;
656
71
}
657
658
14
static uint64_t getMipsPageCount(uint64_t Size) {
659
14
  return (Size + 0xfffe) / 0xffff + 1;
660
14
}
661
662
MipsGotSection::MipsGotSection()
663
    : SyntheticSection(SHF_ALLOC | SHF_WRITE | SHF_MIPS_GPREL, SHT_PROGBITS, 16,
664
179
                       ".got") {}
665
666
void MipsGotSection::addEntry(InputFile &File, Symbol &Sym, int64_t Addend,
667
10.1k
                              RelExpr Expr) {
668
10.1k
  FileGot &G = getGot(File);
669
10.1k
  if (Expr == R_MIPS_GOT_LOCAL_PAGE) {
670
29
    if (const OutputSection *OS = Sym.getOutputSection())
671
25
      G.PagesMap.insert({OS, {}});
672
4
    else
673
4
      G.Local16.insert({{nullptr, getMipsPageAddr(Sym.getVA(Addend))}, 0});
674
10.0k
  } else if (Sym.isTls())
675
13
    G.Tls.insert({&Sym, 0});
676
10.0k
  else if (Sym.IsPreemptible && 
Expr == R_ABS41
)
677
4
    G.Relocs.insert({&Sym, 0});
678
10.0k
  else if (Sym.IsPreemptible)
679
37
    G.Global.insert({&Sym, 0});
680
10.0k
  else if (Expr == R_MIPS_GOT_OFF32)
681
12
    G.Local32.insert({{&Sym, Addend}, 0});
682
10.0k
  else
683
10.0k
    G.Local16.insert({{&Sym, Addend}, 0});
684
10.1k
}
685
686
12
void MipsGotSection::addDynTlsEntry(InputFile &File, Symbol &Sym) {
687
12
  getGot(File).DynTlsSymbols.insert({&Sym, 0});
688
12
}
689
690
6
void MipsGotSection::addTlsIndex(InputFile &File) {
691
6
  getGot(File).DynTlsSymbols.insert({nullptr, 0});
692
6
}
693
694
114
size_t MipsGotSection::FileGot::getEntriesNum() const {
695
114
  return getPageEntriesNum() + Local16.size() + Global.size() + Relocs.size() +
696
114
         Tls.size() + DynTlsSymbols.size() * 2;
697
114
}
698
699
218
size_t MipsGotSection::FileGot::getPageEntriesNum() const {
700
218
  size_t Num = 0;
701
218
  for (const std::pair<const OutputSection *, FileGot::PageBlock> &P : PagesMap)
702
52
    Num += P.second.Count;
703
218
  return Num;
704
218
}
705
706
59
size_t MipsGotSection::FileGot::getIndexedEntriesNum() const {
707
59
  size_t Count = getPageEntriesNum() + Local16.size() + Global.size();
708
59
  // If there are relocation-only entries in the GOT, TLS entries
709
59
  // are allocated after them. TLS entries should be addressable
710
59
  // by 16-bit index so count both reloc-only and TLS entries.
711
59
  if (!Tls.empty() || 
!DynTlsSymbols.empty()50
)
712
10
    Count += Relocs.size() + Tls.size() + DynTlsSymbols.size() * 2;
713
59
  return Count;
714
59
}
715
716
10.1k
MipsGotSection::FileGot &MipsGotSection::getGot(InputFile &F) {
717
10.1k
  if (!F.MipsGotIndex.hasValue()) {
718
58
    Gots.emplace_back();
719
58
    Gots.back().File = &F;
720
58
    F.MipsGotIndex = Gots.size() - 1;
721
58
  }
722
10.1k
  return Gots[*F.MipsGotIndex];
723
10.1k
}
724
725
uint64_t MipsGotSection::getPageEntryOffset(const InputFile *F,
726
                                            const Symbol &Sym,
727
29
                                            int64_t Addend) const {
728
29
  const FileGot &G = Gots[*F->MipsGotIndex];
729
29
  uint64_t Index = 0;
730
29
  if (const OutputSection *OutSec = Sym.getOutputSection()) {
731
25
    uint64_t SecAddr = getMipsPageAddr(OutSec->Addr);
732
25
    uint64_t SymAddr = getMipsPageAddr(Sym.getVA(Addend));
733
25
    Index = G.PagesMap.lookup(OutSec).FirstIndex + (SymAddr - SecAddr) / 0xffff;
734
25
  } else {
735
4
    Index = G.Local16.lookup({nullptr, getMipsPageAddr(Sym.getVA(Addend))});
736
4
  }
737
29
  return Index * Config->Wordsize;
738
29
}
739
740
uint64_t MipsGotSection::getSymEntryOffset(const InputFile *F, const Symbol &S,
741
10.0k
                                           int64_t Addend) const {
742
10.0k
  const FileGot &G = Gots[*F->MipsGotIndex];
743
10.0k
  Symbol *Sym = const_cast<Symbol *>(&S);
744
10.0k
  if (Sym->isTls())
745
13
    return G.Tls.lookup(Sym) * Config->Wordsize;
746
10.0k
  if (Sym->IsPreemptible)
747
37
    return G.Global.lookup(Sym) * Config->Wordsize;
748
10.0k
  return G.Local16.lookup({Sym, Addend}) * Config->Wordsize;
749
10.0k
}
750
751
6
uint64_t MipsGotSection::getTlsIndexOffset(const InputFile *F) const {
752
6
  const FileGot &G = Gots[*F->MipsGotIndex];
753
6
  return G.DynTlsSymbols.lookup(nullptr) * Config->Wordsize;
754
6
}
755
756
uint64_t MipsGotSection::getGlobalDynOffset(const InputFile *F,
757
12
                                            const Symbol &S) const {
758
12
  const FileGot &G = Gots[*F->MipsGotIndex];
759
12
  Symbol *Sym = const_cast<Symbol *>(&S);
760
12
  return G.DynTlsSymbols.lookup(Sym) * Config->Wordsize;
761
12
}
762
763
100
const Symbol *MipsGotSection::getFirstGlobalEntry() const {
764
100
  if (Gots.empty())
765
55
    return nullptr;
766
45
  const FileGot &PrimGot = Gots.front();
767
45
  if (!PrimGot.Global.empty())
768
27
    return PrimGot.Global.front().first;
769
18
  if (!PrimGot.Relocs.empty())
770
5
    return PrimGot.Relocs.front().first;
771
13
  return nullptr;
772
13
}
773
774
100
unsigned MipsGotSection::getLocalEntriesNum() const {
775
100
  if (Gots.empty())
776
55
    return HeaderEntriesNum;
777
45
  return HeaderEntriesNum + Gots.front().getPageEntriesNum() +
778
45
         Gots.front().Local16.size();
779
45
}
780
781
59
bool MipsGotSection::tryMergeGots(FileGot &Dst, FileGot &Src, bool IsPrimary) {
782
59
  FileGot Tmp = Dst;
783
59
  set_union(Tmp.PagesMap, Src.PagesMap);
784
59
  set_union(Tmp.Local16, Src.Local16);
785
59
  set_union(Tmp.Global, Src.Global);
786
59
  set_union(Tmp.Relocs, Src.Relocs);
787
59
  set_union(Tmp.Tls, Src.Tls);
788
59
  set_union(Tmp.DynTlsSymbols, Src.DynTlsSymbols);
789
59
790
59
  size_t Count = IsPrimary ? 
HeaderEntriesNum58
:
01
;
791
59
  Count += Tmp.getIndexedEntriesNum();
792
59
793
59
  if (Count * Config->Wordsize > Config->MipsGotSize)
794
4
    return false;
795
55
796
55
  std::swap(Tmp, Dst);
797
55
  return true;
798
55
}
799
800
158
void MipsGotSection::finalizeContents() { updateAllocSize(); }
801
802
339
bool MipsGotSection::updateAllocSize() {
803
339
  Size = HeaderEntriesNum * Config->Wordsize;
804
339
  for (const FileGot &G : Gots)
805
114
    Size += G.getEntriesNum() * Config->Wordsize;
806
339
  return false;
807
339
}
808
809
169
template <class ELFT> void MipsGotSection::build() {
810
169
  if (Gots.empty())
811
115
    return;
812
54
813
54
  std::vector<FileGot> MergedGots(1);
814
54
815
54
  // For each GOT move non-preemptible symbols from the `Global`
816
54
  // to `Local16` list. Preemptible symbol might become non-preemptible
817
54
  // one if, for example, it gets a related copy relocation.
818
58
  for (FileGot &Got : Gots) {
819
58
    for (auto &P: Got.Global)
820
35
      if (!P.first->IsPreemptible)
821
0
        Got.Local16.insert({{P.first, 0}, 0});
822
58
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
35
      return !P.first->IsPreemptible;
824
35
    });
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, false> >()::'lambda'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
822
3
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
3
      return !P.first->IsPreemptible;
824
3
    });
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, false> >()::'lambda'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
822
28
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
28
      return !P.first->IsPreemptible;
824
28
    });
Unexecuted instantiation: void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, true> >()::'lambda'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, true> >()::'lambda'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
822
4
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
4
      return !P.first->IsPreemptible;
824
4
    });
825
58
  }
826
54
827
54
  // For each GOT remove "reloc-only" entry if there is "global"
828
54
  // entry for the same symbol. And add local entries which indexed
829
54
  // using 32-bit value at the end of 16-bit entries.
830
58
  for (FileGot &Got : Gots) {
831
58
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
4
      return Got.Global.count(P.first);
833
4
    });
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, false> >()::'lambda0'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
831
1
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
1
      return Got.Global.count(P.first);
833
1
    });
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, false> >()::'lambda0'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
831
1
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
1
      return Got.Global.count(P.first);
833
1
    });
Unexecuted instantiation: void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, true> >()::'lambda0'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, true> >()::'lambda0'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
831
2
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
2
      return Got.Global.count(P.first);
833
2
    });
834
58
    set_union(Got.Local16, Got.Local32);
835
58
    Got.Local32.clear();
836
58
  }
837
54
838
54
  // Evaluate number of "reloc-only" entries in the resulting GOT.
839
54
  // To do that put all unique "reloc-only" and "global" entries
840
54
  // from all GOTs to the future primary GOT.
841
54
  FileGot *PrimGot = &MergedGots.front();
842
58
  for (FileGot &Got : Gots) {
843
58
    set_union(PrimGot->Relocs, Got.Global);
844
58
    set_union(PrimGot->Relocs, Got.Relocs);
845
58
    Got.Relocs.clear();
846
58
  }
847
54
848
54
  // Evaluate number of "page" entries in each GOT.
849
58
  for (FileGot &Got : Gots) {
850
58
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
851
58
         Got.PagesMap) {
852
14
      const OutputSection *OS = P.first;
853
14
      uint64_t SecSize = 0;
854
16
      for (BaseCommand *Cmd : OS->SectionCommands) {
855
16
        if (auto *ISD = dyn_cast<InputSectionDescription>(Cmd))
856
24
          
for (InputSection *IS : ISD->Sections)15
{
857
24
            uint64_t Off = alignTo(SecSize, IS->Alignment);
858
24
            SecSize = Off + IS->getSize();
859
24
          }
860
16
      }
861
14
      P.second.Count = getMipsPageCount(SecSize);
862
14
    }
863
58
  }
864
54
865
54
  // Merge GOTs. Try to join as much as possible GOTs but do not exceed
866
54
  // maximum GOT size. At first, try to fill the primary GOT because
867
54
  // the primary GOT can be accessed in the most effective way. If it
868
54
  // is not possible, try to fill the last GOT in the list, and finally
869
54
  // create a new GOT if both attempts failed.
870
58
  for (FileGot &SrcGot : Gots) {
871
58
    InputFile *File = SrcGot.File;
872
58
    if (tryMergeGots(MergedGots.front(), SrcGot, true)) {
873
54
      File->MipsGotIndex = 0;
874
54
    } else {
875
4
      // If this is the first time we failed to merge with the primary GOT,
876
4
      // MergedGots.back() will also be the primary GOT. We must make sure not
877
4
      // to try to merge again with IsPrimary=false, as otherwise, if the
878
4
      // inputs are just right, we could allow the primary GOT to become 1 or 2
879
4
      // words too big due to ignoring the header size.
880
4
      if (MergedGots.size() == 1 ||
881
4
          
!tryMergeGots(MergedGots.back(), SrcGot, false)1
) {
882
3
        MergedGots.emplace_back();
883
3
        std::swap(MergedGots.back(), SrcGot);
884
3
      }
885
4
      File->MipsGotIndex = MergedGots.size() - 1;
886
4
    }
887
58
  }
888
54
  std::swap(Gots, MergedGots);
889
54
890
54
  // Reduce number of "reloc-only" entries in the primary GOT
891
54
  // by substracting "global" entries exist in the primary GOT.
892
54
  PrimGot = &Gots.front();
893
54
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
38
    return PrimGot->Global.count(P.first);
895
38
  });
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, false> >()::'lambda1'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
893
4
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
4
    return PrimGot->Global.count(P.first);
895
4
  });
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, false> >()::'lambda1'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
893
28
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
28
    return PrimGot->Global.count(P.first);
895
28
  });
Unexecuted instantiation: void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, true> >()::'lambda1'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, true> >()::'lambda1'(std::__1::pair<lld::elf::Symbol*, unsigned long> const&)::operator()(std::__1::pair<lld::elf::Symbol*, unsigned long> const&) const
Line
Count
Source
893
6
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
6
    return PrimGot->Global.count(P.first);
895
6
  });
896
54
897
54
  // Calculate indexes for each GOT entry.
898
54
  size_t Index = HeaderEntriesNum;
899
57
  for (FileGot &Got : Gots) {
900
57
    Got.StartIndex = &Got == PrimGot ? 
054
:
Index3
;
901
57
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
902
57
         Got.PagesMap) {
903
13
      // For each output section referenced by GOT page relocations calculate
904
13
      // and save into PagesMap an upper bound of MIPS GOT entries required
905
13
      // to store page addresses of local symbols. We assume the worst case -
906
13
      // each 64kb page of the output section has at least one GOT relocation
907
13
      // against it. And take in account the case when the section intersects
908
13
      // page boundaries.
909
13
      P.second.FirstIndex = Index;
910
13
      Index += P.second.Count;
911
13
    }
912
57
    for (auto &P: Got.Local16)
913
10.0k
      P.second = Index++;
914
57
    for (auto &P: Got.Global)
915
34
      P.second = Index++;
916
57
    for (auto &P: Got.Relocs)
917
6
      P.second = Index++;
918
57
    for (auto &P: Got.Tls)
919
12
      P.second = Index++;
920
57
    for (auto &P: Got.DynTlsSymbols) {
921
17
      P.second = Index;
922
17
      Index += 2;
923
17
    }
924
57
  }
925
54
926
54
  // Update Symbol::GotIndex field to use this
927
54
  // value later in the `sortMipsSymbols` function.
928
54
  for (auto &P : PrimGot->Global)
929
32
    P.first->GotIndex = P.second;
930
54
  for (auto &P : PrimGot->Relocs)
931
6
    P.first->GotIndex = P.second;
932
54
933
54
  // Create dynamic relocations.
934
57
  for (FileGot &Got : Gots) {
935
57
    // Create dynamic relocations for TLS entries.
936
57
    for (std::pair<Symbol *, size_t> &P : Got.Tls) {
937
12
      Symbol *S = P.first;
938
12
      uint64_t Offset = P.second * Config->Wordsize;
939
12
      if (S->IsPreemptible)
940
9
        InX::RelaDyn->addReloc(Target->TlsGotRel, this, Offset, S);
941
12
    }
942
57
    for (std::pair<Symbol *, size_t> &P : Got.DynTlsSymbols) {
943
17
      Symbol *S = P.first;
944
17
      uint64_t Offset = P.second * Config->Wordsize;
945
17
      if (S == nullptr) {
946
6
        if (!Config->Pic)
947
3
          continue;
948
3
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
949
11
      } else {
950
11
        // When building a shared library we still need a dynamic relocation
951
11
        // for the module index. Therefore only checking for
952
11
        // S->IsPreemptible is not sufficient (this happens e.g. for
953
11
        // thread-locals that have been marked as local through a linker script)
954
11
        if (!S->IsPreemptible && 
!Config->Pic4
)
955
3
          continue;
956
8
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
957
8
        // However, we can skip writing the TLS offset reloc for non-preemptible
958
8
        // symbols since it is known even in shared libraries
959
8
        if (!S->IsPreemptible)
960
1
          continue;
961
7
        Offset += Config->Wordsize;
962
7
        InX::RelaDyn->addReloc(Target->TlsOffsetRel, this, Offset, S);
963
7
      }
964
17
    }
965
57
966
57
    // Do not create dynamic relocations for non-TLS
967
57
    // entries in the primary GOT.
968
57
    if (&Got == PrimGot)
969
54
      continue;
970
3
971
3
    // Dynamic relocations for "global" entries.
972
3
    for (const std::pair<Symbol *, size_t> &P : Got.Global) {
973
2
      uint64_t Offset = P.second * Config->Wordsize;
974
2
      InX::RelaDyn->addReloc(Target->RelativeRel, this, Offset, P.first);
975
2
    }
976
3
    if (!Config->Pic)
977
1
      continue;
978
2
    // Dynamic relocations for "local" entries in case of PIC.
979
2
    for (const std::pair<const OutputSection *, FileGot::PageBlock> &L :
980
2
         Got.PagesMap) {
981
1
      size_t PageCount = L.second.Count;
982
7
      for (size_t PI = 0; PI < PageCount; 
++PI6
) {
983
6
        uint64_t Offset = (L.second.FirstIndex + PI) * Config->Wordsize;
984
6
        InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, L.first,
985
6
                                int64_t(PI * 0x10000)});
986
6
      }
987
1
    }
988
2
    for (const std::pair<GotEntry, size_t> &P : Got.Local16) {
989
1
      uint64_t Offset = P.second * Config->Wordsize;
990
1
      InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, true,
991
1
                              P.first.first, P.first.second});
992
1
    }
993
2
  }
994
54
}
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, false> >()
Line
Count
Source
809
17
template <class ELFT> void MipsGotSection::build() {
810
17
  if (Gots.empty())
811
12
    return;
812
5
813
5
  std::vector<FileGot> MergedGots(1);
814
5
815
5
  // For each GOT move non-preemptible symbols from the `Global`
816
5
  // to `Local16` list. Preemptible symbol might become non-preemptible
817
5
  // one if, for example, it gets a related copy relocation.
818
5
  for (FileGot &Got : Gots) {
819
5
    for (auto &P: Got.Global)
820
3
      if (!P.first->IsPreemptible)
821
0
        Got.Local16.insert({{P.first, 0}, 0});
822
5
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
5
      return !P.first->IsPreemptible;
824
5
    });
825
5
  }
826
5
827
5
  // For each GOT remove "reloc-only" entry if there is "global"
828
5
  // entry for the same symbol. And add local entries which indexed
829
5
  // using 32-bit value at the end of 16-bit entries.
830
5
  for (FileGot &Got : Gots) {
831
5
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
5
      return Got.Global.count(P.first);
833
5
    });
834
5
    set_union(Got.Local16, Got.Local32);
835
5
    Got.Local32.clear();
836
5
  }
837
5
838
5
  // Evaluate number of "reloc-only" entries in the resulting GOT.
839
5
  // To do that put all unique "reloc-only" and "global" entries
840
5
  // from all GOTs to the future primary GOT.
841
5
  FileGot *PrimGot = &MergedGots.front();
842
5
  for (FileGot &Got : Gots) {
843
5
    set_union(PrimGot->Relocs, Got.Global);
844
5
    set_union(PrimGot->Relocs, Got.Relocs);
845
5
    Got.Relocs.clear();
846
5
  }
847
5
848
5
  // Evaluate number of "page" entries in each GOT.
849
5
  for (FileGot &Got : Gots) {
850
5
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
851
5
         Got.PagesMap) {
852
0
      const OutputSection *OS = P.first;
853
0
      uint64_t SecSize = 0;
854
0
      for (BaseCommand *Cmd : OS->SectionCommands) {
855
0
        if (auto *ISD = dyn_cast<InputSectionDescription>(Cmd))
856
0
          for (InputSection *IS : ISD->Sections) {
857
0
            uint64_t Off = alignTo(SecSize, IS->Alignment);
858
0
            SecSize = Off + IS->getSize();
859
0
          }
860
0
      }
861
0
      P.second.Count = getMipsPageCount(SecSize);
862
0
    }
863
5
  }
864
5
865
5
  // Merge GOTs. Try to join as much as possible GOTs but do not exceed
866
5
  // maximum GOT size. At first, try to fill the primary GOT because
867
5
  // the primary GOT can be accessed in the most effective way. If it
868
5
  // is not possible, try to fill the last GOT in the list, and finally
869
5
  // create a new GOT if both attempts failed.
870
5
  for (FileGot &SrcGot : Gots) {
871
5
    InputFile *File = SrcGot.File;
872
5
    if (tryMergeGots(MergedGots.front(), SrcGot, true)) {
873
5
      File->MipsGotIndex = 0;
874
5
    } else {
875
0
      // If this is the first time we failed to merge with the primary GOT,
876
0
      // MergedGots.back() will also be the primary GOT. We must make sure not
877
0
      // to try to merge again with IsPrimary=false, as otherwise, if the
878
0
      // inputs are just right, we could allow the primary GOT to become 1 or 2
879
0
      // words too big due to ignoring the header size.
880
0
      if (MergedGots.size() == 1 ||
881
0
          !tryMergeGots(MergedGots.back(), SrcGot, false)) {
882
0
        MergedGots.emplace_back();
883
0
        std::swap(MergedGots.back(), SrcGot);
884
0
      }
885
0
      File->MipsGotIndex = MergedGots.size() - 1;
886
0
    }
887
5
  }
888
5
  std::swap(Gots, MergedGots);
889
5
890
5
  // Reduce number of "reloc-only" entries in the primary GOT
891
5
  // by substracting "global" entries exist in the primary GOT.
892
5
  PrimGot = &Gots.front();
893
5
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
5
    return PrimGot->Global.count(P.first);
895
5
  });
896
5
897
5
  // Calculate indexes for each GOT entry.
898
5
  size_t Index = HeaderEntriesNum;
899
5
  for (FileGot &Got : Gots) {
900
5
    Got.StartIndex = &Got == PrimGot ? 0 : 
Index0
;
901
5
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
902
5
         Got.PagesMap) {
903
0
      // For each output section referenced by GOT page relocations calculate
904
0
      // and save into PagesMap an upper bound of MIPS GOT entries required
905
0
      // to store page addresses of local symbols. We assume the worst case -
906
0
      // each 64kb page of the output section has at least one GOT relocation
907
0
      // against it. And take in account the case when the section intersects
908
0
      // page boundaries.
909
0
      P.second.FirstIndex = Index;
910
0
      Index += P.second.Count;
911
0
    }
912
5
    for (auto &P: Got.Local16)
913
2
      P.second = Index++;
914
5
    for (auto &P: Got.Global)
915
3
      P.second = Index++;
916
5
    for (auto &P: Got.Relocs)
917
1
      P.second = Index++;
918
5
    for (auto &P: Got.Tls)
919
0
      P.second = Index++;
920
5
    for (auto &P: Got.DynTlsSymbols) {
921
0
      P.second = Index;
922
0
      Index += 2;
923
0
    }
924
5
  }
925
5
926
5
  // Update Symbol::GotIndex field to use this
927
5
  // value later in the `sortMipsSymbols` function.
928
5
  for (auto &P : PrimGot->Global)
929
3
    P.first->GotIndex = P.second;
930
5
  for (auto &P : PrimGot->Relocs)
931
1
    P.first->GotIndex = P.second;
932
5
933
5
  // Create dynamic relocations.
934
5
  for (FileGot &Got : Gots) {
935
5
    // Create dynamic relocations for TLS entries.
936
5
    for (std::pair<Symbol *, size_t> &P : Got.Tls) {
937
0
      Symbol *S = P.first;
938
0
      uint64_t Offset = P.second * Config->Wordsize;
939
0
      if (S->IsPreemptible)
940
0
        InX::RelaDyn->addReloc(Target->TlsGotRel, this, Offset, S);
941
0
    }
942
5
    for (std::pair<Symbol *, size_t> &P : Got.DynTlsSymbols) {
943
0
      Symbol *S = P.first;
944
0
      uint64_t Offset = P.second * Config->Wordsize;
945
0
      if (S == nullptr) {
946
0
        if (!Config->Pic)
947
0
          continue;
948
0
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
949
0
      } else {
950
0
        // When building a shared library we still need a dynamic relocation
951
0
        // for the module index. Therefore only checking for
952
0
        // S->IsPreemptible is not sufficient (this happens e.g. for
953
0
        // thread-locals that have been marked as local through a linker script)
954
0
        if (!S->IsPreemptible && !Config->Pic)
955
0
          continue;
956
0
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
957
0
        // However, we can skip writing the TLS offset reloc for non-preemptible
958
0
        // symbols since it is known even in shared libraries
959
0
        if (!S->IsPreemptible)
960
0
          continue;
961
0
        Offset += Config->Wordsize;
962
0
        InX::RelaDyn->addReloc(Target->TlsOffsetRel, this, Offset, S);
963
0
      }
964
0
    }
965
5
966
5
    // Do not create dynamic relocations for non-TLS
967
5
    // entries in the primary GOT.
968
5
    if (&Got == PrimGot)
969
5
      continue;
970
0
971
0
    // Dynamic relocations for "global" entries.
972
0
    for (const std::pair<Symbol *, size_t> &P : Got.Global) {
973
0
      uint64_t Offset = P.second * Config->Wordsize;
974
0
      InX::RelaDyn->addReloc(Target->RelativeRel, this, Offset, P.first);
975
0
    }
976
0
    if (!Config->Pic)
977
0
      continue;
978
0
    // Dynamic relocations for "local" entries in case of PIC.
979
0
    for (const std::pair<const OutputSection *, FileGot::PageBlock> &L :
980
0
         Got.PagesMap) {
981
0
      size_t PageCount = L.second.Count;
982
0
      for (size_t PI = 0; PI < PageCount; ++PI) {
983
0
        uint64_t Offset = (L.second.FirstIndex + PI) * Config->Wordsize;
984
0
        InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, L.first,
985
0
                                int64_t(PI * 0x10000)});
986
0
      }
987
0
    }
988
0
    for (const std::pair<GotEntry, size_t> &P : Got.Local16) {
989
0
      uint64_t Offset = P.second * Config->Wordsize;
990
0
      InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, true,
991
0
                              P.first.first, P.first.second});
992
0
    }
993
0
  }
994
5
}
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, false> >()
Line
Count
Source
809
113
template <class ELFT> void MipsGotSection::build() {
810
113
  if (Gots.empty())
811
78
    return;
812
35
813
35
  std::vector<FileGot> MergedGots(1);
814
35
815
35
  // For each GOT move non-preemptible symbols from the `Global`
816
35
  // to `Local16` list. Preemptible symbol might become non-preemptible
817
35
  // one if, for example, it gets a related copy relocation.
818
37
  for (FileGot &Got : Gots) {
819
37
    for (auto &P: Got.Global)
820
28
      if (!P.first->IsPreemptible)
821
0
        Got.Local16.insert({{P.first, 0}, 0});
822
37
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
37
      return !P.first->IsPreemptible;
824
37
    });
825
37
  }
826
35
827
35
  // For each GOT remove "reloc-only" entry if there is "global"
828
35
  // entry for the same symbol. And add local entries which indexed
829
35
  // using 32-bit value at the end of 16-bit entries.
830
37
  for (FileGot &Got : Gots) {
831
37
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
37
      return Got.Global.count(P.first);
833
37
    });
834
37
    set_union(Got.Local16, Got.Local32);
835
37
    Got.Local32.clear();
836
37
  }
837
35
838
35
  // Evaluate number of "reloc-only" entries in the resulting GOT.
839
35
  // To do that put all unique "reloc-only" and "global" entries
840
35
  // from all GOTs to the future primary GOT.
841
35
  FileGot *PrimGot = &MergedGots.front();
842
37
  for (FileGot &Got : Gots) {
843
37
    set_union(PrimGot->Relocs, Got.Global);
844
37
    set_union(PrimGot->Relocs, Got.Relocs);
845
37
    Got.Relocs.clear();
846
37
  }
847
35
848
35
  // Evaluate number of "page" entries in each GOT.
849
37
  for (FileGot &Got : Gots) {
850
37
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
851
37
         Got.PagesMap) {
852
10
      const OutputSection *OS = P.first;
853
10
      uint64_t SecSize = 0;
854
12
      for (BaseCommand *Cmd : OS->SectionCommands) {
855
12
        if (auto *ISD = dyn_cast<InputSectionDescription>(Cmd))
856
18
          
for (InputSection *IS : ISD->Sections)11
{
857
18
            uint64_t Off = alignTo(SecSize, IS->Alignment);
858
18
            SecSize = Off + IS->getSize();
859
18
          }
860
12
      }
861
10
      P.second.Count = getMipsPageCount(SecSize);
862
10
    }
863
37
  }
864
35
865
35
  // Merge GOTs. Try to join as much as possible GOTs but do not exceed
866
35
  // maximum GOT size. At first, try to fill the primary GOT because
867
35
  // the primary GOT can be accessed in the most effective way. If it
868
35
  // is not possible, try to fill the last GOT in the list, and finally
869
35
  // create a new GOT if both attempts failed.
870
37
  for (FileGot &SrcGot : Gots) {
871
37
    InputFile *File = SrcGot.File;
872
37
    if (tryMergeGots(MergedGots.front(), SrcGot, true)) {
873
35
      File->MipsGotIndex = 0;
874
35
    } else {
875
2
      // If this is the first time we failed to merge with the primary GOT,
876
2
      // MergedGots.back() will also be the primary GOT. We must make sure not
877
2
      // to try to merge again with IsPrimary=false, as otherwise, if the
878
2
      // inputs are just right, we could allow the primary GOT to become 1 or 2
879
2
      // words too big due to ignoring the header size.
880
2
      if (MergedGots.size() == 1 ||
881
2
          
!tryMergeGots(MergedGots.back(), SrcGot, false)1
) {
882
1
        MergedGots.emplace_back();
883
1
        std::swap(MergedGots.back(), SrcGot);
884
1
      }
885
2
      File->MipsGotIndex = MergedGots.size() - 1;
886
2
    }
887
37
  }
888
35
  std::swap(Gots, MergedGots);
889
35
890
35
  // Reduce number of "reloc-only" entries in the primary GOT
891
35
  // by substracting "global" entries exist in the primary GOT.
892
35
  PrimGot = &Gots.front();
893
35
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
35
    return PrimGot->Global.count(P.first);
895
35
  });
896
35
897
35
  // Calculate indexes for each GOT entry.
898
35
  size_t Index = HeaderEntriesNum;
899
36
  for (FileGot &Got : Gots) {
900
36
    Got.StartIndex = &Got == PrimGot ? 
035
:
Index1
;
901
36
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
902
36
         Got.PagesMap) {
903
9
      // For each output section referenced by GOT page relocations calculate
904
9
      // and save into PagesMap an upper bound of MIPS GOT entries required
905
9
      // to store page addresses of local symbols. We assume the worst case -
906
9
      // each 64kb page of the output section has at least one GOT relocation
907
9
      // against it. And take in account the case when the section intersects
908
9
      // page boundaries.
909
9
      P.second.FirstIndex = Index;
910
9
      Index += P.second.Count;
911
9
    }
912
36
    for (auto &P: Got.Local16)
913
16
      P.second = Index++;
914
36
    for (auto &P: Got.Global)
915
27
      P.second = Index++;
916
36
    for (auto &P: Got.Relocs)
917
3
      P.second = Index++;
918
36
    for (auto &P: Got.Tls)
919
8
      P.second = Index++;
920
36
    for (auto &P: Got.DynTlsSymbols) {
921
10
      P.second = Index;
922
10
      Index += 2;
923
10
    }
924
36
  }
925
35
926
35
  // Update Symbol::GotIndex field to use this
927
35
  // value later in the `sortMipsSymbols` function.
928
35
  for (auto &P : PrimGot->Global)
929
25
    P.first->GotIndex = P.second;
930
35
  for (auto &P : PrimGot->Relocs)
931
3
    P.first->GotIndex = P.second;
932
35
933
35
  // Create dynamic relocations.
934
36
  for (FileGot &Got : Gots) {
935
36
    // Create dynamic relocations for TLS entries.
936
36
    for (std::pair<Symbol *, size_t> &P : Got.Tls) {
937
8
      Symbol *S = P.first;
938
8
      uint64_t Offset = P.second * Config->Wordsize;
939
8
      if (S->IsPreemptible)
940
6
        InX::RelaDyn->addReloc(Target->TlsGotRel, this, Offset, S);
941
8
    }
942
36
    for (std::pair<Symbol *, size_t> &P : Got.DynTlsSymbols) {
943
10
      Symbol *S = P.first;
944
10
      uint64_t Offset = P.second * Config->Wordsize;
945
10
      if (S == nullptr) {
946
4
        if (!Config->Pic)
947
2
          continue;
948
2
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
949
6
      } else {
950
6
        // When building a shared library we still need a dynamic relocation
951
6
        // for the module index. Therefore only checking for
952
6
        // S->IsPreemptible is not sufficient (this happens e.g. for
953
6
        // thread-locals that have been marked as local through a linker script)
954
6
        if (!S->IsPreemptible && 
!Config->Pic2
)
955
2
          continue;
956
4
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
957
4
        // However, we can skip writing the TLS offset reloc for non-preemptible
958
4
        // symbols since it is known even in shared libraries
959
4
        if (!S->IsPreemptible)
960
0
          continue;
961
4
        Offset += Config->Wordsize;
962
4
        InX::RelaDyn->addReloc(Target->TlsOffsetRel, this, Offset, S);
963
4
      }
964
10
    }
965
36
966
36
    // Do not create dynamic relocations for non-TLS
967
36
    // entries in the primary GOT.
968
36
    if (&Got == PrimGot)
969
35
      continue;
970
1
971
1
    // Dynamic relocations for "global" entries.
972
2
    
for (const std::pair<Symbol *, size_t> &P : Got.Global)1
{
973
2
      uint64_t Offset = P.second * Config->Wordsize;
974
2
      InX::RelaDyn->addReloc(Target->RelativeRel, this, Offset, P.first);
975
2
    }
976
1
    if (!Config->Pic)
977
0
      continue;
978
1
    // Dynamic relocations for "local" entries in case of PIC.
979
1
    for (const std::pair<const OutputSection *, FileGot::PageBlock> &L :
980
1
         Got.PagesMap) {
981
1
      size_t PageCount = L.second.Count;
982
7
      for (size_t PI = 0; PI < PageCount; 
++PI6
) {
983
6
        uint64_t Offset = (L.second.FirstIndex + PI) * Config->Wordsize;
984
6
        InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, L.first,
985
6
                                int64_t(PI * 0x10000)});
986
6
      }
987
1
    }
988
1
    for (const std::pair<GotEntry, size_t> &P : Got.Local16) {
989
0
      uint64_t Offset = P.second * Config->Wordsize;
990
0
      InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, true,
991
0
                              P.first.first, P.first.second});
992
0
    }
993
1
  }
994
35
}
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)1, true> >()
Line
Count
Source
809
2
template <class ELFT> void MipsGotSection::build() {
810
2
  if (Gots.empty())
811
2
    return;
812
0
813
0
  std::vector<FileGot> MergedGots(1);
814
0
815
0
  // For each GOT move non-preemptible symbols from the `Global`
816
0
  // to `Local16` list. Preemptible symbol might become non-preemptible
817
0
  // one if, for example, it gets a related copy relocation.
818
0
  for (FileGot &Got : Gots) {
819
0
    for (auto &P: Got.Global)
820
0
      if (!P.first->IsPreemptible)
821
0
        Got.Local16.insert({{P.first, 0}, 0});
822
0
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
0
      return !P.first->IsPreemptible;
824
0
    });
825
0
  }
826
0
827
0
  // For each GOT remove "reloc-only" entry if there is "global"
828
0
  // entry for the same symbol. And add local entries which indexed
829
0
  // using 32-bit value at the end of 16-bit entries.
830
0
  for (FileGot &Got : Gots) {
831
0
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
0
      return Got.Global.count(P.first);
833
0
    });
834
0
    set_union(Got.Local16, Got.Local32);
835
0
    Got.Local32.clear();
836
0
  }
837
0
838
0
  // Evaluate number of "reloc-only" entries in the resulting GOT.
839
0
  // To do that put all unique "reloc-only" and "global" entries
840
0
  // from all GOTs to the future primary GOT.
841
0
  FileGot *PrimGot = &MergedGots.front();
842
0
  for (FileGot &Got : Gots) {
843
0
    set_union(PrimGot->Relocs, Got.Global);
844
0
    set_union(PrimGot->Relocs, Got.Relocs);
845
0
    Got.Relocs.clear();
846
0
  }
847
0
848
0
  // Evaluate number of "page" entries in each GOT.
849
0
  for (FileGot &Got : Gots) {
850
0
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
851
0
         Got.PagesMap) {
852
0
      const OutputSection *OS = P.first;
853
0
      uint64_t SecSize = 0;
854
0
      for (BaseCommand *Cmd : OS->SectionCommands) {
855
0
        if (auto *ISD = dyn_cast<InputSectionDescription>(Cmd))
856
0
          for (InputSection *IS : ISD->Sections) {
857
0
            uint64_t Off = alignTo(SecSize, IS->Alignment);
858
0
            SecSize = Off + IS->getSize();
859
0
          }
860
0
      }
861
0
      P.second.Count = getMipsPageCount(SecSize);
862
0
    }
863
0
  }
864
0
865
0
  // Merge GOTs. Try to join as much as possible GOTs but do not exceed
866
0
  // maximum GOT size. At first, try to fill the primary GOT because
867
0
  // the primary GOT can be accessed in the most effective way. If it
868
0
  // is not possible, try to fill the last GOT in the list, and finally
869
0
  // create a new GOT if both attempts failed.
870
0
  for (FileGot &SrcGot : Gots) {
871
0
    InputFile *File = SrcGot.File;
872
0
    if (tryMergeGots(MergedGots.front(), SrcGot, true)) {
873
0
      File->MipsGotIndex = 0;
874
0
    } else {
875
0
      // If this is the first time we failed to merge with the primary GOT,
876
0
      // MergedGots.back() will also be the primary GOT. We must make sure not
877
0
      // to try to merge again with IsPrimary=false, as otherwise, if the
878
0
      // inputs are just right, we could allow the primary GOT to become 1 or 2
879
0
      // words too big due to ignoring the header size.
880
0
      if (MergedGots.size() == 1 ||
881
0
          !tryMergeGots(MergedGots.back(), SrcGot, false)) {
882
0
        MergedGots.emplace_back();
883
0
        std::swap(MergedGots.back(), SrcGot);
884
0
      }
885
0
      File->MipsGotIndex = MergedGots.size() - 1;
886
0
    }
887
0
  }
888
0
  std::swap(Gots, MergedGots);
889
0
890
0
  // Reduce number of "reloc-only" entries in the primary GOT
891
0
  // by substracting "global" entries exist in the primary GOT.
892
0
  PrimGot = &Gots.front();
893
0
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
0
    return PrimGot->Global.count(P.first);
895
0
  });
896
0
897
0
  // Calculate indexes for each GOT entry.
898
0
  size_t Index = HeaderEntriesNum;
899
0
  for (FileGot &Got : Gots) {
900
0
    Got.StartIndex = &Got == PrimGot ? 0 : Index;
901
0
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
902
0
         Got.PagesMap) {
903
0
      // For each output section referenced by GOT page relocations calculate
904
0
      // and save into PagesMap an upper bound of MIPS GOT entries required
905
0
      // to store page addresses of local symbols. We assume the worst case -
906
0
      // each 64kb page of the output section has at least one GOT relocation
907
0
      // against it. And take in account the case when the section intersects
908
0
      // page boundaries.
909
0
      P.second.FirstIndex = Index;
910
0
      Index += P.second.Count;
911
0
    }
912
0
    for (auto &P: Got.Local16)
913
0
      P.second = Index++;
914
0
    for (auto &P: Got.Global)
915
0
      P.second = Index++;
916
0
    for (auto &P: Got.Relocs)
917
0
      P.second = Index++;
918
0
    for (auto &P: Got.Tls)
919
0
      P.second = Index++;
920
0
    for (auto &P: Got.DynTlsSymbols) {
921
0
      P.second = Index;
922
0
      Index += 2;
923
0
    }
924
0
  }
925
0
926
0
  // Update Symbol::GotIndex field to use this
927
0
  // value later in the `sortMipsSymbols` function.
928
0
  for (auto &P : PrimGot->Global)
929
0
    P.first->GotIndex = P.second;
930
0
  for (auto &P : PrimGot->Relocs)
931
0
    P.first->GotIndex = P.second;
932
0
933
0
  // Create dynamic relocations.
934
0
  for (FileGot &Got : Gots) {
935
0
    // Create dynamic relocations for TLS entries.
936
0
    for (std::pair<Symbol *, size_t> &P : Got.Tls) {
937
0
      Symbol *S = P.first;
938
0
      uint64_t Offset = P.second * Config->Wordsize;
939
0
      if (S->IsPreemptible)
940
0
        InX::RelaDyn->addReloc(Target->TlsGotRel, this, Offset, S);
941
0
    }
942
0
    for (std::pair<Symbol *, size_t> &P : Got.DynTlsSymbols) {
943
0
      Symbol *S = P.first;
944
0
      uint64_t Offset = P.second * Config->Wordsize;
945
0
      if (S == nullptr) {
946
0
        if (!Config->Pic)
947
0
          continue;
948
0
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
949
0
      } else {
950
0
        // When building a shared library we still need a dynamic relocation
951
0
        // for the module index. Therefore only checking for
952
0
        // S->IsPreemptible is not sufficient (this happens e.g. for
953
0
        // thread-locals that have been marked as local through a linker script)
954
0
        if (!S->IsPreemptible && !Config->Pic)
955
0
          continue;
956
0
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
957
0
        // However, we can skip writing the TLS offset reloc for non-preemptible
958
0
        // symbols since it is known even in shared libraries
959
0
        if (!S->IsPreemptible)
960
0
          continue;
961
0
        Offset += Config->Wordsize;
962
0
        InX::RelaDyn->addReloc(Target->TlsOffsetRel, this, Offset, S);
963
0
      }
964
0
    }
965
0
966
0
    // Do not create dynamic relocations for non-TLS
967
0
    // entries in the primary GOT.
968
0
    if (&Got == PrimGot)
969
0
      continue;
970
0
971
0
    // Dynamic relocations for "global" entries.
972
0
    for (const std::pair<Symbol *, size_t> &P : Got.Global) {
973
0
      uint64_t Offset = P.second * Config->Wordsize;
974
0
      InX::RelaDyn->addReloc(Target->RelativeRel, this, Offset, P.first);
975
0
    }
976
0
    if (!Config->Pic)
977
0
      continue;
978
0
    // Dynamic relocations for "local" entries in case of PIC.
979
0
    for (const std::pair<const OutputSection *, FileGot::PageBlock> &L :
980
0
         Got.PagesMap) {
981
0
      size_t PageCount = L.second.Count;
982
0
      for (size_t PI = 0; PI < PageCount; ++PI) {
983
0
        uint64_t Offset = (L.second.FirstIndex + PI) * Config->Wordsize;
984
0
        InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, L.first,
985
0
                                int64_t(PI * 0x10000)});
986
0
      }
987
0
    }
988
0
    for (const std::pair<GotEntry, size_t> &P : Got.Local16) {
989
0
      uint64_t Offset = P.second * Config->Wordsize;
990
0
      InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, true,
991
0
                              P.first.first, P.first.second});
992
0
    }
993
0
  }
994
0
}
void lld::elf::MipsGotSection::build<llvm::object::ELFType<(llvm::support::endianness)0, true> >()
Line
Count
Source
809
37
template <class ELFT> void MipsGotSection::build() {
810
37
  if (Gots.empty())
811
23
    return;
812
14
813
14
  std::vector<FileGot> MergedGots(1);
814
14
815
14
  // For each GOT move non-preemptible symbols from the `Global`
816
14
  // to `Local16` list. Preemptible symbol might become non-preemptible
817
14
  // one if, for example, it gets a related copy relocation.
818
16
  for (FileGot &Got : Gots) {
819
16
    for (auto &P: Got.Global)
820
4
      if (!P.first->IsPreemptible)
821
0
        Got.Local16.insert({{P.first, 0}, 0});
822
16
    Got.Global.remove_if([&](const std::pair<Symbol *, size_t> &P) {
823
16
      return !P.first->IsPreemptible;
824
16
    });
825
16
  }
826
14
827
14
  // For each GOT remove "reloc-only" entry if there is "global"
828
14
  // entry for the same symbol. And add local entries which indexed
829
14
  // using 32-bit value at the end of 16-bit entries.
830
16
  for (FileGot &Got : Gots) {
831
16
    Got.Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
832
16
      return Got.Global.count(P.first);
833
16
    });
834
16
    set_union(Got.Local16, Got.Local32);
835
16
    Got.Local32.clear();
836
16
  }
837
14
838
14
  // Evaluate number of "reloc-only" entries in the resulting GOT.
839
14
  // To do that put all unique "reloc-only" and "global" entries
840
14
  // from all GOTs to the future primary GOT.
841
14
  FileGot *PrimGot = &MergedGots.front();
842
16
  for (FileGot &Got : Gots) {
843
16
    set_union(PrimGot->Relocs, Got.Global);
844
16
    set_union(PrimGot->Relocs, Got.Relocs);
845
16
    Got.Relocs.clear();
846
16
  }
847
14
848
14
  // Evaluate number of "page" entries in each GOT.
849
16
  for (FileGot &Got : Gots) {
850
16
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
851
16
         Got.PagesMap) {
852
4
      const OutputSection *OS = P.first;
853
4
      uint64_t SecSize = 0;
854
4
      for (BaseCommand *Cmd : OS->SectionCommands) {
855
4
        if (auto *ISD = dyn_cast<InputSectionDescription>(Cmd))
856
6
          
for (InputSection *IS : ISD->Sections)4
{
857
6
            uint64_t Off = alignTo(SecSize, IS->Alignment);
858
6
            SecSize = Off + IS->getSize();
859
6
          }
860
4
      }
861
4
      P.second.Count = getMipsPageCount(SecSize);
862
4
    }
863
16
  }
864
14
865
14
  // Merge GOTs. Try to join as much as possible GOTs but do not exceed
866
14
  // maximum GOT size. At first, try to fill the primary GOT because
867
14
  // the primary GOT can be accessed in the most effective way. If it
868
14
  // is not possible, try to fill the last GOT in the list, and finally
869
14
  // create a new GOT if both attempts failed.
870
16
  for (FileGot &SrcGot : Gots) {
871
16
    InputFile *File = SrcGot.File;
872
16
    if (tryMergeGots(MergedGots.front(), SrcGot, true)) {
873
14
      File->MipsGotIndex = 0;
874
14
    } else {
875
2
      // If this is the first time we failed to merge with the primary GOT,
876
2
      // MergedGots.back() will also be the primary GOT. We must make sure not
877
2
      // to try to merge again with IsPrimary=false, as otherwise, if the
878
2
      // inputs are just right, we could allow the primary GOT to become 1 or 2
879
2
      // words too big due to ignoring the header size.
880
2
      if (MergedGots.size() == 1 ||
881
2
          
!tryMergeGots(MergedGots.back(), SrcGot, false)0
) {
882
2
        MergedGots.emplace_back();
883
2
        std::swap(MergedGots.back(), SrcGot);
884
2
      }
885
2
      File->MipsGotIndex = MergedGots.size() - 1;
886
2
    }
887
16
  }
888
14
  std::swap(Gots, MergedGots);
889
14
890
14
  // Reduce number of "reloc-only" entries in the primary GOT
891
14
  // by substracting "global" entries exist in the primary GOT.
892
14
  PrimGot = &Gots.front();
893
14
  PrimGot->Relocs.remove_if([&](const std::pair<Symbol *, size_t> &P) {
894
14
    return PrimGot->Global.count(P.first);
895
14
  });
896
14
897
14
  // Calculate indexes for each GOT entry.
898
14
  size_t Index = HeaderEntriesNum;
899
16
  for (FileGot &Got : Gots) {
900
16
    Got.StartIndex = &Got == PrimGot ? 
014
:
Index2
;
901
16
    for (std::pair<const OutputSection *, FileGot::PageBlock> &P :
902
16
         Got.PagesMap) {
903
4
      // For each output section referenced by GOT page relocations calculate
904
4
      // and save into PagesMap an upper bound of MIPS GOT entries required
905
4
      // to store page addresses of local symbols. We assume the worst case -
906
4
      // each 64kb page of the output section has at least one GOT relocation
907
4
      // against it. And take in account the case when the section intersects
908
4
      // page boundaries.
909
4
      P.second.FirstIndex = Index;
910
4
      Index += P.second.Count;
911
4
    }
912
16
    for (auto &P: Got.Local16)
913
10.0k
      P.second = Index++;
914
16
    for (auto &P: Got.Global)
915
4
      P.second = Index++;
916
16
    for (auto &P: Got.Relocs)
917
2
      P.second = Index++;
918
16
    for (auto &P: Got.Tls)
919
4
      P.second = Index++;
920
16
    for (auto &P: Got.DynTlsSymbols) {
921
7
      P.second = Index;
922
7
      Index += 2;
923
7
    }
924
16
  }
925
14
926
14
  // Update Symbol::GotIndex field to use this
927
14
  // value later in the `sortMipsSymbols` function.
928
14
  for (auto &P : PrimGot->Global)
929
4
    P.first->GotIndex = P.second;
930
14
  for (auto &P : PrimGot->Relocs)
931
2
    P.first->GotIndex = P.second;
932
14
933
14
  // Create dynamic relocations.
934
16
  for (FileGot &Got : Gots) {
935
16
    // Create dynamic relocations for TLS entries.
936
16
    for (std::pair<Symbol *, size_t> &P : Got.Tls) {
937
4
      Symbol *S = P.first;
938
4
      uint64_t Offset = P.second * Config->Wordsize;
939
4
      if (S->IsPreemptible)
940
3
        InX::RelaDyn->addReloc(Target->TlsGotRel, this, Offset, S);
941
4
    }
942
16
    for (std::pair<Symbol *, size_t> &P : Got.DynTlsSymbols) {
943
7
      Symbol *S = P.first;
944
7
      uint64_t Offset = P.second * Config->Wordsize;
945
7
      if (S == nullptr) {
946
2
        if (!Config->Pic)
947
1
          continue;
948
1
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
949
5
      } else {
950
5
        // When building a shared library we still need a dynamic relocation
951
5
        // for the module index. Therefore only checking for
952
5
        // S->IsPreemptible is not sufficient (this happens e.g. for
953
5
        // thread-locals that have been marked as local through a linker script)
954
5
        if (!S->IsPreemptible && 
!Config->Pic2
)
955
1
          continue;
956
4
        InX::RelaDyn->addReloc(Target->TlsModuleIndexRel, this, Offset, S);
957
4
        // However, we can skip writing the TLS offset reloc for non-preemptible
958
4
        // symbols since it is known even in shared libraries
959
4
        if (!S->IsPreemptible)
960
1
          continue;
961
3
        Offset += Config->Wordsize;
962
3
        InX::RelaDyn->addReloc(Target->TlsOffsetRel, this, Offset, S);
963
3
      }
964
7
    }
965
16
966
16
    // Do not create dynamic relocations for non-TLS
967
16
    // entries in the primary GOT.
968
16
    if (&Got == PrimGot)
969
14
      continue;
970
2
971
2
    // Dynamic relocations for "global" entries.
972
2
    for (const std::pair<Symbol *, size_t> &P : Got.Global) {
973
0
      uint64_t Offset = P.second * Config->Wordsize;
974
0
      InX::RelaDyn->addReloc(Target->RelativeRel, this, Offset, P.first);
975
0
    }
976
2
    if (!Config->Pic)
977
1
      continue;
978
1
    // Dynamic relocations for "local" entries in case of PIC.
979
1
    for (const std::pair<const OutputSection *, FileGot::PageBlock> &L :
980
1
         Got.PagesMap) {
981
0
      size_t PageCount = L.second.Count;
982
0
      for (size_t PI = 0; PI < PageCount; ++PI) {
983
0
        uint64_t Offset = (L.second.FirstIndex + PI) * Config->Wordsize;
984
0
        InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, L.first,
985
0
                                int64_t(PI * 0x10000)});
986
0
      }
987
0
    }
988
1
    for (const std::pair<GotEntry, size_t> &P : Got.Local16) {
989
1
      uint64_t Offset = P.second * Config->Wordsize;
990
1
      InX::RelaDyn->addReloc({Target->RelativeRel, this, Offset, true,
991
1
                              P.first.first, P.first.second});
992
1
    }
993
1
  }
994
14
}
995
996
338
bool MipsGotSection::empty() const {
997
338
  // We add the .got section to the result for dynamic MIPS target because
998
338
  // its address and properties are mentioned in the .dynamic section.
999
338
  return Config->Relocatable;
1000
338
}
1001
1002
10.3k
uint64_t MipsGotSection::getGp(const InputFile *F) const {
1003
10.3k
  // For files without related GOT or files refer a primary GOT
1004
10.3k
  // returns "common" _gp value. For secondary GOTs calculate
1005
10.3k
  // individual _gp values.
1006
10.3k
  if (!F || 
!F->MipsGotIndex.hasValue()10.1k
||
*F->MipsGotIndex == 010.1k
)
1007
321
    return ElfSym::MipsGp->getVA(0);
1008
10.0k
  return getVA() + Gots[*F->MipsGotIndex].StartIndex * Config->Wordsize +
1009
10.0k
         0x7ff0;
1010
10.0k
}
1011
1012
158
void MipsGotSection::writeTo(uint8_t *Buf) {
1013
158
  // Set the MSB of the second GOT slot. This is not required by any
1014
158
  // MIPS ABI documentation, though.
1015
158
  //
1016
158
  // There is a comment in glibc saying that "The MSB of got[1] of a
1017
158
  // gnu object is set to identify gnu objects," and in GNU gold it
1018
158
  // says "the second entry will be used by some runtime loaders".
1019
158
  // But how this field is being used is unclear.
1020
158
  //
1021
158
  // We are not really willing to mimic other linkers behaviors
1022
158
  // without understanding why they do that, but because all files
1023
158
  // generated by GNU tools have this special GOT value, and because
1024
158
  // we've been doing this for years, it is probably a safe bet to
1025
158
  // keep doing this for now. We really need to revisit this to see
1026
158
  // if we had to do this.
1027
158
  writeUint(Buf + Config->Wordsize, (uint64_t)1 << (Config->Wordsize * 8 - 1));
1028
158
  for (const FileGot &G : Gots) {
1029
10.1k
    auto Write = [&](size_t I, const Symbol *S, int64_t A) {
1030
10.1k
      uint64_t VA = A;
1031
10.1k
      if (S) {
1032
10.0k
        VA = S->getVA(A);
1033
10.0k
        if (S->StOther & STO_MIPS_MICROMIPS)
1034
3
          VA |= 1;
1035
10.0k
      }
1036
10.1k
      writeUint(Buf + I * Config->Wordsize, VA);
1037
10.1k
    };
1038
57
    // Write 'page address' entries to the local part of the GOT.
1039
57
    for (const std::pair<const OutputSection *, FileGot::PageBlock> &L :
1040
57
         G.PagesMap) {
1041
13
      size_t PageCount = L.second.Count;
1042
13
      uint64_t FirstPageAddr = getMipsPageAddr(L.first->Addr);
1043
49
      for (size_t PI = 0; PI < PageCount; 
++PI36
)
1044
36
        Write(L.second.FirstIndex + PI, nullptr, FirstPageAddr + PI * 0x10000);
1045
13
    }
1046
57
    // Local, global, TLS, reloc-only  entries.
1047
57
    // If TLS entry has a corresponding dynamic relocations, leave it
1048
57
    // initialized by zero. Write down adjusted TLS symbol's values otherwise.
1049
57
    // To calculate the adjustments use offsets for thread-local storage.
1050
57
    // https://www.linux-mips.org/wiki/NPTL
1051
57
    for (const std::pair<GotEntry, size_t> &P : G.Local16)
1052
10.0k
      Write(P.second, P.first.first, P.first.second);
1053
57
    // Write VA to the primary GOT only. For secondary GOTs that
1054
57
    // will be done by REL32 dynamic relocations.
1055
57
    if (&G == &Gots.front())
1056
54
      for (const std::pair<const Symbol *, size_t> &P : G.Global)
1057
32
        Write(P.second, P.first, 0);
1058
57
    for (const std::pair<Symbol *, size_t> &P : G.Relocs)
1059
6
      Write(P.second, P.first, 0);
1060
57
    for (const std::pair<Symbol *, size_t> &P : G.Tls)
1061
12
      Write(P.second, P.first, P.first->IsPreemptible ? 
09
:
-0x70003
);
1062
57
    for (const std::pair<Symbol *, size_t> &P : G.DynTlsSymbols) {
1063
17
      if (P.first == nullptr && 
!Config->Pic6
)
1064
3
        Write(P.second, nullptr, 1);
1065
14
      else if (P.first && 
!P.first->IsPreemptible11
) {
1066
4
        // If we are emitting PIC code with relocations we mustn't write
1067
4
        // anything to the GOT here. When using Elf_Rel relocations the value
1068
4
        // one will be treated as an addend and will cause crashes at runtime
1069
4
        if (!Config->Pic)
1070
3
          Write(P.second, nullptr, 1);
1071
4
        Write(P.second + 1, P.first, -0x8000);
1072
4
      }
1073
17
    }
1074
57
  }
1075
158
}
1076
1077
// On PowerPC the .plt section is used to hold the table of function addresses
1078
// instead of the .got.plt, and the type is SHT_NOBITS similar to a .bss
1079
// section. I don't know why we have a BSS style type for the section but it is
1080
// consitent across both 64-bit PowerPC ABIs as well as the 32-bit PowerPC ABI.
1081
GotPltSection::GotPltSection()
1082
    : SyntheticSection(SHF_ALLOC | SHF_WRITE,
1083
                       Config->EMachine == EM_PPC64 ? SHT_NOBITS : SHT_PROGBITS,
1084
                       Target->GotPltEntrySize,
1085
2.23k
                       Config->EMachine == EM_PPC64 ? ".plt" : ".got.plt") {}
1086
1087
284
void GotPltSection::addEntry(Symbol &Sym) {
1088
284
  assert(Sym.PltIndex == Entries.size());
1089
284
  Entries.push_back(&Sym);
1090
284
}
1091
1092
652
size_t GotPltSection::getSize() const {
1093
652
  return (Target->GotPltHeaderEntriesNum + Entries.size()) *
1094
652
         Target->GotPltEntrySize;
1095
652
}
1096
1097
208
void GotPltSection::writeTo(uint8_t *Buf) {
1098
208
  Target->writeGotPltHeader(Buf);
1099
208
  Buf += Target->GotPltHeaderEntriesNum * Target->GotPltEntrySize;
1100
262
  for (const Symbol *B : Entries) {
1101
262
    Target->writeGotPlt(Buf, *B);
1102
262
    Buf += Config->Wordsize;
1103
262
  }
1104
208
}
1105
1106
4.25k
bool GotPltSection::empty() const {
1107
4.25k
  // We need to emit a GOT.PLT even if it's empty if there's a symbol that
1108
4.25k
  // references the _GLOBAL_OFFSET_TABLE_ and the Target defines the symbol
1109
4.25k
  // relative to the .got.plt section.
1110
4.25k
  return Entries.empty() &&
1111
4.25k
         
!(3.84k
ElfSym::GlobalOffsetTable3.84k
&&
Target->GotBaseSymInGotPlt90
);
1112
4.25k
}
1113
1114
2.23k
static StringRef getIgotPltName() {
1115
2.23k
  // On ARM the IgotPltSection is part of the GotSection.
1116
2.23k
  if (Config->EMachine == EM_ARM)
1117
131
    return ".got";
1118
2.10k
1119
2.10k
  // On PowerPC64 the GotPltSection is renamed to '.plt' so the IgotPltSection
1120
2.10k
  // needs to be named the same.
1121
2.10k
  if (Config->EMachine == EM_PPC64)
1122
83
    return ".plt";
1123
2.01k
1124
2.01k
  return ".got.plt";
1125
2.01k
}
1126
1127
// On PowerPC64 the GotPltSection type is SHT_NOBITS so we have to follow suit
1128
// with the IgotPltSection.
1129
IgotPltSection::IgotPltSection()
1130
    : SyntheticSection(SHF_ALLOC | SHF_WRITE,
1131
                       Config->EMachine == EM_PPC64 ? SHT_NOBITS : SHT_PROGBITS,
1132
2.23k
                       Target->GotPltEntrySize, getIgotPltName()) {}
1133
1134
32
void IgotPltSection::addEntry(Symbol &Sym) {
1135
32
  Sym.IsInIgot = true;
1136
32
  assert(Sym.PltIndex == Entries.size());
1137
32
  Entries.push_back(&Sym);
1138
32
}
1139
1140
61
size_t IgotPltSection::getSize() const {
1141
61
  return Entries.size() * Target->GotPltEntrySize;
1142
61
}
1143
1144
17
void IgotPltSection::writeTo(uint8_t *Buf) {
1145
30
  for (const Symbol *B : Entries) {
1146
30
    Target->writeIgotPlt(Buf, *B);
1147
30
    Buf += Config->Wordsize;
1148
30
  }
1149
17
}
1150
1151
StringTableSection::StringTableSection(StringRef Name, bool Dynamic)
1152
    : SyntheticSection(Dynamic ? (uint64_t)SHF_ALLOC : 0, SHT_STRTAB, 1, Name),
1153
6.69k
      Dynamic(Dynamic) {
1154
6.69k
  // ELF string tables start with a NUL byte.
1155
6.69k
  addString("");
1156
6.69k
}
1157
1158
// Adds a string to the string table. If HashIt is true we hash and check for
1159
// duplicates. It is optional because the name of global symbols are already
1160
// uniqued and hashing them again has a big cost for a small value: uniquing
1161
// them with some other string that happens to be the same.
1162
441k
unsigned StringTableSection::addString(StringRef S, bool HashIt) {
1163
441k
  if (HashIt) {
1164
423k
    auto R = StringMap.insert(std::make_pair(S, this->Size));
1165
423k
    if (!R.second)
1166
66.0k
      return R.first->second;
1167
375k
  }
1168
375k
  unsigned Ret = this->Size;
1169
375k
  this->Size = this->Size + S.size() + 1;
1170
375k
  Strings.push_back(S);
1171
375k
  return Ret;
1172
375k
}
1173
1174
5.23k
void StringTableSection::writeTo(uint8_t *Buf) {
1175
373k
  for (StringRef S : Strings) {
1176
373k
    memcpy(Buf, S.data(), S.size());
1177
373k
    Buf[S.size()] = '\0';
1178
373k
    Buf += S.size() + 1;
1179
373k
  }
1180
5.23k
}
1181
1182
// Returns the number of version definition entries. Because the first entry
1183
// is for the version definition itself, it is the number of versioned symbols
1184
// plus one. Note that we don't support multiple versions yet.
1185
1.34k
static unsigned getVerDefNum() { return Config->VersionDefinitions.size() + 1; }
1186
1187
template <class ELFT>
1188
DynamicSection<ELFT>::DynamicSection()
1189
    : SyntheticSection(SHF_ALLOC | SHF_WRITE, SHT_DYNAMIC, Config->Wordsize,
1190
2.23k
                       ".dynamic") {
1191
2.23k
  this->Entsize = ELFT::Is64Bits ? 
161.84k
:
8388
;
1192
2.23k
1193
2.23k
  // .dynamic section is not writable on MIPS and on Fuchsia OS
1194
2.23k
  // which passes -z rodynamic.
1195
2.23k
  // See "Special Section" in Chapter 4 in the following document:
1196
2.23k
  // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf
1197
2.23k
  if (Config->EMachine == EM_MIPS || 
Config->ZRodynamic2.05k
)
1198
182
    this->Flags = SHF_ALLOC;
1199
2.23k
1200
2.23k
  // Add strings to .dynstr early so that .dynstr's size will be
1201
2.23k
  // fixed early.
1202
2.23k
  for (StringRef S : Config->FilterList)
1203
6
    addInt(DT_FILTER, InX::DynStrTab->addString(S));
1204
2.23k
  for (StringRef S : Config->AuxiliaryList)
1205
4
    addInt(DT_AUXILIARY, InX::DynStrTab->addString(S));
1206
2.23k
1207
2.23k
  if (!Config->Rpath.empty())
1208
8
    addInt(Config->EnableNewDtags ? 
DT_RUNPATH7
:
DT_RPATH1
,
1209
8
           InX::DynStrTab->addString(Config->Rpath));
1210
2.23k
1211
2.23k
  for (InputFile *File : SharedFiles) {
1212
327
    SharedFile<ELFT> *F = cast<SharedFile<ELFT>>(File);
1213
327
    if (F->IsNeeded)
1214
312
      addInt(DT_NEEDED, InX::DynStrTab->addString(F->SoName));
1215
327
  }
1216
2.23k
  if (!Config->SoName.empty())
1217
27
    addInt(DT_SONAME, InX::DynStrTab->addString(Config->SoName));
1218
2.23k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::DynamicSection()
Line
Count
Source
1190
269
                       ".dynamic") {
1191
269
  this->Entsize = ELFT::Is64Bits ? 
160
: 8;
1192
269
1193
269
  // .dynamic section is not writable on MIPS and on Fuchsia OS
1194
269
  // which passes -z rodynamic.
1195
269
  // See "Special Section" in Chapter 4 in the following document:
1196
269
  // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf
1197
269
  if (Config->EMachine == EM_MIPS || 
Config->ZRodynamic252
)
1198
17
    this->Flags = SHF_ALLOC;
1199
269
1200
269
  // Add strings to .dynstr early so that .dynstr's size will be
1201
269
  // fixed early.
1202
269
  for (StringRef S : Config->FilterList)
1203
0
    addInt(DT_FILTER, InX::DynStrTab->addString(S));
1204
269
  for (StringRef S : Config->AuxiliaryList)
1205
0
    addInt(DT_AUXILIARY, InX::DynStrTab->addString(S));
1206
269
1207
269
  if (!Config->Rpath.empty())
1208
2
    addInt(Config->EnableNewDtags ? DT_RUNPATH : 
DT_RPATH0
,
1209
2
           InX::DynStrTab->addString(Config->Rpath));
1210
269
1211
269
  for (InputFile *File : SharedFiles) {
1212
53
    SharedFile<ELFT> *F = cast<SharedFile<ELFT>>(File);
1213
53
    if (F->IsNeeded)
1214
47
      addInt(DT_NEEDED, InX::DynStrTab->addString(F->SoName));
1215
53
  }
1216
269
  if (!Config->SoName.empty())
1217
4
    addInt(DT_SONAME, InX::DynStrTab->addString(Config->SoName));
1218
269
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::DynamicSection()
Line
Count
Source
1190
119
                       ".dynamic") {
1191
119
  this->Entsize = ELFT::Is64Bits ? 
160
: 8;
1192
119
1193
119
  // .dynamic section is not writable on MIPS and on Fuchsia OS
1194
119
  // which passes -z rodynamic.
1195
119
  // See "Special Section" in Chapter 4 in the following document:
1196
119
  // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf
1197
119
  if (Config->EMachine == EM_MIPS || 
Config->ZRodynamic3
)
1198
116
    this->Flags = SHF_ALLOC;
1199
119
1200
119
  // Add strings to .dynstr early so that .dynstr's size will be
1201
119
  // fixed early.
1202
119
  for (StringRef S : Config->FilterList)
1203
0
    addInt(DT_FILTER, InX::DynStrTab->addString(S));
1204
119
  for (StringRef S : Config->AuxiliaryList)
1205
0
    addInt(DT_AUXILIARY, InX::DynStrTab->addString(S));
1206
119
1207
119
  if (!Config->Rpath.empty())
1208
0
    addInt(Config->EnableNewDtags ? DT_RUNPATH : DT_RPATH,
1209
0
           InX::DynStrTab->addString(Config->Rpath));
1210
119
1211
119
  for (InputFile *File : SharedFiles) {
1212
24
    SharedFile<ELFT> *F = cast<SharedFile<ELFT>>(File);
1213
24
    if (F->IsNeeded)
1214
24
      addInt(DT_NEEDED, InX::DynStrTab->addString(F->SoName));
1215
24
  }
1216
119
  if (!Config->SoName.empty())
1217
0
    addInt(DT_SONAME, InX::DynStrTab->addString(Config->SoName));
1218
119
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::DynamicSection()
Line
Count
Source
1190
1.76k
                       ".dynamic") {
1191
1.76k
  this->Entsize = ELFT::Is64Bits ? 16 : 
80
;
1192
1.76k
1193
1.76k
  // .dynamic section is not writable on MIPS and on Fuchsia OS
1194
1.76k
  // which passes -z rodynamic.
1195
1.76k
  // See "Special Section" in Chapter 4 in the following document:
1196
1.76k
  // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf
1197
1.76k
  if (Config->EMachine == EM_MIPS || 
Config->ZRodynamic1.75k
)
1198
5
    this->Flags = SHF_ALLOC;
1199
1.76k
1200
1.76k
  // Add strings to .dynstr early so that .dynstr's size will be
1201
1.76k
  // fixed early.
1202
1.76k
  for (StringRef S : Config->FilterList)
1203
6
    addInt(DT_FILTER, InX::DynStrTab->addString(S));
1204
1.76k
  for (StringRef S : Config->AuxiliaryList)
1205
4
    addInt(DT_AUXILIARY, InX::DynStrTab->addString(S));
1206
1.76k
1207
1.76k
  if (!Config->Rpath.empty())
1208
5
    addInt(Config->EnableNewDtags ? 
DT_RUNPATH4
:
DT_RPATH1
,
1209
5
           InX::DynStrTab->addString(Config->Rpath));
1210
1.76k
1211
1.76k
  for (InputFile *File : SharedFiles) {
1212
234
    SharedFile<ELFT> *F = cast<SharedFile<ELFT>>(File);
1213
234
    if (F->IsNeeded)
1214
225
      addInt(DT_NEEDED, InX::DynStrTab->addString(F->SoName));
1215
234
  }
1216
1.76k
  if (!Config->SoName.empty())
1217
23
    addInt(DT_SONAME, InX::DynStrTab->addString(Config->SoName));
1218
1.76k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::DynamicSection()
Line
Count
Source
1190
85
                       ".dynamic") {
1191
85
  this->Entsize = ELFT::Is64Bits ? 16 : 
80
;
1192
85
1193
85
  // .dynamic section is not writable on MIPS and on Fuchsia OS
1194
85
  // which passes -z rodynamic.
1195
85
  // See "Special Section" in Chapter 4 in the following document:
1196
85
  // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf
1197
85
  if (Config->EMachine == EM_MIPS || 
Config->ZRodynamic41
)
1198
44
    this->Flags = SHF_ALLOC;
1199
85
1200
85
  // Add strings to .dynstr early so that .dynstr's size will be
1201
85
  // fixed early.
1202
85
  for (StringRef S : Config->FilterList)
1203
0
    addInt(DT_FILTER, InX::DynStrTab->addString(S));
1204
85
  for (StringRef S : Config->AuxiliaryList)
1205
0
    addInt(DT_AUXILIARY, InX::DynStrTab->addString(S));
1206
85
1207
85
  if (!Config->Rpath.empty())
1208
1
    addInt(Config->EnableNewDtags ? DT_RUNPATH : 
DT_RPATH0
,
1209
1
           InX::DynStrTab->addString(Config->Rpath));
1210
85
1211
85
  for (InputFile *File : SharedFiles) {
1212
16
    SharedFile<ELFT> *F = cast<SharedFile<ELFT>>(File);
1213
16
    if (F->IsNeeded)
1214
16
      addInt(DT_NEEDED, InX::DynStrTab->addString(F->SoName));
1215
16
  }
1216
85
  if (!Config->SoName.empty())
1217
0
    addInt(DT_SONAME, InX::DynStrTab->addString(Config->SoName));
1218
85
}
1219
1220
template <class ELFT>
1221
100
void DynamicSection<ELFT>::add(int32_t Tag, std::function<uint64_t()> Fn) {
1222
100
  Entries.push_back({Tag, Fn});
1223
100
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::add(int, std::__1::function<unsigned long long ()>)
Line
Count
Source
1221
8
void DynamicSection<ELFT>::add(int32_t Tag, std::function<uint64_t()> Fn) {
1222
8
  Entries.push_back({Tag, Fn});
1223
8
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::add(int, std::__1::function<unsigned long long ()>)
Line
Count
Source
1221
69
void DynamicSection<ELFT>::add(int32_t Tag, std::function<uint64_t()> Fn) {
1222
69
  Entries.push_back({Tag, Fn});
1223
69
}
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::add(int, std::__1::function<unsigned long long ()>)
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::add(int, std::__1::function<unsigned long long ()>)
Line
Count
Source
1221
23
void DynamicSection<ELFT>::add(int32_t Tag, std::function<uint64_t()> Fn) {
1222
23
  Entries.push_back({Tag, Fn});
1223
23
}
1224
1225
template <class ELFT>
1226
4.90k
void DynamicSection<ELFT>::addInt(int32_t Tag, uint64_t Val) {
1227
4.90k
  Entries.push_back({Tag, [=] 
{ return Val; }4.85k
});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addInt(int, unsigned long long)::'lambda'()::operator()() const
Line
Count
Source
1227
648
  Entries.push_back({Tag, [=] { return Val; }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addInt(int, unsigned long long)::'lambda'()::operator()() const
Line
Count
Source
1227
624
  Entries.push_back({Tag, [=] { return Val; }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addInt(int, unsigned long long)::'lambda'()::operator()() const
Line
Count
Source
1227
3.24k
  Entries.push_back({Tag, [=] { return Val; }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addInt(int, unsigned long long)::'lambda'()::operator()() const
Line
Count
Source
1227
333
  Entries.push_back({Tag, [=] { return Val; }});
1228
4.90k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addInt(int, unsigned long long)
Line
Count
Source
1226
649
void DynamicSection<ELFT>::addInt(int32_t Tag, uint64_t Val) {
1227
649
  Entries.push_back({Tag, [=] { return Val; }});
1228
649
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addInt(int, unsigned long long)
Line
Count
Source
1226
624
void DynamicSection<ELFT>::addInt(int32_t Tag, uint64_t Val) {
1227
624
  Entries.push_back({Tag, [=] { return Val; }});
1228
624
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addInt(int, unsigned long long)
Line
Count
Source
1226
3.30k
void DynamicSection<ELFT>::addInt(int32_t Tag, uint64_t Val) {
1227
3.30k
  Entries.push_back({Tag, [=] { return Val; }});
1228
3.30k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addInt(int, unsigned long long)
Line
Count
Source
1226
333
void DynamicSection<ELFT>::addInt(int32_t Tag, uint64_t Val) {
1227
333
  Entries.push_back({Tag, [=] { return Val; }});
1228
333
}
1229
1230
template <class ELFT>
1231
4.90k
void DynamicSection<ELFT>::addInSec(int32_t Tag, InputSection *Sec) {
1232
4.90k
  Entries.push_back({Tag, [=] 
{ return Sec->getVA(0); }4.86k
});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addInSec(int, lld::elf::InputSection*)::'lambda'()::operator()() const
Line
Count
Source
1232
639
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addInSec(int, lld::elf::InputSection*)::'lambda'()::operator()() const
Line
Count
Source
1232
334
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addInSec(int, lld::elf::InputSection*)::'lambda'()::operator()() const
Line
Count
Source
1232
3.64k
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addInSec(int, lld::elf::InputSection*)::'lambda'()::operator()() const
Line
Count
Source
1232
246
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
1233
4.90k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addInSec(int, lld::elf::InputSection*)
Line
Count
Source
1231
639
void DynamicSection<ELFT>::addInSec(int32_t Tag, InputSection *Sec) {
1232
639
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
1233
639
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addInSec(int, lld::elf::InputSection*)
Line
Count
Source
1231
334
void DynamicSection<ELFT>::addInSec(int32_t Tag, InputSection *Sec) {
1232
334
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
1233
334
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addInSec(int, lld::elf::InputSection*)
Line
Count
Source
1231
3.68k
void DynamicSection<ELFT>::addInSec(int32_t Tag, InputSection *Sec) {
1232
3.68k
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
1233
3.68k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addInSec(int, lld::elf::InputSection*)
Line
Count
Source
1231
246
void DynamicSection<ELFT>::addInSec(int32_t Tag, InputSection *Sec) {
1232
246
  Entries.push_back({Tag, [=] { return Sec->getVA(0); }});
1233
246
}
1234
1235
template <class ELFT>
1236
29
void DynamicSection<ELFT>::addInSecRelative(int32_t Tag, InputSection *Sec) {
1237
29
  size_t TagOffset = Entries.size() * Entsize;
1238
29
  Entries.push_back(
1239
29
      {Tag, [=] { return Sec->getVA(0) - (getVA() + TagOffset); }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addInSecRelative(int, lld::elf::InputSection*)::'lambda'()::operator()() const
Line
Count
Source
1239
2
      {Tag, [=] { return Sec->getVA(0) - (getVA() + TagOffset); }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addInSecRelative(int, lld::elf::InputSection*)::'lambda'()::operator()() const
Line
Count
Source
1239
21
      {Tag, [=] { return Sec->getVA(0) - (getVA() + TagOffset); }});
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addInSecRelative(int, lld::elf::InputSection*)::'lambda'()::operator()() const
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addInSecRelative(int, lld::elf::InputSection*)::'lambda'()::operator()() const
Line
Count
Source
1239
6
      {Tag, [=] { return Sec->getVA(0) - (getVA() + TagOffset); }});
1240
29
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addInSecRelative(int, lld::elf::InputSection*)
Line
Count
Source
1236
2
void DynamicSection<ELFT>::addInSecRelative(int32_t Tag, InputSection *Sec) {
1237
2
  size_t TagOffset = Entries.size() * Entsize;
1238
2
  Entries.push_back(
1239
2
      {Tag, [=] { return Sec->getVA(0) - (getVA() + TagOffset); }});
1240
2
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addInSecRelative(int, lld::elf::InputSection*)
Line
Count
Source
1236
21
void DynamicSection<ELFT>::addInSecRelative(int32_t Tag, InputSection *Sec) {
1237
21
  size_t TagOffset = Entries.size() * Entsize;
1238
21
  Entries.push_back(
1239
21
      {Tag, [=] { return Sec->getVA(0) - (getVA() + TagOffset); }});
1240
21
}
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addInSecRelative(int, lld::elf::InputSection*)
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addInSecRelative(int, lld::elf::InputSection*)
Line
Count
Source
1236
6
void DynamicSection<ELFT>::addInSecRelative(int32_t Tag, InputSection *Sec) {
1237
6
  size_t TagOffset = Entries.size() * Entsize;
1238
6
  Entries.push_back(
1239
6
      {Tag, [=] { return Sec->getVA(0) - (getVA() + TagOffset); }});
1240
6
}
1241
1242
template <class ELFT>
1243
8
void DynamicSection<ELFT>::addOutSec(int32_t Tag, OutputSection *Sec) {
1244
8
  Entries.push_back({Tag, [=] { return Sec->Addr; }});
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addOutSec(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addOutSec(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addOutSec(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
Line
Count
Source
1244
8
  Entries.push_back({Tag, [=] { return Sec->Addr; }});
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addOutSec(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
1245
8
}
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addOutSec(int, lld::elf::OutputSection*)
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addOutSec(int, lld::elf::OutputSection*)
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addOutSec(int, lld::elf::OutputSection*)
Line
Count
Source
1243
8
void DynamicSection<ELFT>::addOutSec(int32_t Tag, OutputSection *Sec) {
1244
8
  Entries.push_back({Tag, [=] { return Sec->Addr; }});
1245
8
}
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addOutSec(int, lld::elf::OutputSection*)
1246
1247
template <class ELFT>
1248
433
void DynamicSection<ELFT>::addSize(int32_t Tag, OutputSection *Sec) {
1249
433
  Entries.push_back({Tag, [=] 
{ return Sec->Size; }429
});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addSize(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
Line
Count
Source
1249
83
  Entries.push_back({Tag, [=] { return Sec->Size; }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addSize(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
Line
Count
Source
1249
19
  Entries.push_back({Tag, [=] { return Sec->Size; }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addSize(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
Line
Count
Source
1249
298
  Entries.push_back({Tag, [=] { return Sec->Size; }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addSize(int, lld::elf::OutputSection*)::'lambda'()::operator()() const
Line
Count
Source
1249
29
  Entries.push_back({Tag, [=] { return Sec->Size; }});
1250
433
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addSize(int, lld::elf::OutputSection*)
Line
Count
Source
1248
83
void DynamicSection<ELFT>::addSize(int32_t Tag, OutputSection *Sec) {
1249
83
  Entries.push_back({Tag, [=] { return Sec->Size; }});
1250
83
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addSize(int, lld::elf::OutputSection*)
Line
Count
Source
1248
19
void DynamicSection<ELFT>::addSize(int32_t Tag, OutputSection *Sec) {
1249
19
  Entries.push_back({Tag, [=] { return Sec->Size; }});
1250
19
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addSize(int, lld::elf::OutputSection*)
Line
Count
Source
1248
302
void DynamicSection<ELFT>::addSize(int32_t Tag, OutputSection *Sec) {
1249
302
  Entries.push_back({Tag, [=] { return Sec->Size; }});
1250
302
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addSize(int, lld::elf::OutputSection*)
Line
Count
Source
1248
29
void DynamicSection<ELFT>::addSize(int32_t Tag, OutputSection *Sec) {
1249
29
  Entries.push_back({Tag, [=] { return Sec->Size; }});
1250
29
}
1251
1252
template <class ELFT>
1253
8
void DynamicSection<ELFT>::addSym(int32_t Tag, Symbol *Sym) {
1254
8
  Entries.push_back({Tag, [=] { return Sym->getVA(); }});
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addSym(int, lld::elf::Symbol*)::'lambda'()::operator()() const
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addSym(int, lld::elf::Symbol*)::'lambda'()::operator()() const
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addSym(int, lld::elf::Symbol*)::'lambda'()::operator()() const
Line
Count
Source
1254
8
  Entries.push_back({Tag, [=] { return Sym->getVA(); }});
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addSym(int, lld::elf::Symbol*)::'lambda'()::operator()() const
1255
8
}
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::addSym(int, lld::elf::Symbol*)
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::addSym(int, lld::elf::Symbol*)
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::addSym(int, lld::elf::Symbol*)
Line
Count
Source
1253
8
void DynamicSection<ELFT>::addSym(int32_t Tag, Symbol *Sym) {
1254
8
  Entries.push_back({Tag, [=] { return Sym->getVA(); }});
1255
8
}
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::addSym(int, lld::elf::Symbol*)
1256
1257
// Add remaining entries to complete .dynamic contents.
1258
1.06k
template <class ELFT> void DynamicSection<ELFT>::finalizeContents() {
1259
1.06k
  if (this->Size)
1260
0
    return; // Already finalized.
1261
1.06k
1262
1.06k
  // Set DT_FLAGS and DT_FLAGS_1.
1263
1.06k
  uint32_t DtFlags = 0;
1264
1.06k
  uint32_t DtFlags1 = 0;
1265
1.06k
  if (Config->Bsymbolic)
1266
6
    DtFlags |= DF_SYMBOLIC;
1267
1.06k
  if (Config->ZInitfirst)
1268
1
    DtFlags1 |= DF_1_INITFIRST;
1269
1.06k
  if (Config->ZNodelete)
1270
1
    DtFlags1 |= DF_1_NODELETE;
1271
1.06k
  if (Config->ZNodlopen)
1272
1
    DtFlags1 |= DF_1_NOOPEN;
1273
1.06k
  if (Config->ZNow) {
1274
4
    DtFlags |= DF_BIND_NOW;
1275
4
    DtFlags1 |= DF_1_NOW;
1276
4
  }
1277
1.06k
  if (Config->ZOrigin) {
1278
1
    DtFlags |= DF_ORIGIN;
1279
1
    DtFlags1 |= DF_1_ORIGIN;
1280
1
  }
1281
1.06k
  if (!Config->ZText)
1282
11
    DtFlags |= DF_TEXTREL;
1283
1.06k
1284
1.06k
  if (DtFlags)
1285
20
    addInt(DT_FLAGS, DtFlags);
1286
1.06k
  if (DtFlags1)
1287
4
    addInt(DT_FLAGS_1, DtFlags1);
1288
1.06k
1289
1.06k
  // DT_DEBUG is a pointer to debug informaion used by debuggers at runtime. We
1290
1.06k
  // need it for each process, so we don't write it for DSOs. The loader writes
1291
1.06k
  // the pointer into this entry.
1292
1.06k
  //
1293
1.06k
  // DT_DEBUG is the only .dynamic entry that needs to be written to. Some
1294
1.06k
  // systems (currently only Fuchsia OS) provide other means to give the
1295
1.06k
  // debugger this information. Such systems may choose make .dynamic read-only.
1296
1.06k
  // If the target is such a system (used -z rodynamic) don't write DT_DEBUG.
1297
1.06k
  if (!Config->Shared && 
!Config->Relocatable292
&&
!Config->ZRodynamic290
)
1298
289
    addInt(DT_DEBUG, 0);
1299
1.06k
1300
1.06k
  this->Link = InX::DynStrTab->getParent()->SectionIndex;
1301
1.06k
  if (!InX::RelaDyn->empty()) {
1302
214
    addInSec(InX::RelaDyn->DynamicTag, InX::RelaDyn);
1303
214
    addSize(InX::RelaDyn->SizeDynamicTag, InX::RelaDyn->getParent());
1304
214
1305
214
    bool IsRela = Config->IsRela;
1306
214
    addInt(IsRela ? 
DT_RELAENT153
:
DT_RELENT61
,
1307
214
           IsRela ? 
sizeof(Elf_Rela)153
:
sizeof(Elf_Rel)61
);
1308
214
1309
214
    // MIPS dynamic loader does not support RELCOUNT tag.
1310
214
    // The problem is in the tight relation between dynamic
1311
214
    // relocations and GOT. So do not emit this tag on MIPS.
1312
214
    if (Config->EMachine != EM_MIPS) {
1313
198
      size_t NumRelativeRels = InX::RelaDyn->getRelativeRelocCount();
1314
198
      if (Config->ZCombreloc && 
NumRelativeRels197
)
1315
42
        addInt(IsRela ? 
DT_RELACOUNT29
:
DT_RELCOUNT13
, NumRelativeRels);
1316
198
    }
1317
214
  }
1318
1.06k
  if (InX::RelrDyn && 
!InX::RelrDyn->Relocs.empty()3
) {
1319
3
    addInSec(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELR0
: DT_RELR,
1320
3
             InX::RelrDyn);
1321
3
    addSize(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELRSZ0
: DT_RELRSZ,
1322
3
            InX::RelrDyn->getParent());
1323
3
    addInt(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELRENT0
: DT_RELRENT,
1324
3
           sizeof(Elf_Relr));
1325
3
  }
1326
1.06k
  // .rel[a].plt section usually consists of two parts, containing plt and
1327
1.06k
  // iplt relocations. It is possible to have only iplt relocations in the
1328
1.06k
  // output. In that case RelaPlt is empty and have zero offset, the same offset
1329
1.06k
  // as RelaIplt have. And we still want to emit proper dynamic tags for that
1330
1.06k
  // case, so here we always use RelaPlt as marker for the begining of
1331
1.06k
  // .rel[a].plt section.
1332
1.06k
  if (InX::RelaPlt->getParent()->Live) {
1333
208
    addInSec(DT_JMPREL, InX::RelaPlt);
1334
208
    addSize(DT_PLTRELSZ, InX::RelaPlt->getParent());
1335
208
    switch (Config->EMachine) {
1336
208
    case EM_MIPS:
1337
15
      addInSec(DT_MIPS_PLTGOT, InX::GotPlt);
1338
15
      break;
1339
208
    case EM_SPARCV9:
1340
0
      addInSec(DT_PLTGOT, InX::Plt);
1341
0
      break;
1342
208
    default:
1343
193
      addInSec(DT_PLTGOT, InX::GotPlt);
1344
193
      break;
1345
208
    }
1346
208
    addInt(DT_PLTREL, Config->IsRela ? 
DT_RELA161
:
DT_REL47
);
1347
208
  }
1348
1.06k
1349
1.06k
  addInSec(DT_SYMTAB, InX::DynSymTab);
1350
1.06k
  addInt(DT_SYMENT, sizeof(Elf_Sym));
1351
1.06k
  addInSec(DT_STRTAB, InX::DynStrTab);
1352
1.06k
  addInt(DT_STRSZ, InX::DynStrTab->getSize());
1353
1.06k
  if (!Config->ZText)
1354
11
    addInt(DT_TEXTREL, 0);
1355
1.06k
  if (InX::GnuHashTab)
1356
835
    addInSec(DT_GNU_HASH, InX::GnuHashTab);
1357
1.06k
  if (InX::HashTab)
1358
1.05k
    addInSec(DT_HASH, InX::HashTab);
1359
1.06k
1360
1.06k
  if (Out::PreinitArray) {
1361
3
    addOutSec(DT_PREINIT_ARRAY, Out::PreinitArray);
1362
3
    addSize(DT_PREINIT_ARRAYSZ, Out::PreinitArray);
1363
3
  }
1364
1.06k
  if (Out::InitArray) {
1365
3
    addOutSec(DT_INIT_ARRAY, Out::InitArray);
1366
3
    addSize(DT_INIT_ARRAYSZ, Out::InitArray);
1367
3
  }
1368
1.06k
  if (Out::FiniArray) {
1369
2
    addOutSec(DT_FINI_ARRAY, Out::FiniArray);
1370
2
    addSize(DT_FINI_ARRAYSZ, Out::FiniArray);
1371
2
  }
1372
1.06k
1373
1.06k
  if (Symbol *B = Symtab->find(Config->Init))
1374
6
    if (B->isDefined())
1375
4
      addSym(DT_INIT, B);
1376
1.06k
  if (Symbol *B = Symtab->find(Config->Fini))
1377
6
    if (B->isDefined())
1378
4
      addSym(DT_FINI, B);
1379
1.06k
1380
1.06k
  bool HasVerNeed = In<ELFT>::VerNeed->getNeedNum() != 0;
1381
1.06k
  if (HasVerNeed || 
In<ELFT>::VerDef1.05k
)
1382
59
    addInSec(DT_VERSYM, In<ELFT>::VerSym);
1383
1.06k
  if (In<ELFT>::VerDef) {
1384
52
    addInSec(DT_VERDEF, In<ELFT>::VerDef);
1385
52
    addInt(DT_VERDEFNUM, getVerDefNum());
1386
52
  }
1387
1.06k
  if (HasVerNeed) {
1388
8
    addInSec(DT_VERNEED, In<ELFT>::VerNeed);
1389
8
    addInt(DT_VERNEEDNUM, In<ELFT>::VerNeed->getNeedNum());
1390
8
  }
1391
1.06k
1392
1.06k
  if (Config->EMachine == EM_MIPS) {
1393
100
    addInt(DT_MIPS_RLD_VERSION, 1);
1394
100
    addInt(DT_MIPS_FLAGS, RHF_NOTPOT);
1395
100
    addInt(DT_MIPS_BASE_ADDRESS, Target->getImageBase());
1396
100
    addInt(DT_MIPS_SYMTABNO, InX::DynSymTab->getNumSymbols());
1397
100
1398
100
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::finalizeContents()::'lambda'()::operator()() const
Line
Count
Source
1398
8
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::finalizeContents()::'lambda'()::operator()() const
Line
Count
Source
1398
69
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::finalizeContents()::'lambda'()::operator()() const
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::finalizeContents()::'lambda'()::operator()() const
Line
Count
Source
1398
23
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
1399
100
1400
100
    if (const Symbol *B = InX::MipsGot->getFirstGlobalEntry())
1401
32
      addInt(DT_MIPS_GOTSYM, B->DynsymIndex);
1402
68
    else
1403
68
      addInt(DT_MIPS_GOTSYM, InX::DynSymTab->getNumSymbols());
1404
100
    addInSec(DT_PLTGOT, InX::MipsGot);
1405
100
    if (InX::MipsRldMap) {
1406
29
      if (!Config->Pie)
1407
26
        addInSec(DT_MIPS_RLD_MAP, InX::MipsRldMap);
1408
29
      // Store the offset to the .rld_map section
1409
29
      // relative to the address of the tag.
1410
29
      addInSecRelative(DT_MIPS_RLD_MAP_REL, InX::MipsRldMap);
1411
29
    }
1412
100
  }
1413
1.06k
1414
1.06k
  // Glink dynamic tag is required by the V2 abi if the plt section isn't empty.
1415
1.06k
  if (Config->EMachine == EM_PPC64 && 
!InX::Plt->empty()55
) {
1416
20
    // The Glink tag points to 32 bytes before the first lazy symbol resolution
1417
20
    // stub, which starts directly after the header.
1418
20
    Entries.push_back({DT_PPC64_GLINK, [=] {
1419
20
                         unsigned Offset = Target->PltHeaderSize - 32;
1420
20
                         return InX::Plt->getVA(0) + Offset;
1421
20
                       }});
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::finalizeContents()::'lambda0'()::operator()() const
Unexecuted instantiation: lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::finalizeContents()::'lambda0'()::operator()() const
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::finalizeContents()::'lambda0'()::operator()() const
Line
Count
Source
1418
10
    Entries.push_back({DT_PPC64_GLINK, [=] {
1419
10
                         unsigned Offset = Target->PltHeaderSize - 32;
1420
10
                         return InX::Plt->getVA(0) + Offset;
1421
10
                       }});
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::finalizeContents()::'lambda0'()::operator()() const
Line
Count
Source
1418
10
    Entries.push_back({DT_PPC64_GLINK, [=] {
1419
10
                         unsigned Offset = Target->PltHeaderSize - 32;
1420
10
                         return InX::Plt->getVA(0) + Offset;
1421
10
                       }});
1422
20
  }
1423
1.06k
1424
1.06k
  addInt(DT_NULL, 0);
1425
1.06k
1426
1.06k
  getParent()->Link = this->Link;
1427
1.06k
  this->Size = Entries.size() * this->Entsize;
1428
1.06k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::finalizeContents()
Line
Count
Source
1258
139
template <class ELFT> void DynamicSection<ELFT>::finalizeContents() {
1259
139
  if (this->Size)
1260
0
    return; // Already finalized.
1261
139
1262
139
  // Set DT_FLAGS and DT_FLAGS_1.
1263
139
  uint32_t DtFlags = 0;
1264
139
  uint32_t DtFlags1 = 0;
1265
139
  if (Config->Bsymbolic)
1266
2
    DtFlags |= DF_SYMBOLIC;
1267
139
  if (Config->ZInitfirst)
1268
0
    DtFlags1 |= DF_1_INITFIRST;
1269
139
  if (Config->ZNodelete)
1270
0
    DtFlags1 |= DF_1_NODELETE;
1271
139
  if (Config->ZNodlopen)
1272
0
    DtFlags1 |= DF_1_NOOPEN;
1273
139
  if (Config->ZNow) {
1274
0
    DtFlags |= DF_BIND_NOW;
1275
0
    DtFlags1 |= DF_1_NOW;
1276
0
  }
1277
139
  if (Config->ZOrigin) {
1278
0
    DtFlags |= DF_ORIGIN;
1279
0
    DtFlags1 |= DF_1_ORIGIN;
1280
0
  }
1281
139
  if (!Config->ZText)
1282
0
    DtFlags |= DF_TEXTREL;
1283
139
1284
139
  if (DtFlags)
1285
2
    addInt(DT_FLAGS, DtFlags);
1286
139
  if (DtFlags1)
1287
0
    addInt(DT_FLAGS_1, DtFlags1);
1288
139
1289
139
  // DT_DEBUG is a pointer to debug informaion used by debuggers at runtime. We
1290
139
  // need it for each process, so we don't write it for DSOs. The loader writes
1291
139
  // the pointer into this entry.
1292
139
  //
1293
139
  // DT_DEBUG is the only .dynamic entry that needs to be written to. Some
1294
139
  // systems (currently only Fuchsia OS) provide other means to give the
1295
139
  // debugger this information. Such systems may choose make .dynamic read-only.
1296
139
  // If the target is such a system (used -z rodynamic) don't write DT_DEBUG.
1297
139
  if (!Config->Shared && 
!Config->Relocatable41
&&
!Config->ZRodynamic41
)
1298
41
    addInt(DT_DEBUG, 0);
1299
139
1300
139
  this->Link = InX::DynStrTab->getParent()->SectionIndex;
1301
139
  if (!InX::RelaDyn->empty()) {
1302
46
    addInSec(InX::RelaDyn->DynamicTag, InX::RelaDyn);
1303
46
    addSize(InX::RelaDyn->SizeDynamicTag, InX::RelaDyn->getParent());
1304
46
1305
46
    bool IsRela = Config->IsRela;
1306
46
    addInt(IsRela ? 
DT_RELAENT0
: DT_RELENT,
1307
46
           IsRela ? 
sizeof(Elf_Rela)0
: sizeof(Elf_Rel));
1308
46
1309
46
    // MIPS dynamic loader does not support RELCOUNT tag.
1310
46
    // The problem is in the tight relation between dynamic
1311
46
    // relocations and GOT. So do not emit this tag on MIPS.
1312
46
    if (Config->EMachine != EM_MIPS) {
1313
45
      size_t NumRelativeRels = InX::RelaDyn->getRelativeRelocCount();
1314
45
      if (Config->ZCombreloc && NumRelativeRels)
1315
13
        addInt(IsRela ? 
DT_RELACOUNT0
: DT_RELCOUNT, NumRelativeRels);
1316
45
    }
1317
46
  }
1318
139
  if (InX::RelrDyn && 
!InX::RelrDyn->Relocs.empty()2
) {
1319
2
    addInSec(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELR0
: DT_RELR,
1320
2
             InX::RelrDyn);
1321
2
    addSize(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELRSZ0
: DT_RELRSZ,
1322
2
            InX::RelrDyn->getParent());
1323
2
    addInt(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELRENT0
: DT_RELRENT,
1324
2
           sizeof(Elf_Relr));
1325
2
  }
1326
139
  // .rel[a].plt section usually consists of two parts, containing plt and
1327
139
  // iplt relocations. It is possible to have only iplt relocations in the
1328
139
  // output. In that case RelaPlt is empty and have zero offset, the same offset
1329
139
  // as RelaIplt have. And we still want to emit proper dynamic tags for that
1330
139
  // case, so here we always use RelaPlt as marker for the begining of
1331
139
  // .rel[a].plt section.
1332
139
  if (InX::RelaPlt->getParent()->Live) {
1333
35
    addInSec(DT_JMPREL, InX::RelaPlt);
1334
35
    addSize(DT_PLTRELSZ, InX::RelaPlt->getParent());
1335
35
    switch (Config->EMachine) {
1336
35
    case EM_MIPS:
1337
2
      addInSec(DT_MIPS_PLTGOT, InX::GotPlt);
1338
2
      break;
1339
35
    case EM_SPARCV9:
1340
0
      addInSec(DT_PLTGOT, InX::Plt);
1341
0
      break;
1342
35
    default:
1343
33
      addInSec(DT_PLTGOT, InX::GotPlt);
1344
33
      break;
1345
35
    }
1346
35
    addInt(DT_PLTREL, Config->IsRela ? 
DT_RELA1
:
DT_REL34
);
1347
35
  }
1348
139
1349
139
  addInSec(DT_SYMTAB, InX::DynSymTab);
1350
139
  addInt(DT_SYMENT, sizeof(Elf_Sym));
1351
139
  addInSec(DT_STRTAB, InX::DynStrTab);
1352
139
  addInt(DT_STRSZ, InX::DynStrTab->getSize());
1353
139
  if (!Config->ZText)
1354
0
    addInt(DT_TEXTREL, 0);
1355
139
  if (InX::GnuHashTab)
1356
96
    addInSec(DT_GNU_HASH, InX::GnuHashTab);
1357
139
  if (InX::HashTab)
1358
137
    addInSec(DT_HASH, InX::HashTab);
1359
139
1360
139
  if (Out::PreinitArray) {
1361
0
    addOutSec(DT_PREINIT_ARRAY, Out::PreinitArray);
1362
0
    addSize(DT_PREINIT_ARRAYSZ, Out::PreinitArray);
1363
0
  }
1364
139
  if (Out::InitArray) {
1365
0
    addOutSec(DT_INIT_ARRAY, Out::InitArray);
1366
0
    addSize(DT_INIT_ARRAYSZ, Out::InitArray);
1367
0
  }
1368
139
  if (Out::FiniArray) {
1369
0
    addOutSec(DT_FINI_ARRAY, Out::FiniArray);
1370
0
    addSize(DT_FINI_ARRAYSZ, Out::FiniArray);
1371
0
  }
1372
139
1373
139
  if (Symbol *B = Symtab->find(Config->Init))
1374
0
    if (B->isDefined())
1375
0
      addSym(DT_INIT, B);
1376
139
  if (Symbol *B = Symtab->find(Config->Fini))
1377
0
    if (B->isDefined())
1378
0
      addSym(DT_FINI, B);
1379
139
1380
139
  bool HasVerNeed = In<ELFT>::VerNeed->getNeedNum() != 0;
1381
139
  if (HasVerNeed || In<ELFT>::VerDef)
1382
0
    addInSec(DT_VERSYM, In<ELFT>::VerSym);
1383
139
  if (In<ELFT>::VerDef) {
1384
0
    addInSec(DT_VERDEF, In<ELFT>::VerDef);
1385
0
    addInt(DT_VERDEFNUM, getVerDefNum());
1386
0
  }
1387
139
  if (HasVerNeed) {
1388
0
    addInSec(DT_VERNEED, In<ELFT>::VerNeed);
1389
0
    addInt(DT_VERNEEDNUM, In<ELFT>::VerNeed->getNeedNum());
1390
0
  }
1391
139
1392
139
  if (Config->EMachine == EM_MIPS) {
1393
8
    addInt(DT_MIPS_RLD_VERSION, 1);
1394
8
    addInt(DT_MIPS_FLAGS, RHF_NOTPOT);
1395
8
    addInt(DT_MIPS_BASE_ADDRESS, Target->getImageBase());
1396
8
    addInt(DT_MIPS_SYMTABNO, InX::DynSymTab->getNumSymbols());
1397
8
1398
8
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
1399
8
1400
8
    if (const Symbol *B = InX::MipsGot->getFirstGlobalEntry())
1401
3
      addInt(DT_MIPS_GOTSYM, B->DynsymIndex);
1402
5
    else
1403
5
      addInt(DT_MIPS_GOTSYM, InX::DynSymTab->getNumSymbols());
1404
8
    addInSec(DT_PLTGOT, InX::MipsGot);
1405
8
    if (InX::MipsRldMap) {
1406
2
      if (!Config->Pie)
1407
2
        addInSec(DT_MIPS_RLD_MAP, InX::MipsRldMap);
1408
2
      // Store the offset to the .rld_map section
1409
2
      // relative to the address of the tag.
1410
2
      addInSecRelative(DT_MIPS_RLD_MAP_REL, InX::MipsRldMap);
1411
2
    }
1412
8
  }
1413
139
1414
139
  // Glink dynamic tag is required by the V2 abi if the plt section isn't empty.
1415
139
  if (Config->EMachine == EM_PPC64 && 
!InX::Plt->empty()0
) {
1416
0
    // The Glink tag points to 32 bytes before the first lazy symbol resolution
1417
0
    // stub, which starts directly after the header.
1418
0
    Entries.push_back({DT_PPC64_GLINK, [=] {
1419
0
                         unsigned Offset = Target->PltHeaderSize - 32;
1420
0
                         return InX::Plt->getVA(0) + Offset;
1421
0
                       }});
1422
0
  }
1423
139
1424
139
  addInt(DT_NULL, 0);
1425
139
1426
139
  getParent()->Link = this->Link;
1427
139
  this->Size = Entries.size() * this->Entsize;
1428
139
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::finalizeContents()
Line
Count
Source
1258
71
template <class ELFT> void DynamicSection<ELFT>::finalizeContents() {
1259
71
  if (this->Size)
1260
0
    return; // Already finalized.
1261
71
1262
71
  // Set DT_FLAGS and DT_FLAGS_1.
1263
71
  uint32_t DtFlags = 0;
1264
71
  uint32_t DtFlags1 = 0;
1265
71
  if (Config->Bsymbolic)
1266
1
    DtFlags |= DF_SYMBOLIC;
1267
71
  if (Config->ZInitfirst)
1268
0
    DtFlags1 |= DF_1_INITFIRST;
1269
71
  if (Config->ZNodelete)
1270
0
    DtFlags1 |= DF_1_NODELETE;
1271
71
  if (Config->ZNodlopen)
1272
0
    DtFlags1 |= DF_1_NOOPEN;
1273
71
  if (Config->ZNow) {
1274
0
    DtFlags |= DF_BIND_NOW;
1275
0
    DtFlags1 |= DF_1_NOW;
1276
0
  }
1277
71
  if (Config->ZOrigin) {
1278
0
    DtFlags |= DF_ORIGIN;
1279
0
    DtFlags1 |= DF_1_ORIGIN;
1280
0
  }
1281
71
  if (!Config->ZText)
1282
0
    DtFlags |= DF_TEXTREL;
1283
71
1284
71
  if (DtFlags)
1285
1
    addInt(DT_FLAGS, DtFlags);
1286
71
  if (DtFlags1)
1287
0
    addInt(DT_FLAGS_1, DtFlags1);
1288
71
1289
71
  // DT_DEBUG is a pointer to debug informaion used by debuggers at runtime. We
1290
71
  // need it for each process, so we don't write it for DSOs. The loader writes
1291
71
  // the pointer into this entry.
1292
71
  //
1293
71
  // DT_DEBUG is the only .dynamic entry that needs to be written to. Some
1294
71
  // systems (currently only Fuchsia OS) provide other means to give the
1295
71
  // debugger this information. Such systems may choose make .dynamic read-only.
1296
71
  // If the target is such a system (used -z rodynamic) don't write DT_DEBUG.
1297
71
  if (!Config->Shared && 
!Config->Relocatable21
&&
!Config->ZRodynamic21
)
1298
21
    addInt(DT_DEBUG, 0);
1299
71
1300
71
  this->Link = InX::DynStrTab->getParent()->SectionIndex;
1301
71
  if (!InX::RelaDyn->empty()) {
1302
8
    addInSec(InX::RelaDyn->DynamicTag, InX::RelaDyn);
1303
8
    addSize(InX::RelaDyn->SizeDynamicTag, InX::RelaDyn->getParent());
1304
8
1305
8
    bool IsRela = Config->IsRela;
1306
8
    addInt(IsRela ? 
DT_RELAENT1
:
DT_RELENT7
,
1307
8
           IsRela ? 
sizeof(Elf_Rela)1
:
sizeof(Elf_Rel)7
);
1308
8
1309
8
    // MIPS dynamic loader does not support RELCOUNT tag.
1310
8
    // The problem is in the tight relation between dynamic
1311
8
    // relocations and GOT. So do not emit this tag on MIPS.
1312
8
    if (Config->EMachine != EM_MIPS) {
1313
1
      size_t NumRelativeRels = InX::RelaDyn->getRelativeRelocCount();
1314
1
      if (Config->ZCombreloc && NumRelativeRels)
1315
0
        addInt(IsRela ? DT_RELACOUNT : DT_RELCOUNT, NumRelativeRels);
1316
1
    }
1317
8
  }
1318
71
  if (InX::RelrDyn && 
!InX::RelrDyn->Relocs.empty()0
) {
1319
0
    addInSec(Config->UseAndroidRelrTags ? DT_ANDROID_RELR : DT_RELR,
1320
0
             InX::RelrDyn);
1321
0
    addSize(Config->UseAndroidRelrTags ? DT_ANDROID_RELRSZ : DT_RELRSZ,
1322
0
            InX::RelrDyn->getParent());
1323
0
    addInt(Config->UseAndroidRelrTags ? DT_ANDROID_RELRENT : DT_RELRENT,
1324
0
           sizeof(Elf_Relr));
1325
0
  }
1326
71
  // .rel[a].plt section usually consists of two parts, containing plt and
1327
71
  // iplt relocations. It is possible to have only iplt relocations in the
1328
71
  // output. In that case RelaPlt is empty and have zero offset, the same offset
1329
71
  // as RelaIplt have. And we still want to emit proper dynamic tags for that
1330
71
  // case, so here we always use RelaPlt as marker for the begining of
1331
71
  // .rel[a].plt section.
1332
71
  if (InX::RelaPlt->getParent()->Live) {
1333
11
    addInSec(DT_JMPREL, InX::RelaPlt);
1334
11
    addSize(DT_PLTRELSZ, InX::RelaPlt->getParent());
1335
11
    switch (Config->EMachine) {
1336
11
    case EM_MIPS:
1337
11
      addInSec(DT_MIPS_PLTGOT, InX::GotPlt);
1338
11
      break;
1339
11
    case EM_SPARCV9:
1340
0
      addInSec(DT_PLTGOT, InX::Plt);
1341
0
      break;
1342
11
    default:
1343
0
      addInSec(DT_PLTGOT, InX::GotPlt);
1344
0
      break;
1345
11
    }
1346
11
    addInt(DT_PLTREL, Config->IsRela ? 
DT_RELA0
: DT_REL);
1347
11
  }
1348
71
1349
71
  addInSec(DT_SYMTAB, InX::DynSymTab);
1350
71
  addInt(DT_SYMENT, sizeof(Elf_Sym));
1351
71
  addInSec(DT_STRTAB, InX::DynStrTab);
1352
71
  addInt(DT_STRSZ, InX::DynStrTab->getSize());
1353
71
  if (!Config->ZText)
1354
0
    addInt(DT_TEXTREL, 0);
1355
71
  if (InX::GnuHashTab)
1356
1
    addInSec(DT_GNU_HASH, InX::GnuHashTab);
1357
71
  if (InX::HashTab)
1358
71
    addInSec(DT_HASH, InX::HashTab);
1359
71
1360
71
  if (Out::PreinitArray) {
1361
0
    addOutSec(DT_PREINIT_ARRAY, Out::PreinitArray);
1362
0
    addSize(DT_PREINIT_ARRAYSZ, Out::PreinitArray);
1363
0
  }
1364
71
  if (Out::InitArray) {
1365
0
    addOutSec(DT_INIT_ARRAY, Out::InitArray);
1366
0
    addSize(DT_INIT_ARRAYSZ, Out::InitArray);
1367
0
  }
1368
71
  if (Out::FiniArray) {
1369
0
    addOutSec(DT_FINI_ARRAY, Out::FiniArray);
1370
0
    addSize(DT_FINI_ARRAYSZ, Out::FiniArray);
1371
0
  }
1372
71
1373
71
  if (Symbol *B = Symtab->find(Config->Init))
1374
0
    if (B->isDefined())
1375
0
      addSym(DT_INIT, B);
1376
71
  if (Symbol *B = Symtab->find(Config->Fini))
1377
0
    if (B->isDefined())
1378
0
      addSym(DT_FINI, B);
1379
71
1380
71
  bool HasVerNeed = In<ELFT>::VerNeed->getNeedNum() != 0;
1381
71
  if (HasVerNeed || 
In<ELFT>::VerDef70
)
1382
1
    addInSec(DT_VERSYM, In<ELFT>::VerSym);
1383
71
  if (In<ELFT>::VerDef) {
1384
0
    addInSec(DT_VERDEF, In<ELFT>::VerDef);
1385
0
    addInt(DT_VERDEFNUM, getVerDefNum());
1386
0
  }
1387
71
  if (HasVerNeed) {
1388
1
    addInSec(DT_VERNEED, In<ELFT>::VerNeed);
1389
1
    addInt(DT_VERNEEDNUM, In<ELFT>::VerNeed->getNeedNum());
1390
1
  }
1391
71
1392
71
  if (Config->EMachine == EM_MIPS) {
1393
69
    addInt(DT_MIPS_RLD_VERSION, 1);
1394
69
    addInt(DT_MIPS_FLAGS, RHF_NOTPOT);
1395
69
    addInt(DT_MIPS_BASE_ADDRESS, Target->getImageBase());
1396
69
    addInt(DT_MIPS_SYMTABNO, InX::DynSymTab->getNumSymbols());
1397
69
1398
69
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
1399
69
1400
69
    if (const Symbol *B = InX::MipsGot->getFirstGlobalEntry())
1401
23
      addInt(DT_MIPS_GOTSYM, B->DynsymIndex);
1402
46
    else
1403
46
      addInt(DT_MIPS_GOTSYM, InX::DynSymTab->getNumSymbols());
1404
69
    addInSec(DT_PLTGOT, InX::MipsGot);
1405
69
    if (InX::MipsRldMap) {
1406
21
      if (!Config->Pie)
1407
19
        addInSec(DT_MIPS_RLD_MAP, InX::MipsRldMap);
1408
21
      // Store the offset to the .rld_map section
1409
21
      // relative to the address of the tag.
1410
21
      addInSecRelative(DT_MIPS_RLD_MAP_REL, InX::MipsRldMap);
1411
21
    }
1412
69
  }
1413
71
1414
71
  // Glink dynamic tag is required by the V2 abi if the plt section isn't empty.
1415
71
  if (Config->EMachine == EM_PPC64 && 
!InX::Plt->empty()0
) {
1416
0
    // The Glink tag points to 32 bytes before the first lazy symbol resolution
1417
0
    // stub, which starts directly after the header.
1418
0
    Entries.push_back({DT_PPC64_GLINK, [=] {
1419
0
                         unsigned Offset = Target->PltHeaderSize - 32;
1420
0
                         return InX::Plt->getVA(0) + Offset;
1421
0
                       }});
1422
0
  }
1423
71
1424
71
  addInt(DT_NULL, 0);
1425
71
1426
71
  getParent()->Link = this->Link;
1427
71
  this->Size = Entries.size() * this->Entsize;
1428
71
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::finalizeContents()
Line
Count
Source
1258
807
template <class ELFT> void DynamicSection<ELFT>::finalizeContents() {
1259
807
  if (this->Size)
1260
0
    return; // Already finalized.
1261
807
1262
807
  // Set DT_FLAGS and DT_FLAGS_1.
1263
807
  uint32_t DtFlags = 0;
1264
807
  uint32_t DtFlags1 = 0;
1265
807
  if (Config->Bsymbolic)
1266
3
    DtFlags |= DF_SYMBOLIC;
1267
807
  if (Config->ZInitfirst)
1268
1
    DtFlags1 |= DF_1_INITFIRST;
1269
807
  if (Config->ZNodelete)
1270
1
    DtFlags1 |= DF_1_NODELETE;
1271
807
  if (Config->ZNodlopen)
1272
1
    DtFlags1 |= DF_1_NOOPEN;
1273
807
  if (Config->ZNow) {
1274
4
    DtFlags |= DF_BIND_NOW;
1275
4
    DtFlags1 |= DF_1_NOW;
1276
4
  }
1277
807
  if (Config->ZOrigin) {
1278
1
    DtFlags |= DF_ORIGIN;
1279
1
    DtFlags1 |= DF_1_ORIGIN;
1280
1
  }
1281
807
  if (!Config->ZText)
1282
8
    DtFlags |= DF_TEXTREL;
1283
807
1284
807
  if (DtFlags)
1285
14
    addInt(DT_FLAGS, DtFlags);
1286
807
  if (DtFlags1)
1287
4
    addInt(DT_FLAGS_1, DtFlags1);
1288
807
1289
807
  // DT_DEBUG is a pointer to debug informaion used by debuggers at runtime. We
1290
807
  // need it for each process, so we don't write it for DSOs. The loader writes
1291
807
  // the pointer into this entry.
1292
807
  //
1293
807
  // DT_DEBUG is the only .dynamic entry that needs to be written to. Some
1294
807
  // systems (currently only Fuchsia OS) provide other means to give the
1295
807
  // debugger this information. Such systems may choose make .dynamic read-only.
1296
807
  // If the target is such a system (used -z rodynamic) don't write DT_DEBUG.
1297
807
  if (!Config->Shared && 
!Config->Relocatable215
&&
!Config->ZRodynamic213
)
1298
212
    addInt(DT_DEBUG, 0);
1299
807
1300
807
  this->Link = InX::DynStrTab->getParent()->SectionIndex;
1301
807
  if (!InX::RelaDyn->empty()) {
1302
143
    addInSec(InX::RelaDyn->DynamicTag, InX::RelaDyn);
1303
143
    addSize(InX::RelaDyn->SizeDynamicTag, InX::RelaDyn->getParent());
1304
143
1305
143
    bool IsRela = Config->IsRela;
1306
143
    addInt(IsRela ? DT_RELAENT : 
DT_RELENT0
,
1307
143
           IsRela ? sizeof(Elf_Rela) : 
sizeof(Elf_Rel)0
);
1308
143
1309
143
    // MIPS dynamic loader does not support RELCOUNT tag.
1310
143
    // The problem is in the tight relation between dynamic
1311
143
    // relocations and GOT. So do not emit this tag on MIPS.
1312
143
    if (Config->EMachine != EM_MIPS) {
1313
143
      size_t NumRelativeRels = InX::RelaDyn->getRelativeRelocCount();
1314
143
      if (Config->ZCombreloc && 
NumRelativeRels142
)
1315
28
        addInt(IsRela ? DT_RELACOUNT : 
DT_RELCOUNT0
, NumRelativeRels);
1316
143
    }
1317
143
  }
1318
807
  if (InX::RelrDyn && 
!InX::RelrDyn->Relocs.empty()1
) {
1319
1
    addInSec(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELR0
: DT_RELR,
1320
1
             InX::RelrDyn);
1321
1
    addSize(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELRSZ0
: DT_RELRSZ,
1322
1
            InX::RelrDyn->getParent());
1323
1
    addInt(Config->UseAndroidRelrTags ? 
DT_ANDROID_RELRENT0
: DT_RELRENT,
1324
1
           sizeof(Elf_Relr));
1325
1
  }
1326
807
  // .rel[a].plt section usually consists of two parts, containing plt and
1327
807
  // iplt relocations. It is possible to have only iplt relocations in the
1328
807
  // output. In that case RelaPlt is empty and have zero offset, the same offset
1329
807
  // as RelaIplt have. And we still want to emit proper dynamic tags for that
1330
807
  // case, so here we always use RelaPlt as marker for the begining of
1331
807
  // .rel[a].plt section.
1332
807
  if (InX::RelaPlt->getParent()->Live) {
1333
150
    addInSec(DT_JMPREL, InX::RelaPlt);
1334
150
    addSize(DT_PLTRELSZ, InX::RelaPlt->getParent());
1335
150
    switch (Config->EMachine) {
1336
150
    case EM_MIPS:
1337
0
      addInSec(DT_MIPS_PLTGOT, InX::GotPlt);
1338
0
      break;
1339
150
    case EM_SPARCV9:
1340
0
      addInSec(DT_PLTGOT, InX::Plt);
1341
0
      break;
1342
150
    default:
1343
150
      addInSec(DT_PLTGOT, InX::GotPlt);
1344
150
      break;
1345
150
    }
1346
150
    addInt(DT_PLTREL, Config->IsRela ? DT_RELA : 
DT_REL0
);
1347
150
  }
1348
807
1349
807
  addInSec(DT_SYMTAB, InX::DynSymTab);
1350
807
  addInt(DT_SYMENT, sizeof(Elf_Sym));
1351
807
  addInSec(DT_STRTAB, InX::DynStrTab);
1352
807
  addInt(DT_STRSZ, InX::DynStrTab->getSize());
1353
807
  if (!Config->ZText)
1354
8
    addInt(DT_TEXTREL, 0);
1355
807
  if (InX::GnuHashTab)
1356
711
    addInSec(DT_GNU_HASH, InX::GnuHashTab);
1357
807
  if (InX::HashTab)
1358
800
    addInSec(DT_HASH, InX::HashTab);
1359
807
1360
807
  if (Out::PreinitArray) {
1361
3
    addOutSec(DT_PREINIT_ARRAY, Out::PreinitArray);
1362
3
    addSize(DT_PREINIT_ARRAYSZ, Out::PreinitArray);
1363
3
  }
1364
807
  if (Out::InitArray) {
1365
3
    addOutSec(DT_INIT_ARRAY, Out::InitArray);
1366
3
    addSize(DT_INIT_ARRAYSZ, Out::InitArray);
1367
3
  }
1368
807
  if (Out::FiniArray) {
1369
2
    addOutSec(DT_FINI_ARRAY, Out::FiniArray);
1370
2
    addSize(DT_FINI_ARRAYSZ, Out::FiniArray);
1371
2
  }
1372
807
1373
807
  if (Symbol *B = Symtab->find(Config->Init))
1374
6
    if (B->isDefined())
1375
4
      addSym(DT_INIT, B);
1376
807
  if (Symbol *B = Symtab->find(Config->Fini))
1377
6
    if (B->isDefined())
1378
4
      addSym(DT_FINI, B);
1379
807
1380
807
  bool HasVerNeed = In<ELFT>::VerNeed->getNeedNum() != 0;
1381
807
  if (HasVerNeed || 
In<ELFT>::VerDef800
)
1382
58
    addInSec(DT_VERSYM, In<ELFT>::VerSym);
1383
807
  if (In<ELFT>::VerDef) {
1384
52
    addInSec(DT_VERDEF, In<ELFT>::VerDef);
1385
52
    addInt(DT_VERDEFNUM, getVerDefNum());
1386
52
  }
1387
807
  if (HasVerNeed) {
1388
7
    addInSec(DT_VERNEED, In<ELFT>::VerNeed);
1389
7
    addInt(DT_VERNEEDNUM, In<ELFT>::VerNeed->getNeedNum());
1390
7
  }
1391
807
1392
807
  if (Config->EMachine == EM_MIPS) {
1393
0
    addInt(DT_MIPS_RLD_VERSION, 1);
1394
0
    addInt(DT_MIPS_FLAGS, RHF_NOTPOT);
1395
0
    addInt(DT_MIPS_BASE_ADDRESS, Target->getImageBase());
1396
0
    addInt(DT_MIPS_SYMTABNO, InX::DynSymTab->getNumSymbols());
1397
0
1398
0
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
1399
0
1400
0
    if (const Symbol *B = InX::MipsGot->getFirstGlobalEntry())
1401
0
      addInt(DT_MIPS_GOTSYM, B->DynsymIndex);
1402
0
    else
1403
0
      addInt(DT_MIPS_GOTSYM, InX::DynSymTab->getNumSymbols());
1404
0
    addInSec(DT_PLTGOT, InX::MipsGot);
1405
0
    if (InX::MipsRldMap) {
1406
0
      if (!Config->Pie)
1407
0
        addInSec(DT_MIPS_RLD_MAP, InX::MipsRldMap);
1408
0
      // Store the offset to the .rld_map section
1409
0
      // relative to the address of the tag.
1410
0
      addInSecRelative(DT_MIPS_RLD_MAP_REL, InX::MipsRldMap);
1411
0
    }
1412
0
  }
1413
807
1414
807
  // Glink dynamic tag is required by the V2 abi if the plt section isn't empty.
1415
807
  if (Config->EMachine == EM_PPC64 && 
!InX::Plt->empty()28
) {
1416
10
    // The Glink tag points to 32 bytes before the first lazy symbol resolution
1417
10
    // stub, which starts directly after the header.
1418
10
    Entries.push_back({DT_PPC64_GLINK, [=] {
1419
10
                         unsigned Offset = Target->PltHeaderSize - 32;
1420
10
                         return InX::Plt->getVA(0) + Offset;
1421
10
                       }});
1422
10
  }
1423
807
1424
807
  addInt(DT_NULL, 0);
1425
807
1426
807
  getParent()->Link = this->Link;
1427
807
  this->Size = Entries.size() * this->Entsize;
1428
807
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::finalizeContents()
Line
Count
Source
1258
50
template <class ELFT> void DynamicSection<ELFT>::finalizeContents() {
1259
50
  if (this->Size)
1260
0
    return; // Already finalized.
1261
50
1262
50
  // Set DT_FLAGS and DT_FLAGS_1.
1263
50
  uint32_t DtFlags = 0;
1264
50
  uint32_t DtFlags1 = 0;
1265
50
  if (Config->Bsymbolic)
1266
0
    DtFlags |= DF_SYMBOLIC;
1267
50
  if (Config->ZInitfirst)
1268
0
    DtFlags1 |= DF_1_INITFIRST;
1269
50
  if (Config->ZNodelete)
1270
0
    DtFlags1 |= DF_1_NODELETE;
1271
50
  if (Config->ZNodlopen)
1272
0
    DtFlags1 |= DF_1_NOOPEN;
1273
50
  if (Config->ZNow) {
1274
0
    DtFlags |= DF_BIND_NOW;
1275
0
    DtFlags1 |= DF_1_NOW;
1276
0
  }
1277
50
  if (Config->ZOrigin) {
1278
0
    DtFlags |= DF_ORIGIN;
1279
0
    DtFlags1 |= DF_1_ORIGIN;
1280
0
  }
1281
50
  if (!Config->ZText)
1282
3
    DtFlags |= DF_TEXTREL;
1283
50
1284
50
  if (DtFlags)
1285
3
    addInt(DT_FLAGS, DtFlags);
1286
50
  if (DtFlags1)
1287
0
    addInt(DT_FLAGS_1, DtFlags1);
1288
50
1289
50
  // DT_DEBUG is a pointer to debug informaion used by debuggers at runtime. We
1290
50
  // need it for each process, so we don't write it for DSOs. The loader writes
1291
50
  // the pointer into this entry.
1292
50
  //
1293
50
  // DT_DEBUG is the only .dynamic entry that needs to be written to. Some
1294
50
  // systems (currently only Fuchsia OS) provide other means to give the
1295
50
  // debugger this information. Such systems may choose make .dynamic read-only.
1296
50
  // If the target is such a system (used -z rodynamic) don't write DT_DEBUG.
1297
50
  if (!Config->Shared && 
!Config->Relocatable15
&&
!Config->ZRodynamic15
)
1298
15
    addInt(DT_DEBUG, 0);
1299
50
1300
50
  this->Link = InX::DynStrTab->getParent()->SectionIndex;
1301
50
  if (!InX::RelaDyn->empty()) {
1302
17
    addInSec(InX::RelaDyn->DynamicTag, InX::RelaDyn);
1303
17
    addSize(InX::RelaDyn->SizeDynamicTag, InX::RelaDyn->getParent());
1304
17
1305
17
    bool IsRela = Config->IsRela;
1306
17
    addInt(IsRela ? 
DT_RELAENT9
:
DT_RELENT8
,
1307
17
           IsRela ? 
sizeof(Elf_Rela)9
:
sizeof(Elf_Rel)8
);
1308
17
1309
17
    // MIPS dynamic loader does not support RELCOUNT tag.
1310
17
    // The problem is in the tight relation between dynamic
1311
17
    // relocations and GOT. So do not emit this tag on MIPS.
1312
17
    if (Config->EMachine != EM_MIPS) {
1313
9
      size_t NumRelativeRels = InX::RelaDyn->getRelativeRelocCount();
1314
9
      if (Config->ZCombreloc && NumRelativeRels)
1315
1
        addInt(IsRela ? DT_RELACOUNT : 
DT_RELCOUNT0
, NumRelativeRels);
1316
9
    }
1317
17
  }
1318
50
  if (InX::RelrDyn && 
!InX::RelrDyn->Relocs.empty()0
) {
1319
0
    addInSec(Config->UseAndroidRelrTags ? DT_ANDROID_RELR : DT_RELR,
1320
0
             InX::RelrDyn);
1321
0
    addSize(Config->UseAndroidRelrTags ? DT_ANDROID_RELRSZ : DT_RELRSZ,
1322
0
            InX::RelrDyn->getParent());
1323
0
    addInt(Config->UseAndroidRelrTags ? DT_ANDROID_RELRENT : DT_RELRENT,
1324
0
           sizeof(Elf_Relr));
1325
0
  }
1326
50
  // .rel[a].plt section usually consists of two parts, containing plt and
1327
50
  // iplt relocations. It is possible to have only iplt relocations in the
1328
50
  // output. In that case RelaPlt is empty and have zero offset, the same offset
1329
50
  // as RelaIplt have. And we still want to emit proper dynamic tags for that
1330
50
  // case, so here we always use RelaPlt as marker for the begining of
1331
50
  // .rel[a].plt section.
1332
50
  if (InX::RelaPlt->getParent()->Live) {
1333
12
    addInSec(DT_JMPREL, InX::RelaPlt);
1334
12
    addSize(DT_PLTRELSZ, InX::RelaPlt->getParent());
1335
12
    switch (Config->EMachine) {
1336
12
    case EM_MIPS:
1337
2
      addInSec(DT_MIPS_PLTGOT, InX::GotPlt);
1338
2
      break;
1339
12
    case EM_SPARCV9:
1340
0
      addInSec(DT_PLTGOT, InX::Plt);
1341
0
      break;
1342
12
    default:
1343
10
      addInSec(DT_PLTGOT, InX::GotPlt);
1344
10
      break;
1345
12
    }
1346
12
    addInt(DT_PLTREL, Config->IsRela ? 
DT_RELA10
:
DT_REL2
);
1347
12
  }
1348
50
1349
50
  addInSec(DT_SYMTAB, InX::DynSymTab);
1350
50
  addInt(DT_SYMENT, sizeof(Elf_Sym));
1351
50
  addInSec(DT_STRTAB, InX::DynStrTab);
1352
50
  addInt(DT_STRSZ, InX::DynStrTab->getSize());
1353
50
  if (!Config->ZText)
1354
3
    addInt(DT_TEXTREL, 0);
1355
50
  if (InX::GnuHashTab)
1356
27
    addInSec(DT_GNU_HASH, InX::GnuHashTab);
1357
50
  if (InX::HashTab)
1358
50
    addInSec(DT_HASH, InX::HashTab);
1359
50
1360
50
  if (Out::PreinitArray) {
1361
0
    addOutSec(DT_PREINIT_ARRAY, Out::PreinitArray);
1362
0
    addSize(DT_PREINIT_ARRAYSZ, Out::PreinitArray);
1363
0
  }
1364
50
  if (Out::InitArray) {
1365
0
    addOutSec(DT_INIT_ARRAY, Out::InitArray);
1366
0
    addSize(DT_INIT_ARRAYSZ, Out::InitArray);
1367
0
  }
1368
50
  if (Out::FiniArray) {
1369
0
    addOutSec(DT_FINI_ARRAY, Out::FiniArray);
1370
0
    addSize(DT_FINI_ARRAYSZ, Out::FiniArray);
1371
0
  }
1372
50
1373
50
  if (Symbol *B = Symtab->find(Config->Init))
1374
0
    if (B->isDefined())
1375
0
      addSym(DT_INIT, B);
1376
50
  if (Symbol *B = Symtab->find(Config->Fini))
1377
0
    if (B->isDefined())
1378
0
      addSym(DT_FINI, B);
1379
50
1380
50
  bool HasVerNeed = In<ELFT>::VerNeed->getNeedNum() != 0;
1381
50
  if (HasVerNeed || In<ELFT>::VerDef)
1382
0
    addInSec(DT_VERSYM, In<ELFT>::VerSym);
1383
50
  if (In<ELFT>::VerDef) {
1384
0
    addInSec(DT_VERDEF, In<ELFT>::VerDef);
1385
0
    addInt(DT_VERDEFNUM, getVerDefNum());
1386
0
  }
1387
50
  if (HasVerNeed) {
1388
0
    addInSec(DT_VERNEED, In<ELFT>::VerNeed);
1389
0
    addInt(DT_VERNEEDNUM, In<ELFT>::VerNeed->getNeedNum());
1390
0
  }
1391
50
1392
50
  if (Config->EMachine == EM_MIPS) {
1393
23
    addInt(DT_MIPS_RLD_VERSION, 1);
1394
23
    addInt(DT_MIPS_FLAGS, RHF_NOTPOT);
1395
23
    addInt(DT_MIPS_BASE_ADDRESS, Target->getImageBase());
1396
23
    addInt(DT_MIPS_SYMTABNO, InX::DynSymTab->getNumSymbols());
1397
23
1398
23
    add(DT_MIPS_LOCAL_GOTNO, [] { return InX::MipsGot->getLocalEntriesNum(); });
1399
23
1400
23
    if (const Symbol *B = InX::MipsGot->getFirstGlobalEntry())
1401
6
      addInt(DT_MIPS_GOTSYM, B->DynsymIndex);
1402
17
    else
1403
17
      addInt(DT_MIPS_GOTSYM, InX::DynSymTab->getNumSymbols());
1404
23
    addInSec(DT_PLTGOT, InX::MipsGot);
1405
23
    if (InX::MipsRldMap) {
1406
6
      if (!Config->Pie)
1407
5
        addInSec(DT_MIPS_RLD_MAP, InX::MipsRldMap);
1408
6
      // Store the offset to the .rld_map section
1409
6
      // relative to the address of the tag.
1410
6
      addInSecRelative(DT_MIPS_RLD_MAP_REL, InX::MipsRldMap);
1411
6
    }
1412
23
  }
1413
50
1414
50
  // Glink dynamic tag is required by the V2 abi if the plt section isn't empty.
1415
50
  if (Config->EMachine == EM_PPC64 && 
!InX::Plt->empty()27
) {
1416
10
    // The Glink tag points to 32 bytes before the first lazy symbol resolution
1417
10
    // stub, which starts directly after the header.
1418
10
    Entries.push_back({DT_PPC64_GLINK, [=] {
1419
10
                         unsigned Offset = Target->PltHeaderSize - 32;
1420
10
                         return InX::Plt->getVA(0) + Offset;
1421
10
                       }});
1422
10
  }
1423
50
1424
50
  addInt(DT_NULL, 0);
1425
50
1426
50
  getParent()->Link = this->Link;
1427
50
  this->Size = Entries.size() * this->Entsize;
1428
50
}
1429
1430
1.05k
template <class ELFT> void DynamicSection<ELFT>::writeTo(uint8_t *Buf) {
1431
1.05k
  auto *P = reinterpret_cast<Elf_Dyn *>(Buf);
1432
1.05k
1433
10.3k
  for (std::pair<int32_t, std::function<uint64_t()>> &KV : Entries) {
1434
10.3k
    P->d_tag = KV.first;
1435
10.3k
    P->d_un.d_val = KV.second();
1436
10.3k
    ++P;
1437
10.3k
  }
1438
1.05k
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::writeTo(unsigned char*)
Line
Count
Source
1430
139
template <class ELFT> void DynamicSection<ELFT>::writeTo(uint8_t *Buf) {
1431
139
  auto *P = reinterpret_cast<Elf_Dyn *>(Buf);
1432
139
1433
1.38k
  for (std::pair<int32_t, std::function<uint64_t()>> &KV : Entries) {
1434
1.38k
    P->d_tag = KV.first;
1435
1.38k
    P->d_un.d_val = KV.second();
1436
1.38k
    ++P;
1437
1.38k
  }
1438
139
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::writeTo(unsigned char*)
Line
Count
Source
1430
71
template <class ELFT> void DynamicSection<ELFT>::writeTo(uint8_t *Buf) {
1431
71
  auto *P = reinterpret_cast<Elf_Dyn *>(Buf);
1432
71
1433
1.06k
  for (std::pair<int32_t, std::function<uint64_t()>> &KV : Entries) {
1434
1.06k
    P->d_tag = KV.first;
1435
1.06k
    P->d_un.d_val = KV.second();
1436
1.06k
    ++P;
1437
1.06k
  }
1438
71
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::writeTo(unsigned char*)
Line
Count
Source
1430
798
template <class ELFT> void DynamicSection<ELFT>::writeTo(uint8_t *Buf) {
1431
798
  auto *P = reinterpret_cast<Elf_Dyn *>(Buf);
1432
798
1433
7.21k
  for (std::pair<int32_t, std::function<uint64_t()>> &KV : Entries) {
1434
7.21k
    P->d_tag = KV.first;
1435
7.21k
    P->d_un.d_val = KV.second();
1436
7.21k
    ++P;
1437
7.21k
  }
1438
798
}
lld::elf::DynamicSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::writeTo(unsigned char*)
Line
Count
Source
1430
50
template <class ELFT> void DynamicSection<ELFT>::writeTo(uint8_t *Buf) {
1431
50
  auto *P = reinterpret_cast<Elf_Dyn *>(Buf);
1432
50
1433
647
  for (std::pair<int32_t, std::function<uint64_t()>> &KV : Entries) {
1434
647
    P->d_tag = KV.first;
1435
647
    P->d_un.d_val = KV.second();
1436
647
    ++P;
1437
647
  }
1438
50
}
1439
1440
910
uint64_t DynamicReloc::getOffset() const {
1441
910
  return InputSec->getVA(OffsetInSec);
1442
910
}
1443
1444
584
int64_t DynamicReloc::computeAddend() const {
1445
584
  if (UseSymVA)
1446
148
    return Sym->getVA(Addend);
1447
436
  if (!OutputSec)
1448
436
    return Addend;
1449
0
  // See the comment in the DynamicReloc ctor.
1450
0
  return getMipsPageAddr(OutputSec->Addr) + Addend;
1451
0
}
1452
1453
1.57k
uint32_t DynamicReloc::getSymIndex() const {
1454
1.57k
  if (Sym && 
!UseSymVA1.51k
)
1455
1.08k
    return Sym->DynsymIndex;
1456
488
  return 0;
1457
488
}
1458
1459
RelocationBaseSection::RelocationBaseSection(StringRef Name, uint32_t Type,
1460
                                             int32_t DynamicTag,
1461
                                             int32_t SizeDynamicTag)
1462
    : SyntheticSection(SHF_ALLOC, Type, Config->Wordsize, Name),
1463
6.69k
      DynamicTag(DynamicTag), SizeDynamicTag(SizeDynamicTag) {}
1464
1465
void RelocationBaseSection::addReloc(RelType DynType, InputSectionBase *IS,
1466
134
                                     uint64_t OffsetInSec, Symbol *Sym) {
1467
134
  addReloc({DynType, IS, OffsetInSec, false, Sym, 0});
1468
134
}
1469
1470
void RelocationBaseSection::addReloc(RelType DynType,
1471
                                     InputSectionBase *InputSec,
1472
                                     uint64_t OffsetInSec, Symbol *Sym,
1473
                                     int64_t Addend, RelExpr Expr,
1474
409
                                     RelType Type) {
1475
409
  // Write the addends to the relocated address if required. We skip
1476
409
  // it if the written value would be zero.
1477
409
  if (Config->WriteAddends && 
(143
Expr != R_ADDEND143
||
Addend != 062
))
1478
95
    InputSec->Relocations.push_back({Expr, Type, OffsetInSec, Addend, Sym});
1479
409
  addReloc({DynType, InputSec, OffsetInSec, Expr != R_ADDEND, Sym, Addend});
1480
409
}
1481
1482
870
void RelocationBaseSection::addReloc(const DynamicReloc &Reloc) {
1483
870
  if (Reloc.Type == Target->RelativeRel)
1484
187
    ++NumRelativeRelocs;
1485
870
  Relocs.push_back(Reloc);
1486
870
}
1487
1488
438
void RelocationBaseSection::finalizeContents() {
1489
438
  // If all relocations are R_*_RELATIVE they don't refer to any
1490
438
  // dynamic symbol and we don't need a dynamic symbol table. If that
1491
438
  // is the case, just use 0 as the link.
1492
438
  Link = InX::DynSymTab ? 
InX::DynSymTab->getParent()->SectionIndex429
:
09
;
1493
438
1494
438
  // Set required output section properties.
1495
438
  getParent()->Link = Link;
1496
438
}
1497
1498
RelrBaseSection::RelrBaseSection()
1499
    : SyntheticSection(SHF_ALLOC,
1500
                       Config->UseAndroidRelrTags ? SHT_ANDROID_RELR : SHT_RELR,
1501
3
                       Config->Wordsize, ".relr.dyn") {}
1502
1503
template <class ELFT>
1504
static void encodeDynamicReloc(typename ELFT::Rela *P,
1505
910
                               const DynamicReloc &Rel) {
1506
910
  if (Config->IsRela)
1507
584
    P->r_addend = Rel.computeAddend();
1508
910
  P->r_offset = Rel.getOffset();
1509
910
  P->setSymbolAndType(Rel.getSymIndex(), Rel.Type, Config->IsMips64EL);
1510
910
}
SyntheticSections.cpp:void encodeDynamicReloc<llvm::object::ELFType<(llvm::support::endianness)1, false> >(llvm::object::ELFType<(llvm::support::endianness)1, false>::Rela*, lld::elf::DynamicReloc const&)
Line
Count
Source
1505
264
                               const DynamicReloc &Rel) {
1506
264
  if (Config->IsRela)
1507
1
    P->r_addend = Rel.computeAddend();
1508
264
  P->r_offset = Rel.getOffset();
1509
264
  P->setSymbolAndType(Rel.getSymIndex(), Rel.Type, Config->IsMips64EL);
1510
264
}
SyntheticSections.cpp:void encodeDynamicReloc<llvm::object::ELFType<(llvm::support::endianness)0, false> >(llvm::object::ELFType<(llvm::support::endianness)0, false>::Rela*, lld::elf::DynamicReloc const&)
Line
Count
Source
1505
45
                               const DynamicReloc &Rel) {
1506
45
  if (Config->IsRela)
1507
1
    P->r_addend = Rel.computeAddend();
1508
45
  P->r_offset = Rel.getOffset();
1509
45
  P->setSymbolAndType(Rel.getSymIndex(), Rel.Type, Config->IsMips64EL);
1510
45
}
SyntheticSections.cpp:void encodeDynamicReloc<llvm::object::ELFType<(llvm::support::endianness)1, true> >(llvm::object::ELFType<(llvm::support::endianness)1, true>::Rela*, lld::elf::DynamicReloc const&)
Line
Count
Source
1505
548
                               const DynamicReloc &Rel) {
1506
548
  if (Config->IsRela)
1507
548
    P->r_addend = Rel.computeAddend();
1508
548
  P->r_offset = Rel.getOffset();
1509
548
  P->setSymbolAndType(Rel.getSymIndex(), Rel.Type, Config->IsMips64EL);
1510
548
}
SyntheticSections.cpp:void encodeDynamicReloc<llvm::object::ELFType<(llvm::support::endianness)0, true> >(llvm::object::ELFType<(llvm::support::endianness)0, true>::Rela*, lld::elf::DynamicReloc const&)
Line
Count
Source
1505
53
                               const DynamicReloc &Rel) {
1506
53
  if (Config->IsRela)
1507
34
    P->r_addend = Rel.computeAddend();
1508
53
  P->r_offset = Rel.getOffset();
1509
53
  P->setSymbolAndType(Rel.getSymIndex(), Rel.Type, Config->IsMips64EL);
1510
53
}
1511
1512
template <class ELFT>
1513
RelocationSection<ELFT>::RelocationSection(StringRef Name, bool Sort)
1514
    : RelocationBaseSection(Name, Config->IsRela ? SHT_RELA : SHT_REL,
1515
                            Config->IsRela ? DT_RELA : DT_REL,
1516
                            Config->IsRela ? DT_RELASZ : DT_RELSZ),
1517
6.69k
      Sort(Sort) {
1518
6.69k
  this->Entsize = Config->IsRela ? 
sizeof(Elf_Rela)5.41k
:
sizeof(Elf_Rel)1.28k
;
1519
6.69k
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::RelocationSection(llvm::StringRef, bool)
Line
Count
Source
1517
806
      Sort(Sort) {
1518
806
  this->Entsize = Config->IsRela ? 
sizeof(Elf_Rela)9
:
sizeof(Elf_Rel)797
;
1519
806
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::RelocationSection(llvm::StringRef, bool)
Line
Count
Source
1517
357
      Sort(Sort) {
1518
357
  this->Entsize = Config->IsRela ? 
sizeof(Elf_Rela)9
:
sizeof(Elf_Rel)348
;
1519
357
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::RelocationSection(llvm::StringRef, bool)
Line
Count
Source
1517
5.27k
      Sort(Sort) {
1518
5.27k
  this->Entsize = Config->IsRela ? 
sizeof(Elf_Rela)5.27k
:
sizeof(Elf_Rel)6
;
1519
5.27k
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::RelocationSection(llvm::StringRef, bool)
Line
Count
Source
1517
255
      Sort(Sort) {
1518
255
  this->Entsize = Config->IsRela ? 
sizeof(Elf_Rela)123
:
sizeof(Elf_Rel)132
;
1519
255
}
1520
1521
485
static bool compRelocations(const DynamicReloc &A, const DynamicReloc &B) {
1522
485
  bool AIsRel = A.Type == Target->RelativeRel;
1523
485
  bool BIsRel = B.Type == Target->RelativeRel;
1524
485
  if (AIsRel != BIsRel)
1525
154
    return AIsRel;
1526
331
  return A.getSymIndex() < B.getSymIndex();
1527
331
}
1528
1529
432
template <class ELFT> void RelocationSection<ELFT>::writeTo(uint8_t *Buf) {
1530
432
  if (Sort)
1531
208
    std::stable_sort(Relocs.begin(), Relocs.end(), compRelocations);
1532
432
1533
802
  for (const DynamicReloc &Rel : Relocs) {
1534
802
    encodeDynamicReloc<ELFT>(reinterpret_cast<Elf_Rela *>(Buf), Rel);
1535
802
    Buf += Config->IsRela ? 
sizeof(Elf_Rela)530
:
sizeof(Elf_Rel)272
;
1536
802
  }
1537
432
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::writeTo(unsigned char*)
Line
Count
Source
1529
86
template <class ELFT> void RelocationSection<ELFT>::writeTo(uint8_t *Buf) {
1530
86
  if (Sort)
1531
45
    std::stable_sort(Relocs.begin(), Relocs.end(), compRelocations);
1532
86
1533
210
  for (const DynamicReloc &Rel : Relocs) {
1534
210
    encodeDynamicReloc<ELFT>(reinterpret_cast<Elf_Rela *>(Buf), Rel);
1535
210
    Buf += Config->IsRela ? 
sizeof(Elf_Rela)1
:
sizeof(Elf_Rel)209
;
1536
210
  }
1537
86
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::writeTo(unsigned char*)
Line
Count
Source
1529
19
template <class ELFT> void RelocationSection<ELFT>::writeTo(uint8_t *Buf) {
1530
19
  if (Sort)
1531
8
    std::stable_sort(Relocs.begin(), Relocs.end(), compRelocations);
1532
19
1533
45
  for (const DynamicReloc &Rel : Relocs) {
1534
45
    encodeDynamicReloc<ELFT>(reinterpret_cast<Elf_Rela *>(Buf), Rel);
1535
45
    Buf += Config->IsRela ? 
sizeof(Elf_Rela)1
:
sizeof(Elf_Rel)44
;
1536
45
  }
1537
19
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::writeTo(unsigned char*)
Line
Count
Source
1529
297
template <class ELFT> void RelocationSection<ELFT>::writeTo(uint8_t *Buf) {
1530
297
  if (Sort)
1531
138
    std::stable_sort(Relocs.begin(), Relocs.end(), compRelocations);
1532
297
1533
494
  for (const DynamicReloc &Rel : Relocs) {
1534
494
    encodeDynamicReloc<ELFT>(reinterpret_cast<Elf_Rela *>(Buf), Rel);
1535
494
    Buf += Config->IsRela ? sizeof(Elf_Rela) : 
sizeof(Elf_Rel)0
;
1536
494
  }
1537
297
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::writeTo(unsigned char*)
Line
Count
Source
1529
30
template <class ELFT> void RelocationSection<ELFT>::writeTo(uint8_t *Buf) {
1530
30
  if (Sort)
1531
17
    std::stable_sort(Relocs.begin(), Relocs.end(), compRelocations);
1532
30
1533
53
  for (const DynamicReloc &Rel : Relocs) {
1534
53
    encodeDynamicReloc<ELFT>(reinterpret_cast<Elf_Rela *>(Buf), Rel);
1535
53
    Buf += Config->IsRela ? 
sizeof(Elf_Rela)34
:
sizeof(Elf_Rel)19
;
1536
53
  }
1537
30
}
1538
1539
316
template <class ELFT> unsigned RelocationSection<ELFT>::getRelocOffset() {
1540
316
  return this->Entsize * Relocs.size();
1541
316
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::getRelocOffset()
Line
Count
Source
1539
80
template <class ELFT> unsigned RelocationSection<ELFT>::getRelocOffset() {
1540
80
  return this->Entsize * Relocs.size();
1541
80
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::getRelocOffset()
Line
Count
Source
1539
13
template <class ELFT> unsigned RelocationSection<ELFT>::getRelocOffset() {
1540
13
  return this->Entsize * Relocs.size();
1541
13
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::getRelocOffset()
Line
Count
Source
1539
210
template <class ELFT> unsigned RelocationSection<ELFT>::getRelocOffset() {
1540
210
  return this->Entsize * Relocs.size();
1541
210
}
lld::elf::RelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::getRelocOffset()
Line
Count
Source
1539
13
template <class ELFT> unsigned RelocationSection<ELFT>::getRelocOffset() {
1540
13
  return this->Entsize * Relocs.size();
1541
13
}
1542
1543
template <class ELFT>
1544
AndroidPackedRelocationSection<ELFT>::AndroidPackedRelocationSection(
1545
    StringRef Name)
1546
    : RelocationBaseSection(
1547
          Name, Config->IsRela ? SHT_ANDROID_RELA : SHT_ANDROID_REL,
1548
          Config->IsRela ? DT_ANDROID_RELA : DT_ANDROID_REL,
1549
2
          Config->IsRela ? DT_ANDROID_RELASZ : DT_ANDROID_RELSZ) {
1550
2
  this->Entsize = 1;
1551
2
}
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::AndroidPackedRelocationSection(llvm::StringRef)
Line
Count
Source
1549
1
          Config->IsRela ? DT_ANDROID_RELASZ : DT_ANDROID_RELSZ) {
1550
1
  this->Entsize = 1;
1551
1
}
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::AndroidPackedRelocationSection(llvm::StringRef)
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::AndroidPackedRelocationSection(llvm::StringRef)
Line
Count
Source
1549
1
          Config->IsRela ? DT_ANDROID_RELASZ : DT_ANDROID_RELSZ) {
1550
1
  this->Entsize = 1;
1551
1
}
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::AndroidPackedRelocationSection(llvm::StringRef)
1552
1553
template <class ELFT>
1554
4
bool AndroidPackedRelocationSection<ELFT>::updateAllocSize() {
1555
4
  // This function computes the contents of an Android-format packed relocation
1556
4
  // section.
1557
4
  //
1558
4
  // This format compresses relocations by using relocation groups to factor out
1559
4
  // fields that are common between relocations and storing deltas from previous
1560
4
  // relocations in SLEB128 format (which has a short representation for small
1561
4
  // numbers). A good example of a relocation type with common fields is
1562
4
  // R_*_RELATIVE, which is normally used to represent function pointers in
1563
4
  // vtables. In the REL format, each relative relocation has the same r_info
1564
4
  // field, and is only different from other relative relocations in terms of
1565
4
  // the r_offset field. By sorting relocations by offset, grouping them by
1566
4
  // r_info and representing each relocation with only the delta from the
1567
4
  // previous offset, each 8-byte relocation can be compressed to as little as 1
1568
4
  // byte (or less with run-length encoding). This relocation packer was able to
1569
4
  // reduce the size of the relocation section in an Android Chromium DSO from
1570
4
  // 2,911,184 bytes to 174,693 bytes, or 6% of the original size.
1571
4
  //
1572
4
  // A relocation section consists of a header containing the literal bytes
1573
4
  // 'APS2' followed by a sequence of SLEB128-encoded integers. The first two
1574
4
  // elements are the total number of relocations in the section and an initial
1575
4
  // r_offset value. The remaining elements define a sequence of relocation
1576
4
  // groups. Each relocation group starts with a header consisting of the
1577
4
  // following elements:
1578
4
  //
1579
4
  // - the number of relocations in the relocation group
1580
4
  // - flags for the relocation group
1581
4
  // - (if RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG is set) the r_offset delta
1582
4
  //   for each relocation in the group.
1583
4
  // - (if RELOCATION_GROUPED_BY_INFO_FLAG is set) the value of the r_info
1584
4
  //   field for each relocation in the group.
1585
4
  // - (if RELOCATION_GROUP_HAS_ADDEND_FLAG and
1586
4
  //   RELOCATION_GROUPED_BY_ADDEND_FLAG are set) the r_addend delta for
1587
4
  //   each relocation in the group.
1588
4
  //
1589
4
  // Following the relocation group header are descriptions of each of the
1590
4
  // relocations in the group. They consist of the following elements:
1591
4
  //
1592
4
  // - (if RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG is not set) the r_offset
1593
4
  //   delta for this relocation.
1594
4
  // - (if RELOCATION_GROUPED_BY_INFO_FLAG is not set) the value of the r_info
1595
4
  //   field for this relocation.
1596
4
  // - (if RELOCATION_GROUP_HAS_ADDEND_FLAG is set and
1597
4
  //   RELOCATION_GROUPED_BY_ADDEND_FLAG is not set) the r_addend delta for
1598
4
  //   this relocation.
1599
4
1600
4
  size_t OldSize = RelocData.size();
1601
4
1602
4
  RelocData = {'A', 'P', 'S', '2'};
1603
4
  raw_svector_ostream OS(RelocData);
1604
194
  auto Add = [&](int64_t V) { encodeSLEB128(V, OS); };
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::updateAllocSize()::'lambda'(long long)::operator()(long long) const
Line
Count
Source
1604
70
  auto Add = [&](int64_t V) { encodeSLEB128(V, OS); };
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::updateAllocSize()::'lambda'(long long)::operator()(long long) const
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::updateAllocSize()::'lambda'(long long)::operator()(long long) const
Line
Count
Source
1604
124
  auto Add = [&](int64_t V) { encodeSLEB128(V, OS); };
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::updateAllocSize()::'lambda'(long long)::operator()(long long) const
1605
4
1606
4
  // The format header includes the number of relocations and the initial
1607
4
  // offset (we set this to zero because the first relocation group will
1608
4
  // perform the initial adjustment).
1609
4
  Add(Relocs.size());
1610
4
  Add(0);
1611
4
1612
4
  std::vector<Elf_Rela> Relatives, NonRelatives;
1613
4
1614
108
  for (const DynamicReloc &Rel : Relocs) {
1615
108
    Elf_Rela R;
1616
108
    encodeDynamicReloc<ELFT>(&R, Rel);
1617
108
1618
108
    if (R.getType(Config->IsMips64EL) == Target->RelativeRel)
1619
100
      Relatives.push_back(R);
1620
8
    else
1621
8
      NonRelatives.push_back(R);
1622
108
  }
1623
4
1624
4
  llvm::sort(Relatives.begin(), Relatives.end(),
1625
96
             [](const Elf_Rel &A, const Elf_Rel &B) {
1626
96
               return A.r_offset < B.r_offset;
1627
96
             });
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, false> const&) const
Line
Count
Source
1625
48
             [](const Elf_Rel &A, const Elf_Rel &B) {
1626
48
               return A.r_offset < B.r_offset;
1627
48
             });
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, false> const&) const
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, false> const&) const
Line
Count
Source
1625
48
             [](const Elf_Rel &A, const Elf_Rel &B) {
1626
48
               return A.r_offset < B.r_offset;
1627
48
             });
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, false> const&) const
1628
4
1629
4
  // Try to find groups of relative relocations which are spaced one word
1630
4
  // apart from one another. These generally correspond to vtable entries. The
1631
4
  // format allows these groups to be encoded using a sort of run-length
1632
4
  // encoding, but each group will cost 7 bytes in addition to the offset from
1633
4
  // the previous group, so it is only profitable to do this for groups of
1634
4
  // size 8 or larger.
1635
4
  std::vector<Elf_Rela> UngroupedRelatives;
1636
4
  std::vector<std::vector<Elf_Rela>> RelativeGroups;
1637
20
  for (auto I = Relatives.begin(), E = Relatives.end(); I != E;) {
1638
16
    std::vector<Elf_Rela> Group;
1639
100
    do {
1640
100
      Group.push_back(*I++);
1641
100
    } while (I != E && 
(I - 1)->r_offset + Config->Wordsize == I->r_offset96
);
1642
16
1643
16
    if (Group.size() < 8)
1644
8
      UngroupedRelatives.insert(UngroupedRelatives.end(), Group.begin(),
1645
8
                                Group.end());
1646
8
    else
1647
8
      RelativeGroups.emplace_back(std::move(Group));
1648
16
  }
1649
4
1650
4
  unsigned HasAddendIfRela =
1651
4
      Config->IsRela ? 
RELOCATION_GROUP_HAS_ADDEND_FLAG2
:
02
;
1652
4
1653
4
  uint64_t Offset = 0;
1654
4
  uint64_t Addend = 0;
1655
4
1656
4
  // Emit the run-length encoding for the groups of adjacent relative
1657
4
  // relocations. Each group is represented using two groups in the packed
1658
4
  // format. The first is used to set the current offset to the start of the
1659
4
  // group (and also encodes the first relocation), and the second encodes the
1660
4
  // remaining relocations.
1661
8
  for (std::vector<Elf_Rela> &G : RelativeGroups) {
1662
8
    // The first relocation in the group.
1663
8
    Add(1);
1664
8
    Add(RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG |
1665
8
        RELOCATION_GROUPED_BY_INFO_FLAG | HasAddendIfRela);
1666
8
    Add(G[0].r_offset - Offset);
1667
8
    Add(Target->RelativeRel);
1668
8
    if (Config->IsRela) {
1669
4
      Add(G[0].r_addend - Addend);
1670
4
      Addend = G[0].r_addend;
1671
4
    }
1672
8
1673
8
    // The remaining relocations.
1674
8
    Add(G.size() - 1);
1675
8
    Add(RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG |
1676
8
        RELOCATION_GROUPED_BY_INFO_FLAG | HasAddendIfRela);
1677
8
    Add(Config->Wordsize);
1678
8
    Add(Target->RelativeRel);
1679
8
    if (Config->IsRela) {
1680
34
      for (auto I = G.begin() + 1, E = G.end(); I != E; 
++I30
) {
1681
30
        Add(I->r_addend - Addend);
1682
30
        Addend = I->r_addend;
1683
30
      }
1684
4
    }
1685
8
1686
8
    Offset = G.back().r_offset;
1687
8
  }
1688
4
1689
4
  // Now the ungrouped relatives.
1690
4
  if (!UngroupedRelatives.empty()) {
1691
4
    Add(UngroupedRelatives.size());
1692
4
    Add(RELOCATION_GROUPED_BY_INFO_FLAG | HasAddendIfRela);
1693
4
    Add(Target->RelativeRel);
1694
32
    for (Elf_Rela &R : UngroupedRelatives) {
1695
32
      Add(R.r_offset - Offset);
1696
32
      Offset = R.r_offset;
1697
32
      if (Config->IsRela) {
1698
16
        Add(R.r_addend - Addend);
1699
16
        Addend = R.r_addend;
1700
16
      }
1701
32
    }
1702
4
  }
1703
4
1704
4
  // Finally the non-relative relocations.
1705
4
  llvm::sort(NonRelatives.begin(), NonRelatives.end(),
1706
4
             [](const Elf_Rela &A, const Elf_Rela &B) {
1707
4
               return A.r_offset < B.r_offset;
1708
4
             });
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, false>, true> const&) const
Line
Count
Source
1706
2
             [](const Elf_Rela &A, const Elf_Rela &B) {
1707
2
               return A.r_offset < B.r_offset;
1708
2
             });
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, false>, true> const&) const
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)1, true>, true> const&) const
Line
Count
Source
1706
2
             [](const Elf_Rela &A, const Elf_Rela &B) {
1707
2
               return A.r_offset < B.r_offset;
1708
2
             });
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, true> >::updateAllocSize()::'lambda'(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> const&)::operator()(llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> const&, llvm::object::Elf_Rel_Impl<llvm::object::ELFType<(llvm::support::endianness)0, true>, true> const&) const
1709
4
  if (!NonRelatives.empty()) {
1710
4
    Add(NonRelatives.size());
1711
4
    Add(HasAddendIfRela);
1712
8
    for (Elf_Rela &R : NonRelatives) {
1713
8
      Add(R.r_offset - Offset);
1714
8
      Offset = R.r_offset;
1715
8
      Add(R.r_info);
1716
8
      if (Config->IsRela) {
1717
4
        Add(R.r_addend - Addend);
1718
4
        Addend = R.r_addend;
1719
4
      }
1720
8
    }
1721
4
  }
1722
4
1723
4
  // Returns whether the section size changed. We need to keep recomputing both
1724
4
  // section layout and the contents of this section until the size converges
1725
4
  // because changing this section's size can affect section layout, which in
1726
4
  // turn can affect the sizes of the LEB-encoded integers stored in this
1727
4
  // section.
1728
4
  return RelocData.size() != OldSize;
1729
4
}
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, false> >::updateAllocSize()
Line
Count
Source
1554
2
bool AndroidPackedRelocationSection<ELFT>::updateAllocSize() {
1555
2
  // This function computes the contents of an Android-format packed relocation
1556
2
  // section.
1557
2
  //
1558
2
  // This format compresses relocations by using relocation groups to factor out
1559
2
  // fields that are common between relocations and storing deltas from previous
1560
2
  // relocations in SLEB128 format (which has a short representation for small
1561
2
  // numbers). A good example of a relocation type with common fields is
1562
2
  // R_*_RELATIVE, which is normally used to represent function pointers in
1563
2
  // vtables. In the REL format, each relative relocation has the same r_info
1564
2
  // field, and is only different from other relative relocations in terms of
1565
2
  // the r_offset field. By sorting relocations by offset, grouping them by
1566
2
  // r_info and representing each relocation with only the delta from the
1567
2
  // previous offset, each 8-byte relocation can be compressed to as little as 1
1568
2
  // byte (or less with run-length encoding). This relocation packer was able to
1569
2
  // reduce the size of the relocation section in an Android Chromium DSO from
1570
2
  // 2,911,184 bytes to 174,693 bytes, or 6% of the original size.
1571
2
  //
1572
2
  // A relocation section consists of a header containing the literal bytes
1573
2
  // 'APS2' followed by a sequence of SLEB128-encoded integers. The first two
1574
2
  // elements are the total number of relocations in the section and an initial
1575
2
  // r_offset value. The remaining elements define a sequence of relocation
1576
2
  // groups. Each relocation group starts with a header consisting of the
1577
2
  // following elements:
1578
2
  //
1579
2
  // - the number of relocations in the relocation group
1580
2
  // - flags for the relocation group
1581
2
  // - (if RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG is set) the r_offset delta
1582
2
  //   for each relocation in the group.
1583
2
  // - (if RELOCATION_GROUPED_BY_INFO_FLAG is set) the value of the r_info
1584
2
  //   field for each relocation in the group.
1585
2
  // - (if RELOCATION_GROUP_HAS_ADDEND_FLAG and
1586
2
  //   RELOCATION_GROUPED_BY_ADDEND_FLAG are set) the r_addend delta for
1587
2
  //   each relocation in the group.
1588
2
  //
1589
2
  // Following the relocation group header are descriptions of each of the
1590
2
  // relocations in the group. They consist of the following elements:
1591
2
  //
1592
2
  // - (if RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG is not set) the r_offset
1593
2
  //   delta for this relocation.
1594
2
  // - (if RELOCATION_GROUPED_BY_INFO_FLAG is not set) the value of the r_info
1595
2
  //   field for this relocation.
1596
2
  // - (if RELOCATION_GROUP_HAS_ADDEND_FLAG is set and
1597
2
  //   RELOCATION_GROUPED_BY_ADDEND_FLAG is not set) the r_addend delta for
1598
2
  //   this relocation.
1599
2
1600
2
  size_t OldSize = RelocData.size();
1601
2
1602
2
  RelocData = {'A', 'P', 'S', '2'};
1603
2
  raw_svector_ostream OS(RelocData);
1604
2
  auto Add = [&](int64_t V) { encodeSLEB128(V, OS); };
1605
2
1606
2
  // The format header includes the number of relocations and the initial
1607
2
  // offset (we set this to zero because the first relocation group will
1608
2
  // perform the initial adjustment).
1609
2
  Add(Relocs.size());
1610
2
  Add(0);
1611
2
1612
2
  std::vector<Elf_Rela> Relatives, NonRelatives;
1613
2
1614
54
  for (const DynamicReloc &Rel : Relocs) {
1615
54
    Elf_Rela R;
1616
54
    encodeDynamicReloc<ELFT>(&R, Rel);
1617
54
1618
54
    if (R.getType(Config->IsMips64EL) == Target->RelativeRel)
1619
50
      Relatives.push_back(R);
1620
4
    else
1621
4
      NonRelatives.push_back(R);
1622
54
  }
1623
2
1624
2
  llvm::sort(Relatives.begin(), Relatives.end(),
1625
2
             [](const Elf_Rel &A, const Elf_Rel &B) {
1626
2
               return A.r_offset < B.r_offset;
1627
2
             });
1628
2
1629
2
  // Try to find groups of relative relocations which are spaced one word
1630
2
  // apart from one another. These generally correspond to vtable entries. The
1631
2
  // format allows these groups to be encoded using a sort of run-length
1632
2
  // encoding, but each group will cost 7 bytes in addition to the offset from
1633
2
  // the previous group, so it is only profitable to do this for groups of
1634
2
  // size 8 or larger.
1635
2
  std::vector<Elf_Rela> UngroupedRelatives;
1636
2
  std::vector<std::vector<Elf_Rela>> RelativeGroups;
1637
10
  for (auto I = Relatives.begin(), E = Relatives.end(); I != E;) {
1638
8
    std::vector<Elf_Rela> Group;
1639
50
    do {
1640
50
      Group.push_back(*I++);
1641
50
    } while (I != E && 
(I - 1)->r_offset + Config->Wordsize == I->r_offset48
);
1642
8
1643
8
    if (Group.size() < 8)
1644
4
      UngroupedRelatives.insert(UngroupedRelatives.end(), Group.begin(),
1645
4
                                Group.end());
1646
4
    else
1647
4
      RelativeGroups.emplace_back(std::move(Group));
1648
8
  }
1649
2
1650
2
  unsigned HasAddendIfRela =
1651
2
      Config->IsRela ? 
RELOCATION_GROUP_HAS_ADDEND_FLAG0
: 0;
1652
2
1653
2
  uint64_t Offset = 0;
1654
2
  uint64_t Addend = 0;
1655
2
1656
2
  // Emit the run-length encoding for the groups of adjacent relative
1657
2
  // relocations. Each group is represented using two groups in the packed
1658
2
  // format. The first is used to set the current offset to the start of the
1659
2
  // group (and also encodes the first relocation), and the second encodes the
1660
2
  // remaining relocations.
1661
4
  for (std::vector<Elf_Rela> &G : RelativeGroups) {
1662
4
    // The first relocation in the group.
1663
4
    Add(1);
1664
4
    Add(RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG |
1665
4
        RELOCATION_GROUPED_BY_INFO_FLAG | HasAddendIfRela);
1666
4
    Add(G[0].r_offset - Offset);
1667
4
    Add(Target->RelativeRel);
1668
4
    if (Config->IsRela) {
1669
0
      Add(G[0].r_addend - Addend);
1670
0
      Addend = G[0].r_addend;
1671
0
    }
1672
4
1673
4
    // The remaining relocations.
1674
4
    Add(G.size() - 1);
1675
4
    Add(RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG |
1676
4
        RELOCATION_GROUPED_BY_INFO_FLAG | HasAddendIfRela);
1677
4
    Add(Config->Wordsize);
1678
4
    Add(Target->RelativeRel);
1679
4
    if (Config->IsRela) {
1680
0
      for (auto I = G.begin() + 1, E = G.end(); I != E; ++I) {
1681
0
        Add(I->r_addend - Addend);
1682
0
        Addend = I->r_addend;
1683
0
      }
1684
0
    }
1685
4
1686
4
    Offset = G.back().r_offset;
1687
4
  }
1688
2
1689
2
  // Now the ungrouped relatives.
1690
2
  if (!UngroupedRelatives.empty()) {
1691
2
    Add(UngroupedRelatives.size());
1692
2
    Add(RELOCATION_GROUPED_BY_INFO_FLAG | HasAddendIfRela);
1693
2
    Add(Target->RelativeRel);
1694
16
    for (Elf_Rela &R : UngroupedRelatives) {
1695
16
      Add(R.r_offset - Offset);
1696
16
      Offset = R.r_offset;
1697
16
      if (Config->IsRela) {
1698
0
        Add(R.r_addend - Addend);
1699
0
        Addend = R.r_addend;
1700
0
      }
1701
16
    }
1702
2
  }
1703
2
1704
2
  // Finally the non-relative relocations.
1705
2
  llvm::sort(NonRelatives.begin(), NonRelatives.end(),
1706
2
             [](const Elf_Rela &A, const Elf_Rela &B) {
1707
2
               return A.r_offset < B.r_offset;
1708
2
             });
1709
2
  if (!NonRelatives.empty()) {
1710
2
    Add(NonRelatives.size());
1711
2
    Add(HasAddendIfRela);
1712
4
    for (Elf_Rela &R : NonRelatives) {
1713
4
      Add(R.r_offset - Offset);
1714
4
      Offset = R.r_offset;
1715
4
      Add(R.r_info);
1716
4
      if (Config->IsRela) {
1717
0
        Add(R.r_addend - Addend);
1718
0
        Addend = R.r_addend;
1719
0
      }
1720
4
    }
1721
2
  }
1722
2
1723
2
  // Returns whether the section size changed. We need to keep recomputing both
1724
2
  // section layout and the contents of this section until the size converges
1725
2
  // because changing this section's size can affect section layout, which in
1726
2
  // turn can affect the sizes of the LEB-encoded integers stored in this
1727
2
  // section.
1728
2
  return RelocData.size() != OldSize;
1729
2
}
Unexecuted instantiation: lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)0, false> >::updateAllocSize()
lld::elf::AndroidPackedRelocationSection<llvm::object::ELFType<(llvm::support::endianness)1, true> >::updateAllocSize()
Line
Count
Source
1554
2
bool AndroidPackedRelocationSection<ELFT>::updateAllocSize() {
1555
2
  // This function computes the contents of an Android-format packed relocation
1556
2
  // section.
1557
2
  //
1558
2
  // This format compresses relocations by using relocation groups to factor out
1559
2
  // fields that are common between relocations and storing deltas from previous
1560
2
  // relocations in SLEB128 format (which has a short representation for small
1561
2
  // numbers). A good example of a relocation type with common fields is
1562
2
  // R_*_RELATIVE, which is normally used to represent function pointers in
1563
2
  // vtables. In the REL format, each relative relocation has the same r_info
1564
2
  // field, and is only different from other relative relocations in terms of
1565
2
  // the r_offset field. By sorting relocations by offset, grouping them by
1566
2
  // r_info and representing each relocation with only the delta from the
1567
2
  // previous offset, each 8-byte relocation can be compressed to as little as 1
1568
2
  // byte (or less with run-length encoding). This relocation packer was able to
1569
2
  // reduce the size of the relocation section in an Android Chromium DSO from
1570
2
  // 2,911,184 bytes to 174,693 bytes, or 6% of the original size.
1571
2
  //
1572
2
  // A relocation section consists of a header containing the literal bytes
1573
2
  // 'APS2' followed by a sequence of SLEB128-encoded integers. The first two
1574
2
  // elements are the total number of relocations in the section and an initial
1575
2
  // r_offset value. The remaining elements define a sequence of relocation
1576
2
  // groups. Each relocation group starts with a header consisting of the
1577
2
  // following elements:
1578
2
  //
1579
2
  // - the number of relocations in the relocation group
1580
2
  // - flags for the relocation group
1581
2
  // - (if RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG is set) the r_offset delta
1582
2
  //   for each relocation in the group.
1583
2
  // - (if RELOCATION_GROUPED_BY_INFO_FLAG is set) the value of the r_info
1584
2
  //   field for each relocation in the group.
1585
2
  // - (if RELOCATION_GROUP_HAS_ADDEND_FLAG and
1586
2
  //   RELOCATION_GROUPED_BY_ADDEND_FLAG are set) the r_addend delta for
1587
2
  //   each relocation in the group.
1588
2
  //
1589
2
  // Following the relocation group header are descriptions of each of the
1590
2
  // relocations in the group. They consist of the following elements:
1591
2
  //
1592
2
  // - (if RELOCATION_GROUPED_BY_OFFSET_DELTA_FLAG is not set) the r_offset
1593
2
  //   delta for this relocation.
1594
2
  // - (if RELOCATION_GROUPED_BY_INFO_FLAG is not set) the value of the r_info
1595
2
  //   field for this relocation.
1596
2
  // - (if RELOCATION_GROUP_HAS_ADDEND_FLAG is set and
1597
2
  //   RELOCATION_GROUPED_BY_ADDEND_FLAG is not set) the r_addend delta for
1598
2
  //   this relocation.
1599
2
1600
2
  size_t OldSize = RelocData.size();
1601
2
1602
2
  RelocData = {'A', 'P', 'S', '2'};
1603
2
  raw_svector_ostream OS(RelocData);
1604
2
  auto Add = [&](int64_t V) { encodeSLEB128(V, OS); };
1605
2
1606
2
  // The format header includes the number of relocations and the initial
1607
2
  // offset (we set this to zero because the first relocation group will
1608
2
  // perform the initial adjustment).