diff --git a/include/llvm/MC/MCSymbol.h b/include/llvm/MC/MCSymbol.h index 61b139510e3..7624d46294e 100644 --- a/include/llvm/MC/MCSymbol.h +++ b/include/llvm/MC/MCSymbol.h @@ -35,10 +35,6 @@ class MCSymbolData { PointerIntPair Fragment; - /// Flags - The Flags field is used by object file implementations to store - /// additional per symbol information which is not easily classified. - uint32_t Flags = 0; - public: MCSymbolData() = default; @@ -59,17 +55,6 @@ public: Fragment.setInt((Fragment.getInt() & ~2) | (unsigned(Value) << 1)); } - /// getFlags - Get the (implementation defined) symbol flags. - uint32_t getFlags() const { return Flags; } - - /// setFlags - Set the (implementation defined) symbol flags. - void setFlags(uint32_t Value) { Flags = Value; } - - /// modifyFlags - Modify the flags via a mask - void modifyFlags(uint32_t Value, uint32_t Mask) { - Flags = (Flags & ~Mask) | Value; - } - /// @} void dump() const; @@ -133,6 +118,10 @@ class MCSymbol { uint64_t CommonSize; }; + /// The Flags field is used by object file implementations to store + /// additional per symbol information which is not easily classified. + mutable uint32_t Flags = 0; + mutable MCSymbolData Data; private: // MCContext creates and uniques these. @@ -297,6 +286,17 @@ public: /// Is this a 'common' symbol. bool isCommon() const { return CommonAlign != -1U; } + /// Get the (implementation defined) symbol flags. + uint32_t getFlags() const { return Flags; } + + /// Set the (implementation defined) symbol flags. + void setFlags(uint32_t Value) const { Flags = Value; } + + /// Modify the flags via a mask + void modifyFlags(uint32_t Value, uint32_t Mask) const { + Flags = (Flags & ~Mask) | Value; + } + /// print - Print the value to the stream \p OS. void print(raw_ostream &OS) const; diff --git a/lib/MC/MCAssembler.cpp b/lib/MC/MCAssembler.cpp index 02619121a02..e7e6fa92afa 100644 --- a/lib/MC/MCAssembler.cpp +++ b/lib/MC/MCAssembler.cpp @@ -1188,7 +1188,6 @@ void MCSymbolData::dump() const { OS << "> ELF_STB_Shift; + uint32_t Binding = (Sym.getFlags() & (0xf << ELF_STB_Shift)) >> ELF_STB_Shift; assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL || Binding == ELF::STB_WEAK || Binding == ELF::STB_GNU_UNIQUE); return Binding; } void MCELF::SetType(const MCSymbol &Sym, unsigned Type) { - MCSymbolData &SD = Sym.getData(); assert(Type == ELF::STT_NOTYPE || Type == ELF::STT_OBJECT || Type == ELF::STT_FUNC || Type == ELF::STT_SECTION || Type == ELF::STT_COMMON || Type == ELF::STT_TLS || Type == ELF::STT_GNU_IFUNC); - uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STT_Shift); - SD.setFlags(OtherFlags | (Type << ELF_STT_Shift)); + uint32_t OtherFlags = Sym.getFlags() & ~(0xf << ELF_STT_Shift); + Sym.setFlags(OtherFlags | (Type << ELF_STT_Shift)); } unsigned MCELF::GetType(const MCSymbol &Sym) { - MCSymbolData &SD = Sym.getData(); - uint32_t Type = (SD.getFlags() & (0xf << ELF_STT_Shift)) >> ELF_STT_Shift; + uint32_t Type = (Sym.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_COMMON || Type == ELF::STT_TLS || Type == ELF::STT_GNU_IFUNC); @@ -58,18 +54,16 @@ unsigned MCELF::GetType(const MCSymbol &Sym) { // Visibility is stored in the first two bits of st_other // st_other values are stored in the second byte of get/setFlags void MCELF::SetVisibility(MCSymbol &Sym, unsigned Visibility) { - MCSymbolData &SD = Sym.getData(); assert(Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_INTERNAL || Visibility == ELF::STV_HIDDEN || Visibility == ELF::STV_PROTECTED); - uint32_t OtherFlags = SD.getFlags() & ~(0x3 << ELF_STV_Shift); - SD.setFlags(OtherFlags | (Visibility << ELF_STV_Shift)); + uint32_t OtherFlags = Sym.getFlags() & ~(0x3 << ELF_STV_Shift); + Sym.setFlags(OtherFlags | (Visibility << ELF_STV_Shift)); } unsigned MCELF::GetVisibility(const MCSymbol &Sym) { - MCSymbolData &SD = Sym.getData(); unsigned Visibility = - (SD.getFlags() & (0x3 << ELF_STV_Shift)) >> ELF_STV_Shift; + (Sym.getFlags() & (0x3 << 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; @@ -78,15 +72,12 @@ unsigned MCELF::GetVisibility(const MCSymbol &Sym) { // Other is stored in the last six bits of st_other // st_other values are stored in the second byte of get/setFlags void MCELF::setOther(MCSymbol &Sym, unsigned Other) { - MCSymbolData &SD = Sym.getData(); - uint32_t OtherFlags = SD.getFlags() & ~(0x3f << ELF_STO_Shift); - SD.setFlags(OtherFlags | (Other << ELF_STO_Shift)); + uint32_t OtherFlags = Sym.getFlags() & ~(0x3f << ELF_STO_Shift); + Sym.setFlags(OtherFlags | (Other << ELF_STO_Shift)); } unsigned MCELF::getOther(const MCSymbol &Sym) { - MCSymbolData &SD = Sym.getData(); - unsigned Other = - (SD.getFlags() & (0x3f << ELF_STO_Shift)) >> ELF_STO_Shift; + unsigned Other = (Sym.getFlags() & (0x3f << ELF_STO_Shift)) >> ELF_STO_Shift; return Other; } diff --git a/lib/MC/MCMachOStreamer.cpp b/lib/MC/MCMachOStreamer.cpp index dfefd947c8b..542a10cb855 100644 --- a/lib/MC/MCMachOStreamer.cpp +++ b/lib/MC/MCMachOStreamer.cpp @@ -176,7 +176,7 @@ void MCMachOStreamer::EmitEHSymAttributes(const MCSymbol *Symbol, getAssembler().getOrCreateSymbolData(*Symbol); if (SD.isExternal()) EmitSymbolAttribute(EHSymbol, MCSA_Global); - if (SD.getFlags() & SF_WeakDefinition) + if (Symbol->getFlags() & SF_WeakDefinition) EmitSymbolAttribute(EHSymbol, MCSA_WeakDefinition); if (SD.isPrivateExtern()) EmitSymbolAttribute(EHSymbol, MCSA_PrivateExtern); @@ -194,7 +194,6 @@ void MCMachOStreamer::EmitLabel(MCSymbol *Symbol) { MCObjectStreamer::EmitLabel(Symbol); - MCSymbolData &SD = Symbol->getData(); // This causes the reference type flag to be cleared. Darwin 'as' was "trying" // to clear the weak reference and weak definition bits too, but the // implementation was buggy. For now we just try to match 'as', for @@ -202,7 +201,7 @@ void MCMachOStreamer::EmitLabel(MCSymbol *Symbol) { // // FIXME: Cleanup this code, these bits should be emitted based on semantic // properties, not on the order of definition, etc. - SD.setFlags(SD.getFlags() & ~SF_ReferenceTypeMask); + Symbol->setFlags(Symbol->getFlags() & ~SF_ReferenceTypeMask); } void MCMachOStreamer::EmitDataRegion(DataRegionData::KindTy Kind) { @@ -329,25 +328,25 @@ bool MCMachOStreamer::EmitSymbolAttribute(MCSymbol *Symbol, // // FIXME: Cleanup this code, these bits should be emitted based on semantic // properties, not on the order of definition, etc. - SD.setFlags(SD.getFlags() & ~SF_ReferenceTypeUndefinedLazy); + Symbol->setFlags(Symbol->getFlags() & ~SF_ReferenceTypeUndefinedLazy); break; case MCSA_LazyReference: // FIXME: This requires -dynamic. - SD.setFlags(SD.getFlags() | SF_NoDeadStrip); + Symbol->setFlags(Symbol->getFlags() | SF_NoDeadStrip); if (Symbol->isUndefined()) - SD.setFlags(SD.getFlags() | SF_ReferenceTypeUndefinedLazy); + Symbol->setFlags(Symbol->getFlags() | SF_ReferenceTypeUndefinedLazy); break; // Since .reference sets the no dead strip bit, it is equivalent to // .no_dead_strip in practice. case MCSA_Reference: case MCSA_NoDeadStrip: - SD.setFlags(SD.getFlags() | SF_NoDeadStrip); + Symbol->setFlags(Symbol->getFlags() | SF_NoDeadStrip); break; case MCSA_SymbolResolver: - SD.setFlags(SD.getFlags() | SF_SymbolResolver); + Symbol->setFlags(Symbol->getFlags() | SF_SymbolResolver); break; case MCSA_PrivateExtern: @@ -358,17 +357,17 @@ bool MCMachOStreamer::EmitSymbolAttribute(MCSymbol *Symbol, case MCSA_WeakReference: // FIXME: This requires -dynamic. if (Symbol->isUndefined()) - SD.setFlags(SD.getFlags() | SF_WeakReference); + Symbol->setFlags(Symbol->getFlags() | SF_WeakReference); break; case MCSA_WeakDefinition: // FIXME: 'as' enforces that this is defined and global. The manual claims // it has to be in a coalesced section, but this isn't enforced. - SD.setFlags(SD.getFlags() | SF_WeakDefinition); + Symbol->setFlags(Symbol->getFlags() | SF_WeakDefinition); break; case MCSA_WeakDefAutoPrivate: - SD.setFlags(SD.getFlags() | SF_WeakDefinition | SF_WeakReference); + Symbol->setFlags(Symbol->getFlags() | SF_WeakDefinition | SF_WeakReference); break; } @@ -379,8 +378,8 @@ void MCMachOStreamer::EmitSymbolDesc(MCSymbol *Symbol, unsigned DescValue) { // Encode the 'desc' value into the lowest implementation defined bits. assert(DescValue == (DescValue & SF_DescFlagsMask) && "Invalid .desc value!"); - getAssembler().getOrCreateSymbolData(*Symbol).setFlags( - DescValue & SF_DescFlagsMask); + getAssembler().getOrCreateSymbolData(*Symbol); + Symbol->setFlags(DescValue & SF_DescFlagsMask); } void MCMachOStreamer::EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size, diff --git a/lib/MC/MachObjectWriter.cpp b/lib/MC/MachObjectWriter.cpp index 6d8e7ae147f..07427cf8b03 100644 --- a/lib/MC/MachObjectWriter.cpp +++ b/lib/MC/MachObjectWriter.cpp @@ -46,7 +46,7 @@ bool MachObjectWriter::doesSymbolRequireExternRelocation(const MCSymbol &S) { // References to weak definitions require external relocation entries; the // definition may not always be the one in the same object file. - if (S.getData().getFlags() & SF_WeakDefinition) + if (S.getFlags() & SF_WeakDefinition) return true; // Otherwise, we can use an internal relocation. @@ -333,7 +333,7 @@ void MachObjectWriter::WriteNlist(MachSymbolData &MSD, const MCSymbol *AliasedSymbol = &findAliasedSymbol(*Symbol); uint8_t SectionIndex = MSD.SectionIndex; uint8_t Type = 0; - uint16_t Flags = Data.getFlags(); + uint16_t Flags = Symbol->getFlags(); uint64_t Address = 0; bool IsAlias = Symbol != AliasedSymbol; @@ -520,9 +520,9 @@ void MachObjectWriter::BindIndirectSymbols(MCAssembler &Asm) { // // FIXME: Do not hardcode. bool Created; - MCSymbolData &Entry = Asm.getOrCreateSymbolData(*it->Symbol, &Created); + Asm.getOrCreateSymbolData(*it->Symbol, &Created); if (Created) - Entry.setFlags(Entry.getFlags() | 0x0001); + it->Symbol->setFlags(it->Symbol->getFlags() | 0x0001); } } diff --git a/lib/MC/WinCOFFObjectWriter.cpp b/lib/MC/WinCOFFObjectWriter.cpp index 72a92204f1a..c24217e5230 100644 --- a/lib/MC/WinCOFFObjectWriter.cpp +++ b/lib/MC/WinCOFFObjectWriter.cpp @@ -383,7 +383,7 @@ void WinCOFFObjectWriter::DefineSymbol(const MCSymbol &Symbol, COFFSymbol *coff_symbol = GetOrCreateCOFFSymbol(&Symbol); SymbolMap[&Symbol] = coff_symbol; - if (Symbol.getData().getFlags() & COFF::SF_WeakExternal) { + if (Symbol.getFlags() & COFF::SF_WeakExternal) { coff_symbol->Data.StorageClass = COFF::IMAGE_SYM_CLASS_WEAK_EXTERNAL; if (Symbol.isVariable()) { @@ -418,8 +418,8 @@ void WinCOFFObjectWriter::DefineSymbol(const MCSymbol &Symbol, const MCSymbol *Base = Layout.getBaseSymbol(Symbol); coff_symbol->Data.Value = getSymbolValue(Symbol, Layout); - coff_symbol->Data.Type = (ResSymData.getFlags() & 0x0000FFFF) >> 0; - coff_symbol->Data.StorageClass = (ResSymData.getFlags() & 0x00FF0000) >> 16; + coff_symbol->Data.Type = (Symbol.getFlags() & 0x0000FFFF) >> 0; + coff_symbol->Data.StorageClass = (Symbol.getFlags() & 0x00FF0000) >> 16; // If no storage class was specified in the streamer, define it here. if (coff_symbol->Data.StorageClass == 0) { @@ -664,8 +664,7 @@ bool WinCOFFObjectWriter::IsSymbolRefDifferenceFullyResolvedImpl( // MS LINK expects to be able to replace all references to a function with a // thunk to implement their /INCREMENTAL feature. Make sure we don't optimize // away any relocations to functions. - if ((((SymA.getData().getFlags() & COFF::SF_TypeMask) >> - COFF::SF_TypeShift) >> + if ((((SymA.getFlags() & COFF::SF_TypeMask) >> COFF::SF_TypeShift) >> COFF::SCT_COMPLEX_TYPE_SHIFT) == COFF::IMAGE_SYM_DTYPE_FUNCTION) return false; return MCObjectWriter::IsSymbolRefDifferenceFullyResolvedImpl(Asm, SymA, FB, diff --git a/lib/MC/WinCOFFStreamer.cpp b/lib/MC/WinCOFFStreamer.cpp index 262e375abc3..8b8d469c564 100644 --- a/lib/MC/WinCOFFStreamer.cpp +++ b/lib/MC/WinCOFFStreamer.cpp @@ -102,7 +102,7 @@ bool MCWinCOFFStreamer::EmitSymbolAttribute(MCSymbol *Symbol, default: return false; case MCSA_WeakReference: case MCSA_Weak: - SD.modifyFlags(COFF::SF_WeakExternal, COFF::SF_WeakExternal); + Symbol->modifyFlags(COFF::SF_WeakExternal, COFF::SF_WeakExternal); SD.setExternal(true); break; case MCSA_Global: @@ -136,8 +136,9 @@ void MCWinCOFFStreamer::EmitCOFFSymbolStorageClass(int StorageClass) { FatalError("storage class value '" + Twine(StorageClass) + "' out of range"); - MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*CurSymbol); - SD.modifyFlags(StorageClass << COFF::SF_ClassShift, COFF::SF_ClassMask); + getAssembler().getOrCreateSymbolData(*CurSymbol); + CurSymbol->modifyFlags(StorageClass << COFF::SF_ClassShift, + COFF::SF_ClassMask); } void MCWinCOFFStreamer::EmitCOFFSymbolType(int Type) { @@ -147,8 +148,8 @@ void MCWinCOFFStreamer::EmitCOFFSymbolType(int Type) { if (Type & ~0xffff) FatalError("type value '" + Twine(Type) + "' out of range"); - MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*CurSymbol); - SD.modifyFlags(Type << COFF::SF_TypeShift, COFF::SF_TypeMask); + getAssembler().getOrCreateSymbolData(*CurSymbol); + CurSymbol->modifyFlags(Type << COFF::SF_TypeShift, COFF::SF_TypeMask); } void MCWinCOFFStreamer::EndCOFFSymbolDef() {