summaryrefslogtreecommitdiffstats
path: root/contrib/llvm/lib/MC/MCAssembler.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/llvm/lib/MC/MCAssembler.cpp')
-rw-r--r--contrib/llvm/lib/MC/MCAssembler.cpp354
1 files changed, 142 insertions, 212 deletions
diff --git a/contrib/llvm/lib/MC/MCAssembler.cpp b/contrib/llvm/lib/MC/MCAssembler.cpp
index e3c2443..868b0f1 100644
--- a/contrib/llvm/lib/MC/MCAssembler.cpp
+++ b/contrib/llvm/lib/MC/MCAssembler.cpp
@@ -69,19 +69,19 @@ MCAsmLayout::MCAsmLayout(MCAssembler &Asm)
{
// Compute the section layout order. Virtual sections must go last.
for (MCAssembler::iterator it = Asm.begin(), ie = Asm.end(); it != ie; ++it)
- if (!it->getSection().isVirtualSection())
+ if (!it->isVirtualSection())
SectionOrder.push_back(&*it);
for (MCAssembler::iterator it = Asm.begin(), ie = Asm.end(); it != ie; ++it)
- if (it->getSection().isVirtualSection())
+ if (it->isVirtualSection())
SectionOrder.push_back(&*it);
}
bool MCAsmLayout::isFragmentValid(const MCFragment *F) const {
- const MCSectionData &SD = *F->getParent();
- const MCFragment *LastValid = LastValidFragment.lookup(&SD);
+ const MCSection *Sec = F->getParent();
+ const MCFragment *LastValid = LastValidFragment.lookup(Sec);
if (!LastValid)
return false;
- assert(LastValid->getParent() == F->getParent());
+ assert(LastValid->getParent() == Sec);
return F->getLayoutOrder() <= LastValid->getLayoutOrder();
}
@@ -92,16 +92,14 @@ void MCAsmLayout::invalidateFragmentsFrom(MCFragment *F) {
// Otherwise, reset the last valid fragment to the previous fragment
// (if this is the first fragment, it will be NULL).
- const MCSectionData &SD = *F->getParent();
- LastValidFragment[&SD] = F->getPrevNode();
+ LastValidFragment[F->getParent()] = F->getPrevNode();
}
void MCAsmLayout::ensureValid(const MCFragment *F) const {
- MCSectionData &SD = *F->getParent();
-
- MCFragment *Cur = LastValidFragment[&SD];
+ MCSection *Sec = F->getParent();
+ MCFragment *Cur = LastValidFragment[Sec];
if (!Cur)
- Cur = &*SD.begin();
+ Cur = Sec->begin();
else
Cur = Cur->getNextNode();
@@ -120,41 +118,36 @@ uint64_t MCAsmLayout::getFragmentOffset(const MCFragment *F) const {
}
// Simple getSymbolOffset helper for the non-varibale case.
-static bool getLabelOffset(const MCAsmLayout &Layout, const MCSymbolData &SD,
+static bool getLabelOffset(const MCAsmLayout &Layout, const MCSymbol &S,
bool ReportError, uint64_t &Val) {
+ const MCSymbolData &SD = S.getData();
if (!SD.getFragment()) {
if (ReportError)
report_fatal_error("unable to evaluate offset to undefined symbol '" +
- SD.getSymbol().getName() + "'");
+ S.getName() + "'");
return false;
}
Val = Layout.getFragmentOffset(SD.getFragment()) + SD.getOffset();
return true;
}
-static bool getSymbolOffsetImpl(const MCAsmLayout &Layout,
- const MCSymbolData *SD, bool ReportError,
- uint64_t &Val) {
- const MCSymbol &S = SD->getSymbol();
-
+static bool getSymbolOffsetImpl(const MCAsmLayout &Layout, const MCSymbol &S,
+ bool ReportError, uint64_t &Val) {
if (!S.isVariable())
- return getLabelOffset(Layout, *SD, ReportError, Val);
+ return getLabelOffset(Layout, S, ReportError, Val);
// If SD is a variable, evaluate it.
MCValue Target;
- if (!S.getVariableValue()->EvaluateAsValue(Target, &Layout, nullptr))
+ if (!S.getVariableValue()->EvaluateAsRelocatable(Target, &Layout, nullptr))
report_fatal_error("unable to evaluate offset for variable '" +
S.getName() + "'");
uint64_t Offset = Target.getConstant();
- const MCAssembler &Asm = Layout.getAssembler();
-
const MCSymbolRefExpr *A = Target.getSymA();
if (A) {
uint64_t ValA;
- if (!getLabelOffset(Layout, Asm.getSymbolData(A->getSymbol()), ReportError,
- ValA))
+ if (!getLabelOffset(Layout, A->getSymbol(), ReportError, ValA))
return false;
Offset += ValA;
}
@@ -162,8 +155,7 @@ static bool getSymbolOffsetImpl(const MCAsmLayout &Layout,
const MCSymbolRefExpr *B = Target.getSymB();
if (B) {
uint64_t ValB;
- if (!getLabelOffset(Layout, Asm.getSymbolData(B->getSymbol()), ReportError,
- ValB))
+ if (!getLabelOffset(Layout, B->getSymbol(), ReportError, ValB))
return false;
Offset -= ValB;
}
@@ -172,13 +164,13 @@ static bool getSymbolOffsetImpl(const MCAsmLayout &Layout,
return true;
}
-bool MCAsmLayout::getSymbolOffset(const MCSymbolData *SD, uint64_t &Val) const {
- return getSymbolOffsetImpl(*this, SD, false, Val);
+bool MCAsmLayout::getSymbolOffset(const MCSymbol &S, uint64_t &Val) const {
+ return getSymbolOffsetImpl(*this, S, false, Val);
}
-uint64_t MCAsmLayout::getSymbolOffset(const MCSymbolData *SD) const {
+uint64_t MCAsmLayout::getSymbolOffset(const MCSymbol &S) const {
uint64_t Val;
- getSymbolOffsetImpl(*this, SD, true, Val);
+ getSymbolOffsetImpl(*this, S, true, Val);
return Val;
}
@@ -188,12 +180,12 @@ const MCSymbol *MCAsmLayout::getBaseSymbol(const MCSymbol &Symbol) const {
const MCExpr *Expr = Symbol.getVariableValue();
MCValue Value;
- if (!Expr->EvaluateAsValue(Value, this, nullptr))
+ if (!Expr->evaluateAsValue(Value, *this))
llvm_unreachable("Invalid Expression");
const MCSymbolRefExpr *RefB = Value.getSymB();
if (RefB)
- Assembler.getContext().FatalError(
+ Assembler.getContext().reportFatalError(
SMLoc(), Twine("symbol '") + RefB->getSymbol().getName() +
"' could not be evaluated in a subtraction expression");
@@ -201,26 +193,37 @@ const MCSymbol *MCAsmLayout::getBaseSymbol(const MCSymbol &Symbol) const {
if (!A)
return nullptr;
- return &A->getSymbol();
+ const MCSymbol &ASym = A->getSymbol();
+ const MCAssembler &Asm = getAssembler();
+ const MCSymbolData &ASD = Asm.getSymbolData(ASym);
+ if (ASD.isCommon()) {
+ // FIXME: we should probably add a SMLoc to MCExpr.
+ Asm.getContext().reportFatalError(SMLoc(),
+ "Common symbol " + ASym.getName() +
+ " cannot be used in assignment expr");
+ }
+
+ return &ASym;
}
-uint64_t MCAsmLayout::getSectionAddressSize(const MCSectionData *SD) const {
+uint64_t MCAsmLayout::getSectionAddressSize(const MCSection *Sec) const {
// The size is the last fragment's end offset.
- const MCFragment &F = SD->getFragmentList().back();
+ const MCFragment &F = Sec->getFragmentList().back();
return getFragmentOffset(&F) + getAssembler().computeFragmentSize(*this, F);
}
-uint64_t MCAsmLayout::getSectionFileSize(const MCSectionData *SD) const {
+uint64_t MCAsmLayout::getSectionFileSize(const MCSection *Sec) const {
// Virtual sections have no file size.
- if (SD->getSection().isVirtualSection())
+ if (Sec->isVirtualSection())
return 0;
// Otherwise, the file size is the same as the address space size.
- return getSectionAddressSize(SD);
+ return getSectionAddressSize(Sec);
}
-uint64_t MCAsmLayout::computeBundlePadding(const MCFragment *F,
- uint64_t FOffset, uint64_t FSize) {
+uint64_t llvm::computeBundlePadding(const MCAssembler &Assembler,
+ const MCFragment *F,
+ uint64_t FOffset, uint64_t FSize) {
uint64_t BundleSize = Assembler.getBundleAlignSize();
assert(BundleSize > 0 &&
"computeBundlePadding should only be called if bundling is enabled");
@@ -267,9 +270,8 @@ MCFragment::MCFragment() : Kind(FragmentType(~0)) {
MCFragment::~MCFragment() {
}
-MCFragment::MCFragment(FragmentType _Kind, MCSectionData *_Parent)
- : Kind(_Kind), Parent(_Parent), Atom(nullptr), Offset(~UINT64_C(0))
-{
+MCFragment::MCFragment(FragmentType Kind, MCSection *Parent)
+ : Kind(Kind), Parent(Parent), Atom(nullptr), Offset(~UINT64_C(0)) {
if (Parent)
Parent->getFragmentList().push_back(this);
}
@@ -286,84 +288,6 @@ MCEncodedFragmentWithFixups::~MCEncodedFragmentWithFixups() {
/* *** */
-MCSectionData::MCSectionData() : Section(nullptr) {}
-
-MCSectionData::MCSectionData(const MCSection &_Section, MCAssembler *A)
- : Section(&_Section),
- Ordinal(~UINT32_C(0)),
- Alignment(1),
- BundleLockState(NotBundleLocked),
- BundleLockNestingDepth(0),
- BundleGroupBeforeFirstInst(false),
- HasInstructions(false)
-{
- if (A)
- A->getSectionList().push_back(this);
-}
-
-MCSectionData::iterator
-MCSectionData::getSubsectionInsertionPoint(unsigned Subsection) {
- if (Subsection == 0 && SubsectionFragmentMap.empty())
- return end();
-
- SmallVectorImpl<std::pair<unsigned, MCFragment *> >::iterator MI =
- std::lower_bound(SubsectionFragmentMap.begin(), SubsectionFragmentMap.end(),
- std::make_pair(Subsection, (MCFragment *)nullptr));
- bool ExactMatch = false;
- if (MI != SubsectionFragmentMap.end()) {
- ExactMatch = MI->first == Subsection;
- if (ExactMatch)
- ++MI;
- }
- iterator IP;
- if (MI == SubsectionFragmentMap.end())
- IP = end();
- else
- IP = MI->second;
- if (!ExactMatch && Subsection != 0) {
- // The GNU as documentation claims that subsections have an alignment of 4,
- // although this appears not to be the case.
- MCFragment *F = new MCDataFragment();
- SubsectionFragmentMap.insert(MI, std::make_pair(Subsection, F));
- getFragmentList().insert(IP, F);
- F->setParent(this);
- }
- return IP;
-}
-
-void MCSectionData::setBundleLockState(BundleLockStateType NewState) {
- if (NewState == NotBundleLocked) {
- if (BundleLockNestingDepth == 0) {
- report_fatal_error("Mismatched bundle_lock/unlock directives");
- }
- if (--BundleLockNestingDepth == 0) {
- BundleLockState = NotBundleLocked;
- }
- return;
- }
-
- // If any of the directives is an align_to_end directive, the whole nested
- // group is align_to_end. So don't downgrade from align_to_end to just locked.
- if (BundleLockState != BundleLockedAlignToEnd) {
- BundleLockState = NewState;
- }
- ++BundleLockNestingDepth;
-}
-
-/* *** */
-
-MCSymbolData::MCSymbolData() : Symbol(nullptr) {}
-
-MCSymbolData::MCSymbolData(const MCSymbol &_Symbol, MCFragment *_Fragment,
- uint64_t _Offset, MCAssembler *A)
- : Symbol(&_Symbol), Fragment(_Fragment), Offset(_Offset),
- SymbolSize(nullptr), CommonAlign(-1U), Flags(0), Index(0) {
- if (A)
- A->getSymbolList().push_back(this);
-}
-
-/* *** */
-
MCAssembler::MCAssembler(MCContext &Context_, MCAsmBackend &Backend_,
MCCodeEmitter &Emitter_, MCObjectWriter &Writer_,
raw_ostream &OS_)
@@ -379,8 +303,6 @@ MCAssembler::~MCAssembler() {
void MCAssembler::reset() {
Sections.clear();
Symbols.clear();
- SectionMap.clear();
- SymbolMap.clear();
IndirectSymbols.clear();
DataRegions.clear();
LinkerOptions.clear();
@@ -425,6 +347,16 @@ bool MCAssembler::isThumbFunc(const MCSymbol *Symbol) const {
return true;
}
+void MCAssembler::addLocalUsedInReloc(const MCSymbol &Sym) {
+ assert(Sym.isTemporary());
+ LocalsUsedInReloc.insert(&Sym);
+}
+
+bool MCAssembler::isLocalUsedInReloc(const MCSymbol &Sym) const {
+ assert(Sym.isTemporary());
+ return LocalsUsedInReloc.count(&Sym);
+}
+
bool MCAssembler::isSymbolLinkerVisible(const MCSymbol &Symbol) const {
// Non-temporary labels should always be visible to the linker.
if (!Symbol.isTemporary())
@@ -434,39 +366,29 @@ bool MCAssembler::isSymbolLinkerVisible(const MCSymbol &Symbol) const {
if (!Symbol.isInSection())
return false;
- // Otherwise, check if the section requires symbols even for temporary labels.
- return getBackend().doesSectionRequireSymbols(Symbol.getSection());
+ if (isLocalUsedInReloc(Symbol))
+ return true;
+
+ return false;
}
-const MCSymbolData *MCAssembler::getAtom(const MCSymbolData *SD) const {
+const MCSymbol *MCAssembler::getAtom(const MCSymbol &S) const {
// Linker visible symbols define atoms.
- if (isSymbolLinkerVisible(SD->getSymbol()))
- return SD;
+ if (isSymbolLinkerVisible(S))
+ return &S;
// Absolute and undefined symbols have no defining atom.
- if (!SD->getFragment())
+ if (!S.getData().getFragment())
return nullptr;
// Non-linker visible symbols in sections which can't be atomized have no
// defining atom.
if (!getContext().getAsmInfo()->isSectionAtomizableBySymbols(
- SD->getFragment()->getParent()->getSection()))
+ *S.getData().getFragment()->getParent()))
return nullptr;
// Otherwise, return the atom for the containing fragment.
- return SD->getFragment()->getAtom();
-}
-
-// Try to fully compute Expr to an absolute value and if that fails produce
-// a relocatable expr.
-// FIXME: Should this be the behavior of EvaluateAsRelocatable itself?
-static bool evaluate(const MCExpr &Expr, const MCAsmLayout &Layout,
- const MCFixup &Fixup, MCValue &Target) {
- if (Expr.EvaluateAsValue(Target, &Layout, &Fixup)) {
- if (Target.isAbsolute())
- return true;
- }
- return Expr.EvaluateAsRelocatable(Target, &Layout, &Fixup);
+ return S.getData().getFragment()->getAtom();
}
bool MCAssembler::evaluateFixup(const MCAsmLayout &Layout,
@@ -478,8 +400,8 @@ bool MCAssembler::evaluateFixup(const MCAsmLayout &Layout,
// probably merge the two into a single callback that tries to evaluate a
// fixup and records a relocation if one is needed.
const MCExpr *Expr = Fixup.getValue();
- if (!evaluate(*Expr, Layout, Fixup, Target))
- getContext().FatalError(Fixup.getLoc(), "expected relocatable expression");
+ if (!Expr->EvaluateAsRelocatable(Target, &Layout, &Fixup))
+ getContext().reportFatalError(Fixup.getLoc(), "expected relocatable expression");
bool IsPCRel = Backend.getFixupKindInfo(
Fixup.getKind()).Flags & MCFixupKindInfo::FKF_IsPCRel;
@@ -493,14 +415,11 @@ bool MCAssembler::evaluateFixup(const MCAsmLayout &Layout,
} else {
const MCSymbolRefExpr *A = Target.getSymA();
const MCSymbol &SA = A->getSymbol();
- if (A->getKind() != MCSymbolRefExpr::VK_None ||
- SA.AliasedSymbol().isUndefined()) {
+ if (A->getKind() != MCSymbolRefExpr::VK_None || SA.isUndefined()) {
IsResolved = false;
} else {
- const MCSymbolData &DataA = getSymbolData(SA);
- IsResolved =
- getWriter().IsSymbolRefDifferenceFullyResolvedImpl(*this, DataA,
- *DF, false, true);
+ IsResolved = getWriter().IsSymbolRefDifferenceFullyResolvedImpl(
+ *this, SA, *DF, false, true);
}
}
} else {
@@ -510,14 +429,14 @@ bool MCAssembler::evaluateFixup(const MCAsmLayout &Layout,
Value = Target.getConstant();
if (const MCSymbolRefExpr *A = Target.getSymA()) {
- const MCSymbol &Sym = A->getSymbol().AliasedSymbol();
+ const MCSymbol &Sym = A->getSymbol();
if (Sym.isDefined())
- Value += Layout.getSymbolOffset(&getSymbolData(Sym));
+ Value += Layout.getSymbolOffset(Sym);
}
if (const MCSymbolRefExpr *B = Target.getSymB()) {
- const MCSymbol &Sym = B->getSymbol().AliasedSymbol();
+ const MCSymbol &Sym = B->getSymbol();
if (Sym.isDefined())
- Value -= Layout.getSymbolOffset(&getSymbolData(Sym));
+ Value -= Layout.getSymbolOffset(Sym);
}
@@ -630,7 +549,12 @@ void MCAsmLayout::layoutFragment(MCFragment *F) {
// The fragment's offset will point to after the padding, and its computed
// size won't include the padding.
//
- if (Assembler.isBundlingEnabled() && F->hasInstructions()) {
+ // When the -mc-relax-all flag is used, we optimize bundling by writting the
+ // bundle padding directly into fragments when the instructions are emitted
+ // inside the streamer.
+ //
+ if (Assembler.isBundlingEnabled() && !Assembler.getRelaxAll() &&
+ F->hasInstructions()) {
assert(isa<MCEncodedFragment>(F) &&
"Only MCEncodedFragment implementations have instructions");
uint64_t FSize = Assembler.computeFragmentSize(*this, *F);
@@ -638,7 +562,8 @@ void MCAsmLayout::layoutFragment(MCFragment *F) {
if (FSize > Assembler.getBundleAlignSize())
report_fatal_error("Fragment can't be larger than a bundle size");
- uint64_t RequiredBundlePadding = computeBundlePadding(F, F->Offset, FSize);
+ uint64_t RequiredBundlePadding = computeBundlePadding(Assembler, F,
+ F->Offset, FSize);
if (RequiredBundlePadding > UINT8_MAX)
report_fatal_error("Padding cannot exceed 255 bytes");
F->setBundlePadding(static_cast<uint8_t>(RequiredBundlePadding));
@@ -653,24 +578,18 @@ static void writeFragmentContents(const MCFragment &F, MCObjectWriter *OW) {
OW->WriteBytes(EF.getContents());
}
-/// \brief Write the fragment \p F to the output file.
-static void writeFragment(const MCAssembler &Asm, const MCAsmLayout &Layout,
- const MCFragment &F) {
- MCObjectWriter *OW = &Asm.getWriter();
-
- // FIXME: Embed in fragments instead?
- uint64_t FragmentSize = Asm.computeFragmentSize(Layout, F);
-
+void MCAssembler::writeFragmentPadding(const MCFragment &F, uint64_t FSize,
+ MCObjectWriter *OW) const {
// Should NOP padding be written out before this fragment?
unsigned BundlePadding = F.getBundlePadding();
if (BundlePadding > 0) {
- assert(Asm.isBundlingEnabled() &&
+ assert(isBundlingEnabled() &&
"Writing bundle padding with disabled bundling");
assert(F.hasInstructions() &&
"Writing bundle padding for a fragment without instructions");
- unsigned TotalLength = BundlePadding + static_cast<unsigned>(FragmentSize);
- if (F.alignToBundleEnd() && TotalLength > Asm.getBundleAlignSize()) {
+ unsigned TotalLength = BundlePadding + static_cast<unsigned>(FSize);
+ if (F.alignToBundleEnd() && TotalLength > getBundleAlignSize()) {
// If the padding itself crosses a bundle boundary, it must be emitted
// in 2 pieces, since even nop instructions must not cross boundaries.
// v--------------v <- BundleAlignSize
@@ -679,16 +598,27 @@ static void writeFragment(const MCAssembler &Asm, const MCAsmLayout &Layout,
// | Prev |####|####| F |
// ----------------------------
// ^-------------------^ <- TotalLength
- unsigned DistanceToBoundary = TotalLength - Asm.getBundleAlignSize();
- if (!Asm.getBackend().writeNopData(DistanceToBoundary, OW))
+ unsigned DistanceToBoundary = TotalLength - getBundleAlignSize();
+ if (!getBackend().writeNopData(DistanceToBoundary, OW))
report_fatal_error("unable to write NOP sequence of " +
Twine(DistanceToBoundary) + " bytes");
BundlePadding -= DistanceToBoundary;
}
- if (!Asm.getBackend().writeNopData(BundlePadding, OW))
+ if (!getBackend().writeNopData(BundlePadding, OW))
report_fatal_error("unable to write NOP sequence of " +
Twine(BundlePadding) + " bytes");
}
+}
+
+/// \brief Write the fragment \p F to the output file.
+static void writeFragment(const MCAssembler &Asm, const MCAsmLayout &Layout,
+ const MCFragment &F) {
+ MCObjectWriter *OW = &Asm.getWriter();
+
+ // FIXME: Embed in fragments instead?
+ uint64_t FragmentSize = Asm.computeFragmentSize(Layout, F);
+
+ Asm.writeFragmentPadding(F, FragmentSize, OW);
// This variable (and its dummy usage) is to participate in the assert at
// the end of the function.
@@ -773,7 +703,7 @@ static void writeFragment(const MCAssembler &Asm, const MCAsmLayout &Layout,
case MCFragment::FT_LEB: {
const MCLEBFragment &LF = cast<MCLEBFragment>(F);
- OW->WriteBytes(LF.getContents().str());
+ OW->WriteBytes(LF.getContents());
break;
}
@@ -789,12 +719,12 @@ static void writeFragment(const MCAssembler &Asm, const MCAsmLayout &Layout,
case MCFragment::FT_Dwarf: {
const MCDwarfLineAddrFragment &OF = cast<MCDwarfLineAddrFragment>(F);
- OW->WriteBytes(OF.getContents().str());
+ OW->WriteBytes(OF.getContents());
break;
}
case MCFragment::FT_DwarfFrame: {
const MCDwarfCallFrameFragment &CF = cast<MCDwarfCallFrameFragment>(F);
- OW->WriteBytes(CF.getContents().str());
+ OW->WriteBytes(CF.getContents());
break;
}
}
@@ -803,15 +733,15 @@ static void writeFragment(const MCAssembler &Asm, const MCAsmLayout &Layout,
"The stream should advance by fragment size");
}
-void MCAssembler::writeSectionData(const MCSectionData *SD,
+void MCAssembler::writeSectionData(const MCSection *Sec,
const MCAsmLayout &Layout) const {
// Ignore virtual sections.
- if (SD->getSection().isVirtualSection()) {
- assert(Layout.getSectionFileSize(SD) == 0 && "Invalid size for section!");
+ if (Sec->isVirtualSection()) {
+ assert(Layout.getSectionFileSize(Sec) == 0 && "Invalid size for section!");
// Check that contents are only things legal inside a virtual section.
- for (MCSectionData::const_iterator it = SD->begin(),
- ie = SD->end(); it != ie; ++it) {
+ for (MCSection::const_iterator it = Sec->begin(), ie = Sec->end(); it != ie;
+ ++it) {
switch (it->getKind()) {
default: llvm_unreachable("Invalid fragment in virtual section!");
case MCFragment::FT_Data: {
@@ -823,7 +753,7 @@ void MCAssembler::writeSectionData(const MCSectionData *SD,
"Cannot have fixups in virtual section!");
for (unsigned i = 0, e = DF.getContents().size(); i != e; ++i)
if (DF.getContents()[i]) {
- if (auto *ELFSec = dyn_cast<const MCSectionELF>(&SD->getSection()))
+ if (auto *ELFSec = dyn_cast<const MCSectionELF>(Sec))
report_fatal_error("non-zero initializer found in section '" +
ELFSec->getSectionName() + "'");
else
@@ -852,12 +782,12 @@ void MCAssembler::writeSectionData(const MCSectionData *SD,
uint64_t Start = getWriter().getStream().tell();
(void)Start;
- for (MCSectionData::const_iterator it = SD->begin(), ie = SD->end();
- it != ie; ++it)
+ for (MCSection::const_iterator it = Sec->begin(), ie = Sec->end(); it != ie;
+ ++it)
writeFragment(*this, Layout, *it);
assert(getWriter().getStream().tell() - Start ==
- Layout.getSectionAddressSize(SD));
+ Layout.getSectionAddressSize(Sec));
}
std::pair<uint64_t, bool> MCAssembler::handleFixup(const MCAsmLayout &Layout,
@@ -892,18 +822,18 @@ void MCAssembler::Finish() {
// Create dummy fragments to eliminate any empty sections, this simplifies
// layout.
if (it->getFragmentList().empty())
- new MCDataFragment(it);
+ new MCDataFragment(&*it);
it->setOrdinal(SectionIndex++);
}
// Assign layout order indices to sections and fragments.
for (unsigned i = 0, e = Layout.getSectionOrder().size(); i != e; ++i) {
- MCSectionData *SD = Layout.getSectionOrder()[i];
- SD->setLayoutOrder(i);
+ MCSection *Sec = Layout.getSectionOrder()[i];
+ Sec->setLayoutOrder(i);
unsigned FragmentIndex = 0;
- for (MCSectionData::iterator iFrag = SD->begin(), iFragEnd = SD->end();
+ for (MCSection::iterator iFrag = Sec->begin(), iFragEnd = Sec->end();
iFrag != iFragEnd; ++iFrag)
iFrag->setLayoutOrder(FragmentIndex++);
}
@@ -931,8 +861,8 @@ void MCAssembler::Finish() {
// Evaluate and apply the fixups, generating relocation entries as necessary.
for (MCAssembler::iterator it = begin(), ie = end(); it != ie; ++it) {
- for (MCSectionData::iterator it2 = it->begin(),
- ie2 = it->end(); it2 != ie2; ++it2) {
+ for (MCSection::iterator it2 = it->begin(), ie2 = it->end(); it2 != ie2;
+ ++it2) {
MCEncodedFragmentWithFixups *F =
dyn_cast<MCEncodedFragmentWithFixups>(it2);
if (F) {
@@ -1005,7 +935,7 @@ bool MCAssembler::relaxInstruction(MCAsmLayout &Layout,
SmallVector<MCFixup, 4> Fixups;
SmallString<256> Code;
raw_svector_ostream VecOS(Code);
- getEmitter().EncodeInstruction(Relaxed, VecOS, Fixups, F.getSubtargetInfo());
+ getEmitter().encodeInstruction(Relaxed, VecOS, Fixups, F.getSubtargetInfo());
VecOS.flush();
// Update the fragment.
@@ -1018,7 +948,10 @@ bool MCAssembler::relaxInstruction(MCAsmLayout &Layout,
bool MCAssembler::relaxLEB(MCAsmLayout &Layout, MCLEBFragment &LF) {
uint64_t OldSize = LF.getContents().size();
- int64_t Value = LF.getValue().evaluateKnownAbsolute(Layout);
+ int64_t Value;
+ bool Abs = LF.getValue().evaluateKnownAbsolute(Value, Layout);
+ if (!Abs)
+ report_fatal_error("sleb128 and uleb128 expressions must be absolute");
SmallString<8> &Data = LF.getContents();
Data.clear();
raw_svector_ostream OSE(Data);
@@ -1034,7 +967,10 @@ bool MCAssembler::relaxDwarfLineAddr(MCAsmLayout &Layout,
MCDwarfLineAddrFragment &DF) {
MCContext &Context = Layout.getAssembler().getContext();
uint64_t OldSize = DF.getContents().size();
- int64_t AddrDelta = DF.getAddrDelta().evaluateKnownAbsolute(Layout);
+ int64_t AddrDelta;
+ bool Abs = DF.getAddrDelta().evaluateKnownAbsolute(AddrDelta, Layout);
+ assert(Abs && "We created a line delta with an invalid expression");
+ (void) Abs;
int64_t LineDelta;
LineDelta = DF.getLineDelta();
SmallString<8> &Data = DF.getContents();
@@ -1049,7 +985,10 @@ bool MCAssembler::relaxDwarfCallFrameFragment(MCAsmLayout &Layout,
MCDwarfCallFrameFragment &DF) {
MCContext &Context = Layout.getAssembler().getContext();
uint64_t OldSize = DF.getContents().size();
- int64_t AddrDelta = DF.getAddrDelta().evaluateKnownAbsolute(Layout);
+ int64_t AddrDelta;
+ bool Abs = DF.getAddrDelta().evaluateKnownAbsolute(AddrDelta, Layout);
+ assert(Abs && "We created call frame with an invalid expression");
+ (void) Abs;
SmallString<8> &Data = DF.getContents();
Data.clear();
raw_svector_ostream OSE(Data);
@@ -1058,7 +997,7 @@ bool MCAssembler::relaxDwarfCallFrameFragment(MCAsmLayout &Layout,
return OldSize != Data.size();
}
-bool MCAssembler::layoutSectionOnce(MCAsmLayout &Layout, MCSectionData &SD) {
+bool MCAssembler::layoutSectionOnce(MCAsmLayout &Layout, MCSection &Sec) {
// Holds the first fragment which needed relaxing during this layout. It will
// remain NULL if none were relaxed.
// When a fragment is relaxed, all the fragments following it should get
@@ -1066,7 +1005,7 @@ bool MCAssembler::layoutSectionOnce(MCAsmLayout &Layout, MCSectionData &SD) {
MCFragment *FirstRelaxedFragment = nullptr;
// Attempt to relax all the fragments in the section.
- for (MCSectionData::iterator I = SD.begin(), IE = SD.end(); I != IE; ++I) {
+ for (MCSection::iterator I = Sec.begin(), IE = Sec.end(); I != IE; ++I) {
// Check if this is a fragment that needs relaxation.
bool RelaxedFrag = false;
switch(I->getKind()) {
@@ -1105,8 +1044,8 @@ bool MCAssembler::layoutOnce(MCAsmLayout &Layout) {
bool WasRelaxed = false;
for (iterator it = begin(), ie = end(); it != ie; ++it) {
- MCSectionData &SD = *it;
- while (layoutSectionOnce(Layout, SD))
+ MCSection &Sec = *it;
+ while (layoutSectionOnce(Layout, Sec))
WasRelaxed = true;
}
@@ -1245,27 +1184,14 @@ void MCFragment::dump() {
OS << ">";
}
-void MCSectionData::dump() {
- raw_ostream &OS = llvm::errs();
-
- OS << "<MCSectionData";
- OS << " Alignment:" << getAlignment()
- << " Fragments:[\n ";
- for (iterator it = begin(), ie = end(); it != ie; ++it) {
- if (it != begin()) OS << ",\n ";
- it->dump();
- }
- OS << "]>";
-}
-
void MCSymbolData::dump() const {
raw_ostream &OS = llvm::errs();
- OS << "<MCSymbolData Symbol:" << getSymbol()
+ OS << "<MCSymbolData"
<< " Fragment:" << getFragment();
if (!isCommon())
OS << " Offset:" << getOffset();
- OS << " Flags:" << getFlags() << " Index:" << getIndex();
+ OS << " Flags:" << getFlags();
if (isCommon())
OS << " (common, size:" << getCommonSize()
<< " align: " << getCommonAlignment() << ")";
@@ -1290,7 +1216,11 @@ void MCAssembler::dump() {
for (symbol_iterator it = symbol_begin(), ie = symbol_end(); it != ie; ++it) {
if (it != symbol_begin()) OS << ",\n ";
+ OS << "(";
it->dump();
+ OS << ", Index:" << it->getIndex() << ", ";
+ it->getData().dump();
+ OS << ")";
}
OS << "]>\n";
}
OpenPOWER on IntegriCloud