forked from OSchip/llvm-project
[AArch64] Support .reloc *, R_AARCH64_NONE, *
Summary: This can be used to create references among sections. When --gc-sections is used, the referenced section will be retained if the origin section is retained. Reviewed By: peter.smith Differential Revision: https://reviews.llvm.org/D61973 llvm-svn: 360981
This commit is contained in:
parent
43ca0e9eb8
commit
aa6102ad8e
|
@ -41,6 +41,8 @@ public:
|
||||||
return AArch64::NumTargetFixupKinds;
|
return AArch64::NumTargetFixupKinds;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Optional<MCFixupKind> getFixupKind(StringRef Name) const override;
|
||||||
|
|
||||||
const MCFixupKindInfo &getFixupKindInfo(MCFixupKind Kind) const override {
|
const MCFixupKindInfo &getFixupKindInfo(MCFixupKind Kind) const override {
|
||||||
const static MCFixupKindInfo Infos[AArch64::NumTargetFixupKinds] = {
|
const static MCFixupKindInfo Infos[AArch64::NumTargetFixupKinds] = {
|
||||||
// This table *must* be in the order that the fixup_* kinds are defined
|
// This table *must* be in the order that the fixup_* kinds are defined
|
||||||
|
@ -103,6 +105,7 @@ static unsigned getFixupKindNumBytes(unsigned Kind) {
|
||||||
default:
|
default:
|
||||||
llvm_unreachable("Unknown fixup kind!");
|
llvm_unreachable("Unknown fixup kind!");
|
||||||
|
|
||||||
|
case FK_NONE:
|
||||||
case AArch64::fixup_aarch64_tlsdesc_call:
|
case AArch64::fixup_aarch64_tlsdesc_call:
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
@ -304,6 +307,7 @@ static uint64_t adjustFixupValue(const MCFixup &Fixup, const MCValue &Target,
|
||||||
if (Value & 0x3)
|
if (Value & 0x3)
|
||||||
Ctx.reportError(Fixup.getLoc(), "fixup not sufficiently aligned");
|
Ctx.reportError(Fixup.getLoc(), "fixup not sufficiently aligned");
|
||||||
return (Value >> 2) & 0x3ffffff;
|
return (Value >> 2) & 0x3ffffff;
|
||||||
|
case FK_NONE:
|
||||||
case FK_Data_1:
|
case FK_Data_1:
|
||||||
case FK_Data_2:
|
case FK_Data_2:
|
||||||
case FK_Data_4:
|
case FK_Data_4:
|
||||||
|
@ -314,6 +318,12 @@ static uint64_t adjustFixupValue(const MCFixup &Fixup, const MCValue &Target,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Optional<MCFixupKind> AArch64AsmBackend::getFixupKind(StringRef Name) const {
|
||||||
|
if (TheTriple.isOSBinFormatELF() && Name == "R_AARCH64_NONE")
|
||||||
|
return FK_NONE;
|
||||||
|
return MCAsmBackend::getFixupKind(Name);
|
||||||
|
}
|
||||||
|
|
||||||
/// getFixupKindContainereSizeInBytes - The number of bytes of the
|
/// getFixupKindContainereSizeInBytes - The number of bytes of the
|
||||||
/// container involved in big endian or 0 if the item is little endian
|
/// container involved in big endian or 0 if the item is little endian
|
||||||
unsigned AArch64AsmBackend::getFixupKindContainereSizeInBytes(unsigned Kind) const {
|
unsigned AArch64AsmBackend::getFixupKindContainereSizeInBytes(unsigned Kind) const {
|
||||||
|
@ -445,6 +455,10 @@ bool AArch64AsmBackend::writeNopData(raw_ostream &OS, uint64_t Count) const {
|
||||||
bool AArch64AsmBackend::shouldForceRelocation(const MCAssembler &Asm,
|
bool AArch64AsmBackend::shouldForceRelocation(const MCAssembler &Asm,
|
||||||
const MCFixup &Fixup,
|
const MCFixup &Fixup,
|
||||||
const MCValue &Target) {
|
const MCValue &Target) {
|
||||||
|
unsigned Kind = Fixup.getKind();
|
||||||
|
if (Kind == FK_NONE)
|
||||||
|
return true;
|
||||||
|
|
||||||
// The ADRP instruction adds some multiple of 0x1000 to the current PC &
|
// The ADRP instruction adds some multiple of 0x1000 to the current PC &
|
||||||
// ~0xfff. This means that the required offset to reach a symbol can vary by
|
// ~0xfff. This means that the required offset to reach a symbol can vary by
|
||||||
// up to one step depending on where the ADRP is in memory. For example:
|
// up to one step depending on where the ADRP is in memory. For example:
|
||||||
|
@ -457,14 +471,14 @@ bool AArch64AsmBackend::shouldForceRelocation(const MCAssembler &Asm,
|
||||||
// same page as the ADRP and the instruction should encode 0x0. Assuming the
|
// same page as the ADRP and the instruction should encode 0x0. Assuming the
|
||||||
// section isn't 0x1000-aligned, we therefore need to delegate this decision
|
// section isn't 0x1000-aligned, we therefore need to delegate this decision
|
||||||
// to the linker -- a relocation!
|
// to the linker -- a relocation!
|
||||||
if ((uint32_t)Fixup.getKind() == AArch64::fixup_aarch64_pcrel_adrp_imm21)
|
if (Kind == AArch64::fixup_aarch64_pcrel_adrp_imm21)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
AArch64MCExpr::VariantKind RefKind =
|
AArch64MCExpr::VariantKind RefKind =
|
||||||
static_cast<AArch64MCExpr::VariantKind>(Target.getRefKind());
|
static_cast<AArch64MCExpr::VariantKind>(Target.getRefKind());
|
||||||
AArch64MCExpr::VariantKind SymLoc = AArch64MCExpr::getSymbolLoc(RefKind);
|
AArch64MCExpr::VariantKind SymLoc = AArch64MCExpr::getSymbolLoc(RefKind);
|
||||||
// LDR GOT relocations need a relocation
|
// LDR GOT relocations need a relocation
|
||||||
if ((uint32_t)Fixup.getKind() == AArch64::fixup_aarch64_ldr_pcrel_imm19 &&
|
if (Kind == AArch64::fixup_aarch64_ldr_pcrel_imm19 &&
|
||||||
SymLoc == AArch64MCExpr::VK_GOT)
|
SymLoc == AArch64MCExpr::VK_GOT)
|
||||||
return true;
|
return true;
|
||||||
return false;
|
return false;
|
||||||
|
|
|
@ -185,6 +185,8 @@ unsigned AArch64ELFObjectWriter::getRelocType(MCContext &Ctx,
|
||||||
if (IsILP32 && isNonILP32reloc(Fixup, RefKind, Ctx))
|
if (IsILP32 && isNonILP32reloc(Fixup, RefKind, Ctx))
|
||||||
return ELF::R_AARCH64_NONE;
|
return ELF::R_AARCH64_NONE;
|
||||||
switch ((unsigned)Fixup.getKind()) {
|
switch ((unsigned)Fixup.getKind()) {
|
||||||
|
case FK_NONE:
|
||||||
|
return ELF::R_AARCH64_NONE;
|
||||||
case FK_Data_1:
|
case FK_Data_1:
|
||||||
Ctx.reportError(Fixup.getLoc(), "1-byte data relocations not supported");
|
Ctx.reportError(Fixup.getLoc(), "1-byte data relocations not supported");
|
||||||
return ELF::R_AARCH64_NONE;
|
return ELF::R_AARCH64_NONE;
|
||||||
|
|
|
@ -0,0 +1,25 @@
|
||||||
|
# RUN: llvm-mc -triple=aarch64-linux-musl %s | FileCheck --check-prefix=PRINT %s
|
||||||
|
|
||||||
|
# RUN: llvm-mc -filetype=obj -triple=aarch64-linux-musl %s | llvm-readobj -r | FileCheck %s
|
||||||
|
|
||||||
|
# PRINT: .reloc 8, R_AARCH64_NONE, .data
|
||||||
|
# PRINT: .reloc 4, R_AARCH64_NONE, foo+4
|
||||||
|
# PRINT: .reloc 0, R_AARCH64_NONE, 8
|
||||||
|
.text
|
||||||
|
ret
|
||||||
|
nop
|
||||||
|
nop
|
||||||
|
.reloc 8, R_AARCH64_NONE, .data
|
||||||
|
.reloc 4, R_AARCH64_NONE, foo+4
|
||||||
|
.reloc 0, R_AARCH64_NONE, 8
|
||||||
|
|
||||||
|
.data
|
||||||
|
.globl foo
|
||||||
|
foo:
|
||||||
|
.word 0
|
||||||
|
.word 0
|
||||||
|
.word 0
|
||||||
|
|
||||||
|
# CHECK: 0x8 R_AARCH64_NONE .data 0x0
|
||||||
|
# CHECK-NEXT: 0x4 R_AARCH64_NONE foo 0x4
|
||||||
|
# CHECK-NEXT: 0x0 R_AARCH64_NONE - 0x8
|
Loading…
Reference in New Issue