[lld] r362867 - [ELF][PPC] Simplify {read,write}FromHalf16
Fangrui Song via llvm-commits
llvm-commits at lists.llvm.org
Fri Jun 7 22:19:06 PDT 2019
Author: maskray
Date: Fri Jun 7 22:19:05 2019
New Revision: 362867
URL: http://llvm.org/viewvc/llvm-project?rev=362867&view=rev
Log:
[ELF][PPC] Simplify {read,write}FromHalf16
I've change the variable names used in PPC64.cpp from "Instr" to "Insn"
because "Insn" is a more common abbreviation for "instruction".
While changing PPC64.cpp relocateOne(), make R_PPC64_ADDR16_LO{_DS}
slightly more efficient by saving a read and a write for the TocOptimize
case.
Reviewed By: ruiu
Differential Revision: https://reviews.llvm.org/D63043
Modified:
lld/trunk/ELF/Arch/PPC.cpp
lld/trunk/ELF/Arch/PPC64.cpp
Modified: lld/trunk/ELF/Arch/PPC.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Arch/PPC.cpp?rev=362867&r1=362866&r2=362867&view=diff
==============================================================================
--- lld/trunk/ELF/Arch/PPC.cpp (original)
+++ lld/trunk/ELF/Arch/PPC.cpp Fri Jun 7 22:19:05 2019
@@ -53,11 +53,11 @@ static uint16_t lo(uint32_t V) { return
static uint16_t ha(uint32_t V) { return (V + 0x8000) >> 16; }
static uint32_t readFromHalf16(const uint8_t *Loc) {
- return read32(Loc - (Config->EKind == ELF32BEKind ? 2 : 0));
+ return read32(Config->IsLE ? Loc : Loc - 2);
}
static void writeFromHalf16(uint8_t *Loc, uint32_t Insn) {
- write32(Loc - (Config->EKind == ELF32BEKind ? 2 : 0), Insn);
+ write32(Config->IsLE ? Loc : Loc - 2, Insn);
}
void elf::writePPC32GlinkSection(uint8_t *Buf, size_t NumEntries) {
Modified: lld/trunk/ELF/Arch/PPC64.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Arch/PPC64.cpp?rev=362867&r1=362866&r2=362867&view=diff
==============================================================================
--- lld/trunk/ELF/Arch/PPC64.cpp (original)
+++ lld/trunk/ELF/Arch/PPC64.cpp Fri Jun 7 22:19:05 2019
@@ -274,12 +274,12 @@ static bool isInstructionUpdateForm(uint
// pointer is pointing into the middle of the word we want to extract, and on
// little-endian it is pointing to the start of the word. These 2 helpers are to
// simplify reading and writing in that context.
-static void writeInstrFromHalf16(uint8_t *Loc, uint32_t Instr) {
- write32(Loc - (Config->EKind == ELF64BEKind ? 2 : 0), Instr);
+static void writeFromHalf16(uint8_t *Loc, uint32_t Insn) {
+ write32(Config->IsLE ? Loc : Loc - 2, Insn);
}
-static uint32_t readInstrFromHalf16(const uint8_t *Loc) {
- return read32(Loc - (Config->EKind == ELF64BEKind ? 2 : 0));
+static uint32_t readFromHalf16(const uint8_t *Loc) {
+ return read32(Config->IsLE ? Loc : Loc - 2);
}
PPC64::PPC64() {
@@ -361,10 +361,10 @@ void PPC64::relaxGot(uint8_t *Loc, RelTy
case R_PPC64_TOC16_LO_DS: {
// Convert "ld reg, .LC0 at toc@l(reg)" to "addi reg, reg, var at toc@l" or
// "addi reg, 2, var at toc".
- uint32_t Instr = readInstrFromHalf16(Loc);
- if (getPrimaryOpCode(Instr) != LD)
+ uint32_t Insn = readFromHalf16(Loc);
+ if (getPrimaryOpCode(Insn) != LD)
error("expected a 'ld' for got-indirect to toc-relative relaxing");
- writeInstrFromHalf16(Loc, (Instr & 0x03FFFFFF) | 0x38000000);
+ writeFromHalf16(Loc, (Insn & 0x03ffffff) | 0x38000000);
relocateOne(Loc, R_PPC64_TOC16_LO, Val);
break;
}
@@ -391,11 +391,11 @@ void PPC64::relaxTlsGdToLe(uint8_t *Loc,
switch (Type) {
case R_PPC64_GOT_TLSGD16_HA:
- writeInstrFromHalf16(Loc, 0x60000000); // nop
+ writeFromHalf16(Loc, 0x60000000); // nop
break;
case R_PPC64_GOT_TLSGD16:
case R_PPC64_GOT_TLSGD16_LO:
- writeInstrFromHalf16(Loc, 0x3c6d0000); // addis r3, r13
+ writeFromHalf16(Loc, 0x3c6d0000); // addis r3, r13
relocateOne(Loc, R_PPC64_TPREL16_HA, Val);
break;
case R_PPC64_TLSGD:
@@ -430,10 +430,10 @@ void PPC64::relaxTlsLdToLe(uint8_t *Loc,
switch (Type) {
case R_PPC64_GOT_TLSLD16_HA:
- writeInstrFromHalf16(Loc, 0x60000000); // nop
+ writeFromHalf16(Loc, 0x60000000); // nop
break;
case R_PPC64_GOT_TLSLD16_LO:
- writeInstrFromHalf16(Loc, 0x3c6d0000); // addis r3, r13, 0
+ writeFromHalf16(Loc, 0x3c6d0000); // addis r3, r13, 0
break;
case R_PPC64_TLSLD:
write32(Loc, 0x60000000); // nop
@@ -757,7 +757,7 @@ void PPC64::relocateOne(uint8_t *Loc, Re
checkInt(Loc, Val, 16, OriginalType);
// DQ-form instructions use bits 28-31 as part of the instruction encoding
// DS-form instructions only use bits 30-31.
- uint16_t Mask = isDQFormInstruction(readInstrFromHalf16(Loc)) ? 0xF : 0x3;
+ uint16_t Mask = isDQFormInstruction(readFromHalf16(Loc)) ? 0xf : 0x3;
checkAlignment(Loc, lo(Val), Mask + 1, OriginalType);
write16(Loc, (read16(Loc) & Mask) | lo(Val));
} break;
@@ -765,7 +765,7 @@ void PPC64::relocateOne(uint8_t *Loc, Re
case R_PPC64_REL16_HA:
case R_PPC64_TPREL16_HA:
if (Config->TocOptimize && ShouldTocOptimize && ha(Val) == 0)
- writeInstrFromHalf16(Loc, 0x60000000);
+ writeFromHalf16(Loc, 0x60000000);
else
write16(Loc, ha(Val));
break;
@@ -797,35 +797,36 @@ void PPC64::relocateOne(uint8_t *Loc, Re
// changed into a nop. The lo part then needs to be updated to use the
// toc-pointer register r2, as the base register.
if (Config->TocOptimize && ShouldTocOptimize && ha(Val) == 0) {
- uint32_t Instr = readInstrFromHalf16(Loc);
- if (isInstructionUpdateForm(Instr))
+ uint32_t Insn = readFromHalf16(Loc);
+ if (isInstructionUpdateForm(Insn))
error(getErrorLocation(Loc) +
"can't toc-optimize an update instruction: 0x" +
- utohexstr(Instr));
- Instr = (Instr & 0xFFE00000) | 0x00020000;
- writeInstrFromHalf16(Loc, Instr);
+ utohexstr(Insn));
+ writeFromHalf16(Loc, (Insn & 0xffe00000) | 0x00020000 | lo(Val));
+ } else {
+ write16(Loc, lo(Val));
}
- write16(Loc, lo(Val));
break;
case R_PPC64_ADDR16_LO_DS:
case R_PPC64_TPREL16_LO_DS: {
// DQ-form instructions use bits 28-31 as part of the instruction encoding
// DS-form instructions only use bits 30-31.
- uint32_t Inst = readInstrFromHalf16(Loc);
- uint16_t Mask = isDQFormInstruction(Inst) ? 0xF : 0x3;
+ uint32_t Insn = readFromHalf16(Loc);
+ uint16_t Mask = isDQFormInstruction(Insn) ? 0xf : 0x3;
checkAlignment(Loc, lo(Val), Mask + 1, OriginalType);
if (Config->TocOptimize && ShouldTocOptimize && ha(Val) == 0) {
// When the high-adjusted part of a toc relocation evalutes to 0, it is
// changed into a nop. The lo part then needs to be updated to use the toc
// pointer register r2, as the base register.
- if (isInstructionUpdateForm(Inst))
+ if (isInstructionUpdateForm(Insn))
error(getErrorLocation(Loc) +
"Can't toc-optimize an update instruction: 0x" +
- Twine::utohexstr(Inst));
- Inst = (Inst & 0xFFE0000F) | 0x00020000;
- writeInstrFromHalf16(Loc, Inst);
+ Twine::utohexstr(Insn));
+ Insn &= 0xffe00000 | Mask;
+ writeFromHalf16(Loc, Insn | 0x00020000 | lo(Val));
+ } else {
+ write16(Loc, (read16(Loc) & Mask) | lo(Val));
}
- write16(Loc, (read16(Loc) & Mask) | lo(Val));
} break;
case R_PPC64_ADDR32:
case R_PPC64_REL32:
@@ -934,8 +935,8 @@ void PPC64::relaxTlsGdToIe(uint8_t *Loc,
case R_PPC64_GOT_TLSGD16_LO: {
// Relax from addi r3, rA, sym at got@tlsgd at l to
// ld r3, sym at got@tprel at l(rA)
- uint32_t InputRegister = (readInstrFromHalf16(Loc) & (0x1f << 16));
- writeInstrFromHalf16(Loc, 0xE8600000 | InputRegister);
+ uint32_t RA = (readFromHalf16(Loc) & (0x1f << 16));
+ writeFromHalf16(Loc, 0xe8600000 | RA);
relocateOne(Loc, R_PPC64_GOT_TPREL16_LO_DS, Val);
return;
}
More information about the llvm-commits
mailing list