SymbolBody constructor and friends take isFunc and isTLS boolean arguments.
ELF symbols have already a type so than be easily passed as argument.
If we want to support another type, this scheme is not good enough, that is,
the current code logic would require passing another `bool isObject` around.
Up to two argument, this stretching exercise was a little bit goofy but
still acceptable, but with more types to support, is just too much, IMHO.
Change the code so that the type is passed instead.
Differential Revision: http://reviews.llvm.org/D17871
llvm-svn: 262684
SymVA = Out<ELFT>::Got->getMipsLocalFullAddr(*Body);
else
SymVA = Body->getGotVA<ELFT>();
- if (Body->IsTls)
+ if (Body->isTls())
Type = Target->getTlsGotRel(Type);
} else if (!Target->needsCopyRel<ELFT>(Type, *Body) &&
isa<SharedSymbol<ELFT>>(*Body)) {
return;
}
- if (New->IsTls != Existing->IsTls) {
+ if (New->isTls() != Existing->isTls()) {
error("TLS attribute mismatch for symbol: " + conflictMsg(Existing, New));
return;
}
L->setWeak();
// FIXME: Do we need to copy more?
- L->IsTls = Undef->IsTls;
+ if (Undef->isTls())
+ L->setTls();
return;
}
auto *SS = cast<SharedSymbol<ELFT>>(this);
if (!SS->NeedsCopyOrPltAddr)
return 0;
- if (SS->IsFunc)
+ if (SS->isFunc())
return getPltVA<ELFT>();
else
return Out<ELFT>::Bss->getVA() + SS->OffsetInBss;
}
Defined::Defined(Kind K, StringRef Name, bool IsWeak, uint8_t Visibility,
- bool IsTls, bool IsFunction)
- : SymbolBody(K, Name, IsWeak, Visibility, IsTls, IsFunction) {}
+ uint8_t Type)
+ : SymbolBody(K, Name, IsWeak, Visibility, Type) {}
DefinedBitcode::DefinedBitcode(StringRef Name, bool IsWeak)
- : Defined(DefinedBitcodeKind, Name, IsWeak, STV_DEFAULT, false, false) {}
+ : Defined(DefinedBitcodeKind, Name, IsWeak, STV_DEFAULT, 0 /* Type */) {}
bool DefinedBitcode::classof(const SymbolBody *S) {
return S->kind() == DefinedBitcodeKind;
}
Undefined::Undefined(SymbolBody::Kind K, StringRef N, bool IsWeak,
- uint8_t Visibility, bool IsTls)
- : SymbolBody(K, N, IsWeak, Visibility, IsTls, /*IsFunction*/ false),
+ uint8_t Visibility, uint8_t Type)
+ : SymbolBody(K, N, IsWeak, Visibility, Type),
CanKeepUndefined(false) {}
Undefined::Undefined(StringRef N, bool IsWeak, uint8_t Visibility,
bool CanKeepUndefined)
- : Undefined(SymbolBody::UndefinedKind, N, IsWeak, Visibility,
- /*IsTls*/ false) {
+ : Undefined(SymbolBody::UndefinedKind, N, IsWeak, Visibility, 0 /* Type */) {
this->CanKeepUndefined = CanKeepUndefined;
}
UndefinedElf<ELFT>::UndefinedElf(StringRef N, const Elf_Sym &Sym)
: Undefined(SymbolBody::UndefinedElfKind, N,
Sym.getBinding() == llvm::ELF::STB_WEAK, Sym.getVisibility(),
- Sym.getType() == llvm::ELF::STT_TLS),
+ Sym.getType()),
Sym(Sym) {}
template <typename ELFT>
OutputSectionBase<ELFT> &Section,
uint8_t Visibility)
: Defined(SymbolBody::DefinedSyntheticKind, N, false, Visibility,
- /*IsTls*/ false, /*IsFunction*/ false),
+ 0 /* Type */),
Value(Value), Section(Section) {}
DefinedCommon::DefinedCommon(StringRef N, uint64_t Size, uint64_t Alignment,
bool IsWeak, uint8_t Visibility)
: Defined(SymbolBody::DefinedCommonKind, N, IsWeak, Visibility,
- /*IsTls*/ false, /*IsFunction*/ false) {
+ 0 /* Type */) {
MaxAlignment = Alignment;
this->Size = Size;
}
bool isLazy() const { return SymbolKind == LazyKind; }
bool isShared() const { return SymbolKind == SharedKind; }
bool isUsedInRegularObj() const { return IsUsedInRegularObj; }
- bool isFunc() const { return IsFunc; }
+ bool isFunc() const { return Type == llvm::ELF::STT_FUNC; }
+ bool isTls() const { return Type == llvm::ELF::STT_TLS; }
// Returns the symbol name.
StringRef getName() const { return Name; }
protected:
SymbolBody(Kind K, StringRef Name, bool IsWeak, uint8_t Visibility,
- bool IsTls, bool IsFunc)
+ uint8_t Type)
: SymbolKind(K), IsWeak(IsWeak), Visibility(Visibility),
- MustBeInDynSym(false), NeedsCopyOrPltAddr(false), IsTls(IsTls),
- IsFunc(IsFunc), Name(Name) {
+ MustBeInDynSym(false), NeedsCopyOrPltAddr(false),
+ Type(Type), Name(Name) {
IsUsedInRegularObj = K != SharedKind && K != LazyKind;
}
// symbol or if the symbol should point to its plt entry.
unsigned NeedsCopyOrPltAddr : 1;
- unsigned IsTls : 1;
-
protected:
- unsigned IsFunc : 1;
+ uint8_t Type;
StringRef Name;
Symbol *Backref = nullptr;
// The base class for any defined symbols.
class Defined : public SymbolBody {
public:
- Defined(Kind K, StringRef Name, bool IsWeak, uint8_t Visibility, bool IsTls,
- bool IsFunction);
+ Defined(Kind K, StringRef Name, bool IsWeak, uint8_t Visibility,
+ uint8_t Type);
static bool classof(const SymbolBody *S) { return S->isDefined(); }
};
public:
DefinedElf(Kind K, StringRef N, const Elf_Sym &Sym)
: Defined(K, N, Sym.getBinding() == llvm::ELF::STB_WEAK,
- Sym.getVisibility(), Sym.getType() == llvm::ELF::STT_TLS,
- Sym.getType() == llvm::ELF::STT_FUNC),
+ Sym.getVisibility(), Sym.getType()),
Sym(Sym) {}
const Elf_Sym &Sym;
bool CanKeepUndefined;
protected:
- Undefined(Kind K, StringRef N, bool IsWeak, uint8_t Visibility, bool IsTls);
+ Undefined(Kind K, StringRef N, bool IsWeak, uint8_t Visibility, uint8_t Type);
public:
Undefined(StringRef N, bool IsWeak, uint8_t Visibility,
// OffsetInBss is significant only when needsCopy() is true.
uintX_t OffsetInBss = 0;
- bool needsCopy() const { return this->NeedsCopyOrPltAddr && !this->IsFunc; }
+ bool needsCopy() const { return this->NeedsCopyOrPltAddr && !this->isFunc(); }
};
// This class represents a symbol defined in an archive file. It is
public:
Lazy(ArchiveFile *F, const llvm::object::Archive::Symbol S)
: SymbolBody(LazyKind, S.getName(), false, llvm::ELF::STV_DEFAULT,
- /*IsTls*/ false, /*IsFunction*/ false),
+ /* Type */ 0),
File(F), Sym(S) {}
static bool classof(const SymbolBody *S) { return S->kind() == LazyKind; }
// was already returned.
std::unique_ptr<InputFile> getMember();
+ void setTls() { this->Type = llvm::ELF::STT_TLS; }
void setWeak() { IsWeak = true; }
void setUsedInRegularObj() { IsUsedInRegularObj = true; }
}
bool X86TargetInfo::needsGot(uint32_t Type, SymbolBody &S) const {
- if (S.IsTls && Type == R_386_TLS_GD)
+ if (S.isTls() && Type == R_386_TLS_GD)
return Target->canRelaxTls(Type, &S) && canBePreempted(&S);
if (Type == R_386_TLS_GOTIE || Type == R_386_TLS_IE)
return !canRelaxTls(Type, &S);
}
bool X86TargetInfo::canRelaxTls(unsigned Type, const SymbolBody *S) const {
- if (Config->Shared || (S && !S->IsTls))
+ if (Config->Shared || (S && !S->isTls()))
return false;
return Type == R_386_TLS_LDO_32 || Type == R_386_TLS_LDM ||
Type == R_386_TLS_GD || (Type == R_386_TLS_IE && !canBePreempted(S)) ||
}
bool X86_64TargetInfo::canRelaxTls(unsigned Type, const SymbolBody *S) const {
- if (Config->Shared || (S && !S->IsTls))
+ if (Config->Shared || (S && !S->isTls()))
return false;
return Type == R_X86_64_TLSGD || Type == R_X86_64_TLSLD ||
Type == R_X86_64_DTPOFF32 ||
}
bool AArch64TargetInfo::canRelaxTls(unsigned Type, const SymbolBody *S) const {
- if (Config->Shared || (S && !S->IsTls))
+ if (Config->Shared || (S && !S->isTls()))
return false;
// Global-Dynamic relocs can be relaxed to Initial-Exec if the target is
return true;
}
- if (!Body || !Body->IsTls)
+ if (!Body || !Body->isTls())
return false;
if (Target->isTlsGlobalDynamicRel(Type)) {
if (CBP || Dynrel) {
uint32_t DynType;
if (CBP)
- DynType = Body->IsTls ? Target->TlsGotRel : Target->GotRel;
+ DynType = Body->isTls() ? Target->TlsGotRel : Target->GotRel;
else
DynType = Target->RelativeRel;
Out<ELFT>::RelaDyn->addReloc(