summaryrefslogtreecommitdiffstats
path: root/llvm/lib
diff options
context:
space:
mode:
authorRafael Espindola <rafael.espindola@gmail.com>2015-06-03 21:52:06 +0000
committerRafael Espindola <rafael.espindola@gmail.com>2015-06-03 21:52:06 +0000
commit212fdde20540d79cf227f3e5a5e008099aad37b8 (patch)
treedfbceb001f81e0a9069ef22cd396da49dfb2b383 /llvm/lib
parent9f0c63bfdfe849095ff8c673f7b6bdb993144fa5 (diff)
downloadbcm5719-llvm-212fdde20540d79cf227f3e5a5e008099aad37b8.tar.gz
bcm5719-llvm-212fdde20540d79cf227f3e5a5e008099aad37b8.zip
Remember if a weakref of a symbol has been used.
This avoids yet another last minute patching of the binding. While at it, also simplify the weakref implementation a bit by not walking past it in the expression evaluation. llvm-svn: 238982
Diffstat (limited to 'llvm/lib')
-rw-r--r--llvm/lib/MC/ELFObjectWriter.cpp40
-rw-r--r--llvm/lib/MC/MCExpr.cpp7
-rw-r--r--llvm/lib/MC/MCSymbolELF.cpp6
3 files changed, 27 insertions, 26 deletions
diff --git a/llvm/lib/MC/ELFObjectWriter.cpp b/llvm/lib/MC/ELFObjectWriter.cpp
index bf9a29a41db..6e3f9d189dd 100644
--- a/llvm/lib/MC/ELFObjectWriter.cpp
+++ b/llvm/lib/MC/ELFObjectWriter.cpp
@@ -98,7 +98,6 @@ class ELFObjectWriter : public MCObjectWriter {
/// The target specific ELF writer instance.
std::unique_ptr<MCELFObjectTargetWriter> TargetObjectWriter;
- SmallPtrSet<const MCSymbol *, 16> WeakrefUsedInReloc;
DenseMap<const MCSymbolELF *, const MCSymbolELF *> Renames;
llvm::DenseMap<const MCSectionELF *, std::vector<ELFRelocationEntry>>
@@ -141,7 +140,6 @@ class ELFObjectWriter : public MCObjectWriter {
: MCObjectWriter(OS, IsLittleEndian), TargetObjectWriter(MOTW) {}
void reset() override {
- WeakrefUsedInReloc.clear();
Renames.clear();
Relocations.clear();
StrTabBuilder.clear();
@@ -589,25 +587,6 @@ bool ELFObjectWriter::shouldRelocateWithSymbol(const MCAssembler &Asm,
return false;
}
-static const MCSymbol *getWeakRef(const MCSymbolRefExpr &Ref) {
- const MCSymbol &Sym = Ref.getSymbol();
-
- if (Ref.getKind() == MCSymbolRefExpr::VK_WEAKREF)
- return &Sym;
-
- if (!Sym.isVariable())
- return nullptr;
-
- const MCExpr *Expr = Sym.getVariableValue();
- const auto *Inner = dyn_cast<MCSymbolRefExpr>(Expr);
- if (!Inner)
- return nullptr;
-
- if (Inner->getKind() == MCSymbolRefExpr::VK_WEAKREF)
- return &Inner->getSymbol();
- return nullptr;
-}
-
// True if the assembler knows nothing about the final value of the symbol.
// This doesn't cover the comdat issues, since in those cases the assembler
// can at least know that all symbols in the section will move together.
@@ -681,6 +660,17 @@ void ELFObjectWriter::RecordRelocation(MCAssembler &Asm,
const MCSymbolRefExpr *RefA = Target.getSymA();
const auto *SymA = RefA ? cast<MCSymbolELF>(&RefA->getSymbol()) : nullptr;
+ bool ViaWeakRef = false;
+ if (SymA && SymA->isVariable()) {
+ const MCExpr *Expr = SymA->getVariableValue();
+ if (const auto *Inner = dyn_cast<MCSymbolRefExpr>(Expr)) {
+ if (Inner->getKind() == MCSymbolRefExpr::VK_WEAKREF) {
+ SymA = cast<MCSymbolELF>(&Inner->getSymbol());
+ ViaWeakRef = true;
+ }
+ }
+ }
+
unsigned Type = GetRelocType(Target, Fixup, IsPCRel);
bool RelocateWithSymbol = shouldRelocateWithSymbol(Asm, RefA, SymA, C, Type);
if (!RelocateWithSymbol && SymA && !SymA->isUndefined())
@@ -709,8 +699,8 @@ void ELFObjectWriter::RecordRelocation(MCAssembler &Asm,
if (const MCSymbolELF *R = Renames.lookup(SymA))
SymA = R;
- if (const MCSymbol *WeakRef = getWeakRef(*RefA))
- WeakrefUsedInReloc.insert(WeakRef);
+ if (ViaWeakRef)
+ SymA->setIsWeakrefUsedInReloc();
else
SymA->setUsedInReloc();
}
@@ -785,7 +775,7 @@ void ELFObjectWriter::computeSymbolTable(
for (const MCSymbol &S : Asm.symbols()) {
const auto &Symbol = cast<MCSymbolELF>(S);
bool Used = Symbol.isUsedInReloc();
- bool WeakrefUsed = WeakrefUsedInReloc.count(&Symbol);
+ bool WeakrefUsed = Symbol.isWeakrefUsedInReloc();
bool isSignature = Symbol.isSignature();
if (!isInSymtab(Layout, Symbol, Used || WeakrefUsed || isSignature,
@@ -809,8 +799,6 @@ void ELFObjectWriter::computeSymbolTable(
} else {
MSD.SectionIndex = ELF::SHN_UNDEF;
}
- if (!Used && WeakrefUsed)
- Symbol.setBinding(ELF::STB_WEAK);
} else {
const MCSectionELF &Section =
static_cast<const MCSectionELF &>(Symbol.getSection());
diff --git a/llvm/lib/MC/MCExpr.cpp b/llvm/lib/MC/MCExpr.cpp
index 39ea8722547..f5e39e7815d 100644
--- a/llvm/lib/MC/MCExpr.cpp
+++ b/llvm/lib/MC/MCExpr.cpp
@@ -601,6 +601,13 @@ bool MCExpr::evaluateAsValue(MCValue &Res, const MCAsmLayout &Layout) const {
}
static bool canExpand(const MCSymbol &Sym, const MCAssembler *Asm, bool InSet) {
+ const MCExpr *Expr = Sym.getVariableValue();
+ const auto *Inner = dyn_cast<MCSymbolRefExpr>(Expr);
+ if (Inner) {
+ if (Inner->getKind() == MCSymbolRefExpr::VK_WEAKREF)
+ return false;
+ }
+
if (InSet)
return true;
if (!Asm)
diff --git a/llvm/lib/MC/MCSymbolELF.cpp b/llvm/lib/MC/MCSymbolELF.cpp
index 4e6def0c2e1..458248104e0 100644
--- a/llvm/lib/MC/MCSymbolELF.cpp
+++ b/llvm/lib/MC/MCSymbolELF.cpp
@@ -35,6 +35,8 @@ unsigned MCSymbolELF::getBinding() const {
return ELF::STB_LOCAL;
if (isUsedInReloc())
return ELF::STB_GLOBAL;
+ if (isWeakrefUsedInReloc())
+ return ELF::STB_WEAK;
if (isSignature())
return ELF::STB_LOCAL;
return ELF::STB_GLOBAL;
@@ -96,6 +98,10 @@ bool MCSymbolELF::isUsedInReloc() const {
return UsedInReloc;
}
+void MCSymbolELF::setIsWeakrefUsedInReloc() const { WeakrefUsedInReloc = true; }
+
+bool MCSymbolELF::isWeakrefUsedInReloc() const { return WeakrefUsedInReloc; }
+
void MCSymbolELF::setIsSignature() const { IsSignature = true; }
bool MCSymbolELF::isSignature() const { return IsSignature; }
OpenPOWER on IntegriCloud