Don't produce relative relocs to ro segments.

We were already checking for non relative relocations.

If we ever decide to add support for rw text segments this means we will
have a single spot to add the flag.

llvm-svn: 268558
This commit is contained in:
Rafael Espindola
2016-05-04 21:40:07 +00:00
parent 569eaec5f3
commit de17d28a32
3 changed files with 30 additions and 13 deletions

View File

@@ -976,6 +976,7 @@ bool AArch64TargetInfo::usesOnlyLowPageBits(uint32_t Type) const {
case R_AARCH64_LDST64_ABS_LO12_NC:
case R_AARCH64_LDST128_ABS_LO12_NC:
case R_AARCH64_LD64_GOT_LO12_NC:
case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
return true;
}
}

View File

@@ -442,14 +442,25 @@ static bool needsPlt(RelExpr Expr) {
template <class ELFT>
static bool isStaticLinkTimeConstant(RelExpr E, uint32_t Type,
const SymbolBody &Body) {
if (E == R_SIZE)
// These expressions always compute a constant
if (E == R_SIZE || E == R_GOT_FROM_END || E == R_GOT_OFF || E == R_MIPS_GOT ||
E == R_MIPS_GOT_LOCAL || E == R_GOT_PAGE_PC || E == R_GOT_PC ||
E == R_PLT_PC || E == R_TLSGD_PC || E == R_TLSGD || E == R_PPC_PLT_OPD)
return true;
bool AbsVal = (isAbsolute<ELFT>(Body) || Body.isTls()) &&
!refersToGotEntry(E) && !needsPlt(E);
// These never do, except if the entire file is position dependent or if
// only the low bits are used.
if (E == R_GOT || E == R_PLT)
return Target->usesOnlyLowPageBits(Type) || !Config->Pic;
bool RelE = E == R_PC || E == R_PLT_PC || E == R_GOT_PC || E == R_GOTREL ||
E == R_PAGE_PC;
if (Body.isPreemptible())
return false;
if (!Config->Pic)
return true;
bool AbsVal = isAbsolute<ELFT>(Body) || Body.isTls();
bool RelE = E == R_PC || E == R_GOTREL || E == R_PAGE_PC;
if (AbsVal && !RelE)
return true;
if (!AbsVal && RelE)
@@ -497,16 +508,13 @@ static RelExpr fromPlt(RelExpr Expr) {
template <class ELFT>
RelExpr Writer<ELFT>::adjustExpr(SymbolBody &Body, bool IsWrite, RelExpr Expr,
uint32_t Type) {
if (Body.isGnuIFunc())
return toPlt(Expr);
bool Preemptible = Body.isPreemptible();
if (needsPlt(Expr)) {
if (Preemptible)
return Expr;
return fromPlt(Expr);
}
if (Body.isGnuIFunc())
Expr = toPlt(Expr);
else if (needsPlt(Expr) && !Preemptible)
Expr = fromPlt(Expr);
if (IsWrite || refersToGotEntry(Expr) || needsPlt(Expr) || !Preemptible)
if (IsWrite || isStaticLinkTimeConstant<ELFT>(Expr, Type, Body))
return Expr;
// This relocation would require the dynamic linker to write a value to read

View File

@@ -0,0 +1,8 @@
// REQUIRES: x86
// RUN: llvm-mc -filetype=obj -triple=x86_64-pc-linux %s -o %t.o
// RUN: not ld.lld %t.o -o %t.so -shared 2>&1 | FileCheck %s
foo:
.quad foo
// CHECK: relocation R_X86_64_64 cannot be used when making a shared object; recompile with -fPIC.