mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-23 11:13:28 +01:00
Make all static functions become static class methods. Move shared (duplicated) functions to new MCELF class.
llvm-svn: 126686
This commit is contained in:
parent
22d34c260e
commit
6bc6d6ab39
@ -8,6 +8,7 @@ add_llvm_library(LLVMMC
|
|||||||
MCCodeEmitter.cpp
|
MCCodeEmitter.cpp
|
||||||
MCContext.cpp
|
MCContext.cpp
|
||||||
MCDisassembler.cpp
|
MCDisassembler.cpp
|
||||||
|
MCELF.cpp
|
||||||
MCELFObjectTargetWriter.cpp
|
MCELFObjectTargetWriter.cpp
|
||||||
MCELFStreamer.cpp
|
MCELFStreamer.cpp
|
||||||
MCExpr.cpp
|
MCExpr.cpp
|
||||||
|
@ -11,6 +11,7 @@
|
|||||||
//
|
//
|
||||||
//===----------------------------------------------------------------------===//
|
//===----------------------------------------------------------------------===//
|
||||||
|
|
||||||
|
#include "MCELF.h"
|
||||||
#include "llvm/ADT/OwningPtr.h"
|
#include "llvm/ADT/OwningPtr.h"
|
||||||
#include "llvm/ADT/SmallPtrSet.h"
|
#include "llvm/ADT/SmallPtrSet.h"
|
||||||
#include "llvm/ADT/STLExtras.h"
|
#include "llvm/ADT/STLExtras.h"
|
||||||
@ -38,76 +39,33 @@
|
|||||||
#include <vector>
|
#include <vector>
|
||||||
using namespace llvm;
|
using namespace llvm;
|
||||||
|
|
||||||
static unsigned GetType(const MCSymbolData &SD) {
|
|
||||||
uint32_t Type = (SD.getFlags() & (0xf << ELF_STT_Shift)) >> ELF_STT_Shift;
|
|
||||||
assert(Type == ELF::STT_NOTYPE || Type == ELF::STT_OBJECT ||
|
|
||||||
Type == ELF::STT_FUNC || Type == ELF::STT_SECTION ||
|
|
||||||
Type == ELF::STT_FILE || Type == ELF::STT_COMMON ||
|
|
||||||
Type == ELF::STT_TLS);
|
|
||||||
return Type;
|
|
||||||
}
|
|
||||||
|
|
||||||
static unsigned GetBinding(const MCSymbolData &SD) {
|
|
||||||
uint32_t Binding = (SD.getFlags() & (0xf << ELF_STB_Shift)) >> ELF_STB_Shift;
|
|
||||||
assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
|
|
||||||
Binding == ELF::STB_WEAK);
|
|
||||||
return Binding;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void SetBinding(MCSymbolData &SD, unsigned Binding) {
|
|
||||||
assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
|
|
||||||
Binding == ELF::STB_WEAK);
|
|
||||||
uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STB_Shift);
|
|
||||||
SD.setFlags(OtherFlags | (Binding << ELF_STB_Shift));
|
|
||||||
}
|
|
||||||
|
|
||||||
static unsigned GetVisibility(MCSymbolData &SD) {
|
|
||||||
unsigned Visibility =
|
|
||||||
(SD.getFlags() & (0xf << ELF_STV_Shift)) >> ELF_STV_Shift;
|
|
||||||
assert(Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_INTERNAL ||
|
|
||||||
Visibility == ELF::STV_HIDDEN || Visibility == ELF::STV_PROTECTED);
|
|
||||||
return Visibility;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static bool RelocNeedsGOT(MCSymbolRefExpr::VariantKind Variant) {
|
|
||||||
switch (Variant) {
|
|
||||||
default:
|
|
||||||
return false;
|
|
||||||
case MCSymbolRefExpr::VK_GOT:
|
|
||||||
case MCSymbolRefExpr::VK_PLT:
|
|
||||||
case MCSymbolRefExpr::VK_GOTPCREL:
|
|
||||||
case MCSymbolRefExpr::VK_TPOFF:
|
|
||||||
case MCSymbolRefExpr::VK_TLSGD:
|
|
||||||
case MCSymbolRefExpr::VK_GOTTPOFF:
|
|
||||||
case MCSymbolRefExpr::VK_INDNTPOFF:
|
|
||||||
case MCSymbolRefExpr::VK_NTPOFF:
|
|
||||||
case MCSymbolRefExpr::VK_GOTNTPOFF:
|
|
||||||
case MCSymbolRefExpr::VK_TLSLDM:
|
|
||||||
case MCSymbolRefExpr::VK_DTPOFF:
|
|
||||||
case MCSymbolRefExpr::VK_TLSLD:
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static bool isFixupKindPCRel(const MCAssembler &Asm, unsigned Kind) {
|
|
||||||
const MCFixupKindInfo &FKI =
|
|
||||||
Asm.getBackend().getFixupKindInfo((MCFixupKind) Kind);
|
|
||||||
|
|
||||||
return FKI.Flags & MCFixupKindInfo::FKF_IsPCRel;
|
|
||||||
}
|
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
class ELFObjectWriter : public MCObjectWriter {
|
class ELFObjectWriter : public MCObjectWriter {
|
||||||
protected:
|
protected:
|
||||||
|
|
||||||
|
static bool isFixupKindPCRel(const MCAssembler &Asm, unsigned Kind);
|
||||||
|
static bool RelocNeedsGOT(MCSymbolRefExpr::VariantKind Variant);
|
||||||
|
static uint64_t SymbolValue(MCSymbolData &Data, const MCAsmLayout &Layout);
|
||||||
|
static bool isInSymtab(const MCAssembler &Asm, const MCSymbolData &Data,
|
||||||
|
bool Used, bool Renamed);
|
||||||
|
static bool isLocal(const MCSymbolData &Data, bool isSignature,
|
||||||
|
bool isUsedInReloc);
|
||||||
|
static bool IsELFMetaDataSection(const MCSectionData &SD);
|
||||||
|
static uint64_t DataSectionSize(const MCSectionData &SD);
|
||||||
|
static uint64_t GetSectionFileSize(const MCAsmLayout &Layout,
|
||||||
|
const MCSectionData &SD);
|
||||||
|
static uint64_t GetSectionAddressSize(const MCAsmLayout &Layout,
|
||||||
|
const MCSectionData &SD);
|
||||||
|
static void WriteDataSectionData(ELFObjectWriter *W,
|
||||||
|
const MCSectionData &SD);
|
||||||
|
|
||||||
/*static bool isFixupKindX86RIPRel(unsigned Kind) {
|
/*static bool isFixupKindX86RIPRel(unsigned Kind) {
|
||||||
return Kind == X86::reloc_riprel_4byte ||
|
return Kind == X86::reloc_riprel_4byte ||
|
||||||
Kind == X86::reloc_riprel_4byte_movq_load;
|
Kind == X86::reloc_riprel_4byte_movq_load;
|
||||||
}*/
|
}*/
|
||||||
|
|
||||||
|
/// ELFSymbolData - Helper struct for containing some precomputed
|
||||||
/// ELFSymbolData - Helper struct for containing some precomputed information
|
/// information on symbols.
|
||||||
/// on symbols.
|
|
||||||
struct ELFSymbolData {
|
struct ELFSymbolData {
|
||||||
MCSymbolData *SymbolData;
|
MCSymbolData *SymbolData;
|
||||||
uint64_t StringIndex;
|
uint64_t StringIndex;
|
||||||
@ -115,9 +73,9 @@ namespace {
|
|||||||
|
|
||||||
// Support lexicographic sorting.
|
// Support lexicographic sorting.
|
||||||
bool operator<(const ELFSymbolData &RHS) const {
|
bool operator<(const ELFSymbolData &RHS) const {
|
||||||
if (GetType(*SymbolData) == ELF::STT_FILE)
|
if (MCELF::GetType(*SymbolData) == ELF::STT_FILE)
|
||||||
return true;
|
return true;
|
||||||
if (GetType(*RHS.SymbolData) == ELF::STT_FILE)
|
if (MCELF::GetType(*RHS.SymbolData) == ELF::STT_FILE)
|
||||||
return false;
|
return false;
|
||||||
return SymbolData->getSymbol().getName() <
|
return SymbolData->getSymbol().getName() <
|
||||||
RHS.SymbolData->getSymbol().getName();
|
RHS.SymbolData->getSymbol().getName();
|
||||||
@ -429,6 +387,33 @@ namespace {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool ELFObjectWriter::isFixupKindPCRel(const MCAssembler &Asm, unsigned Kind) {
|
||||||
|
const MCFixupKindInfo &FKI =
|
||||||
|
Asm.getBackend().getFixupKindInfo((MCFixupKind) Kind);
|
||||||
|
|
||||||
|
return FKI.Flags & MCFixupKindInfo::FKF_IsPCRel;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ELFObjectWriter::RelocNeedsGOT(MCSymbolRefExpr::VariantKind Variant) {
|
||||||
|
switch (Variant) {
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
case MCSymbolRefExpr::VK_GOT:
|
||||||
|
case MCSymbolRefExpr::VK_PLT:
|
||||||
|
case MCSymbolRefExpr::VK_GOTPCREL:
|
||||||
|
case MCSymbolRefExpr::VK_TPOFF:
|
||||||
|
case MCSymbolRefExpr::VK_TLSGD:
|
||||||
|
case MCSymbolRefExpr::VK_GOTTPOFF:
|
||||||
|
case MCSymbolRefExpr::VK_INDNTPOFF:
|
||||||
|
case MCSymbolRefExpr::VK_NTPOFF:
|
||||||
|
case MCSymbolRefExpr::VK_GOTNTPOFF:
|
||||||
|
case MCSymbolRefExpr::VK_TLSLDM:
|
||||||
|
case MCSymbolRefExpr::VK_DTPOFF:
|
||||||
|
case MCSymbolRefExpr::VK_TLSLD:
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ELFObjectWriter::~ELFObjectWriter()
|
ELFObjectWriter::~ELFObjectWriter()
|
||||||
{}
|
{}
|
||||||
|
|
||||||
@ -533,7 +518,8 @@ void ELFObjectWriter::WriteSymbolEntry(MCDataFragment *SymtabF,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint64_t SymbolValue(MCSymbolData &Data, const MCAsmLayout &Layout) {
|
uint64_t ELFObjectWriter::SymbolValue(MCSymbolData &Data,
|
||||||
|
const MCAsmLayout &Layout) {
|
||||||
if (Data.isCommon() && Data.isExternal())
|
if (Data.isCommon() && Data.isExternal())
|
||||||
return Data.getCommonAlignment();
|
return Data.getCommonAlignment();
|
||||||
|
|
||||||
@ -579,7 +565,7 @@ void ELFObjectWriter::ExecutePostLayoutBinding(MCAssembler &Asm,
|
|||||||
// Aliases defined with .symvar copy the binding from the symbol they alias.
|
// Aliases defined with .symvar copy the binding from the symbol they alias.
|
||||||
// This is the first place we are able to copy this information.
|
// This is the first place we are able to copy this information.
|
||||||
it->setExternal(SD.isExternal());
|
it->setExternal(SD.isExternal());
|
||||||
SetBinding(*it, GetBinding(SD));
|
MCELF::SetBinding(*it, MCELF::GetBinding(SD));
|
||||||
|
|
||||||
StringRef Rest = AliasName.substr(Pos);
|
StringRef Rest = AliasName.substr(Pos);
|
||||||
if (!Symbol.isUndefined() && !Rest.startswith("@@@"))
|
if (!Symbol.isUndefined() && !Rest.startswith("@@@"))
|
||||||
@ -605,9 +591,9 @@ void ELFObjectWriter::WriteSymbol(MCDataFragment *SymtabF,
|
|||||||
bool IsReserved = Data.isCommon() || Data.getSymbol().isAbsolute() ||
|
bool IsReserved = Data.isCommon() || Data.getSymbol().isAbsolute() ||
|
||||||
Data.getSymbol().isVariable();
|
Data.getSymbol().isVariable();
|
||||||
|
|
||||||
uint8_t Binding = GetBinding(OrigData);
|
uint8_t Binding = MCELF::GetBinding(OrigData);
|
||||||
uint8_t Visibility = GetVisibility(OrigData);
|
uint8_t Visibility = MCELF::GetVisibility(OrigData);
|
||||||
uint8_t Type = GetType(Data);
|
uint8_t Type = MCELF::GetType(Data);
|
||||||
|
|
||||||
uint8_t Info = (Binding << ELF_STB_Shift) | (Type << ELF_STT_Shift);
|
uint8_t Info = (Binding << ELF_STB_Shift) | (Type << ELF_STT_Shift);
|
||||||
uint8_t Other = Visibility;
|
uint8_t Other = Visibility;
|
||||||
@ -673,7 +659,7 @@ void ELFObjectWriter::WriteSymbolTable(MCDataFragment *SymtabF,
|
|||||||
(Data.getFlags() & ELF_STB_Weak)) &&
|
(Data.getFlags() & ELF_STB_Weak)) &&
|
||||||
"External symbol requires STB_GLOBAL or STB_WEAK flag");
|
"External symbol requires STB_GLOBAL or STB_WEAK flag");
|
||||||
WriteSymbol(SymtabF, ShndxF, MSD, Layout);
|
WriteSymbol(SymtabF, ShndxF, MSD, Layout);
|
||||||
if (GetBinding(Data) == ELF::STB_LOCAL)
|
if (MCELF::GetBinding(Data) == ELF::STB_LOCAL)
|
||||||
LastLocalSymbolIndex++;
|
LastLocalSymbolIndex++;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -681,7 +667,7 @@ void ELFObjectWriter::WriteSymbolTable(MCDataFragment *SymtabF,
|
|||||||
ELFSymbolData &MSD = UndefinedSymbolData[i];
|
ELFSymbolData &MSD = UndefinedSymbolData[i];
|
||||||
MCSymbolData &Data = *MSD.SymbolData;
|
MCSymbolData &Data = *MSD.SymbolData;
|
||||||
WriteSymbol(SymtabF, ShndxF, MSD, Layout);
|
WriteSymbol(SymtabF, ShndxF, MSD, Layout);
|
||||||
if (GetBinding(Data) == ELF::STB_LOCAL)
|
if (MCELF::GetBinding(Data) == ELF::STB_LOCAL)
|
||||||
LastLocalSymbolIndex++;
|
LastLocalSymbolIndex++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -798,7 +784,7 @@ void ELFObjectWriter::RecordRelocation(const MCAssembler &Asm,
|
|||||||
FixedValue = Value;
|
FixedValue = Value;
|
||||||
unsigned Type = GetRelocType(Target, Fixup, IsPCRel,
|
unsigned Type = GetRelocType(Target, Fixup, IsPCRel,
|
||||||
(RelocSymbol != 0), Addend);
|
(RelocSymbol != 0), Addend);
|
||||||
|
|
||||||
uint64_t RelocOffset = Layout.getFragmentOffset(Fragment) +
|
uint64_t RelocOffset = Layout.getFragmentOffset(Fragment) +
|
||||||
Fixup.getOffset();
|
Fixup.getOffset();
|
||||||
|
|
||||||
@ -816,8 +802,9 @@ ELFObjectWriter::getSymbolIndexInSymbolTable(const MCAssembler &Asm,
|
|||||||
return SD.getIndex();
|
return SD.getIndex();
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool isInSymtab(const MCAssembler &Asm, const MCSymbolData &Data,
|
bool ELFObjectWriter::isInSymtab(const MCAssembler &Asm,
|
||||||
bool Used, bool Renamed) {
|
const MCSymbolData &Data,
|
||||||
|
bool Used, bool Renamed) {
|
||||||
if (Data.getFlags() & ELF_Other_Weakref)
|
if (Data.getFlags() & ELF_Other_Weakref)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@ -836,7 +823,7 @@ static bool isInSymtab(const MCAssembler &Asm, const MCSymbolData &Data,
|
|||||||
if (Symbol.isVariable() && !A.isVariable() && A.isUndefined())
|
if (Symbol.isVariable() && !A.isVariable() && A.isUndefined())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
bool IsGlobal = GetBinding(Data) == ELF::STB_GLOBAL;
|
bool IsGlobal = MCELF::GetBinding(Data) == ELF::STB_GLOBAL;
|
||||||
if (!Symbol.isVariable() && Symbol.isUndefined() && !IsGlobal)
|
if (!Symbol.isVariable() && Symbol.isUndefined() && !IsGlobal)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@ -849,8 +836,8 @@ static bool isInSymtab(const MCAssembler &Asm, const MCSymbolData &Data,
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool isLocal(const MCSymbolData &Data, bool isSignature,
|
bool ELFObjectWriter::isLocal(const MCSymbolData &Data, bool isSignature,
|
||||||
bool isUsedInReloc) {
|
bool isUsedInReloc) {
|
||||||
if (Data.isExternal())
|
if (Data.isExternal())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@ -898,7 +885,7 @@ void ELFObjectWriter::ComputeSymbolTable(MCAssembler &Asm,
|
|||||||
MCSymbol *Sym = Asm.getContext().GetOrCreateSymbol(Name);
|
MCSymbol *Sym = Asm.getContext().GetOrCreateSymbol(Name);
|
||||||
MCSymbolData &Data = Asm.getOrCreateSymbolData(*Sym);
|
MCSymbolData &Data = Asm.getOrCreateSymbolData(*Sym);
|
||||||
Data.setExternal(true);
|
Data.setExternal(true);
|
||||||
SetBinding(Data, ELF::STB_GLOBAL);
|
MCELF::SetBinding(Data, ELF::STB_GLOBAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Build section lookup table.
|
// Build section lookup table.
|
||||||
@ -929,14 +916,14 @@ void ELFObjectWriter::ComputeSymbolTable(MCAssembler &Asm,
|
|||||||
// Undefined symbols are global, but this is the first place we
|
// Undefined symbols are global, but this is the first place we
|
||||||
// are able to set it.
|
// are able to set it.
|
||||||
bool Local = isLocal(*it, isSignature, Used);
|
bool Local = isLocal(*it, isSignature, Used);
|
||||||
if (!Local && GetBinding(*it) == ELF::STB_LOCAL) {
|
if (!Local && MCELF::GetBinding(*it) == ELF::STB_LOCAL) {
|
||||||
MCSymbolData &SD = Asm.getSymbolData(RefSymbol);
|
MCSymbolData &SD = Asm.getSymbolData(RefSymbol);
|
||||||
SetBinding(*it, ELF::STB_GLOBAL);
|
MCELF::SetBinding(*it, ELF::STB_GLOBAL);
|
||||||
SetBinding(SD, ELF::STB_GLOBAL);
|
MCELF::SetBinding(SD, ELF::STB_GLOBAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (RefSymbol.isUndefined() && !Used && WeakrefUsed)
|
if (RefSymbol.isUndefined() && !Used && WeakrefUsed)
|
||||||
SetBinding(*it, ELF::STB_WEAK);
|
MCELF::SetBinding(*it, ELF::STB_WEAK);
|
||||||
|
|
||||||
if (it->isCommon()) {
|
if (it->isCommon()) {
|
||||||
assert(!Local);
|
assert(!Local);
|
||||||
@ -1304,12 +1291,12 @@ void ELFObjectWriter::WriteSection(MCAssembler &Asm,
|
|||||||
Alignment, Section.getEntrySize());
|
Alignment, Section.getEntrySize());
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool IsELFMetaDataSection(const MCSectionData &SD) {
|
bool ELFObjectWriter::IsELFMetaDataSection(const MCSectionData &SD) {
|
||||||
return SD.getOrdinal() == ~UINT32_C(0) &&
|
return SD.getOrdinal() == ~UINT32_C(0) &&
|
||||||
!SD.getSection().isVirtualSection();
|
!SD.getSection().isVirtualSection();
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint64_t DataSectionSize(const MCSectionData &SD) {
|
uint64_t ELFObjectWriter::DataSectionSize(const MCSectionData &SD) {
|
||||||
uint64_t Ret = 0;
|
uint64_t Ret = 0;
|
||||||
for (MCSectionData::const_iterator i = SD.begin(), e = SD.end(); i != e;
|
for (MCSectionData::const_iterator i = SD.begin(), e = SD.end(); i != e;
|
||||||
++i) {
|
++i) {
|
||||||
@ -1320,21 +1307,22 @@ static uint64_t DataSectionSize(const MCSectionData &SD) {
|
|||||||
return Ret;
|
return Ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint64_t GetSectionFileSize(const MCAsmLayout &Layout,
|
uint64_t ELFObjectWriter::GetSectionFileSize(const MCAsmLayout &Layout,
|
||||||
const MCSectionData &SD) {
|
const MCSectionData &SD) {
|
||||||
if (IsELFMetaDataSection(SD))
|
if (IsELFMetaDataSection(SD))
|
||||||
return DataSectionSize(SD);
|
return DataSectionSize(SD);
|
||||||
return Layout.getSectionFileSize(&SD);
|
return Layout.getSectionFileSize(&SD);
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint64_t GetSectionAddressSize(const MCAsmLayout &Layout,
|
uint64_t ELFObjectWriter::GetSectionAddressSize(const MCAsmLayout &Layout,
|
||||||
const MCSectionData &SD) {
|
const MCSectionData &SD) {
|
||||||
if (IsELFMetaDataSection(SD))
|
if (IsELFMetaDataSection(SD))
|
||||||
return DataSectionSize(SD);
|
return DataSectionSize(SD);
|
||||||
return Layout.getSectionAddressSize(&SD);
|
return Layout.getSectionAddressSize(&SD);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void WriteDataSectionData(ELFObjectWriter *W, const MCSectionData &SD) {
|
void ELFObjectWriter::WriteDataSectionData(ELFObjectWriter *W,
|
||||||
|
const MCSectionData &SD) {
|
||||||
for (MCSectionData::const_iterator i = SD.begin(), e = SD.end(); i != e;
|
for (MCSectionData::const_iterator i = SD.begin(), e = SD.end(); i != e;
|
||||||
++i) {
|
++i) {
|
||||||
const MCFragment &F = *i;
|
const MCFragment &F = *i;
|
||||||
|
72
lib/MC/MCELF.cpp
Normal file
72
lib/MC/MCELF.cpp
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
//===- lib/MC/MCELF.cpp - MC ELF ------------------------------------------===//
|
||||||
|
//
|
||||||
|
// The LLVM Compiler Infrastructure
|
||||||
|
//
|
||||||
|
// This file is distributed under the University of Illinois Open Source
|
||||||
|
// License. See LICENSE.TXT for details.
|
||||||
|
//
|
||||||
|
//===----------------------------------------------------------------------===//
|
||||||
|
//
|
||||||
|
// This file implements ELF object file writer information.
|
||||||
|
//
|
||||||
|
//===----------------------------------------------------------------------===//
|
||||||
|
|
||||||
|
#include "MCELF.h"
|
||||||
|
#include "llvm/MC/MCAssembler.h"
|
||||||
|
#include "llvm/MC/MCELFSymbolFlags.h"
|
||||||
|
#include "llvm/MC/MCFixupKindInfo.h"
|
||||||
|
#include "llvm/Support/ELF.h"
|
||||||
|
#include "llvm/Target/TargetAsmBackend.h"
|
||||||
|
|
||||||
|
namespace llvm {
|
||||||
|
|
||||||
|
void MCELF::SetBinding(MCSymbolData &SD, unsigned Binding) {
|
||||||
|
assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
|
||||||
|
Binding == ELF::STB_WEAK);
|
||||||
|
uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STB_Shift);
|
||||||
|
SD.setFlags(OtherFlags | (Binding << ELF_STB_Shift));
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned MCELF::GetBinding(const MCSymbolData &SD) {
|
||||||
|
uint32_t Binding = (SD.getFlags() & (0xf << ELF_STB_Shift)) >> ELF_STB_Shift;
|
||||||
|
assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
|
||||||
|
Binding == ELF::STB_WEAK);
|
||||||
|
return Binding;
|
||||||
|
}
|
||||||
|
|
||||||
|
void MCELF::SetType(MCSymbolData &SD, unsigned Type) {
|
||||||
|
assert(Type == ELF::STT_NOTYPE || Type == ELF::STT_OBJECT ||
|
||||||
|
Type == ELF::STT_FUNC || Type == ELF::STT_SECTION ||
|
||||||
|
Type == ELF::STT_FILE || Type == ELF::STT_COMMON ||
|
||||||
|
Type == ELF::STT_TLS);
|
||||||
|
|
||||||
|
uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STT_Shift);
|
||||||
|
SD.setFlags(OtherFlags | (Type << ELF_STT_Shift));
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned MCELF::GetType(const MCSymbolData &SD) {
|
||||||
|
uint32_t Type = (SD.getFlags() & (0xf << ELF_STT_Shift)) >> ELF_STT_Shift;
|
||||||
|
assert(Type == ELF::STT_NOTYPE || Type == ELF::STT_OBJECT ||
|
||||||
|
Type == ELF::STT_FUNC || Type == ELF::STT_SECTION ||
|
||||||
|
Type == ELF::STT_FILE || Type == ELF::STT_COMMON ||
|
||||||
|
Type == ELF::STT_TLS);
|
||||||
|
return Type;
|
||||||
|
}
|
||||||
|
|
||||||
|
void MCELF::SetVisibility(MCSymbolData &SD, unsigned Visibility) {
|
||||||
|
assert(Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_INTERNAL ||
|
||||||
|
Visibility == ELF::STV_HIDDEN || Visibility == ELF::STV_PROTECTED);
|
||||||
|
|
||||||
|
uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STV_Shift);
|
||||||
|
SD.setFlags(OtherFlags | (Visibility << ELF_STV_Shift));
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned MCELF::GetVisibility(MCSymbolData &SD) {
|
||||||
|
unsigned Visibility =
|
||||||
|
(SD.getFlags() & (0xf << ELF_STV_Shift)) >> ELF_STV_Shift;
|
||||||
|
assert(Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_INTERNAL ||
|
||||||
|
Visibility == ELF::STV_HIDDEN || Visibility == ELF::STV_PROTECTED);
|
||||||
|
return Visibility;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
35
lib/MC/MCELF.h
Normal file
35
lib/MC/MCELF.h
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
//===- lib/MC/MCELF.h - ELF MC --------------------------------------------===//
|
||||||
|
//
|
||||||
|
// The LLVM Compiler Infrastructure
|
||||||
|
//
|
||||||
|
// This file is distributed under the University of Illinois Open Source
|
||||||
|
// License. See LICENSE.TXT for details.
|
||||||
|
//
|
||||||
|
//===----------------------------------------------------------------------===//
|
||||||
|
//
|
||||||
|
// This file contains some support functions used by the ELF Streamer and
|
||||||
|
// ObjectWriter.
|
||||||
|
//
|
||||||
|
//===----------------------------------------------------------------------===//
|
||||||
|
|
||||||
|
#ifndef LLVM_MC_MCELF_H
|
||||||
|
#define LLVM_MC_MCELF_H
|
||||||
|
|
||||||
|
#include "llvm/MC/MCExpr.h"
|
||||||
|
|
||||||
|
namespace llvm {
|
||||||
|
class MCSymbolData;
|
||||||
|
|
||||||
|
class MCELF {
|
||||||
|
public:
|
||||||
|
static void SetBinding(MCSymbolData &SD, unsigned Binding);
|
||||||
|
static unsigned GetBinding(const MCSymbolData &SD);
|
||||||
|
static void SetType(MCSymbolData &SD, unsigned Type);
|
||||||
|
static unsigned GetType(const MCSymbolData &SD);
|
||||||
|
static void SetVisibility(MCSymbolData &SD, unsigned Visibility);
|
||||||
|
static unsigned GetVisibility(MCSymbolData &SD);
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
@ -13,6 +13,7 @@
|
|||||||
|
|
||||||
#include "llvm/MC/MCStreamer.h"
|
#include "llvm/MC/MCStreamer.h"
|
||||||
|
|
||||||
|
#include "MCELF.h"
|
||||||
#include "llvm/ADT/SmallPtrSet.h"
|
#include "llvm/ADT/SmallPtrSet.h"
|
||||||
#include "llvm/MC/MCAssembler.h"
|
#include "llvm/MC/MCAssembler.h"
|
||||||
#include "llvm/MC/MCContext.h"
|
#include "llvm/MC/MCContext.h"
|
||||||
@ -36,38 +37,6 @@ using namespace llvm;
|
|||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
static void SetBinding(MCSymbolData &SD, unsigned Binding) {
|
|
||||||
assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
|
|
||||||
Binding == ELF::STB_WEAK);
|
|
||||||
uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STB_Shift);
|
|
||||||
SD.setFlags(OtherFlags | (Binding << ELF_STB_Shift));
|
|
||||||
}
|
|
||||||
|
|
||||||
static unsigned GetBinding(const MCSymbolData &SD) {
|
|
||||||
uint32_t Binding = (SD.getFlags() & (0xf << ELF_STB_Shift)) >> ELF_STB_Shift;
|
|
||||||
assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
|
|
||||||
Binding == ELF::STB_WEAK);
|
|
||||||
return Binding;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void SetType(MCSymbolData &SD, unsigned Type) {
|
|
||||||
assert(Type == ELF::STT_NOTYPE || Type == ELF::STT_OBJECT ||
|
|
||||||
Type == ELF::STT_FUNC || Type == ELF::STT_SECTION ||
|
|
||||||
Type == ELF::STT_FILE || Type == ELF::STT_COMMON ||
|
|
||||||
Type == ELF::STT_TLS);
|
|
||||||
|
|
||||||
uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STT_Shift);
|
|
||||||
SD.setFlags(OtherFlags | (Type << ELF_STT_Shift));
|
|
||||||
}
|
|
||||||
|
|
||||||
static void SetVisibility(MCSymbolData &SD, unsigned Visibility) {
|
|
||||||
assert(Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_INTERNAL ||
|
|
||||||
Visibility == ELF::STV_HIDDEN || Visibility == ELF::STV_PROTECTED);
|
|
||||||
|
|
||||||
uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STV_Shift);
|
|
||||||
SD.setFlags(OtherFlags | (Visibility << ELF_STV_Shift));
|
|
||||||
}
|
|
||||||
|
|
||||||
class MCELFStreamer : public MCObjectStreamer {
|
class MCELFStreamer : public MCObjectStreamer {
|
||||||
public:
|
public:
|
||||||
MCELFStreamer(MCContext &Context, TargetAsmBackend &TAB,
|
MCELFStreamer(MCContext &Context, TargetAsmBackend &TAB,
|
||||||
@ -194,7 +163,7 @@ void MCELFStreamer::EmitLabel(MCSymbol *Symbol) {
|
|||||||
static_cast<const MCSectionELF&>(Symbol->getSection());
|
static_cast<const MCSectionELF&>(Symbol->getSection());
|
||||||
MCSymbolData &SD = getAssembler().getSymbolData(*Symbol);
|
MCSymbolData &SD = getAssembler().getSymbolData(*Symbol);
|
||||||
if (Section.getFlags() & ELF::SHF_TLS)
|
if (Section.getFlags() & ELF::SHF_TLS)
|
||||||
SetType(SD, ELF::STT_TLS);
|
MCELF::SetType(SD, ELF::STT_TLS);
|
||||||
}
|
}
|
||||||
|
|
||||||
void MCELFStreamer::EmitAssemblerFlag(MCAssemblerFlag Flag) {
|
void MCELFStreamer::EmitAssemblerFlag(MCAssemblerFlag Flag) {
|
||||||
@ -281,54 +250,54 @@ void MCELFStreamer::EmitSymbolAttribute(MCSymbol *Symbol,
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_Global:
|
case MCSA_Global:
|
||||||
SetBinding(SD, ELF::STB_GLOBAL);
|
MCELF::SetBinding(SD, ELF::STB_GLOBAL);
|
||||||
SD.setExternal(true);
|
SD.setExternal(true);
|
||||||
BindingExplicitlySet.insert(Symbol);
|
BindingExplicitlySet.insert(Symbol);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_WeakReference:
|
case MCSA_WeakReference:
|
||||||
case MCSA_Weak:
|
case MCSA_Weak:
|
||||||
SetBinding(SD, ELF::STB_WEAK);
|
MCELF::SetBinding(SD, ELF::STB_WEAK);
|
||||||
SD.setExternal(true);
|
SD.setExternal(true);
|
||||||
BindingExplicitlySet.insert(Symbol);
|
BindingExplicitlySet.insert(Symbol);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_Local:
|
case MCSA_Local:
|
||||||
SetBinding(SD, ELF::STB_LOCAL);
|
MCELF::SetBinding(SD, ELF::STB_LOCAL);
|
||||||
SD.setExternal(false);
|
SD.setExternal(false);
|
||||||
BindingExplicitlySet.insert(Symbol);
|
BindingExplicitlySet.insert(Symbol);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_ELF_TypeFunction:
|
case MCSA_ELF_TypeFunction:
|
||||||
SetType(SD, ELF::STT_FUNC);
|
MCELF::SetType(SD, ELF::STT_FUNC);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_ELF_TypeObject:
|
case MCSA_ELF_TypeObject:
|
||||||
SetType(SD, ELF::STT_OBJECT);
|
MCELF::SetType(SD, ELF::STT_OBJECT);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_ELF_TypeTLS:
|
case MCSA_ELF_TypeTLS:
|
||||||
SetType(SD, ELF::STT_TLS);
|
MCELF::SetType(SD, ELF::STT_TLS);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_ELF_TypeCommon:
|
case MCSA_ELF_TypeCommon:
|
||||||
SetType(SD, ELF::STT_COMMON);
|
MCELF::SetType(SD, ELF::STT_COMMON);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_ELF_TypeNoType:
|
case MCSA_ELF_TypeNoType:
|
||||||
SetType(SD, ELF::STT_NOTYPE);
|
MCELF::SetType(SD, ELF::STT_NOTYPE);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_Protected:
|
case MCSA_Protected:
|
||||||
SetVisibility(SD, ELF::STV_PROTECTED);
|
MCELF::SetVisibility(SD, ELF::STV_PROTECTED);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_Hidden:
|
case MCSA_Hidden:
|
||||||
SetVisibility(SD, ELF::STV_HIDDEN);
|
MCELF::SetVisibility(SD, ELF::STV_HIDDEN);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MCSA_Internal:
|
case MCSA_Internal:
|
||||||
SetVisibility(SD, ELF::STV_INTERNAL);
|
MCELF::SetVisibility(SD, ELF::STV_INTERNAL);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -338,13 +307,13 @@ void MCELFStreamer::EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
|
|||||||
MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
|
MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
|
||||||
|
|
||||||
if (!BindingExplicitlySet.count(Symbol)) {
|
if (!BindingExplicitlySet.count(Symbol)) {
|
||||||
SetBinding(SD, ELF::STB_GLOBAL);
|
MCELF::SetBinding(SD, ELF::STB_GLOBAL);
|
||||||
SD.setExternal(true);
|
SD.setExternal(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
SetType(SD, ELF::STT_OBJECT);
|
MCELF::SetType(SD, ELF::STT_OBJECT);
|
||||||
|
|
||||||
if (GetBinding(SD) == ELF_STB_Local) {
|
if (MCELF::GetBinding(SD) == ELF_STB_Local) {
|
||||||
const MCSection *Section = getAssembler().getContext().getELFSection(".bss",
|
const MCSection *Section = getAssembler().getContext().getELFSection(".bss",
|
||||||
ELF::SHT_NOBITS,
|
ELF::SHT_NOBITS,
|
||||||
ELF::SHF_WRITE |
|
ELF::SHF_WRITE |
|
||||||
@ -364,7 +333,7 @@ void MCELFStreamer::EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
|
|||||||
void MCELFStreamer::EmitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size) {
|
void MCELFStreamer::EmitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size) {
|
||||||
// FIXME: Should this be caught and done earlier?
|
// FIXME: Should this be caught and done earlier?
|
||||||
MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
|
MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
|
||||||
SetBinding(SD, ELF::STB_LOCAL);
|
MCELF::SetBinding(SD, ELF::STB_LOCAL);
|
||||||
SD.setExternal(false);
|
SD.setExternal(false);
|
||||||
BindingExplicitlySet.insert(Symbol);
|
BindingExplicitlySet.insert(Symbol);
|
||||||
// FIXME: ByteAlignment is not needed here, but is required.
|
// FIXME: ByteAlignment is not needed here, but is required.
|
||||||
@ -449,7 +418,7 @@ void MCELFStreamer::fixSymbolsInTLSFixups(const MCExpr *expr) {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
MCSymbolData &SD = getAssembler().getOrCreateSymbolData(symRef.getSymbol());
|
MCSymbolData &SD = getAssembler().getOrCreateSymbolData(symRef.getSymbol());
|
||||||
SetType(SD, ELF::STT_TLS);
|
MCELF::SetType(SD, ELF::STT_TLS);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user