[ELF] Delete relOff from TargetInfo::writePLT
authorFangrui Song <maskray@google.com>
Sat, 14 Dec 2019 23:09:43 +0000 (15:09 -0800)
committerFangrui Song <maskray@google.com>
Mon, 16 Dec 2019 19:10:02 +0000 (11:10 -0800)
This change only affects EM_386. relOff can be computed from `index`
easily, so it is unnecessarily passed as a parameter.

Both in.plt and in.iplt entries are written by writePLT. For in.iplt,
the instruction `push reloc_offset` will change because `index` is now
different. Fortunately, this does not matter because `push; jmp` is only
used by PLT. IPLT does not need the code sequence.

Reviewed By: grimar, ruiu

Differential Revision: https://reviews.llvm.org/D71518

14 files changed:
lld/ELF/Arch/AArch64.cpp
lld/ELF/Arch/ARM.cpp
lld/ELF/Arch/Hexagon.cpp
lld/ELF/Arch/Mips.cpp
lld/ELF/Arch/PPC.cpp
lld/ELF/Arch/PPC64.cpp
lld/ELF/Arch/RISCV.cpp
lld/ELF/Arch/SPARCV9.cpp
lld/ELF/Arch/X86.cpp
lld/ELF/Arch/X86_64.cpp
lld/ELF/SyntheticSections.cpp
lld/ELF/Target.h
lld/test/ELF/gnu-ifunc-i386.s
lld/test/ELF/gnu-ifunc-plt-i386.s

index 4e80e3d..6697ee3 100644 (file)
@@ -38,7 +38,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   bool needsThunk(RelExpr expr, RelType type, const InputFile *file,
                   uint64_t branchAddr, const Symbol &s,
                   int64_t a) const override;
@@ -214,8 +214,7 @@ void AArch64::writePltHeader(uint8_t *buf) const {
 }
 
 void AArch64::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                       uint64_t pltEntryAddr, int32_t index,
-                       unsigned relOff) const {
+                       uint64_t pltEntryAddr, int32_t index) const {
   const uint8_t inst[] = {
       0x10, 0x00, 0x00, 0x90, // adrp x16, Page(&(.plt.got[n]))
       0x11, 0x02, 0x40, 0xf9, // ldr  x17, [x16, Offset(&(.plt.got[n]))]
@@ -570,7 +569,7 @@ public:
   AArch64BtiPac();
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
 
 private:
   bool btiHeader; // bti instruction needed in PLT Header
@@ -630,8 +629,7 @@ void AArch64BtiPac::writePltHeader(uint8_t *buf) const {
 }
 
 void AArch64BtiPac::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                             uint64_t pltEntryAddr, int32_t index,
-                             unsigned relOff) const {
+                             uint64_t pltEntryAddr, int32_t index) const {
   // The PLT entry is of the form:
   // [btiData] addrInst (pacBr | stdBr) [nopData]
   const uint8_t btiData[] = { 0x5f, 0x24, 0x03, 0xd5 }; // bti c
index 0f522d3..d4df027 100644 (file)
@@ -35,7 +35,7 @@ public:
   void writeIgotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   void addPltSymbols(InputSection &isec, uint64_t off) const override;
   void addPltHeaderSymbols(InputSection &isd) const override;
   bool needsThunk(RelExpr expr, RelType type, const InputFile *file,
@@ -216,8 +216,7 @@ void ARM::addPltHeaderSymbols(InputSection &isec) const {
 // Long form PLT entries that do not have any restrictions on the displacement
 // of the .plt from the .plt.got.
 static void writePltLong(uint8_t *buf, uint64_t gotPltEntryAddr,
-                         uint64_t pltEntryAddr, int32_t index,
-                         unsigned relOff) {
+                         uint64_t pltEntryAddr) {
   const uint8_t pltData[] = {
       0x04, 0xc0, 0x9f, 0xe5, //     ldr ip, L2
       0x0f, 0xc0, 0x8c, 0xe0, // L1: add ip, ip, pc
@@ -232,8 +231,7 @@ static void writePltLong(uint8_t *buf, uint64_t gotPltEntryAddr,
 // The default PLT entries require the .plt.got to be within 128 Mb of the
 // .plt in the positive direction.
 void ARM::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                   uint64_t pltEntryAddr, int32_t index,
-                   unsigned relOff) const {
+                   uint64_t pltEntryAddr, int32_t /*index*/) const {
   // The PLT entry is similar to the example given in Appendix A of ELF for
   // the Arm Architecture. Instead of using the Group Relocations to find the
   // optimal rotation for the 8-bit immediate used in the add instructions we
@@ -248,7 +246,7 @@ void ARM::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
   uint64_t offset = gotPltEntryAddr - pltEntryAddr - 8;
   if (!llvm::isUInt<27>(offset)) {
     // We cannot encode the Offset, use the long form.
-    writePltLong(buf, gotPltEntryAddr, pltEntryAddr, index, relOff);
+    writePltLong(buf, gotPltEntryAddr, pltEntryAddr);
     return;
   }
   write32le(buf + 0, pltData[0] | ((offset >> 20) & 0xff));
index 67264a2..7759f31 100644 (file)
@@ -34,7 +34,7 @@ public:
   void relocateOne(uint8_t *loc, RelType type, uint64_t val) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
 };
 } // namespace
 
@@ -303,8 +303,7 @@ void Hexagon::writePltHeader(uint8_t *buf) const {
 }
 
 void Hexagon::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                       uint64_t pltEntryAddr, int32_t index,
-                       unsigned relOff) const {
+                       uint64_t pltEntryAddr, int32_t index) const {
   const uint8_t inst[] = {
       0x00, 0x40, 0x00, 0x00, // { immext (#0)
       0x0e, 0xc0, 0x49, 0x6a, //   r14 = add (pc, ##GOTn@PCREL) }
index 317b22e..048a749 100644 (file)
@@ -33,7 +33,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   bool needsThunk(RelExpr expr, RelType type, const InputFile *file,
                   uint64_t branchAddr, const Symbol &s,
                   int64_t a) const override;
@@ -319,8 +319,7 @@ template <class ELFT> void MIPS<ELFT>::writePltHeader(uint8_t *buf) const {
 
 template <class ELFT>
 void MIPS<ELFT>::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                          uint64_t pltEntryAddr, int32_t index,
-                          unsigned relOff) const {
+                          uint64_t pltEntryAddr, int32_t /*index*/) const {
   if (isMicroMips()) {
     // Overwrite trap instructions written by Writer::writeTrapInstr.
     memset(buf, 0, pltEntrySize);
index b0d93c6..be8ca30 100644 (file)
@@ -32,7 +32,7 @@ public:
     llvm_unreachable("should call writePPC32GlinkSection() instead");
   }
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-    int32_t index, unsigned relOff) const override {
+                int32_t index) const override {
     llvm_unreachable("should call writePPC32GlinkSection() instead");
   }
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
index 41639fb..e9a1c53 100644 (file)
@@ -201,7 +201,7 @@ public:
   RelType getDynRel(RelType type) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   void relocateOne(uint8_t *loc, RelType type, uint64_t val) const override;
   void writeGotHeader(uint8_t *buf) const override;
   bool needsThunk(RelExpr expr, RelType type, const InputFile *file,
@@ -669,8 +669,7 @@ void PPC64::writePltHeader(uint8_t *buf) const {
 }
 
 void PPC64::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                     uint64_t pltEntryAddr, int32_t index,
-                     unsigned relOff) const {
+                     uint64_t pltEntryAddr, int32_t index) const {
   int32_t offset = pltHeaderSize + index * pltEntrySize;
   // bl __glink_PLTresolve
   write32(buf, 0x48000000 | ((-offset) & 0x03FFFFFc));
index e7c0e36..4b5006e 100644 (file)
@@ -28,7 +28,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   RelType getDynRel(RelType type) const override;
   RelExpr getRelExpr(RelType type, const Symbol &s,
                      const uint8_t *loc) const override;
@@ -163,8 +163,7 @@ void RISCV::writePltHeader(uint8_t *buf) const {
 }
 
 void RISCV::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                     uint64_t pltEntryAddr, int32_t index,
-                     unsigned relOff) const {
+                     uint64_t pltEntryAddr, int32_t /*index*/) const {
   // 1: auipc t3, %pcrel_hi(f@.got.plt)
   // l[wd] t3, %pcrel_lo(1b)(t3)
   // jalr t1, t3
index a0afdff..e870c25 100644 (file)
@@ -27,7 +27,7 @@ public:
   RelExpr getRelExpr(RelType type, const Symbol &s,
                      const uint8_t *loc) const override;
   void writePlt(uint8_t *buf, uint64_t gotEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   void relocateOne(uint8_t *loc, RelType type, uint64_t val) const override;
 };
 } // namespace
@@ -125,8 +125,7 @@ void SPARCV9::relocateOne(uint8_t *loc, RelType type, uint64_t val) const {
 }
 
 void SPARCV9::writePlt(uint8_t *buf, uint64_t gotEntryAddr,
-                       uint64_t pltEntryAddr, int32_t index,
-                       unsigned relOff) const {
+                       uint64_t pltEntryAddr, int32_t index) const {
   const uint8_t pltData[] = {
       0x03, 0x00, 0x00, 0x00, // sethi   (. - .PLT0), %g1
       0x30, 0x68, 0x00, 0x00, // ba,a    %xcc, .PLT1
index b27a6e3..31b3b0a 100644 (file)
@@ -34,7 +34,7 @@ public:
   void writeIgotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   void relocateOne(uint8_t *loc, RelType type, uint64_t val) const override;
 
   RelExpr adjustRelaxExpr(RelType type, const uint8_t *data,
@@ -214,8 +214,8 @@ void X86::writePltHeader(uint8_t *buf) const {
 }
 
 void X86::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                   uint64_t pltEntryAddr, int32_t index,
-                   unsigned relOff) const {
+                   uint64_t pltEntryAddr, int32_t index) const {
+  unsigned relOff = in.relaPlt->entsize * index;
   if (config->isPic) {
     const uint8_t inst[] = {
         0xff, 0xa3, 0, 0, 0, 0, // jmp *foo@GOT(%ebx)
@@ -416,7 +416,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
 };
 
 class RetpolineNoPic : public X86 {
@@ -425,7 +425,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
 };
 } // namespace
 
@@ -460,8 +460,8 @@ void RetpolinePic::writePltHeader(uint8_t *buf) const {
 }
 
 void RetpolinePic::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                            uint64_t pltEntryAddr, int32_t index,
-                            unsigned relOff) const {
+                            uint64_t pltEntryAddr, int32_t index) const {
+  unsigned relOff = in.relaPlt->entsize * index;
   const uint8_t insn[] = {
       0x50,                            // pushl %eax
       0x8b, 0x83, 0,    0,    0,    0, // mov foo@GOT(%ebx), %eax
@@ -518,8 +518,8 @@ void RetpolineNoPic::writePltHeader(uint8_t *buf) const {
 }
 
 void RetpolineNoPic::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                              uint64_t pltEntryAddr, int32_t index,
-                              unsigned relOff) const {
+                              uint64_t pltEntryAddr, int32_t index) const {
+  unsigned relOff = in.relaPlt->entsize * index;
   const uint8_t insn[] = {
       0x50,                         // 0:  pushl %eax
       0xa1, 0,    0,    0,    0,    // 1:  mov foo_in_GOT, %eax
index bb8d92f..459fd11 100644 (file)
@@ -34,7 +34,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
   void relocateOne(uint8_t *loc, RelType type, uint64_t val) const override;
 
   RelExpr adjustRelaxExpr(RelType type, const uint8_t *data,
@@ -156,8 +156,7 @@ void X86_64::writePltHeader(uint8_t *buf) const {
 }
 
 void X86_64::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                      uint64_t pltEntryAddr, int32_t index,
-                      unsigned relOff) const {
+                      uint64_t pltEntryAddr, int32_t index) const {
   const uint8_t inst[] = {
       0xff, 0x25, 0, 0, 0, 0, // jmpq *got(%rip)
       0x68, 0, 0, 0, 0,       // pushq <relocation index>
@@ -584,7 +583,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
 };
 
 class RetpolineZNow : public X86_64 {
@@ -593,7 +592,7 @@ public:
   void writeGotPlt(uint8_t *buf, const Symbol &s) const override {}
   void writePltHeader(uint8_t *buf) const override;
   void writePlt(uint8_t *buf, uint64_t gotPltEntryAddr, uint64_t pltEntryAddr,
-                int32_t index, unsigned relOff) const override;
+                int32_t index) const override;
 };
 } // namespace
 
@@ -629,8 +628,7 @@ void Retpoline::writePltHeader(uint8_t *buf) const {
 }
 
 void Retpoline::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                         uint64_t pltEntryAddr, int32_t index,
-                         unsigned relOff) const {
+                         uint64_t pltEntryAddr, int32_t index) const {
   const uint8_t insn[] = {
       0x4c, 0x8b, 0x1d, 0, 0, 0, 0, // 0:  mov foo@GOTPLT(%rip), %r11
       0xe8, 0,    0,    0,    0,    // 7:  callq plt+0x20
@@ -672,8 +670,7 @@ void RetpolineZNow::writePltHeader(uint8_t *buf) const {
 }
 
 void RetpolineZNow::writePlt(uint8_t *buf, uint64_t gotPltEntryAddr,
-                             uint64_t pltEntryAddr, int32_t index,
-                             unsigned relOff) const {
+                             uint64_t pltEntryAddr, int32_t index) const {
   const uint8_t insn[] = {
       0x4c, 0x8b, 0x1d, 0,    0, 0, 0, // mov foo@GOTPLT(%rip), %r11
       0xe9, 0,    0,    0,    0,       // jmp plt+0
index d5b45c8..46529eb 100644 (file)
@@ -2471,17 +2471,11 @@ void PltSection::writeTo(uint8_t *buf) {
     target->writePltHeader(buf);
   size_t off = headerSize;
 
-  RelocationBaseSection *relSec = isIplt ? in.relaIplt : in.relaPlt;
-
-  // The IPlt is immediately after the Plt, account for this in relOff
-  size_t pltOff = isIplt ? in.plt->getSize() : 0;
-
   for (size_t i = 0, e = entries.size(); i != e; ++i) {
     const Symbol *b = entries[i];
-    unsigned relOff = relSec->entsize * i + pltOff;
     uint64_t got = b->getGotPltVA();
     uint64_t plt = this->getVA() + off;
-    target->writePlt(buf + off, got, plt, b->pltIndex, relOff);
+    target->writePlt(buf + off, got, plt, b->pltIndex);
     off += target->pltEntrySize;
   }
 }
index 9d147ed..8abf580 100644 (file)
@@ -42,8 +42,7 @@ public:
   virtual void writePltHeader(uint8_t *buf) const {}
 
   virtual void writePlt(uint8_t *buf, uint64_t gotEntryAddr,
-                        uint64_t pltEntryAddr, int32_t index,
-                        unsigned relOff) const {}
+                        uint64_t pltEntryAddr, int32_t index) const {}
   virtual void addPltHeaderSymbols(InputSection &isec) const {}
   virtual void addPltSymbols(InputSection &isec, uint64_t off) const {}
 
index 2e1a506..6d35059 100644 (file)
 // DISASM-EMPTY:
 // DISASM-NEXT: foo:
 // DISASM-NEXT:   401100:       jmpl *4202784
-// DISASM-NEXT:                 pushl $16
+// DISASM-NEXT:                 pushl $0
 // DISASM-NEXT:                 jmp -32 <_start+0xa>
 // DISASM:      bar:
 // DISASM-NEXT:   401110:       jmpl *4202788
-// DISASM-NEXT:                 pushl $24
+// DISASM-NEXT:                 pushl $8
 // DISASM-NEXT:                 jmp -48 <_start+0xa>
 
 .text
index 9fd933d..180ecc3 100644 (file)
 // DISASM-NEXT:                  pushl   $8
 // DISASM-NEXT:                  jmp     -48 <.plt>
 // DISASM-NEXT:                  jmpl    *4207276
-// DISASM-NEXT:                  pushl   $48
+// DISASM-NEXT:                  pushl   $0
 // DISASM-NEXT:                  jmp     -32 <zed2@plt>
 // DISASM-NEXT:                  jmpl    *4207280
-// DISASM-NEXT:                  pushl   $56
+// DISASM-NEXT:                  pushl   $8
 // DISASM-NEXT:                  jmp     -48 <zed2@plt>
 
 .text